Skip to content

fix: isolate CLI installer shell environment - #3217

Merged
steipete merged 2 commits into
mainfrom
codex/cli-installer-environment
Aug 26, 2026
Merged

fix: isolate CLI installer shell environment#3217
steipete merged 2 commits into
mainfrom
codex/cli-installer-environment

Conversation

@steipete

@steipete steipete commented Aug 26, 2026

Copy link
Copy Markdown
Owner

Summary

Closes #3205.

The repository CLI installer previously launched a nested Bash process at the administrator boundary. This change starts the system POSIX shell with startup protection enabled, uses absolute system tools, and clears the inherited environment before starting AppleScript. The administrator approval requirement, helper validation, and both existing symlink destinations remain unchanged. Shell startup protection blocks inherited functions before validation and error handling; it does not elevate privileges.

Adds a focused regression test to local/macOS CI checks and documents the installer boundary. The in-app Foundation-based installer is unchanged.

Verification

  • /bin/bash Scripts/test_install_codexbar_cli.sh passed: actual macOS Bash-exported functions (including [, set, and exit), startup hooks, inherited shell options, quoting, missing or non-executable helper, fixed destinations, temporary symlink creation, and failure propagation. Positive controls confirm the unprotected system shell imports those functions.
  • POSIX shell syntax, patch whitespace, and make check passed.
  • Independent Codex review of the follow-up reported no actionable P0–P2 findings.
  • Full make test passed: 933 selections across 78 groups, all passing on the first attempt, with no retries or timeouts. No Swift source changed afterward; focused installer checks and make check were rerun for the shell follow-up.
  • Exact-head CI passed for be7cdba409ded64be6b678f279f8cc5f636b46c5: Linux x64/ARM builds, tests and CLI smoke checks; both macOS Swift-test shards; installer/macOS lint checks; provider-engine goldens; and final aggregate. The unrelated musl job was skipped by the existing path gate. GitGuardian also passed.

No administrator request or real system-destination write was used for testing. AppleScript only returned the generated command; execution tests used temporary destinations. Actual macOS authorization behavior was not exercised.

Thanks @Vectrain51 for the report.

@clawsweeper

clawsweeper Bot commented Aug 26, 2026

Copy link
Copy Markdown

🦞👀
ClawSweeper picked this up.

Pull request received. I will update this pull request when review starts.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: fe8250d28f

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread bin/install-codexbar-cli.sh
@clawsweeper clawsweeper Bot added merge-risk: 🚨 security-boundary 🚨 Merging this PR could weaken sandboxing, authorization, credentials, or sensitive data. P1 Urgent regression or broken agent/channel workflow affecting real users now. rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR. labels Aug 26, 2026
@clawsweeper

clawsweeper Bot commented Aug 26, 2026

Copy link
Copy Markdown

Codex review: needs changes before merge. Reviewed August 26, 2026, 4:59 PM ET / 20:59 UTC.

ClawSweeper review

What this changes

The PR switches the repository CLI installer to a protected POSIX shell and clean environment before its administrator-approved symlink command, adds macOS regression coverage, and documents the boundary.

Regression provenance

Possible regression — probable (reviewed change; known regression link). No predecessor PR is attributed.

Merge readiness

⚠️ Ready for maintainer review - 3 items remain

Keep open: this owner-authored PR is a focused candidate fix for the linked installer privilege-boundary report. The security hardening and regression coverage are sound on source review; remove the release-owned changelog edit and let exact-head macOS checks finish.

Priority: P1
Reviewed head: be7cdba409ded64be6b678f279f8cc5f636b46c5

Review scores

Measure Result What it means
Overall readiness 🐚 platinum hermit (4/6) The focused hardening and regression harness are strong, with only the release-owned changelog hunk to remove.
Proof confidence 🌊 off-meta tidepool Not applicable: This owner-authored PR is exempt from the external-contributor proof gate; its supplied focused macOS harness remains useful validation evidence.
Patch quality 🐚 platinum hermit (4/6) 1 actionable review finding remain.

Verification

Check Result Evidence
Real behavior Not applicable Not applicable: This owner-authored PR is exempt from the external-contributor proof gate; its supplied focused macOS harness remains useful validation evidence.
Evidence reviewed 5 items Affected current-main path: The base revision invokes AppleScript with an explicit inherited-environment bash -c command at the administrator boundary, matching the linked report's mechanism.
Hardened boundary: The PR starts with /bin/sh -p, validates the helper after that protection is active, then invokes AppleScript through an empty environment with absolute system tools.
Regression coverage: The added macOS harness proves ordinary /bin/sh imports hostile exported functions, then checks protected startup, hooks, shell options, helper validation, and failure propagation without requesting administrator access.
Findings 1 actionable finding [P3] Remove the release-owned changelog entry
Security None None.

Live Verification

Command: /bin/bash Scripts/test_install_codexbar_cli.sh

Result: FAIL (failed) — execution before step 1 run: sh -lc pnpm install --ignore-scripts --frozen-lockfile failed: ! Corepack is about to download https://registry.npmjs.org/pnpm/-/pnpm-11.24.0.tgz

sh -lc pnpm install --ignore-scripts --frozen-lockfile failed: ! Corepack is about to download https://registry.npmjs.org/pnpm/-/pnpm-11.24.0.tgz

Assertions:

  • FAIL expect_output: CLI installer tests passed (nonprivileged command capture and temporary symlinks).

How this fits together

The repository CLI installer validates CodexBar’s bundled helper and asks macOS to create two system-wide command symlinks. Its shell environment crosses into an administrator-approved command, so inherited startup state must be excluded before validation and privileged execution.

flowchart LR
A[User runs repository installer] --> B[Protected POSIX shell]
B --> C[Validate bundled CLI helper]
C --> D[Clean environment]
D --> E[macOS administrator command]
E --> F[Create CLI symlinks]
F --> G[CodexBar command available]
Loading

Before merge

  • Remove the release-owned changelog entry (P3) - AGENTS.md reserves CHANGELOG.md for release ownership; remove this added unreleased release note and retain the behavior context in the PR body instead.
  • Resolve merge risk (P1) - This changes code immediately before a user-authorized administrator command; the harness captures and exercises the generated command but deliberately does not execute macOS authorization itself.
  • Complete next step (P2) - A narrow mechanical policy repair can remove the release-owned changelog hunk without changing the installer fix.

Findings

  • [P3] Remove the release-owned changelog entry — CHANGELOG.md:5-6
Agent review details

Security

None.

Review metrics

Metric Value Why it matters
Installer coverage 5 files affected; +216/-17 lines; +187 test lines Most of the change is a dedicated macOS harness covering hostile shell state and installer failure paths.

Merge-risk options

Maintainer options:

  1. Complete exact-head macOS validation (recommended)
    Require the focused macOS installer regression check and remaining exact-head checks to pass before merging this administrator-boundary change.

Technical review

Best possible solution:

Land the protected-shell and clean-environment boundary after exact-head macOS validation, while leaving release notes to the release owner.

Do we have a high-confidence way to reproduce the issue?

Yes: current-main source explicitly constructs an administrator-boundary bash -c invocation with no environment reset, and the linked report supplies a concrete affected-version PoC.

Is this the best way to solve the issue?

Yes: protected shell startup plus a clean environment before AppleScript removes the reported inherited-function and startup-hook inputs without changing the approval or symlink contract.

Full review comments:

  • [P3] Remove the release-owned changelog entry — CHANGELOG.md:5-6
    AGENTS.md reserves CHANGELOG.md for release ownership; remove this added unreleased release note and retain the behavior context in the PR body instead.
    Confidence: 0.99

Overall correctness: patch is correct
Overall confidence: 0.94

AGENTS.md: found and applied where relevant.

Codex review notes: model internal, reasoning high; reviewed against cf79d1310493.

Labels

Label changes:

  • add P1: This fixes a local privilege-escalation path that is reached when a user approves the repository CLI installer.
  • add merge-risk: 🚨 security-boundary: The diff changes shell startup and environment handling immediately before administrator-authorized filesystem writes.
  • add rating: 🐚 platinum hermit: Overall readiness is 🐚 platinum hermit; proof is 🌊 off-meta tidepool and patch quality is 🐚 platinum hermit.
  • add status: 👀 ready for maintainer look: ClawSweeper has no concrete contributor-facing blocker left for this PR. Not applicable: This owner-authored PR is exempt from the external-contributor proof gate; its supplied focused macOS harness remains useful validation evidence.

Label justifications:

  • P1: This fixes a local privilege-escalation path that is reached when a user approves the repository CLI installer.
  • merge-risk: 🚨 security-boundary: The diff changes shell startup and environment handling immediately before administrator-authorized filesystem writes.
  • rating: 🐚 platinum hermit: Overall readiness is 🐚 platinum hermit; proof is 🌊 off-meta tidepool and patch quality is 🐚 platinum hermit.
  • status: 👀 ready for maintainer look: ClawSweeper has no concrete contributor-facing blocker left for this PR. Not applicable: This owner-authored PR is exempt from the external-contributor proof gate; its supplied focused macOS harness remains useful validation evidence.

Evidence

Acceptance criteria:

  • [P1] git diff --check.
  • [P1] make check.

What I checked:

  • Affected current-main path: The base revision invokes AppleScript with an explicit inherited-environment bash -c command at the administrator boundary, matching the linked report's mechanism. (bin/install-codexbar-cli.sh:13, cf79d1310493)
  • Hardened boundary: The PR starts with /bin/sh -p, validates the helper after that protection is active, then invokes AppleScript through an empty environment with absolute system tools. (bin/install-codexbar-cli.sh:1, be7cdba409de)
  • Regression coverage: The added macOS harness proves ordinary /bin/sh imports hostile exported functions, then checks protected startup, hooks, shell options, helper validation, and failure propagation without requesting administrator access. (Scripts/test_install_codexbar_cli.sh:84, be7cdba409de)
  • Feature provenance: Current-main history identifies the earlier installer-boundary hardening as commit dbc944d46cd4cf7877d1ca47c44556fe573b46e8; this PR narrows the remaining inherited-shell-state gap. (bin/install-codexbar-cli.sh:25, dbc944d46cd4)
  • Release state: The PR head is not contained by a release tag or the local main ref, so the fix remains unshipped pending merge. (bin/install-codexbar-cli.sh:1, be7cdba409de)

Likely related people:

  • Hinotobi: Commit history attributes the prior in-memory AppleScript administrator-boundary hardening to this contributor. (role: introduced the current installer privilege boundary; confidence: high; commits: dbc944d46cd4; files: bin/install-codexbar-cli.sh)

Rank-up moves

Optional improvements that raise the rating; they are not merge blockers.

  • Remove the CHANGELOG.md edit.
  • Let the exact-head macOS validation complete before merge.

Rating scale

Score Internal tier Crab rank Meaning
6/6 S 🦀 challenger crab Exceptional readiness
5/6 A 🦞 diamond lobster Very strong readiness
4/6 B 🐚 platinum hermit Good normal PR; ordinary maintainer review
3/6 C 🦐 gold shrimp Useful, but confidence is limited
2/6 D 🦪 silver shellfish Proof or implementation needs work
1/6 F 🧂 unranked krab Not merge-ready
N/A NA 🌊 off-meta tidepool Rating does not apply

Overall follows the weaker of proof and patch quality.
Shiny media proof means a screenshot, video, or linked artifact directly shows the changed behavior. Runtime, network, CSP, and security claims still need visible diagnostics.

Workflow

  • ClawSweeper keeps one durable marker-backed review comment per issue or PR.
  • Re-runs edit this comment so the latest verdict, findings, and automation markers stay together instead of adding duplicate bot comments.
  • A fresh review can be triggered by eligible @clawsweeper re-review comments, exact-item GitHub events, scheduled/background review runs, or manual workflow dispatch.
  • PR/issue authors and users with repository write access can comment @clawsweeper re-review or @clawsweeper re-run on an open PR or issue to request a fresh review only.
  • Maintainers can also comment @clawsweeper review to request a fresh review only.
  • Fresh-review commands do not start repair, autofix, rebase, CI repair, or automerge.
  • Maintainer-only repair and merge flows require explicit commands such as @clawsweeper autofix, @clawsweeper automerge, @clawsweeper fix ci, or @clawsweeper address review.
  • Maintainers can comment @clawsweeper explain to ask for more context, or @clawsweeper stop to stop active automation.

@steipete

Copy link
Copy Markdown
Owner Author

Maintainer disposition of the latest automated review: retaining the changelog entry. This is a maintainer-authored user-visible fix, and our maintainer workflow adds the unreleased note before landing. No version or release publication is being performed here. The request to remove it is not an accepted finding.

The reported verification failure occurred during package-manager setup before the macOS installer test executed; it is not an installer regression result. /bin/bash Scripts/test_install_codexbar_cli.sh and make check passed locally, and the exact-head macOS shard has passed the installer regression, Swift tests, and provider-engine goldens: https://github.com/steipete/CodexBar/actions/runs/33012784084. The other shard/final aggregate must finish before merge.

The security proof boundary remains explicit: actual inherited Bash functions and startup hooks are tested, and the generated AppleScript command is captured and exercised against temporary destinations. No administrator authorization request or real system symlink write was used for testing. The administrator approval mechanism and both destination paths are unchanged.

@steipete
steipete merged commit 0b54a92 into main Aug 26, 2026
9 checks passed
@steipete

Copy link
Copy Markdown
Owner Author

Landed on main as 0b54a92. This fixes #3205 while retaining administrator approval, helper validation and both existing CLI symlink destinations.

Verification: /bin/bash Scripts/test_install_codexbar_cli.sh, POSIX shell syntax, git diff --check, and make check passed. The harness uses real macOS Bash exports, positive controls, eight environment variants, missing/non-executable helpers, error propagation, quoted paths and temporary symlink execution. Full local make test passed all 78 groups (933 selections) on the first attempt, without retries/timeouts; no Swift source changed after that run. Independent follow-up review reported no actionable P0–P2 findings.

Exact-head CI passed at https://github.com/steipete/CodexBar/actions/runs/33012784084: Linux x64/ARM builds/tests/smoke checks, both macOS Swift-test shards, macOS installer/lint checks, provider-engine goldens, final aggregate and GitGuardian. The existing path gate skipped the unrelated musl build.

Testing did not request administrator authorization or write real system symlinks. AppleScript returned the generated command, which was exercised only against temporary destinations. The in-app Foundation installer is unchanged. The changelog remains under 0.55.2 Unreleased; no release was published. Thanks @Vectrain51 for the report.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

merge-risk: 🚨 security-boundary 🚨 Merging this PR could weaken sandboxing, authorization, credentials, or sensitive data. P1 Urgent regression or broken agent/channel workflow affecting real users now. rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug/Security] CodexBar installer executes user-controlled BASH_ENV as administrator

1 participant