Every CVE Search/ Get API key

CVE-2026-55086

Etherpad: Import/export use Math.random() for temp file paths; predictable paths on shared /tmp enable symlink-based file overwrite

4.2 MediumFix available

Etherpad is a real-time collaborative editor. Prior to 3.1.0, src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts derive temporary filenames from Math.random() and place them in os.tmpdir(). On a host with a shared world-writable temporary directory, a local unprivileged attacker who predicts a filename can precreate a symbolic link to a file writable by the Etherpad process. Subsequent import or export operations can follow the link through fs.writeFile, fs.rename, or document-conversion output and overwrite the target with partially attacker-controlled content. This issue is fixed in version 3.1.0.

Attack profile

How easy it is to exploit

Attack vector
Local
Complexity
High
Privileges needed
Low
User interaction
None

What an attacker can affect

Confidentiality
Low
Integrity
Low
Availability
None

Exploit likelihood

0.14%Unchanged since Aug 20, 2026
90%50%10%1%

What each source reports

CVE List Score used 4.2

Etherpad: Import/export use Math.random() for temp file paths; predictable paths on shared /tmp enable symlink-based file overwrite

Etherpad is a real-time collaborative editor. Prior to 3.1.0, src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts derive temporary filenames from Math.random() and place them in os.tmpdir(). On a host with a shared world-writable temporary directory, a local unprivileged attacker who predicts a filename can precreate a symbolic link to a file writable by the Etherpad process. Subsequent import or export operations can follow the link through fs.writeFile, fs.rename, or document-conversion output and overwrite the target with partially attacker-controlled content. This issue is fixed in version 3.1.0.

Record
CVE-2026-55086
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Weakness
CWE-59, CWE-377
Updated
2026-11-02
EUVDEUVD-2026-62741 4.2

Etherpad is a real-time collaborative editor. Prior to 3.1.0, src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts derive temporary filenames from Math.random() and place them in os.tmpdir(). On a host with a shared world-writable temporary directory, a local unprivileged attacker who predicts a filename can precreate a symbolic link to a file writable by the Etherpad process. Subsequent import or export operations can follow the link through fs.writeFile, fs.rename, or document-conversion output and overwrite the target with partially attacker-controlled content. This issue is fixed in version 3.1.0.

Record
EUVD-2026-62741
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Updated
2026-11-02
GitHub AdvisoriesGHSA-2jwf-f4xq-f24h 4.2

ep_etherpad-lite: Import/export uses Math.random() for temp file paths; predictable paths on shared /tmp enable symlink-based file overwrite

Description

src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts both compute their temporary working-file paths as:

const randNum = Math.floor(Math.random() * 0xFFFFFFFF);
const srcFile = `${os.tmpdir()}/etherpad_export_${randNum}.html`;
const destFile = `${os.tmpdir()}/etherpad_export_${randNum}.${type}`;

Two flaws compound:

  1. Math.random() is not crypto-secure. It yields at most ~32 bits of entropy and is predictable across calls within the same Node process (V8 shares PRNG state between consecutive Math.random() invocations). An attacker on the same host who observes any earlier temp-file name from logs or other side channels can predict subsequent names.

  2. The paths land in os.tmpdir(). On a typical Linux system this is /tmp — a shared world-writable directory. An unprivileged local attacker can pre-create a symbolic link at a predicted path pointing at any file the Etherpad process can write:

    ln -s /etc/etherpad/SESSIONKEY.txt /tmp/etherpad_export_<predicted>.html
    

    When ExportHandler calls fs.writeFile(srcFile, html) (or ImportHandler calls fs.rename(srcFile, destFile) / soffice writes its converted output to the path), the open syscall follows the symlink and either reads from or overwrites the linked target. For deployments where the Etherpad process runs as a privileged user (notably some Docker base images that run as root, snap confinement edge cases, or hand-rolled systemd units), this becomes arbitrary file overwrite.

The Import path is more impactful in practice: the file content the attacker can land in the symlink target is partially attacker-controlled (the post-soffice/post-mammoth conversion output of the uploaded document).

