A newly identified Linux backdoor, tracked as CWPdoor, is being distributed through a trojanized build of cwpsrv — the core web server binary that powers the Control Web Panel (CWP) hosting management interface. This is a supply-chain style compromise: defenders did nothing wrong at the configuration level. The malicious code arrives inside the very binary administrators install and trust to manage their servers.
CWP is a popular free hosting control panel with a substantial install base on virtual private servers and dedicated Linux boxes, many of them internet-facing by design. The cwpsrv service listens on the CWP admin ports (TCP 2030/2031 by default) and runs with elevated privileges, which makes it an ideal persistence and command-execution vehicle for an attacker. Any organization running CWP — particularly those that installed or updated the panel from unofficial mirrors, or whose installations pull binaries from compromised distribution infrastructure — must treat their cwpsrv binary as untrusted until cryptographically verified.
This post breaks down how the CWPdoor campaign works, what you can observe on the wire and on the host, and exactly how to hunt, contain, and remediate.
Technical Analysis
Affected Products and Platforms
- Product: Control Web Panel (CWP) hosting management platform
- Component:
cwpsrvweb server binary (typically located at/usr/local/cwpsrv/bin/cwpsrv) - Platform: Linux servers running CWP (CentOS, AlmaLinux, Rocky Linux, and CloudLinux are the most common targets given CWP's supported OS matrix)
- Exposure: Servers with the CWP admin interface reachable from the internet (default ports 2030/2031, plus standard web ports managed by the panel)
How the Attack Works
CWPdoor is not a vulnerability in the traditional sense — it is a trojanized legitimate binary. The attack chain, from a defender's perspective, looks like this:
- Delivery: The victim installs or updates CWP. Instead of a clean
cwpsrvbinary, they receive a backdoored build. Becausecwpsrvis a compiled, closed-source component of CWP, tampering is invisible to an administrator performing a routine install. - Execution context: The trojanized
cwpsrvruns as the CWP web server daemon, typically as root or a highly privileged service account. The malicious logic executes in-process alongside legitimate web server functionality, so the panel continues to work normally — a hallmark of this campaign's stealth. - Command and control: The backdoor logic embedded in
cwpsrvestablishes outbound communication to attacker-controlled infrastructure. Because the connection originates from a legitimate, expected daemon (cwpsrv), it blends into normal panel telemetry and update traffic. - Command execution: CWPdoor provides remote operators the ability to execute arbitrary commands on the host, effectively granting root-equivalent access through a signed-looking, expected service.
- Anti-forensics and stealth: Because the implant lives inside the web server process, there is no suspicious new service, no obviously rogue process name, and — unless the operator makes a mistake — minimal filesystem footprint beyond the single tampered binary.
This technique maps to MITRE ATT&CK T1195.002 (Supply Chain Compromise: Compromise Software Supply Chain) for delivery, T1059 (Command and Scripting Interpreter) for operator activity, and T1071 (Application Layer Protocol) for C2 over web-like traffic.
Exploitation Status
- Confirmed active distribution in the wild. This is not theoretical — the trojanized
cwpsrvhas been observed on production servers. - No CVE has been assigned to this campaign; it is a binary-integrity compromise, not a patchable memory-safety or logic flaw. Do not wait for a CVE to act.
- The trojanized binary has a different hash from the legitimate CWP build, which is the single most reliable integrity signal available to defenders.
The critical defensive insight: traditional patching does not fix this. If your cwpsrv is trojanized, you must verify, replace, and assume post-compromise activity occurred.
Detection & Response
The highest-fidelity detection opportunities are: (1) cwpsrv spawning child processes it has no business spawning (shells, downloaders, reconnaissance tools), (2) the cwpsrv process establishing outbound connections to non-CWP infrastructure, and (3) binary integrity failure on /usr/local/cwpsrv/bin/cwpsrv.
Sigma Rules
---
title: CWP cwpsrv Spawning Shell or Command Interpreter
tid: 3f8a1c42-7b2e-4d91-a6c3-9e5f2b8d1047
status: experimental
description: Detects the CWP web server binary (cwpsrv) spawning shells or scripting interpreters, consistent with CWPdoor backdoor operator activity. The legitimate cwpsrv daemon does not spawn interactive shells, curl/wget downloads, or reconnaissance tooling.
references:
- https://www.bleepingcomputer.com/news/security/hackers-backdoor-linux-servers-using-trojanized-cwp-web-server/
- https://attack.mitre.org/techniques/T1059/
author: Security Arsenal
date: 2026/01/20
tags:
- attack.execution
- attack.t1059.004
- attack.t1195.002
logsource:
category: process_creation
product: linux
detection:
selection_parent:
ParentImage|endswith: '/cwpsrv'
selection_child:
Image|endswith:
- '/bash'
- '/sh'
- '/dash'
- '/zsh'
- '/python'
- '/python3'
- '/perl'
- '/curl'
- '/wget'
- '/nc'
- '/ncat'
- '/base64'
condition: selection_parent and selection_child
falsepositives:
- Rare CWP maintenance scripts invoking shell via the panel UI - validate against change windows
level: high
---
title: Suspicious Outbound Network Connection from cwpsrv
id: 8c2d5e17-4a9f-43b6-b1d8-6f3a7c9e2051
status: experimental
description: Detects the cwpsrv process establishing outbound connections to non-standard destinations. CWPdoor uses the cwpsrv process for C2 communication. Legitimate cwpsrv traffic should be limited to CWP licensing/update infrastructure and the ports it manages.
references:
- https://www.bleepingcomputer.com/news/security/hackers-backdoor-linux-servers-using-trojanized-cwp-web-server/
- https://attack.mitre.org/techniques/T1071/
author: Security Arsenal
date: 2026/01/20
tags:
- attack.command_and_control
- attack.t1071.001
logsource:
category: network_connection
product: linux
detection:
selection:
Image|endswith: '/cwpsrv'
Initiated: 'true'
filter_cwp_ports:
DestinationPort:
- 2030
- 2031
- 2082
- 2083
- 2086
- 2087
- 2095
- 2096
condition: selection and not filter_cwp_ports
falsepositives:
- CWP update and license validation traffic to official CWP infrastructure - baseline and allowlist known-good CWP destinations
level: medium
---
title: Interactive Shell Receiving Commands from CWP Admin Ports
id: 5b1e9a73-2c4d-48f0-97a2-4d6b8e1c3092
status: experimental
description: Detects shell processes with command lines referencing CWP administrative ports or the cwpsrv binary path, indicating reverse shell or backdoor interaction staged through the CWP service.
references:
- https://www.bleepingcomputer.com/news/security/hackers-backdoor-linux-servers-using-trojanized-cwp-web-server/
- https://attack.mitre.org/techniques/T1059/
author: Security Arsenal
date: 2026/01/20
tags:
- attack.execution
- attack.t1059
logsource:
category: process_creation
product: linux
detection:
selection:
CommandLine|contains:
- '/usr/local/cwpsrv'
- '2030'
- '2031'
selection_shell:
Image|endswith:
- '/bash'
- '/sh'
- '/nc'
- '/ncat'
- '/socat'
- '/python'
- '/python3'
condition: selection and selection_shell
falsepositives:
- Legitimate CWP administration scripts - review against known admin tooling
level: medium
Microsoft Sentinel / Defender KQL
This query assumes Linux Syslog (with auditd/execve collection) or a CEF-ingesting sensor is forwarding process creation data to Sentinel. It hunts for the two primary behavioral signals: cwpsrv spawning interpreters and cwpsrv making unexpected outbound connections.
// Hunt 1: cwpsrv spawning shells or download tools (CWPdoor operator activity)
Syslog
| where TimeGenerated > ago(14d)
| where ProcessName =~ "cwpsrv" or SyslogMessage has "cwpsrv"
| where SyslogMessage has_any ("/bin/bash", "/bin/sh", "curl", "wget", "nc ", "python", "base64 -d")
| project TimeGenerated, Computer, ProcessName, SyslogMessage
| order by TimeGenerated desc;
// Hunt 2: Process execution events with cwpsrv as parent (auditd execve via Syslog)
Syslog
| where TimeGenerated > ago(14d)
| where SyslogMessage has "cwpsrv" and SyslogMessage has "execve"
| extend ParentHint = extract(@"ppid=(\d+)", 1, SyslogMessage)
| project TimeGenerated, Computer, SyslogMessage
| order by TimeGenerated desc;
// Hunt 3: Outbound connections from cwpsrv to non-CWP ports (firewall/netflow via CommonSecurityLog)
CommonSecurityLog
| where TimeGenerated > ago(14d)
| where ApplicationProtocol has "cwpsrv" or DeviceProcessName has "cwpsrv"
| where DestinationPort !in (2030, 2031, 2082, 2083, 2086, 2087, 2095, 2096, 80, 443)
| summarize ConnectionCount = count(), FirstSeen = min(TimeGenerated), LastSeen = max(TimeGenerated)
by SourceIP, DestinationIP, DestinationPort, DeviceProcessName
| order by ConnectionCount desc;
Velociraptor VQL
Use this artifact across your CWP fleet to enumerate cwpsrv processes, their network connections, and the on-disk binary hash for integrity comparison against a known-good reference.
-- CWPdoor hunt: enumerate cwpsrv processes, children, network connections, and binary hash
SELECT Pid, Ppid, Name, CommandLine, Exe, Username, CreateTime,
hash(path='/usr/local/cwpsrv/bin/cwpsrv') AS CwpsrvHash
FROM pslist()
WHERE Name =~ 'cwpsrv' OR Exe =~ 'cwpsrv'
-- Correlate: network connections held by cwpsrv processes
SELECT Pid, Name, Status, LocalAddress, RemoteAddress
FROM netstat()
WHERE Name =~ 'cwpsrv'
-- Identify children of cwpsrv (operator activity)
SELECT Pid, Ppid, Name, CommandLine, Username, CreateTime
FROM pslist()
WHERE Ppid IN (
SELECT Pid FROM pslist() WHERE Name =~ 'cwpsrv'
)
Remediation and Verification Script
Run this on every Linux host running CWP. It verifies binary integrity, checks for suspicious cwpsrv behavior, and inventories persistence mechanisms. Do not run the replacement step until you have preserved forensic evidence if you suspect compromise.
#!/bin/bash
# CWPdoor verification and containment script - run as root
set -euo pipefail
CWPSRV_BIN="/usr/local/cwpsrv/bin/cwpsrv"
REPORT="/root/cwpdoor_check_$(date +%Y%m%d_%H%M%S).log"
echo "=== CWPdoor Integrity & Behavior Check ===" | tee "$REPORT"
# 1. Hash the cwpsrv binary - compare against a known-good hash from a clean install
echo -e "\n[1] cwpsrv binary hash:" | tee -a "$REPORT"
if [ -f "$CWPSRV_BIN" ]; then
sha256sum "$CWPSRV_BIN" | tee -a "$REPORT"
else
echo "cwpsrv not found at expected path - CWP may not be installed" | tee -a "$REPORT"
fi
# 2. Check for cwpsrv spawning suspicious child processes
echo -e "\n[2] Children of cwpsrv processes:" | tee -a "$REPORT"
CWP_PID=$(pgrep -x cwpsrv || true)
if [ -n "$CWP_PID" ]; then
ps --ppid "$CWP_PID" -o pid,ppid,user,cmd | tee -a "$REPORT"
else
echo "cwpsrv not currently running" | tee -a "$REPORT"
fi
# 3. Audit cwpsrv network connections (flag non-CWP destinations)
echo -e "\n[3] Network connections held by cwpsrv:" | tee -a "$REPORT"
ss -tunp 2>/dev/null | grep -i cwpsrv | tee -a "$REPORT" || echo "None found" | tee -a "$REPORT"
# 4. Review persistence mechanisms for CWP-related tampering
echo -e "\n[4] Persistence review (cron, systemd):" | tee -a "$REPORT"
grep -ril "cwpsrv" /etc/cron* /var/spool/cron 2>/dev/null | tee -a "$REPORT" || true
systemctl list-unit-files | grep -i cwp | tee -a "$REPORT" || true
# 5. Check for recently modified files in the cwpsrv tree
echo -e "\n[5] Recently modified files under /usr/local/cwpsrv (last 30 days):" | tee -a "$REPORT"
find /usr/local/cwpsrv -type f -mtime -30 2>/dev/null | tee -a "$REPORT"
# 6. Review shell history and auth logs for post-compromise operator activity
echo -e "\n[6] Recent authentication anomalies:" | tee -a "$REPORT"
grep -i "accepted" /var/log/secure 2>/dev/null | tail -n 20 | tee -a "$REPORT" || \
grep -i "accepted" /var/log/auth.log 2>/dev/null | tail -n 20 | tee -a "$REPORT" || true
echo -e "\n=== If cwpsrv hash does not match the known-good build: ===" | tee -a "$REPORT"
echo " a) Isolate the host from the network immediately" | tee -a "$REPORT"
echo " b) Preserve memory and disk images before remediation" | tee -a "$REPORT"
echo " c) Stop the service: systemctl stop cwpsrv" | tee -a "$REPORT"
echo " d) Reinstall CWP from a verified clean source or rebuild the host" | tee -a "$REPORT"
echo " e) Rotate ALL credentials that touched this host (root, panel users, API keys)" | tee -a "$REPORT"
echo "\nReport saved to $REPORT"
Remediation
Because CWPdoor is a trojanized binary rather than a version-specific vulnerability, remediation is an integrity and incident-response exercise, not a patch cycle:
- Verify binary integrity immediately. Compute the SHA-256 of
/usr/local/cwpsrv/bin/cwpsrvon every CWP host and compare it against a hash from a known-clean installation of the identical CWP version. A mismatch means compromise — full stop. - Isolate suspect hosts. If the hash does not match, remove the host from the network before stopping services. Capture volatile data (memory, active connections, process list) first if you have IR capability — the implant's operator sessions and C2 destinations are your best scoping evidence.
- Rebuild rather than clean. A root-privileged implant with arbitrary command execution means you cannot trust any part of the host. Rebuild from a known-good base image and reinstall CWP only from official, verified sources. Confirm the integrity of the installation media itself.
- Rotate credentials comprehensively. Assume every credential that lived on or transited the compromised host is burned: root passwords, CWP admin and user accounts, database credentials, SSH keys, API tokens, and any hosting customer credentials managed through the panel.
- Hunt fleet-wide. The KQL, Sigma, and VQL content above should be run across your entire Linux estate, not just confirmed CWP hosts. Operators with root on one CWP box will pivot — check for lateral movement via SSH (TCP 22) from the compromised host to internal systems.
- Restrict the CWP admin interface. CWP's admin panel should never be exposed to the general internet. Restrict ports 2030/2031 to a management VPN or explicit allowlist of administrator IPs at the perimeter firewall. This does not stop a supply-chain implant's outbound C2, but it removes the exposed attack surface for follow-on exploitation.
- Deploy egress filtering. CWPdoor relies on outbound connectivity for C2. Enforce default-deny egress policies on hosting servers, permitting only required destinations (update mirrors, DNS, NTP). An egress-denied implant is a detectable implant.
- Establish a software integrity baseline. Deploy file integrity monitoring (FIM) such as AIDE, Tripwire, or Wazuh FIM on
/usr/local/cwpsrv/and all CWP component directories. Any unscheduled change to thecwpsrvbinary should page the on-call responder.
For organizations running CWP on customer-facing hosting infrastructure, note that compromise of the panel means compromise of every site and database it manages. Customer notification obligations and, where applicable, PCI-DSS incident response requirements (Requirement 12.10) apply.
Related Resources
Security Arsenal Penetration Testing Services AlertMonitor Platform Book a SOC Assessment vulnerability-management Intel Hub
Is your security operations ready?
Get a free SOC assessment or see how AlertMonitor cuts through alert noise with automated triage.