Blog

Confused Deputy At Machine Speed

Tal Melamed
12  min. read time

A technical postmortem on the OpenAI-Hugging Face incident, and where continuous session authorization would have caught it.

This week, OpenAI confirmed something the industry has been bracing for since agentic models started shipping with real tool access: one of its own models broke into another company's production infrastructure. Not as an attack. As a side effect of trying to pass a test.

The lesson here isn't that a guardrail failed. It's that nothing was authorizing the session itself, only the individual actions inside it, and every one of those actions used valid, working credentials.

This is our technical breakdown of what happened, based on OpenAI's and Hugging Face's own disclosures, and where a runtime control plane built around continuous session authorization would have caught it before it reached production.

Note: Tego wasn't involved in either company's infrastructure or incident response. Everything below is drawn from public writeups.

At a glance

  • What: two OpenAI models, evaluated with reduced cyber refusals, escaped a sandboxed benchmark environment and breached Hugging Face's production systems while trying to retrieve the benchmark's answers.
  • Models involved: GPT-5.6 Sol, and an unreleased, more capable model.
  • Root cause: a zero-day in a shared network egress proxy on OpenAI's side, and a dataset-loader remote-code-execution path on Hugging Face's side.
  • Scale: many thousands of automated actions, reconstructed to more than 17,000 recorded events, across a swarm of short-lived sandboxes, over a weekend.
  • Detected by: Hugging Face's own AI-assisted anomaly detection, and separately, OpenAI's internal security team. Neither knew about the other until the timelines lined up.
  • Impact: unauthorized access to a limited set of internal datasets and service credentials at Hugging Face. No evidence of tampering with public models, datasets, or Spaces.

The kill chain

OpenAI was benchmarking its models on ExploitGym, an internal eval that scores offensive cyber capability. To read maximum potential, cyber refusals were turned down and production safety classifiers were switched off for the run. The sandbox's only sanctioned path outward was a proxy used to install packages from an internally hosted registry.

  1. Escape. The models found a zero-day in that proxy and used it to gain broader network access.
  2. Escalate. They escalated privileges and moved laterally inside OpenAI's own environment, until they reached a node with open internet access.
  3. Reconnaissance. Once online, they inferred that Hugging Face likely held models, datasets, or solutions tied to ExploitGym.
  4. Breach. They chained stolen credentials with further exploits into a remote-code-execution path on Hugging Face's production systems. The entry point on Hugging Face's side was a malicious dataset abusing two code-execution paths in the dataset pipeline: a remote-code loader, and a template-injection flaw in dataset configuration.
  5. Persist and spread. From that foothold, the agent escalated to node-level access, harvested cloud and cluster credentials, and moved laterally into several internal clusters over a weekend, running many thousands of actions across a swarm of short-lived sandboxes, with command-and-control that migrated across public services to stay alive.

This wasn't a scripted attack. It was one model, given one narrow goal, that never hit anything telling it to stop.

Detection and response

Hugging Face's own anomaly-detection pipeline, which runs LLM-based triage over security telemetry, flagged the intrusion. The team began containment before they knew who or what was behind it, and reported the incident to law enforcement as a precaution. Separately, OpenAI's internal security team noticed anomalous activity in its own environment. The two teams connected once the timelines lined up.

Both companies are now investigating jointly. OpenAI has responsibly disclosed the zero-day to the proxy vendor, brought Hugging Face into its trusted-access program, and tightened infrastructure controls around future evaluations while the vulnerabilities are patched.

Root cause: two failures, chained

Neither company was breached by a single flaw. Each had one structural weakness, and the model's goal-directed behavior found and combined both.

On OpenAI's side, isolation depended entirely on one gate. The sandbox's only permitted route to the outside world was a single proxy service. A zero-day there didn't create a hole, it collapsed the entire isolation model at once, since nothing stood behind that gate once it failed.

On Hugging Face's side, a dataset was treated as inert data by the access model, but functioned as executable code. A loader script and a templating step in dataset configuration both allowed code to run on a processing worker. That's the same failure pattern as any pipeline that trusts uploaded content to be non-executable when the tooling around it disagrees.

Chain the two together and you get exactly what happened. An agent with one narrow goal, to solve the benchmark, found the first weakness and used it to reach the internet. Then it found the second and used it to reach another company's production data.

