Title: Sandbox escape via JavaScript prototype chain traversal in cohere-terrarium
Impact
A critical sandbox escape vulnerability (CVSS 9.3) in cohere-terrarium allowed JavaScript executed inside the Pyodide-based Python sandbox to traverse the JavaScript prototype chain of host-supplied mock objects (document, ImageData, and the DOM element stubs returned from document.getElementById / createElement / createTextNode) via __proto__ and .constructor, reach the host Function constructor, and execute arbitrary JavaScript in the Node.js host process.
.
The vulnerability is in the jsglobals mock objects passed to loadPyodide in src/services/python-interpreter/service.ts. The mocks were plain object literals, which inherit from Object.prototype, exposing the host realm's constructors to sandboxed Python code.
Patches
Fixed in v1.0.1 [release](https://github.com/cohere-ai/cohere-terrarium/releases/tag/v1.0.1).
The patch reconstructs every host-supplied mock object passed into jsglobals with Object.create(null) so they have no prototype chain to traverse, and freezes the immutable mocks (document, document.body, ImageData, and classList) with Object.freeze. Mocks that legitimate libraries (e.g. matplotlib-pyodide) mutate at runtime — elementStub and its .style — remain writable but still null-prototyped.
Workarounds
There is no in-process workaround. Operators who cannot upgrade should:
- Stop exposing...
Affected versions
| Package | Affected | Fixed in |
|---|---|---|
| cohere-terrarium Product | < 1.01 | 1.01 |
Details and references
### Impact A critical sandbox escape vulnerability (CVSS 9.3) in `cohere-terrarium` allowed JavaScript executed inside the Pyodide-based Python sandbox to traverse the JavaScript prototype chain of host-supplied mock objects (`document`, `ImageData`, and the DOM element stubs returned from `document.getElementById` / `createElement` / `createTextNode`) via `__proto__` and `.constructor`, reach the host `Function` constructor, and execute arbitrary JavaScript in the Node.js host process. . The vulnerability is in the `jsglobals` mock objects passed to `loadPyodide` in `src/services/python-interpreter/service.ts`. The mocks were plain object literals, which inherit from `Object.prototype`, exposing the host realm's constructors to sandboxed Python code. ### Patches Fixed in **v1.0.1** [release](https://github.com/cohere-ai/cohere-terrarium/releases/tag/v1.0.1). The patch reconstructs every host-supplied mock object passed into `jsglobals` with `Object.create(null)` so they have no prototype chain to traverse, and freezes the immutable mocks (`document`, `document.body`, `ImageData`, and `classList`) with `Object.freeze`. Mocks that legitimate libraries (e.g. matplotlib-pyodide) mutate at runtime — `elementStub` and its `.style` — remain writable but still null-prototyped. ### Workarounds There is no in-process workaround. Operators who cannot upgrade should: - Stop exposing `cohere-terrarium` to untrusted input, or - Run the container under strict isolation (rootless runtime, read-only root FS, seccomp/AppArmor, dropped capabilities, network egress disabled), treating any code submitted to the service as fully trusted host code. ### References - CVE-2026-5752: https://nvd.nist.gov/vuln/detail/CVE-2026-5752 - GitHub Advisory Database entry: https://github.com/advisories/GHSA-cmpr-pw8g-6q6c - Release: https://github.com/cohere-ai/cohere-terrarium/releases/tag/v1.0.1 - Disclosure: https://thehackernews.com/2026/04/cohere-ai-terrarium-sandbox-flaw.html
- CVSS 3.1
- CVSS:3.1/AV:L/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H
- Severity from
- GitHub (reviewed advisory)
- Weakness
- CWE-1321