{"id":"GHSA-p6m2-r3w9-mpxw","summary":"rclone local: crafted Range request against a translated symlink panics (DoS)","details":"### Summary\nWhen `backend/local` is used with `--links`/`-l` (or the `links=true` config option), each symlink is exposed as an rclone object whose content is the target path string, suffixed `.rclonelink`. `Object.Open()` decodes an incoming `fs.RangeOption` via `Decode(o.Size())`, then for a translated-symlink object passes the decoded `offset` straight into `openTranslatedLink`, which indexes the target string directly: `linkdst[offset:]`.\n\n`RangeOption.Decode`'s `Start \u003e= 0` branch (an ordinary `Range: bytes=X-` request) sets `offset = o.Start` with no upper bound, unlike its suffix-range branch (`Start \u003c 0`, e.g. `bytes=-N`), which already clamps a too-large value to 0 - the fix for a prior, related crash (issue #6310: \"bytes=-90407\" against a 5-byte object panicked with \"slice bounds out of range\", now covered by an existing regression test). The `Start \u003e= 0` branch never received the analogous protection.\n\nA `Range: bytes=\u003chugeStart\u003e-` request sent to `rclone serve http`/`webdav` (or any consumer of `lib/http/serve`'s `Object()`, which parses and decodes the client's own Range header) against a directory containing a symlink therefore reaches `linkdst[offset:]` with offset far beyond the target string's length, and Go panics with \"slice bounds out of range\" instead of returning an empty read.\n\n### Details\nVulnerable code (before fix):\n```go\nfunc (o *Object) openTranslatedLink(offset, limit int64) (lrc io.ReadCloser, err error) {\n\tlinkdst, err := os.Readlink(o.path)\n\tif err != nil { return nil, err }\n\treturn readers.NewLimitedReadCloser(io.NopCloser(strings.NewReader(linkdst[offset:])), limit), nil\n}\n```\n\n### PoC\nCalled the real production `Object.Open()` on a translated-symlink object (target length 12) with `&fs.RangeOption{Start: math.MaxInt64, End: -1}`:\n```\npanic: runtime error: slice bounds out of range [9223372036854775807:8]\n  ...backend/local.(*Object).openTranslatedLink\n  ...backend/local.(*Object).Open\n```\n\n### Impact\nA remote client can send a single crafted `Range` header against any symlink-backed object exposed by `rclone serve http`/`webdav`/etc (backed by `backend/local` with `--links` enabled) to deterministically panic the request-handling goroutine. Go's `net/http` recovers panics per-connection by default, so this fails the one request/connection rather than crashing the whole server process, and no file handle is left open (the panic occurs before any read handle is acquired) - but it is fully deterministic and remotely triggerable with no authentication or race window needed, unlike some other panic-recovery findings.\n\n### Fix\nClamp `offset` to the length of the target string before slicing, matching how a real file read past EOF behaves (an empty read):\n```go\nif offset \u003e int64(len(linkdst)) {\n\toffset = int64(len(linkdst))\n}\n```\nNote: the shared `RangeOption.Decode()` also has a related, unaddressed issue - `limit = o.End - o.Start + 1` can itself overflow to a large negative number for a huge `End` - but a fix attempted there during this investigation broke `fs/operations/reopen.go`'s `NewReOpen`, which calls `Decode` with its `h.end` field still at its zero value at that point in construction. Flagged for awareness but not changed here to keep this patch minimal and low-risk.","aliases":["BIT-rclone-2026-88015","CVE-2026-88015","GO-2026-6461"],"modified":"2026-09-19T09:25:43.916782095Z","published":"2026-09-10T22:49:27Z","database_specific":{"severity":"MODERATE","github_reviewed":true,"github_reviewed_at":"2026-09-10T22:49:27Z","nvd_published_at":"2026-09-10T16:18:08Z","cwe_ids":["CWE-190","CWE-248"]},"references":[{"type":"WEB","url":"https://github.com/rclone/rclone/security/advisories/GHSA-p6m2-r3w9-mpxw"},{"type":"ADVISORY","url":"https://nvd.nist.gov/vuln/detail/CVE-2026-88015"},{"type":"WEB","url":"https://github.com/rclone/rclone/commit/28bf49d66f94acc3f4f7f318504a706686281af9"},{"type":"PACKAGE","url":"https://github.com/rclone/rclone"},{"type":"WEB","url":"https://github.com/rclone/rclone/releases/tag/v1.75.1"}],"affected":[{"package":{"name":"github.com/rclone/rclone","ecosystem":"Go","purl":"pkg:golang/github.com/rclone/rclone"},"ranges":[{"type":"SEMVER","events":[{"introduced":"0"},{"fixed":"1.75.1"}]}],"database_specific":{"last_known_affected_version_range":"\u003c= 1.75.0","source":"https://github.com/github/advisory-database/blob/main/advisories/github-reviewed/2026/09/GHSA-p6m2-r3w9-mpxw/GHSA-p6m2-r3w9-mpxw.json"}}],"schema_version":"1.9.0","severity":[{"type":"CVSS_V3","score":"CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:L"}]}