CTFSHOW-WEB入门爆破
爆破什么的,都是基操抓包进行爆破可以发现这个base64编码就是我们输入的账号密码payload的配置和处理设置之后开始爆破(注:字典是由题目下载的)滚动到页面最下方,找到“Url-encode these characters...”(URL编码这些字符)。原因:如果不取消,Base64 结尾的会被自动编码为%3d,导致服务器无法识别。得到flag。
web21
爆破什么的,都是基操

抓包进行爆破


可以发现这个base64编码就是我们输入的账号密码

payload的配置和处理设置之后
开始爆破(注:字典是由题目下载的)
滚动到页面最下方,找到 Payload Encoding(Payload 编码),取消勾选 “Url-encode these characters...”(URL编码这些字符)。
-
原因:如果不取消,Base64 结尾的
=会被自动编码为%3d,导致服务器无法识别。

得到flag
web22
域名也可以爆破的,试试爆破这个ctf.show的子域名
失效了
web23
还爆破?这么多代码,告辞!

import hashlib
for i in range(10000000):
token = str(i)
m = hashlib.md5(token.encode()).hexdigest()
if m[1] == m[14] and m[14] == m[17]:
if m[1] in '123456789' and m[31] == '3':
print(token)
break
你需要提交一个 token,它的 MD5 加密值必须同时满足以下条件:
-
第 2、15、18 个字符完全一样。
-
这个相同的字符必须是
1-9之间的数字。 -
最后一个字符(第 32 个字符)必须是
'3'。

得到flag
web24
爆个🔨

mt_rand() 产生的其实是伪随机数。
伪随机的运作原理
你可以把伪随机数生成器想象成一台极其复杂的绞肉机(数学公式):
-
种子(Seed): 你必须先往机器里扔一块初始的肉(数字),这块肉就叫做“种子”。
-
生成: 机器经过一顿复杂的搅动(算法计算),吐出一小块肉(第一个随机数)。
-
循环: 机器内部会保留一部分刚才计算的状态,当你请求第二个随机数时,它会基于刚才的状态继续搅动,吐出第二块肉。
致命的逻辑在于: 因为数学公式是固定的,所以只要你往机器里扔的“种子”完全一样,机器每次搅动吐出来的结果序列就必定一模一样。
<?php
mt_srand(372619038);
echo mt_rand();
?>

得到flag
web25
爆个🔨,不爆了

相比上一题,这道题的难度提升在于:种子变成了未知数(由未知的 $flag 计算而来)。
既然我们不知道种子,怎么预测随机数呢?这题的核心考点是:利用信息泄露(Information Leak)配合工具逆向破解出种子。
分析主要代码逻辑:
步骤 A:确定密码本(初始化种子)
PHP
$r = $_GET['r'];
mt_srand(hexdec(substr(md5($flag), 0,8)));
-
第一行:把你输入的参数赋值给变量
$r。 -
第二行:这是全题最绕的地方。它在调用
mt_srand()函数设置随机数种子。-
md5($flag):把神秘的 flag 变成一串 32 位的十六进制字符串。 -
substr(..., 0, 8):切片,只切下前 8 个字符。 -
hexdec(...):把这 8 个十六进制字符转换成普通的十进制数字。 -
结果:用这个由 flag 算出来的固定数字作为种子。因为种子固定,接下来生成的随机数序列也就固定了。
-
步骤 B:第一道大门(输入比对)
PHP
$rand = intval($r) - intval(mt_rand());
if((!$rand)){
// ... 进门后的代码
}else{
echo $rand;
}
-
代码调用了第一次
mt_rand(),生成了序列里的第一个随机数。 -
然后用你输入的数字减去这个随机数:$rand = r - \text{第一个随机数}$。
-
if((!$rand)):在 PHP 中,!代表取反。只有当$rand的结果为0时(也就是你输入的 $r$ 刚好等于第一个随机数),!0才会变成True,你才能成功通过第一道大门。 -
else { echo $rand; }:如果你猜错了,代码会执行else,把你输入的数字和正确答案的差值打印在屏幕上。(这就是上一题中我们传入?r=0就能套出正确答案的漏洞所在)。
步骤 C:第二道大门(Cookie 终极校验)
PHP
if($_COOKIE['token'] == (mt_rand() + mt_rand())){
echo $flag;
}
-
当你成功通过第一道大门后,代码会连续再调用两次随机数函数,也就是生成了序列里的第二个随机数和第三个随机数,并把它们加在一起。
-
它会去检查你浏览器的 Cookie 里,有没有一个叫做
token的东西。 -
通关条件:你提交的 Cookie 中的
token值,必须等于那第二个和第三个随机数的和。如果相等,执行echo $flag;,游戏结束,打印出你想要的 Flag。
解题:
第一步:代码逻辑分析与寻找突破口
-
种子初始化:
mt_srand(hexdec(substr(md5($flag), 0, 8)));系统用 flag 生成了一个固定的种子。因为 flag 是固定的,所以这个未知种子也是固定的。 -
第一层判断(计算差值):
PHP$rand = intval($r) - intval(mt_rand()); if((!$rand)){ ... } else { echo $rand; }代码将你传入的
r减去生成的第一个随机数。如果差值不是 0(即你没猜对),它会执行else分支,直接把你算错的差值echo打印出来! 💡 突破口就在这里: 如果你故意传入?r=0,那么$rand = 0 - mt_rand()。网页上就会打印出一个负数(比如-12345678)。去掉负号,你就能知道服务器生成的第一个随机数是多少了! -
第二层判断(Cookie 校验):
PHPif($_COOKIE['token']==(mt_rand()+mt_rand())) { echo $flag; }如果你在第一层传入了正确的
r,代码会接着生成第二个和第三个随机数,并将它们相加。你必须在请求的 Cookie 中带上一个名为token的字段,其值等于这个和,才能拿到 flag。

所以第一个随机数是1783215097
第二步使用工具破解种子(php_mt_seed)
Ubuntu 20.04 LTS (本题环境)PHP 7.4 🌟

发现可能是478823514也有可能是2894621996
<?php
mt_srand(478823514);
$r = mt_rand();
$a = mt_rand();
$b = mt_rand();
echo $r;
echo "\n";
$cook = $a + $b;
echo $cook;
?>

说明第一个不对
我们尝试第二个
<?php
mt_srand(2894621996);
$r = mt_rand();
$a = mt_rand();
$b = mt_rand();
echo $r;
echo "\n";
$cook = $a + $b;
echo $cook;
?>

得到flag
web26
这个可以爆

把几个数据全删除得到flag

前端通过输入框限制你必须填,但你通过 Burp Suite 抓包直接把参数值清空,绕过了前端的限制。而后端又没有对“参数为空”做出严格的拦截和报错,反而当成“什么都没发生”或者“默认通关”处理,从而导致了 flag 的泄露。
web27
CTFshow菜鸡学院招生啦!

点击录取名单,可以看到学生的名单


开始爆破日期,找到正确的日期了



得到flag
主要:
在 Burp Suite(底层是 Java)的日期格式化规则中,大小写有着完全不同的含义:
-
MM(大写):代表 月份 (Month) -
mm(小写):代表 分钟 (Minute)
web28
大海捞针


得到flag
爆破结束了
openEuler 是由开放原子开源基金会孵化的全场景开源操作系统项目,面向数字基础设施四大核心场景(服务器、云计算、边缘计算、嵌入式),全面支持 ARM、x86、RISC-V、loongArch、PowerPC、SW-64 等多样性计算架构
更多推荐

所有评论(0)