foreach()

手册
用于遍历数组,一共有两种格式

foreach (iterable_expression as $value)
    statement
foreach (iterable_expression as $key => $value)
    statement

第二种会把当前单元的键名也赋给变量$key
foreach可以通过在$value之前加上 & 来修改数组的元素。此方法将以引用赋值而不是拷贝一个值

<?php
$arr = array(1, 2, 3, 4);
foreach ($arr as &$value) {
    $value = $value * 2;
}
// 现在 $arr 是 array(2, 4, 6, 8)
unset($value); // 最后取消掉引用
?>

数组最后一个元素的 $value 引用在 foreach 循环之后仍会保留。建议使用 unset() 来将其销毁

preg_match_all

手册

preg_match_all(
    string $pattern,//要搜索的模式,字符串形式
    string $subject,//输入字符串
    array &$matches = null,//多维数组,作为输出参数输出所有匹配结果, 数组排序通过flags指定
    int $flags = 0,//见手册
    int $offset = 0//用于 从目标字符串中指定位置开始搜索(单位是字节)
): int|false

搜索subject中所有匹配pattern给定正则表达式 的匹配结果并且将它们以flag指定顺序输出到matches
在第一个匹配找到后, 子序列继续从最后一次匹配位置搜索
正则表达式网站

in_array

手册

in_array(mixed $needle, array $haystack, bool $strict = false): bool

大海捞针,在大海(haystack)中搜索针( needle),如果没有设置 strict 则使用宽松的比较。

绕过

在宽松比较中,字符串开头为数字可以将整个比较变为数字的比较从而导致绕过

call_user_func_array

手册

调用回调函数,并把一个数组参数作为回调函数的参数

call_user_func_array(callable $callback, array $args): mixed

把第一个参数作为回调函数(callback)调用,把参数数组作(args)为回调函数的的参数传入
callback为函数名,而array $args则是函数参数

<?php
function foobar($arg, $arg2) {
    echo __FUNCTION__, " got $arg and $arg2\n";
}
class foo {
    function bar($arg, $arg2) {
        echo __METHOD__, " got $arg and $arg2\n";
    }
}


// Call the foobar() function with 2 arguments
call_user_func_array("foobar", array("one", "two"));

// Call the $foo->bar() method with 2 arguments
$foo = new foo;
call_user_func_array(array($foo, "bar"), array("three", "four"));
?>

输出:

foobar got one and two
foo::bar got three and four

exec

手册

执行一个外部程序

exec(string $command, array &$output = null, int &$result_code = null): string|false

exec() 执行 command参数所指定的命令

result_code 外部命令执行后的返回状态将会被设置到此变量中

类似于system()

system

执行外部程序,并且显示输出

system(string $command, int &$result_code = null): string|false

执行 command 参数所指定的命令,并且输出执行结果
result_code 外部命令执行后的返回状态将会被设置到此变量中
成功则返回命令输出的最后一行,失败则返回 false

strcmp

手册

strcmp(string $string1, string $string2): int

该比较区分大小写

如果 string1 小于 string2 返回 -1;如果 string1 大于 string2 返回 1;如果两者相等,返回 0

挨个比较ascii码

绕过

strcmp("foo", array()) => NULL + PHP Warning
strcmp("foo", new stdClass) => NULL + PHP Warning
strcmp(function(){}, "") => NULL + PHP Warning

strcmp()函数传入数组会返回NULL 在php 中 NULL==0

eregi or ereg

手册

eregi不区分大小写的正则表达式匹配

eregi ( string $pattern , string $string [, array &$regs ] ) : int

本函数和 ereg() 完全相同,只除了在匹配字母字符时忽略大小写的区别

以(不)区分大小写的方式在 string 中寻找与给定的正则表达式 pattern 所匹配的子串

如果找到与 pattern 中圆括号内的子模式相匹配的子串并且函数调用给出了第三个参数 regs,则匹配项将被存入 regs 数组中。$regs[1] 包含第一个左圆括号开始的子串,$regs[2] 包含第二个子串,以此类推。$regs[0] 包含整个匹配的字符串

如果在 string 中找到 pattern 模式的匹配则返回 所匹配字符串的长度,如果没有找到匹配或出错则返回 FALSE。如果没有传递入可选参数 regs 或者所匹配的字符串长度为 0,则本函数返回 1

绕过

两者存在%00截断类似于\0截断

preg_match()

php

preg_match(
    string $pattern,
    string $subject,
    array &$matches = null,
    int $flags = 0,
    int $offset = 0
): int|false

搜索subjectpattern给定的正则表达式的一个匹配
matches
如果提供了参数matches,它将被填充为搜索结果。 $matches[0]将包含完整模式匹配到的文本, $matches[1] 将包含第一个捕获子组匹配到的文本,以此类推

无字母数字webshell

参考

<?php
if(!preg_match('/[a-z0-9]/is',$_GET['shell'])) {
  eval($_GET['shell']);
}

对于类似与以上正则匹配进行绕过

PHP中的短标签

<??>相当于对<?php>的替换。而<?=?>则是相当于<? echo>

<?= '111'?>

PHP中,反引号可以起到命令执行的效果

<?php
$_=`whoami`;
echo $_;

如果我们利用上面短标签的写法,可以把代码简写

<?= `whoami`?>

临时文件泄露

vim 临时文件泄露

http://node4.anna.nssctf.cn:28196/.index.swp

得到之后使用vim即可恢复

vim -r .index.swp

一个好奇的人