---
id: CVE-2026-65607
aliases:
  - GHSA-gw25-m53r-qh88
title: >-
  SiYuan: path traversal via /export/temp/ short-circuit branch (incomplete fix
  for the export-disclosure hardening, GHSA-6865-qjcf-286f)
summary: >-
  SiYuan: path traversal via /export/temp/ short-circuit branch (incomplete fix
  for the export-disclosure hardening, GHSA-6865-qjcf-286f)
severity: medium
cvss: 6.5
cvssVector: 'CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:N/A:N'
vendor: siyuan-note
product: github.com/siyuan-note/siyuan/kernel
ecosystem: go
affected:
  - github.com/siyuan-note/siyuan/kernel < 0.0.0-20260510110132-b763d787d1f2
patched:
  - github.com/siyuan-note/siyuan/kernel 0.0.0-20260510110132-b763d787d1f2
published: '2026-09-03'
updated: '2026-09-03'
source: OSV
sourceUrl: 'https://osv.dev/vulnerability/GHSA-gw25-m53r-qh88'
references:
  - url: >-
      https://github.com/siyuan-note/siyuan/security/advisories/GHSA-gw25-m53r-qh88
  - url: >-
      https://github.com/siyuan-note/siyuan/commit/b763d787d1f2b862c577049e4ee147c5857fe413
  - url: 'https://github.com/siyuan-note/siyuan'
tags:
  - osv
  - go
epss: 0.00586
epssPercentile: 0.45645
ingestedAt: '2026-09-03T19:32:13.601Z'
---

## Overview

## Summary
SiYuan's `/export/` file handler was hardened against export disclosure (issue #12213) by adding an
`IsSubPath(exportBaseDir, fullPath)` check and an `IsSensitivePath()` check in commit `bb481e1`. These guards
were added only to the main branch of the handler. The handler begins with a short-circuit branch:
```go
if strings.HasPrefix(c.Request.URL.Path, "/export/temp/") {
    c.File(filepath.Join(util.TempDir, c.Request.URL.Path))
    return
}
```
This branch joins the **broader** `util.TempDir` with the raw, percent-decoded request path and serves it with
**neither** `IsSubPath` **nor** `IsSensitivePath`. An authenticated request to
`/export/temp/%2e%2e/.../etc/passwd` traverses out of `TempDir` and reads arbitrary files - exactly the
sensitive-file disclosure the patch intended to prevent. Present in the latest master.

## Affected
- From commit `bb481e1` (the hardening) through the latest master.
- Requires SiYuan access authorization (`model.CheckAuth`) - but the patch's stated goal is to deny sensitive-file
  export even to authorized callers.

## Root cause
`kernel/server/serve.go` `serveExport()`: the main branch has `IsSubPath` + `IsSensitivePath`; the
`/export/temp/` short-circuit branch (above it) has neither and uses `util.TempDir` as its root.
`c.Request.URL.Path` is percent-decoded by net/http, so `%2e%2e` becomes `..` and `filepath.Join` collapses it.

## Incomplete-fix lineage
- Export disclosure (issue #12213; CVE-2026-30869) -> fix `bb481e1` / `d68bd5a` (GHSA-6865-qjcf-286f): guards on
  the main branch + `IsSensitivePath` extended to `*.db`/`*.log`.
- Follow-up CVE-2026-41894 (GHSA-hjh7-r5w8-5872) in the same `/export` path family.
- The `/export/temp/` short-circuit branch was never covered by the guards (this report).

## Proof of concept (benign)
1. Authenticate (access auth code).
2. `GET /export/<sensitive>` (main branch) -> 401/403 (guards work).
3. `GET /export/temp/%2e%2e/%2e%2e/.../tmp/<planted-marker>` (or `/etc/hostname`) -> 200 + file content,
   demonstrating the unguarded traversal. The PoC reads only a planted marker / `/etc/hostname`; no credentials.

## Impact
Authenticated arbitrary file read bypassing the sensitive-file protection: `/etc/passwd`, `~/.ssh/*`, SiYuan
`*.db` workspace data, `*.log`. 

## Remediation
- Apply `IsSubPath` + `IsSensitivePath` to the `/export/temp/` branch (or restrict its root to `TempDir/temp` with
  an `IsSubPath` check).
- `filepath.Clean` the request path and reject `..`.
- Merge both branches into one guarded file-serving function.

## References
- Hardening advisory: https://github.com/siyuan-note/siyuan/security/advisories/GHSA-6865-qjcf-286f (commit d68bd5a); issue #12213.
- CVE chain: CVE-2026-30869 -> CVE-2026-41894 (GHSA-hjh7-r5w8-5872).
- serve.go guards commit: https://github.com/siyuan-note/siyuan/commit/bb481e1290c4a34255652ede85a546504505d2a7
- Residual source (master): `kernel/server/serve.go` `serveExport()` lines 308-312.

## Affected packages

- `github.com/siyuan-note/siyuan/kernel < 0.0.0-20260510110132-b763d787d1f2`

## Remediation

Upgrade to a patched release:

- `github.com/siyuan-note/siyuan/kernel 0.0.0-20260510110132-b763d787d1f2`
