ctfshow web 126
# 前言
摆烂闲出屁了,在群里偷偷视奸群友在干嘛
群友对题目wp的一个payload有疑惑,wp的作者也没有解决,好奇开个环境看一下
但是我在服务器上测试了,这个代码行不通,原因是fun参数eval($_REQUEST[m])的长度为18,超出了题目限制16,但是为什么也能成功呢,是某个版本的php特性吗?百思不得其解
# 思路
源码如下
<?php
/*
# -*- coding: utf-8 -*-
# @Author: Firebasky
# @Date: 2020-09-05 20:49:30
# @Last Modified by: h1xa
# @Last Modified time: 2020-09-07 22:02:47
#
#
*/
error_reporting(0);
highlight_file(__FILE__);
include("flag.php");
$a=$_SERVER['argv'];
$c=$_POST['fun'];
if(isset($_POST['CTF_SHOW'])&&isset($_POST['CTF_SHOW.COM'])&&!isset($_GET['fl0g'])){
if(!preg_match("/\\\\|\/|\~|\`|\!|\@|\#|\%|\^|\*|\-|\+|\=|\{|\}|\"|\'|\,|\.|\;|\?|flag|GLOBALS|echo|var_dump|print|g|i|f|c|o|d/i", $c) && strlen($c)<=16){
eval("$c".";");
if($fl0g==="flag_give_me"){
echo $flag;
}
}
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
第一个if判断主要考察了php8之前非法变量名的处理绕过,第二个判断对rce参数进行了过滤,同时要求了长度
作者提供的payload
fun=eval($_REQUEST[m])&m=$fl0g%3d"flag_give_me";&CTF_SHOW=1&CTF[SHOW.COM=1
我想,有了eval函数,为什么还按照题目的思路走,去给变量赋值拿flag,尝试使用rce直接拿flag,函数都禁用了,phpinfo也用不了
找chatgpt扩展了一下知识库
phpinfo平替函数
- phpversion() (获取 PHP 版本)
- get_loaded_extensions() (查看已加载扩展)
- get_defined_constants() (查看所有常量)
- ini_get_all() (获取所有 php.ini 配置项)
- ini_get("配置项") (单独获取某个 php.ini 设置)
这些函数不能直接回显,数组格式下,echo不能打印,题目禁用了var_dump、print_r,使用var_export(类似var_dump)回显出来
另外,题目使用了error_reporting(0);
来抑制报错,不利于调试,通过error_reporting(E_ALL);
来错误回显出来
# 验证
题目使用了disable_function
禁用函数,本想试试能不能用作者的payload蚁剑连上绕过disable_function
,拿个webshell在题目环境上测试,发现连不上
在hackbar测试,使用error_reporting(E_ALL);
回显错误,环境禁用了strlen
竟然没有报错,因为eval写在strlen之后吗?在eval里测试strlen
时才提示被禁用
通过查看配置文件,发现strlen被禁用了,函数禁用了长长的两大行,关键的几个函数被禁用了,没有在尝试蚁剑绕过disable_funcitons了
测试可以发现,使用被禁用的strlen
函数处理数据时会返回NULL
,那么NULL < 16
恒成立为true了,可以说这个参数fun
没有长度限制了,所以wp作者fun
长度为18也正常执行了
本地验证:php.ini禁用strlen
函数后验证,strlen($a) < 16
返回true
开溜