FALCONINTERNET

KindaRails2Shell: Active Exploitation of CVE-2026-66066 Means One Update Isn't Enough

Security
KindaRails2Shell: Active Exploitation of CVE-2026-66066 Means One Update Isn't Enough

Exploitation of CVE-2026-66066 — the Ruby on Rails image-upload chain researchers nicknamed KindaRails2Shell — ticked up from proof-of-concept to active mass attacks in early August. New findings published September 1 show over 7,000 directly reachable vulnerable instances and credential-harvesting campaigns already in motion. If your stack includes any Rails application that handles file uploads, you need to act, and a single version bump very likely will not be enough.

How the Exploit Chain Works

The vulnerability lives in Active Storage, Rails's built-in attachment library, when it uses libvips as its image-processing backend — the default for Rails 7.0 and later. The attack unfolds in three stages, all unauthenticated:

  • Stage 1 — malicious blob upload. An attacker sends a specially crafted file to Active Storage's direct-upload endpoint and declares it image/png. Active Storage trusts the client-supplied content type without verifying the actual file bytes. No login required.
  • Stage 2 — parser confusion. The crafted file satisfies two conflicting parsers simultaneously: libvips reads bytes 0–9 and sees a valid MATLAB 5.0 magic header; libmatio reads bytes 124–125 and interprets the same file as a MAT 7.3 HDF5 container. That discrepancy invokes HDF5's External File List feature, which reads arbitrary files on disk that the Rails process can access — including /proc/self/environ, the Rails credentials file, and anything else the application user can reach.
  • Stage 3 — key theft to shell. Once SECRET_KEY_BASE is in hand, the attacker signs a crafted variation key embedding a malicious ImageProcessing pipeline instruction. Because the Vips pipeline lacks the operation-name validation that MiniMagick enforces, that structure reaches public_send and invokes Kernel#spawn or Kernel#eval — arbitrary command execution at the Rails process level.

The whole chain requires no account, no session, no prior knowledge of the application. Any endpoint that accepts an Active Storage direct upload is the attack surface.

The Patch Gap That Matters

Rails released fixes in late July: 8.1.3.1, 8.0.5.1, and 7.2.3.2. They close the file-read vector by calling Vips.block_untrusted(true) during Active Storage initialization, disabling libvips operations flagged as untrusted. Patched Rails will actually refuse to boot if the installed libvips does not expose that blocking API.

The problem: VulnCheck testing confirmed that even on 8.1.3.1, a variation-key Marshal deserialization pathway still carries RCE risk. The patch addresses Stages 1 and 2; the deserialization issue is a separate, incompletely remediated vector. Updating Rails is necessary — but it is not sufficient on its own.

A complete remediation requires all three:

  • Rails updated to 7.2.3.2, 8.0.5.1, or 8.1.3.1 depending on your branch
  • libvips 8.13 or later on the system — older libvips does not expose the blocking API that patched Rails now requires
  • ruby-vips 2.2.1 or later — the Ruby binding updated to call that API correctly

If you are running managed hosting or container images with a pinned system libvips, verify that version first. On some configurations, older libvips ships silently and the application continues accepting file uploads while the blocking API goes uncalled — the Rails version looks correct, the vulnerability remains.

Who Is Exposed

Affected version ranges span every maintained Rails branch:

  • Rails < 7.2.3.2
  • Rails 8.0.x < 8.0.5.1
  • Rails 8.1.x < 8.1.3.1
  • Rails 6.x applications that have explicitly switched their variant processor to Vips

Ethiack, who discovered and reported the flaw, estimates more than 500,000 sites are potentially exposed. VulnCheck counted roughly 7,100 directly enumerable vulnerable instances as of early August. The spread between those numbers reflects the real attack surface: most Rails apps sit behind reverse proxies and are not publicly fingerprinted, but an attacker who can reach any file-upload endpoint can trigger the chain regardless of whether the host is indexed.

What Attackers Are Actually Doing

The campaigns observed through August 31 have focused on credential harvesting rather than immediate ransomware deployment. Attackers are reading /proc/self/environ, extracting the Rails credentials store, and pulling cloud storage keys (AWS, GCS), database passwords, and third-party API tokens. Command-and-control infrastructure has been traced to hosts in Russia and Israel. Credential exfiltration is typically followed by lateral movement and persistent backdoor installation in a second wave — meaning businesses that were hit weeks ago may not have seen the noisy phase yet.

Companion Threat: CVE-2026-0768 in Langflow

The same VulnCheck report flagged CVE-2026-0768 (CVSS 9.8) in Langflow, the open-source visual AI pipeline builder. An unauthenticated attacker can inject arbitrary Python code through the /api/v1/validate/code endpoint; the injected code executes as root. Over 360 confirmed exploitations were recorded by August 31, with traffic primarily originating from Russia and focused on harvesting API keys and environment credentials before pivoting into connected cloud infrastructure. If you self-host Langflow for AI workflow automation, upgrade to version 1.9.0 immediately.

Steps to Take Right Now

  • Check your Rails version. Run bundle exec rails -v in each application. Any version below the patched thresholds is vulnerable.
  • Check libvips on the server. Run vips --version. You need 8.13 or later. On Debian/Ubuntu: apt-get update && apt-get install libvips-dev. On RHEL/Rocky, check EPEL or build from source if the package manager version is behind.
  • Check ruby-vips. Run bundle exec ruby -e "require 'vips'; puts Vips::VERSION" — you want 2.2.1 or later. Update your Gemfile accordingly.
  • Rotate credentials before or alongside patching. If you cannot confirm your application was clean throughout August, assume the Rails credentials file, SECRET_KEY_BASE, and every API key stored in it have been read. Rotate them all before deploying the patch — rotating after is better than never, but an attacker with a valid variation key signed on the old secret can still operate until that secret is gone.
  • Restrict direct-upload endpoints to authenticated users if your application design allows it. Active Storage direct uploads are Stage 1's front door.
  • Audit upload directories for unexpected .rb, .sh, or .php files. A successful Stage 3 often writes a persistent access mechanism.

This is one of those vulnerabilities that rewards the engineering discipline of keeping secrets in a dedicated secrets manager rather than a committed Rails credentials file. If SECRET_KEY_BASE rotates from a vault on demand, Stage 3 of this chain costs an attacker their stolen key every time you rotate — and the blast radius of any single exfiltration collapses. It is exactly why credential hygiene gets drilled alongside patching cadence.

Need this handled instead of explained?

We do this for a living — talk to an engineer about your setup.