Severity rationale

  • AV:L — requires local access to the host that runs Etherpad. Multi-tenant hosts (shared dev boxes, k8s shared-node setups, single-server CI workers) are the realistic threat surface.
  • AC:H — attacker needs to predict the temp filename, which requires observing prior names or shared PRNG state.
  • PR:L — any unprivileged local account.
  • UI:N — no user interaction.
  • S:C — scope change from local user to whatever the Etherpad process can write.
  • C:L / I:L / A:N — bounded by what the Etherpad process can already touch; confidentiality is via secondary read-paths (the LibreOffice conversion error log can echo bytes from the symlinked file).

Single-tenant deployments where only the Etherpad operator has shell access on the host are not exposed.

Affected versions

  • All ep_etherpad-lite versions through v3.0.0 (inclusive). The Math.floor(Math.random() * 0xFFFFFFFF) pattern is present in src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts for as far back as the repository history extends — older than the 2024-03-16 snapshot at commit 107598b where it first appears in the current file paths, and predating the v1.x era.

Patched versions

  • ep_etherpad-lite >= 3.1.0 — the fix is on develop HEAD as commit 8c6104c. Update this field with the actual tagged release version when it ships.

Proof of concept (sketch)

# Pre-condition: attacker has shell on the same host as Etherpad,
# has read access to /tmp, and Etherpad's process can write to the
# chosen target (e.g. runs as root inside a Docker container).

# 1. Observe a temp filename from logs (or guess via prior exports).
TARGET=/etc/etherpad/SESSIONKEY.txt
GUESS=/tmp/etherpad_export_$(./predict-next-random)$EXT  # implementation-specific

# 2. Place the symlink before Etherpad creates the file.
ln -s "$TARGET" "$GUESS"

# 3. Trigger an export from the Etherpad UI (or via the API).
# Etherpad calls fs.writeFile(srcFile, ...) which open()s the symlink
# target with O_WRONLY|O_TRUNC and clobbers $TARGET with HTML content.

In practice the exact reproduction depends on the host's…

Record
GHSA-2jwf-f4xq-f24h
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Weakness
CWE-59, CWE-377
Updated
2026-11-02
NVD 4.2

Etherpad is a real-time collaborative editor. Prior to 3.1.0, src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts derive temporary filenames from Math.random() and place them in os.tmpdir(). On a host with a shared world-writable temporary directory, a local unprivileged attacker who predicts a filename can precreate a symbolic link to a file writable by the Etherpad process. Subsequent import or export operations can follow the link through fs.writeFile, fs.rename, or document-conversion output and overwrite the target with partially attacker-controlled content. This issue is fixed in version 3.1.0.

Record
CVE-2026-55086
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Weakness
CWE-59, CWE-377
Updated
2026-11-02
OSV 4.2

Etherpad: Import/export use Math.random() for temp file paths; predictable paths on shared /tmp enable symlink-based file overwrite

Etherpad is a real-time collaborative editor. Prior to 3.1.0, src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts derive temporary filenames from Math.random() and place them in os.tmpdir(). On a host with a shared world-writable temporary directory, a local unprivileged attacker who predicts a filename can precreate a symbolic link to a file writable by the Etherpad process. Subsequent import or export operations can follow the link through fs.writeFile, fs.rename, or document-conversion output and overwrite the target with partially attacker-controlled content. This issue is fixed in version 3.1.0.

Record
CVE-2026-55086
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Weakness
CWE-377, CWE-59
Updated
2026-11-02
OSVGHSA-2jwf-f4xq-f24h 4.2

ep_etherpad-lite: Import/export uses Math.random() for temp file paths; predictable paths on shared /tmp enable symlink-based file overwrite

Description

src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts both compute their temporary working-file paths as:

const randNum = Math.floor(Math.random() * 0xFFFFFFFF);
const srcFile = `${os.tmpdir()}/etherpad_export_${randNum}.html`;
const destFile = `${os.tmpdir()}/etherpad_export_${randNum}.${type}`;

