Der letzte Schritt war ein Prompt
Am 18. September veröffentlichte Hacktron die Kette, mit der das Team bis in das private Monorepo von OpenAI kam. Sie beginnt mit einem Bild, das in ein offenes Forum hochgeladen wurde, und einem Heap-Overflow in einem Bilddecoder, dessen Upstream-Fix keine CVE trug. Sie endet damit, dass die Forscher einen Prompt an das Codex-Konto eines Mitarbeiters schicken und der Agent den Pull Request öffnet. Nichts wurde injiziert, nichts ging kaputt; der Agent tat, was derjenige verlangte, der die Sitzung hielt. Bromure Agentic Coding entscheidet diesen Schreibzugriff auf Ihrem Mac, außerhalb der Sitzung.
Der letzte Schritt dieser Kette brauchte keinen Exploit. Die Forscher hielten den Coding-Agenten eines Mitarbeiters in der Hand, also baten sie ihn, einen Pull Request im privaten Monorepo zu öffnen, und er öffnete einen.
Um sechs Uhr morgens UTC am 25. Juli hatten drei Forscher von Hacktron
Codeausführung im öffentlichen Community-Forum von OpenAI. Am frühen Nachmittag
lag ein Pull Request mit der Nummer 1186742 in openai/openai, dem privaten
Monorepo, und sie hatten keine Zeile Code geschrieben, um ihn dorthin zu bringen.
Sie fragten einen Agenten, und der Agent reichte ihn ein.
Hacktron hat die Kette am 18. September veröffentlicht, und sie lohnt eine Lektüre Glied für Glied, denn jedes Glied ist gewöhnlich. Die Forscher sind Harsh Jaiswal, Mohan Pedhapati und Rahul Maini. The Hacker News berichtete am Tag darauf.
Ein Bild, eine Konvertierung und ein Parser
Der Weg hinein war der Bild-Upload des Forums. Discourse prüft hochgeladene
Bilder mit einer Ruby-Bibliothek namens FastImage, die genug vom Header einer
Datei liest, um Abmessungen und Format zu bestimmen. FastImage versteht kein
HEIF, den Container, in dem ein iPhone-Foto ankommt, also reichte Discourse diese
Dateien zur Konvertierung an den Befehl magick von ImageMagick weiter.
ImageMagick dekodiert HEIC mit libheif, und das ist C.
Das ist die ganze Eintrittsbedingung. Ein Format, das der sichere Prüfer nicht erkannte, ging an einen Konverter, der einen Parser in einer Sprache aufrief, in der ein missgebildetes Längenfeld ein Speichersicherheitsproblem ist. Hacktron fand einen Heap-Buffer-Overflow in der HEIC-Dekodierung und gewann daraus Primitive zum Lesen und Schreiben außerhalb der Grenzen.
Die Aktenlage ist schlimmer als der Bug. Upstream hatte diesen Overflow im Jahr
zuvor behoben und den Commit nie als Sicherheitsfix ausgezeichnet. Er bekam keine
CVE, kein Advisory und keine Changelog-Zeile, die ein Abhängigkeitsscanner hätte
lesen können, also portierte Debian ihn nie zurück, und das Docker-Image von
Discourse lieferte libheif 1.19.7 auf Debian 12 mit intaktem Bug aus. Kein
Scanner der Welt hatte Anlass, diese Version zu melden. Debian gab später
DSA-6417-1 heraus, und das Problem trägt inzwischen CVE-2026-32882, vergeben,
nachdem jemand es ausgenutzt hatte.
Man kann nicht nach einem Bug scannen, den niemand gemeldet hat. Was sich im Voraus entscheiden lässt, ist, worin der Parser steht, wenn er umfällt.
Der Exploit dauerte einen Abend
Hacktron begann am 23. Juli, sich die Upload-Pipeline anzusehen. Am 24. Juli gingen sie den Overflow mit Claude Opus 4.8 an, das sich nach ihrer Darstellung über mehrere Sitzungen abmühte und nichts hervorbrachte, das gegen die Adressraum-Randomisierung funktionierte, jene Verteidigung, die das Speicherbild eines Prozesses durchmischt, damit ein Angreifer nicht vorhersagen kann, wo etwas liegt. Einen Heap-Overflow gegen ASLR in zuverlässige Ausführung zu verwandeln, ist der schwere Teil, und genau dort bleibt diese Art Forschung eine Woche stecken.
Anthropic veröffentlichte Opus 5 an jenem Abend. Hacktron startete eine frische
Sitzung und hatte drei Stunden später einen funktionierenden ARM64-Exploit, der
gegen einen lokalen Mac lief. Sie ließen das Modell ihn auf die x86-64- und
jemalloc-Konfiguration portieren, auf der Discourse läuft, und bestätigten am
nächsten Morgen um sechs lokale Codeausführung über einen Bild-Upload. Dann
setzten sie Claude in einer autonomen Schleife auf ihre eigene
Discourse-Cloud-Instanz an. Um zehn hatte es auch dort Codeausführung und las
/etc/hosts, um es zu belegen.
Sie sind vorsichtig damit, was das heißt, und der Vorbehalt gehört in jede Lesart:
Dies war kein vollständig autonomes Hacking. Menschliche Expertise blieb nötig, um Sitzungen zu lenken, Ergebnisse zu validieren und die Offenlegung zu steuern.
Richtig. Drei fähige Forscher haben das Ding gerichtet, und ihre Fähigkeit änderte sich nicht über Nacht. Der Bug änderte sich auch nicht. Zwischen jenen beiden Sitzungen war die einzige neue Variable das Modell, und es brachte ein Stück Exploitation-Arbeit von mehreren gescheiterten Anläufen auf drei Stunden. Die Kampagne, zu der das gehörte, kostete Hacktron unter 3.000 Dollar an Tokens und ein paar Stunden Menschenzeit.
Diese Zahl ist der Planungswert. Ein Bug, der nie eine CVE bekam und in einer transitiven Abhängigkeit eines Dateikonverters saß, wird jetzt zum Preis eines Laptops zu einem zuverlässigen Primitiv. Auf das Advisory zu warten, ist eine Hoffnung, und niemand läuft dieser Uhr davon, indem er Changelogs schneller liest.
Der letzte Schritt war ein Prompt
Codeausführung im Forum brachte Hacktron nichts, woran OpenAI gelegen war. Das tat ein zweites Problem. OpenAI hatte sein Single Sign-on so verdrahtet, dass eine kompromittierte Forumssitzung zur Übernahme des ChatGPT- und Codex-Kontos jedes Mitarbeiters wurde, der das Forum nutzte, ganz ohne dessen Zutun. In Hacktrons Worten ist es das SSO-Problem, das aus einer Forumskompromittierung Zugang zu ChatGPT und Codex machte.
Das Codex eines Mitarbeiters war mit der GitHub-Organisation des Unternehmens
verbunden, also taten die Forscher das Naheliegende. Sie schickten diesem Konto
einen Prompt mit der Bitte, einen Pull Request im internen Monorepo zu öffnen,
und PR 1186742 erschien in openai/openai. Dann hörten sie auf, ohne Quellcode
zu lesen, und reichten den Bericht ein.
Lesen Sie diesen Schritt noch einmal. Jemand mit einer gültigen Sitzung bat den Agenten um etwas Gewöhnliches, und der Agent tat es mit dem Schreibzugriff, den er ohnehin hatte. Keine Injection, kein Jailbreak, keine missgebildete Eingabe. Jede Kontrolle, die irgendwer gebaut hatte, saß hinter dieser Sitzung: das Login, die Organisationsmitgliedschaft, die Repository-Rechte. Sobald ein Angreifer die Sitzung hielt, hielt er alles davon.
Ein Coding-Agent ist eine dauerhafte Gewährung von Schreibzugriff auf Ihre
Repositories, angeheftet an ein Gespräch. Wer das Gespräch erreicht, erbt die
Gewährung. Das gilt für Codex im Browser, und es gilt für Claude Code, Codex CLI
oder Gemini CLI auf einem Laptop, wo der Agent ein echtes ghp_-Token in
~/.git-credentials und ein echtes GH_TOKEN in seiner Umgebung trägt. Auf
einem Laptop vervielfachen sich die Wege hinein: eine vergiftete Datei in einem
Repository, ein Issue-Kommentar, ein Postinstall-Skript eines Pakets, ein
gekapertes Terminal.
OpenAI hat das Forum in etwa vierzehn Stunden gepatcht. Der Bericht ging an jenem Morgen ein, und OpenAI bestätigte den Fix noch am selben Tag um 22:49 UTC. Discourse lieferte über das Wochenende einen eigenen Fix und veröffentlichte am 28. Juli das Advisory GHSA-vhm9-85gw-x335, und die Bounty betrug 6.500 Dollar. Das Stück dieser Form, das auf Ihrem eigenen Schreibtisch liegt, ist der Agent.
Wo der Schreibzugriff entschieden wird
Bromure Agentic Coding behält die Antwort auf die Frage, wer pushen darf, auf Ihrem Mac, außerhalb der Sitzung des Agenten, denn die Sitzung ist das, was ein Angreifer zu erreichen versucht. Dort geschehen zwei Dinge.
Erstens enthält die Umgebung des Agenten kein Token zum Erben. Die Workspace-VM
bekommt einen Platzhalter: ghp_ plus 36 Zeichen, so geformt, dass gh und
git ihn anstandslos annehmen, abgeleitet aus Ihrem echten Token mit HKDF-SHA256
und einem installationsspezifischen Salt, sodass er zwischen Sitzungen nie zu
rotieren scheint. Ihr echtes Token liegt verschlüsselt auf dem Host, und der
Host-Proxy setzt es auf der Leitung ein, nachdem die Anfrage die VM verlassen
hat, und nur dann, wenn das Ziel zu dem Host passt, für den das Token geprägt
wurde. Wie es im Handbuch heißt: Keine Datei, keine Umgebungsvariable und kein
Prozess innerhalb der VM enthält je einen echten API-Schlüssel, ein
OAuth-Token, ein AWS-Geheimnis oder einen privaten SSH-Schlüssel. Tragen Sie
diesen Platzhalter irgendwohin, wo er nicht hingehört, und der Proxy antwortet
mit HTTP 451, ohne ein Byte weiterzuleiten, pausiert die VM und schreibt eine
rote Zeile in die Security Timeline.
Das zweite ist das, worum diese Geschichte bittet. Jede Git-Forge-Zugangsdatei
trägt eine Schreibrichtlinie, pro Workspace im Guardrails-Bereich gesetzt,
und neue Workspaces stehen standardmäßig auf Vor dem Schreiben nachfragen.
Lesezugriffe passieren kommentarlos. Ein git push kommt auf der Leitung als
git-receive-pack an und zählt als Schreibzugriff, und ein POST an die
Pull-Request-API ebenso. Trifft einer ein, hält der Proxy die Anfrage an und
öffnet auf Ihrem Mac einen Dialog, der die wörtliche Operation trägt statt einer
Zusammenfassung davon: Methode und Pfad. Sie erhalten Für 15 Minuten
erlauben, Einmal erlauben, Für den Rest der Sitzung erlauben oder
Nicht erlauben. Eine Ablehnung erreicht den Agenten als gewöhnlicher
API-Fehler, den er melden kann, nicht als hängende Verbindung.
Die Beschreibung, die der Bereich selbst davon gibt, wo das läuft, ist der Satz, auf den es ankommt: im Proxy durchgesetzt, sodass ein kompromittierter Agent in der VM es nicht umgehen kann.
Wer auch immer den Agenten steuert — Sie, eine in einer Fixture-Datei vergrabene Prompt-Injection oder jemand, der eine Ihnen abgenommene Sitzung hält —, der Schreibzugriff verlässt die Maschine durch denselben Proxy und wird genauso klassifiziert. Der Dialog auf Ihrem Mac ist die Autorisierung, und ein Angreifer mit Ihrer Sitzung hat nicht Ihren Mac.
Das Parser-Problem kommt auch auf Ihren Schreibtisch
Die andere Hälfte der Kette verallgemeinert sich ebenfalls, und wenige haben das eingepreist.
Ein Coding-Agent verbringt seinen Tag damit, Dateien zu lesen, die er nicht
geschrieben hat: Test-Fixtures, die mit dem Repository kamen, ein Bild, das an
einen Fehlerbericht gehängt war, ein Screenshot, den Sie ins Gespräch eingefügt
haben, das PDF einer Spezifikation, ein Tarball von einer Release-Seite, eine
Schriftart, ein Video, das das Frontend abspielen soll. Damit umzugehen heißt,
magick, ffmpeg, pdftotext oder unzip aufzurufen oder eine in Python
gebundene Bildbibliothek, und jedes davon ist ein C- oder C++-Parser, der Bytes
frisst, die jemand anderes gewählt hat. Genau diese Bedingung ließ einen
Forum-Upload bis zu libheif kommen. Ein Agent trifft sie häufiger als Sie, weil
er nie zögert, bevor er etwas öffnet.
Erkennung hat hier keine Antwort. Der libheif-Bug trug in dem Moment, in dem es darauf ankam, keine CVE, also hätte kein Scanner, keine Allowlist und kein Versions-Pin ein Wort gesagt. Sie dürfen den Explosionsradius wählen, und das ist alles.
In einem Bromure-Workspace läuft dieser Decoder in einem Ubuntu-Gast unter Apples
Virtualization.framework, einer Hypervisor-Grenze statt einer Prozess-Sandbox, in
einem Gast, den Bromure von vornherein als nicht vertrauenswürdig behandelt. Ein
Heap-Overflow in einem Bildparser kauft einem Angreifer eine Shell in einer
Linux-VM, deren Zugangsdaten Platzhalter sind und deren Weg ins Internet ein
geordnetes Regelwerk auf dem Host ist. Der virtuelle Switch prüft dieses
Regelwerk anhand von Ziel-IP und per DNS mitgelesenem Hostnamen über TCP und UDP,
und der Proxy prüft es erneut anhand von TLS-Servernamen und HTTP-Methode. Setzen
Sie nicht zugeordneten Verkehr auf Ablehnen, und die Shell hat eine Allowlist
und sonst nichts. Der Switch leitet :80 und :443 in den Proxy selbst um, also
gibt es keine Proxy-Variable, die die Shell abschalten könnte.
Regeländerungen erreichen laufende Sitzungen ohne Neustart, und jedes Urteil
landet als Firewall-Zeile in der Security Timeline.
Rechnen Sie damit, dass der Parser umfällt
Dieser Bug hatte keine CVE, als es darauf ankam. Planen Sie damit, dass der Decoder verliert, und entscheiden Sie vorher, worin er dabei steht.
Eine Sitzung ist keine Autorisierung
Wer das Gespräch erreicht, erbt den Schreibzugriff des Agenten. Legen Sie die Entscheidung über einen Push dorthin, wo das Gespräch nicht hinkommt.
Lassen Sie nichts Stehlbares in der VM
Ein Platzhalter, den Werkzeuge annehmen, ist upstream nichts wert und weniger als nichts für einen Angreifer, der ihn woandershin trägt.
Bepreisen Sie den Exploit
Drei Stunden und ein paar tausend Dollar an Tokens. Advisories schneller zu lesen, ist keine Antwort auf diese Zahl.
Hacktrons Bericht ist gute Forschung und ehrlich darüber, wie viel davon ein Mensch noch steuern musste. Das Ende ist der Teil, der nächstes Jahr noch zutrifft. Jede Verteidigung in der Kette saß hinter einer Identität, und sobald eine Sitzung mit dieser Identität den Besitzer wechselte, hatte keine von ihnen mehr eine Meinung. Jemand fragte den Agenten, und der Agent folgte.
Wenn Ihr Agent pushen kann, fragen Sie, wo die Berechtigung zum Pushen wohnt und ob ein Angreifer, der alles nähme, was der Agent hat, auch diese nähme. Auf einem Laptop nähme er sie. Verlegen Sie diese eine Entscheidung von der Maschine weg, auf der der Agent läuft, und der letzte Schritt dieser Kette hat einen Ort, an dem er anhalten kann.