GHSA-436v-8fw5-4mj8: Local settings bypass config trust checks
Summary`mise` loads trust-control settings from a local project `.mise.toml` before the trust check runs. An attacker who can place a malicious `.mise.toml` in a repository can make that same file appear trusted and then reach dangerous directives such as `[env] _.source`, templates, hooks, or tasks.The strongest current variant is `trusted_config_paths = ["/"]`. I confirmed on current `v2026.3.17` in Docker that this causes an untrusted project config to become trusted during `mise hook-env`, which then executes an attacker-controlled `_.source` script. The same preload issue also lets local `yes = true` / `ci = true` auto-approve trust prompts on `v2026.2.18+`, but the primary PoC below uses the stronger `trusted_config_paths` path.DetailsThe vulnerable load order is:[`Settings::try_get()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/settings.rs#L254-L283) preloads local settings files.[`parse_settings_file()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/settings.rs#L505-L510) returns `settings_file.settings` without checking whether the file is trusted.[`trust_check()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/config_file/mod.rs#L297-L321) later consults those already-loaded settings.The main trust-bypass path is in [`is_trusted()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/config_file/mod.rs#L324-L387):If a local project file sets:then every absolute path matches, so the same untrusted file is marked trusted before the dangerous-directive guard is reached.Related variant: [`trust_check()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/config_file/mod.rs#L307-L316) auto-accepts explicit trust prompts when `Settings::get().yes` is true, and [`Settings::try_get()`](https://github.com/jdx/mise/blob/37997e70cd2216d1a86726fba0c8c09c3986ad06/src/config/settings.rs#L330-L332) sets `yes = true` when `ci` is set. I confirmed that regression on `v2026.2.18`, but the primary PoC below does not depend on it.PoCTest environment:Docker`linux-arm64``mise v2026.3.17`Negative control:`mise ls` fails with:and `/tmp/mise-proof.txt` is not created.Primary exploit:with:Then:Observed:Related regression check:`v2026.2.17`: local `yes = true` does not bypass trust`v2026.2.18`: the same local `yes = true` value auto-approves the trust prompt and the side effect file is createdImpactAn attacker who can place a `.mise.toml` in a repository can make `mise` trust and evaluate dangerous directives from that same untrusted file.Demonstrated on current supported versions:execution via `[env] _.source` during `mise hook-env`bypass of the protection that `mise trust` is supposed to provide for dangerous config featuresOn newer versions, the same root cause also lets local `yes` / `ci` values auto-approve explicit trust prompts.Suggested FixDo not honor trust-control settings from non-global project config files.At minimum, ignore these fields when loading local project config:`trusted_config_paths``yes``ci``paranoid`For example:
CVSS v3.1: 7.7