CVE-2026-44881: Portainer Has an Arbitrary File Read via Git Symlink Injection in Stack Auto-Update
(updated )
Portainer supports deploying stacks from Git repositories. When a Git-backed stack is created or updated, Portainer clones the repository using go-git v5, which translates Git blob entries with mode 0o120000 (symlink) into real OS symlinks on the host filesystem via os.Symlink. The only entry blocked from becoming a symlink is .gitmodules; every other path — including docker-compose.yml, which Portainer treats as the stack entry point — is created as a symlink without validation.
Portainer’s GET /api/stacks/{id}/file endpoint then reads the stack entry point with os.ReadFile, which follows OS symlinks transparently. A repository containing docker-compose.yml as a symlink to an arbitrary filesystem path (for example /etc/passwd or a mounted Kubernetes service account token) causes the symlink target’s contents to be returned verbatim in the HTTP response. Any authenticated user with rights to create or update a Git-backed stack — the default configuration in Portainer CE — can read arbitrary files accessible to the Portainer process.
The issue is amplified by Git-stack auto-update: an attacker can create a stack from a legitimate repository, pass initial review, and later push a commit that replaces docker-compose.yml with a symlink; the file read is then triggered on the next scheduled update cycle with no further interaction required.
References
- github.com/advisories/GHSA-rpgq-m5fp-32wr
- github.com/portainer/portainer/releases/tag/2.33.8
- github.com/portainer/portainer/releases/tag/2.39.2
- github.com/portainer/portainer/releases/tag/2.41.0
- github.com/portainer/portainer/security/advisories/GHSA-rpgq-m5fp-32wr
- nvd.nist.gov/vuln/detail/CVE-2026-44881
Code Behaviors & Features
Detect and mitigate CVE-2026-44881 with GitLab Dependency Scanning
Secure your software supply chain by verifying that all open source dependencies used in your projects contain no disclosed vulnerabilities. Learn more about Dependency Scanning →