Events Join us at the AWS Summit in Dubai on 30th September
Read

CVE-2026-110447: The Nextcloud Web Shell Nobody Could Search For

Nextcloud’s Collabora app was exploited 33 days before CVE-2026-110447 published. Web shells found, and CISA KEV sets a 26 October due date.

The 33 Day Blind Spot: How CVE-2026-110447 Outran Its Own CVE

The code fix landed on 9 September. The first attack hit on 10 September. The release shipped on 11 September. The CVE that would tell defenders any of this mattered did not arrive until 14 October.

What Happened?

CVE-2026-110447 is an unauthenticated OS command injection in proxy.php, inside Nextcloud’s Collabora Online Built-in CODE Server app. It scores 9.2 on CVSS v4.

The quirk is timing. The bug only triggers when the local CODE server isn’t running, so a restart or crash exposes it.

Operator-posted access logs show attack requests from 10 September, a day after the fix was committed publicly and a day before release 26.4.303 shipped it. The advisory and CVE followed on 14 October. CISA added it to the Known Exploited Vulnerabilities catalog on 23 October, with remediation due 26 October.

What’s the Impact?

Operators found PHP web shells in the app directory. On one host, the intruder ran discovery commands for password manager files and crypto wallets. An upgrade shuts the bug but leaves an earlier shell in place. Disabling it left the path open. One operator alleged ransomware. Nobody confirmed it.

Indicators of compromise · CVE-2026-110447

Collabora Built-in CODE Server for Nextcloud

Indicators published by server operators who found this activity in their own logs, plus the request characteristics named in the public reports. Scope: Nextcloud installs running the richdocumentscode app below version 26.4.303.

Provenance. Every value below comes from operator reports posted publicly on the project issue tracker and the vendor advisory. Nothing here is inferred, reconstructed or generated. Addresses and callback identifiers were observed in September 2026 and may already be stale, so treat them as retrospective hunting material rather than a live blocklist.

Network and HTTP

TypeIndicatorContext
Source IPv4139.28.18.122Requests logged 10 and 11 September 2026
Source IPv489.38.98.50Request logged 14 September 2026
Callback domainwebhook.siteBeacon target for host fingerprint data
Callback path ID45060ed4-de0b-4119-8f0d-2a2776bbd413Unique collector ID in the 10 September payload
Callback path ID774cf5e1-b5a4-4174-a1ad-0241861029a2Reused across 11 and 14 September payloads
User agentMozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/126.0Static across observed requests. Weak on its own

Request characteristics

