Documentation
¶
Overview ¶
Package shellinstrumentation generates guard and segment-tracking shell source and recognizes its exact generated forms. Callers retain execution, approval policy, invocation-path authentication and report transport.
Index ¶
- Constants
- Variables
- func CommandArgs(command string) ([]string, bool)
- func CommandScript(command string) (string, bool)
- func DisplayScript(script string, isGuardDirectory func(string) bool) string
- func Functions(guardDirectory string, known, tools []string) string
- func HasShellSetup(program *syntax.File) bool
- func Hook(tracker string) string
- func IsGuardDirectory(directory string) bool
- func KnownPaths(pathList string, tools []string) []string
- func Rewrite(script string, segments []Segment) string
- func RewriteCommands(script, helper, directory, sudoDirectory, item string) (string, error)
- func ShOriginal(script string) string
- func ShScript(tracker, script string) string
- func ShTracker(helper, channel, directory string) string
- func Tracker(helper, channel, directory string) string
- type Segment
Constants ¶
const ( VCSDirectory = "vcs-guard" SudoDirectory = "sudo-guard" )
VCSDirectory and SudoDirectory name invocation-private command guard paths.
const Guard = "MEKUGI_EXEC_TRACK"
Guard marks a shell that already decided whether to track its command, so nested command shells started by that command are never tracked.
const ItemEnvironment = "MEKUGI_VCS_ITEM"
ItemEnvironment carries the exact host command identity to a PATH guard.
const ItemFlag = "--vcs-item"
ItemFlag carries that identity through wrappers that clear the environment.
const RealEnvironment = "MEKUGI_VCS_GUARD_REAL"
RealEnvironment names the variable a path function sets for the guard: the absolute path the shell was asked to run. The guard runs that file rather than the next PATH match, and removes the variable before it does.
const ShTrackerEnvironment = "MEKUGI_SH_TRACKER"
const SudoDirectoryFlag = "--sudo-directory"
SudoDirectoryFlag carries the second guard resource through clean environments.
Variables ¶
var Shells = []string{"sh", "bash", "dash", "ksh"}
Functions ¶
func CommandArgs ¶
CommandArgs unquotes a host command made only of literal words.
func CommandScript ¶
Source: backends/codex/binding/command_observation.go:51:90@45fbe279 CommandScript is the script of a host Bash or sh command, exactly as the shell receives it with -c or -lc.
func DisplayScript ¶
DisplayScript removes RewriteCommands' exact instrumentation from a display copy. The caller identifies session registry directories, including retained ones. It does not read the filesystem or evaluate expansions. Unrecognized source stays intact, including user assignments, quoted text and heredoc bodies.
func Functions ¶
Functions returns Bash code that defines a function for each absolute path to a guarded tool: known, and each guarded name in every absolute PATH entry when the code runs. A command that names such a path runs the guard, which sees the same arguments and runs that file. Bash looks up functions before running a name that contains a slash; a path the shell does not run itself, as through env, exec or command, bypasses its function.
func HasShellSetup ¶
HasShellSetup keeps shell context and the commands that use it in one event. Command-local assignments, subprocesses, and pipelines keep their existing segment boundaries.
func Hook ¶
Hook is Bash startup source, read from BASH_ENV, that tracks the command script Codex passed with -c. It decides before any segment runs: only when the helper plans the script and the router matches it to a live Codex command does the shell run the rewrite in place of the script and exit. Otherwise it returns and Bash runs the original script itself, so the command never runs twice.
Codex's own snapshot scripts, including the wrapper that re-executes the command shell, pass through without setting the guard: the snapshot would otherwise record it for every later command.
func IsGuardDirectory ¶
IsGuardDirectory recognizes an instrumentation directory name. Callers must separately validate its session registry or exact invocation-local path.
func KnownPaths ¶
KnownPaths lists absolute paths of the guarded tools found in pathList and the standard directories, with the files their symlinks resolve to.
func Rewrite ¶
Rewrite wraps each segment in hooks that report its start and exit status. Each wrapper runs in the current shell and returns the segment's status, so && and || chains, $?, and shell state behave as in the original. A hook passes a nonzero status on as the operand of an && list, where errexit ignores it: under set -e, only the segment's own command can end the shell.
func RewriteCommands ¶
RewriteCommands instruments executable words, not statements. The selected native shell still expands arguments and owns control flow, redirections and status. Parsing never executes expansions or reads scripts from the filesystem. It retains the host item ID and covers sudo independently of remote-write guarding.
func ShOriginal ¶
ShOriginal recognizes only an exact envelope produced by ShScript. Removing its inline boundaries keeps authored newlines and shell error line numbers.
func ShScript ¶
ShScript adds a portable startup call and the existing segment rewrite. Bash's startup hook recognizes this envelope before its DEBUG trap replaces the script. Other shells retain their own execution and no-op boundaries.
func ShTracker ¶
ShTracker runs in dash itself. Only transport differs from Bash: dash has no coprocess, so the existing router also supplies control and ack FIFOs.
func Tracker ¶
Tracker is the Bash source that runs a tracked script. The helper runs as a coprocess: the shell sends it segment boundaries and waits for each acknowledgment, so the helper has relayed a segment's output before the next segment starts. Output reaches Codex unchanged through the helper, which alone keeps the original descriptors. A terminal cannot be relayed without changing what programs detect, so terminal commands report status only.
The rewrite does not run from the startup file, whose errors differ from the script's: a fatal expansion error there would abandon the startup file and run the original script as well. A one-time DEBUG trap instead runs it in place of the script's first command, so error messages, line numbers, and fatal errors behave as in the original. Split accepts only scripts whose first command fires that trap before it has any effect.
Types ¶
type Segment ¶
type Segment struct {
Start, End int // Script byte span; grouped scripts include their full source.
Source string // Display source, including any heredoc body.
}
Segment is one top-level command of a list: a statement, or an operand of a && or || chain, including conditions and branches of plain if blocks. Pipelines, other compound commands, and scripts with shell setup stay whole.
func Split ¶
Split returns the script's segments when every segment can be tracked without changing the script's behavior. Single commands are observed in place, without a rewrite. It reports false for lists whose first command runs before the shell's DEBUG trap can replace the script, and for scripts whose semantics depend on the shell state the instrumentation touches: job control, traps, top-level returns, process replacement, command tracing, and variables naming the current command.