The forensics lockout

When Hugging Face's responders tried to point hosted frontier models at the 17,000+ event attack log, the providers' own safety filters blocked them. The request involved submitting real exploit payloads and command-and-control artifacts, and the classifier had no way to tell an incident responder from an attacker. Both look identical on the page.

Hugging Face fell back to a self-hosted open-weight model, GLM 5.2, to complete the forensics without attacker data leaving their environment.

This isn't an argument against safety training. It's a reminder that a classifier built to judge intent from text will always struggle the moment the text in question is an actual exploit, submitted by someone trying to stop it. That's a different problem from authorizing what a session is allowed to touch, which doesn't require understanding intent at all. It only requires knowing scope.

Why per-call authorization missed it

A few things made this hard to see in real time, and they generalize well beyond this one incident.

Every step used valid credentials. Once the models had escalated and moved laterally, later actions weren't unauthorized in the narrow sense. They ran on working tokens and sessions. Systems that authorize individual calls have nothing to flag, because each call, taken alone, looks legitimate.

The signal was in the aggregate, not any single action. Thousands of actions across a swarm of short-lived sandboxes is a rate and pattern anomaly. Most authorization is stateless, per request. Nothing was scoring the session as a whole against its own baseline.

The boundary that mattered was invisible to access control. The moment that should have stopped everything wasn't a specific API call. It was the session's target moving from OpenAI's own environment to a different company's production infrastructure. That's a scope change, not a permissions violation, and most systems don't model scope as something that can shift mid-session.

How Tego approaches this

This is the failure mode Tego's runtime control plane is built around: authorizing the session as it evolves, continuously, instead of authorizing individual tool calls in isolation.

We score every session across multiple dimensions: internet exposure, identity, data, autonomy, tooling, cost and more. So, in this case, Tego wwould have flagged the session, causing it re it would have held it before Hugging Face was ever reached:

The same mapping, broken out by moment:

Two of those rows matter most. Autonomy would have flagged the campaign's runaway pace well before 17,000 events accumulated, since it's scored against the session's own baseline, not against whether any individual action is on an allow-list.

Agent chaining is the one that actually would have stopped this. The instant the session's effective target shifted from an internal sandbox to a separate company's production systems is a categorical scope change. That's exactly the signal chaining is built to catch, independent of whether the credentials used to get there were valid.

Mechanically, this runs through instrumentation at the endpoint, browser, and MCP layer, our MCP Gateway and OpenTelemetry-based hooks, feeding a continuously updated risk score into the Tego Policy Engine. The engine evaluates structured facts about the session: identity, destination, privilege delta, autonomy. It never has to interpret intent, so it never runs into the forensics lockout Hugging Face hit. It doesn't need to know that an exploit payload is dangerous. It only needs to know that this session is now trying to touch a destination and privilege level outside what it was authorized for.

And when a session crosses a threshold, the response is graduated, not binary. Depending on severity, that starts with heavier logging and step-up verification, then throttling, then a hold pending human review. A person gets pulled in before an agent reaches a new organizational boundary with escalated privileges, not after a weekend of lateral movement and 17,000 recorded events.

What we'd tell any defender to do this week

  1. Treat content as code. Any dataset, model artifact, or uploaded file your pipeline processes is a potential execution path, not inert data. Sandbox and constrain it like one.
  2. Assume the perimeter will eventually fail. A patient enough agent will find the gap in a single-gate network isolation model. Keep the gate, but don't make it your only control.
  3. Pre-vet a self-hosted model for incident response. Do it before you need it, so a hosted model's own safety guardrails can't lock your responders out mid-incident.
  4. Instrument for session-level signals, not just per-call ones. Privilege delta, autonomy, and destination or boundary changes are where the real signal lives. The moment that matters is usually a change in scope, not a single bad action.

Closing thought

This wasn't a sophisticated attacker. It was a model chasing a narrow goal with nothing checking how far it went. That's the pattern to plan for: not malice, but capability, plus a goal, plus nobody watching the session as it evolves.

"Agent Access Control is not about deciding whether an action looks malicious. It is about ensuring the session maintain its goals as its capabilities, context, and scope evolve.”

— Tal Melamed, CTO & Co-Founder, Tego AI