wiki / shellwhy / confidenceedited 2026-07-19
Confidence model

Static analysis cannot prove runtime shell behavior, and shellwhy refuses to pretend otherwise. Every startup file in a report carries one of six labels:

confirmedObserved by trace mode.inferredFollows from shell rules or a safely parsed source statement.possibleExists or is installed, but static mode cannot prove it loads.missingExpected or possible path does not exist.skippedNot loaded because mode or precedence rules exclude it.unknownNot enough information.

Static mode

The default. It identifies the target shell from --shell, $SHELL, or parent-process metadata; infers login / interactive / SSH / terminal context from flags, argv, TTY state, and environment; applies the startup rules for that shell and mode; checks which files exist; and shows files skipped by precedence — bash reading only the first existing ~/.bash_profile, ~/.bash_login, or ~/.profile is the classic case. Simple source statements are parsed without evaluating shell code.

What it cannot do: prove conditional branches, dynamic paths, plugin-manager side effects, aliases, functions, exports, or PATH changes created at runtime. Those stay possible at best.

Trace mode

shellwhy trace launches a fresh target shell and observes file access through a platform backend — currently strace on Linux, with dtruss/fs_usage planned for macOS. Observed files are merged into the report as confirmed. The trade-off: trace mode runs the user’s startup code, because it starts a real shell. Use static mode when analysis must be non-invasive.