ElementPatternContext
Target endpoint/apps/richdocumentscode/proxy.php?statusThe injection point. Also reached on a disabled app
Encoded traversal%2e%2eUsed in later requests in place of a literal traversal
Command substitution$( / %24%28Shell substitution inside the request path
Space obfuscation${IFS}Avoids literal whitespace in the injected command
Decode and executebase64${IFS}-d|shTerminal stage of the injected chain
Follow up probe?c=idConfirms the dropped file is live

Host and file

TypeIndicatorContext
File path patternapps/richdocumentscode/shx*.phpPrimary dropped file naming pattern
File path patternapps/richdocumentscode/shrf*.phpVariant seen in the earliest report
Observed filenamesshrf4645.php, shxa35d0.php, shx5cf91.php, shxd33ce.php, shxf4645.php, shx13a86.php, shx56367.phpNames are randomised per request. Match the pattern, not the list
SHA-2564b9fbd0663fbfd6028fc216ed18e0d6ef3ae498a7fdc97083e4b0ce3cec40562One recovered dropped file
File behaviourA single line PHP file that reads one HTTP GET parameter and passes it to a shell execution function, returning output in the response. Roughly 70 bytes.Any such file in the app tree is not legitimate
Process anomalyremote_font_config.urlA CODE AppImage or coolwsd process whose font config argument carries shell substitution
Integrity signalNextcloud app integrity check failing for richdocumentscodeHow at least one operator first noticed

Post access discovery targets

CategoryStrings searched on one host
Password manager data*.kdbx, bitwarden, 1password
Wallet and key materialwallet.dat, keystore.json, .bitcoin, .electrum, .monero, .ethereum

Reviewed requests did not show archiving or upload commands, so exfiltration is not confirmed. A shell running as the web server account can still read anything that account can read, so treat credentials and secrets reachable by that account as potentially exposed.

Hunting commands

# dropped files in the app tree find /var/www/nextcloud/apps/richdocumentscode -name ‘sh[xr]*.php’ # installed app and version sudo -u www-data php occ app:list | grep richdocumentscode sudo -E -u www-data php occ integrity:check-app richdocumentscode # request pattern in web server access logs grep -E ‘richdocumentscode/proxy\.php’ /var/log/nginx/access.log* | grep -E ‘%2e%2e|\$\(|\$\{IFS\}’ # live processes carrying an injected font config argument ps aux | grep -E ‘remote_font_config\.url=.*\$\(‘

Log paths and the Nextcloud root differ per install. A hit on the request pattern alone means an attempt. A dropped file, an integrity failure or an anomalous process means it worked, and the host should be handled as compromised rather than simply patched.

Sources. Vendor security advisory GHSA-g3vx-3m76-fghh for CVE-2026-110447; operator reports and access log extracts on CollaboraOnline/richdocumentscode issue 354; the 26.4.303 release tag; CISA Known Exploited Vulnerabilities catalog entry dated 23 October 2026. Compiled 24 October 2026.

Why 33 Days Matters

Scanners key on CVE IDs. For 33 days after the fix shipped, no ID existed, so no one found it or opened a ticket. An October 2026 study of 18,594 open-source CVEs found the median gap between a public code fix and CVE publication was 5.1 days in January 2026, rising to 39.2 days by August. That is one study and should be read as directional, but the shape matches what happened here.

The pattern keeps repeating. We have seen flaws exploited before a patch was released, and cases where CISA confirms active exploitation long after the code was quietly fixed. Severity scores told a mixed story too. This one scored 9.2, and its exploit probability score sat near 1.2%. The web shells were real anyway.

How to Avoid This

  • Upgrade richdocumentscode to 26.4.303 or later, or remove the app outright. On Nextcloud 29 and older, upgrade Nextcloud or drop the app.
  • Treat a disabled app as still installed and still reachable through proxy.php.
  • Search the app directory for PHP files matching the shx and shrf naming pattern, and rotate any secret the web server account could read if you find one.
  • Check egress logs for callbacks to webhook.site from your web server.
  • Watch vendor release feeds and commit activity alongside CVE identifiers.
Check your own instance

Switching the app off is not remediation.

The vulnerable request still reaches proxy.php on a disabled app, and the flaw fires precisely when the local CODE server is down. Find the state you are actually in.

Exposed
App installed, version below 26.4.303
Matches the affected range. Upgrade to 26.4.303 or later, or remove the app entirely.
Still exposed
App disabled but still installed
The enable switch is not a fix. Check the installed package version, then upgrade or remove it.
Flaw closed
Upgraded to 26.4.303 or later
The hole is shut. An upgrade does not undo an earlier compromise, so hunt for leftover PHP files in the app directory.
Out of scope
Separate standalone Collabora server
Not covered by this advisory. Confirm no built in app is also sitting alongside it.
# is the app installed, and at what version? sudo -u www-data php occ app:list | grep richdocumentscode # look for the web shell file pattern operators reported find /var/www/nextcloud/apps/richdocumentscode -name ‘sh[xr]*.php’

Paths vary by install. Conditions drawn from the vendor advisory for CVE-2026-110447 and operator reports on the project issue tracker.

Find It Before the Catalog Does

Scanners wait for an ID. For 33 days, no ID existed to wait for, while anyone reading the public commit had everything they needed. Secure.com closes that gap by starting from what is reachable on your network today.

  • The Red Teammate attacks your approved scope and confirms which exposures actually work against you, so the fix list is ranked by evidence.
  • Asset and app inventory surfaces where a package like this is installed, including instances switched off but never removed.
  • A confirmed finding becomes governed defensive work: a patch workflow, a config change, a retest, with human approval on anything consequential.
  • Record every action, approval,, and outcome so an auditor can see what was found, who signed it off, and when it closed.
  • Start with one teammate, above the stack you already own. Attack. Harden. Prove. Repeat.