OS Command Injection Week: From a Quoted Shell String to a One-Line Webshell
three KEV adds in one week all had the same root cause and nobody wants to say it out loud. Collabora shelled out with a double quote. EG Secure SiteGuard took commands as root. Ahsay took them through a parameter called random. CWE-78 is not exotic. it is what happens every time a developer builds a command line out of user input and trusts the shell to behave. let us reproduce the whole kill chain in a lab so you can actually hunt it instead of reading another “patch now” tweet.
ci.lab.local) that deliberately shells out, built to mirror the real bug classes without touching anyone’s product. do not run these payloads against software you do not own and are not authorized to test. this is detection engineering and authorized red team practice. the point is the defender half at the end.the bug class, in one paragraph
OS command injection (CWE-78) happens when an application builds a shell command out of attacker-influenced data and fails to neutralize the special characters a shell cares about. the classic sink is a system(), exec(), popen(), or bash -c "..." where some of the “…” came from a request. once you are inside a shell context, $(...), backticks, ;, |, &&, and ${IFS} are all yours. the recent KEV cluster is just this bug wearing four different product logos.
why this week proves the point
- Collabora CVE-2026-110447: request-path text landed inside a double-quoted
bash -cstring. double quotes still evaluate$(...). unauthenticated RCE. - EG Secure SiteGuard Server Edition CVE-2026-106931: OS command injection that runs arbitrary commands with root or SYSTEM privileges. KEV October 20.
- Ahsay AhsayCBS CVE-2026-105134: command injection via the
randomparameter of the Replication Receiver endpoint, chainable with CVE-2026-105133.
same mental model, four times. so let us build the generic version and learn to catch all of them at once.
step 1: find the shell-out
the lab endpoint builds a config path by shelling out, which is exactly the Collabora proxy.php shape. the fastest confirmation is a harmless command substitution in a place the app does not expect: if $(id) comes back evaluated, you are in a shell context. no login required when the sink is pre-auth.
curl -s 'http://ci.lab.local/proxy.php/$(id)?status'

$(id) in the path comes back evaluated. that is CWE-78, unauthenticated, no credentials involved.step 2: turn it into a webshell (the way the real campaigns do)
operators do not stop at proof. the Collabora campaign dropped a one-line PHP webshell named shx*.php and moved on to hunting KeePass files and crypto wallets. the reliable delivery trick when your input lands in a shell is: dodge spaces with ${IFS}, dodge quoting with a Base64 blob piped through sh, and write a tiny PHP file the web server will happily serve. the webshell itself is the entire payload in one line:
<?php $c=$_GET['c']??'id'; echo shell_exec($c.' 2>&1');

${IFS} hides the spaces, base64 -d | sh hides the quoting, and the result is an shx*.php webshell running as the web server account. same shape as the in-the-wild attack.notice the webshell runs as www-data, not root. that still matters, because on a shared box the web user can usually read other tenants’ files, database credentials, and config. the SiteGuard CVE is the scarier cousin here because its injection runs as root or SYSTEM outright. the delivery technique is identical; the blast radius depends on what the shell-out ran as.
step 3: detect it, which is the entire reason we did this
command injection to webshell has loud, cheap tells if you are actually looking. you are hunting two things: the injection in the logs, and the dropped file on disk.
- access logs: grep for encoded traversal and shell metacharacters in request paths and parameters:
%2e%2e,$(,%24%28,${IFS}, backticks, and inlinebase64/|shpatterns. legitimate traffic almost never contains command substitution. - new PHP files:
findyour web roots and app directories for recently created.phpfiles, especially short ones matchingshx*/shrf*or anything callingshell_exec($_GET. - process lineage: alert when a web server process spawns
sh,bash,curl, orbase64. your document editor has no business forking a shell that runsbase64 -d. - outbound callbacks: the Collabora payload phoned a
webhook.siteaddress. egress from the web user to pastebin-style or webhook domains is a gift-wrapped detection.

find the recent shx*.php, and confirm the shell_exec($_GET sink. delete it, rotate what the web user could read, patch the shell-out.the fix developers keep not applying
you do not neutralize command injection by blocklisting characters. you avoid the shell. pass arguments as an array to execve-style APIs so there is no shell to interpret metacharacters. if you truly must build a command string, every piece of external input goes through the platform’s shell-arg escaping (escapeshellarg in PHP, and crucially the whole inner command when you wrap it in bash -c, which is the exact mistake 26.4.302 made). Collabora’s own fix diff is the lesson: they had escaped the inner pieces but then dropped the result into a double-quoted bash -c, where $(...) still fires. 26.4.303 wraps the whole inner command in escapeshellarg.
purple-team drill that fits an afternoon
- stand up the lab endpoint, confirm
$(id)evaluates. - drop the one-line webshell via
${IFS}+base64 | sh. - confirm your SOC: did log detection fire on the encoded path? did file monitoring fire on the new PHP? did process lineage fire on web-user-spawns-shell?
- write down which detections missed. ship the rules. delete the lab artifacts and the webshell.
sloth take
four KEV entries, one root cause, zero new ideas. a shell will run whatever you hand it, and developers keep handing it the request path. the lab version takes twenty minutes and teaches you exactly what to grep for the next time a vendor says “command injection” and gives you three days to care. stop treating CWE-78 like a surprise. it is the oldest trick that still works because we keep building command strings out of the internet.
sources
- CVE-2026-110447 (Collabora Built-in CODE Server, CWE-78) advisory and in-the-wild shx*.php webshell reporting, October 2026
- CVE-2026-106931 (EG Secure SiteGuard Server Edition OS command injection, root/SYSTEM), CISA KEV October 20, 2026
- CVE-2026-105134 (Ahsay AhsayCBS command injection via Replication Receiver
randomparameter, chainable with CVE-2026-105133), CISA KEV October 14, 2026 - MITRE CWE-78: Improper Neutralization of Special Elements used in an OS Command