Two flaws compound:

  1. Math.random() is not crypto-secure. It yields at most ~32 bits of entropy and is predictable across calls within the same Node process (V8 shares PRNG state between consecutive Math.random() invocations). An attacker on the same host who observes any earlier temp-file name from logs or other side channels can predict subsequent names.

  2. The paths land in os.tmpdir(). On a typical Linux system this is /tmp — a shared world-writable directory. An unprivileged local attacker can pre-create a symbolic link at a predicted path pointing at any file the Etherpad process can write:

    ln -s /etc/etherpad/SESSIONKEY.txt /tmp/etherpad_export_<predicted>.html
    

    When ExportHandler calls fs.writeFile(srcFile, html) (or ImportHandler calls fs.rename(srcFile, destFile) / soffice writes its converted output to the path), the open syscall follows the symlink and either reads from or overwrites the linked target. For deployments where the Etherpad process runs as a privileged user (notably some Docker base images that run as root, snap confinement edge cases, or hand-rolled systemd units), this becomes arbitrary file overwrite.

The Import path is more impactful in practice: the file content the attacker can land in the symlink target is partially attacker-controlled (the post-soffice/post-mammoth conversion output of the uploaded document).

Severity rationale

  • AV:L — requires local access to the host that runs Etherpad. Multi-tenant hosts (shared dev boxes, k8s shared-node setups, single-server CI workers) are the realistic threat surface.
  • AC:H — attacker needs to predict the temp filename, which requires observing prior names or shared PRNG state.
  • PR:L — any unprivileged local account.
  • UI:N — no user interaction.
  • S:C — scope change from local user to whatever the Etherpad process can write.
  • C:L / I:L / A:N — bounded by what the Etherpad process can already touch; confidentiality is via secondary read-paths (the LibreOffice conversion error log can echo bytes from the symlinked file).

Single-tenant deployments where only the Etherpad operator has shell access on the host are not exposed.

Affected versions

  • All ep_etherpad-lite versions through v3.0.0 (inclusive). The Math.floor(Math.random() * 0xFFFFFFFF) pattern is present in src/node/handler/ImportHandler.ts and src/node/handler/ExportHandler.ts for as far back as the repository history extends — older than the 2024-03-16 snapshot at commit 107598b where it first appears in the current file paths, and predating the v1.x era.

Patched versions

  • ep_etherpad-lite >= 3.1.0 — the fix is on develop HEAD as commit 8c6104c. Update this field with the actual tagged release version when it ships.

Proof of concept (sketch)

# Pre-condition: attacker has shell on the same host as Etherpad,
# has read access to /tmp, and Etherpad's process can write to the
# chosen target (e.g. runs as root inside a Docker container).

# 1. Observe a temp filename from logs (or guess via prior exports).
TARGET=/etc/etherpad/SESSIONKEY.txt
GUESS=/tmp/etherpad_export_$(./predict-next-random)$EXT  # implementation-specific

# 2. Place the symlink before Etherpad creates the file.
ln -s "$TARGET" "$GUESS"

# 3. Trigger an export from the Etherpad UI (or via the API).
# Etherpad calls fs.writeFile(srcFile, ...) which open()s the symlink
# target with O_WRONLY|O_TRUNC and clobbers $TARGET with HTML content.

In practice the exact reproduction depends on the host's…

Record
GHSA-2jwf-f4xq-f24h
CVSS 3.1
4.2 MediumCVSS:3.1/AV:L/AC:H/PR:L/UI:N/S:C/C:L/I:L/A:N
Weakness
CWE-377, CWE-59
Updated
2026-11-02

Affected products

Affected packages

Affected packages
PackageAffectedFixed
ep_etherpad-lite
npm
through 3.0.0
3.1.0
ep_etherpad-lite
npm
before 3.1.0
3.1.0

History

History
RecordedChangedSources
first indexedCVE List, EUVD, GitHub Advisories, NVD, OSV

Dates are when Every CVE recorded each change. Upstream dates may differ.

In short

CVE-2026-55086 is a medium vulnerability (CVSS 4.2) in Ether Etherpad, published August 13, 2026. No source lists public exploit code. EPSS puts the chance of exploitation in the next 30 days at 0.14%, the 3rd percentile. Fixed in ep_etherpad-lite 3.1.0.

References

This page doesn't list everything

Left out here: the rest of 2 source descriptions. The JSON record has them.

MoveEnter Open