fix: git wrapper to strip apm LD_LIBRARY_PATH pollution (Linux)#2
Merged
Conversation
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
問題
apm v0.14.2 (5fd0678) + git 2.54.0 の環境で
apm install -gがサブディレクトリ依存のインストール時に常に失敗する。macOS では再現しない。原因
apm PR #1436 が
git clone --local --sharedを導入した2026-05-21 にマージされた microsoft/apm#1436 (
perf(#1433): sparse-cone consumer materialization for subdir deps) が、サブディレクトリ依存のインストールに sparse-cone materialization を導入した。この最適化でbare_cache.materialize_from_bare()がgit clone --local --shared --no-checkout <bare> <consumer>を呼ぶようになった。partial bare clone では upload-pack にフォールバックする
git clone --local --sharedはソースリポジトリが partial clone (--filter=blob:none) の場合、upload-pack protocol にフォールバックし、git が内部で次を spawn する:/bin/sh -c "git-upload-pack '/path/to/bare'"apm (PyInstaller) が LD_LIBRARY_PATH を汚染している
apm は PyInstaller でビルドされたバイナリとして配布されている。PyInstaller のブートローダーは起動時にバンドルライブラリを読み込ませるため、プロセス環境に次を設定する:
/usr/local/lib/apm/_internal/にはlibreadline.so.8 (336KB)が含まれているが、これはシステムの bash が要求するものより古くrl_print_keybindingシンボルが存在しない。git_subprocess_env()が LD_LIBRARY_PATH を strip しないsrc/apm_cli/utils/git_env.pyのgit_subprocess_env()はGIT_DIR等の git 系変数を strip するが、LD_LIBRARY_PATHは strip しない。そのため git subprocess は汚染されたLD_LIBRARY_PATHを継承する。bash が起動時にクラッシュする
このマシンの
/bin/shは bash で、libreadline.so.8に動的リンクしている。汚染されたLD_LIBRARY_PATHを持つ環境で bash が起動すると:bash が即クラッシュし、git clone が exit 128 で失敗する。
シェルスクリプトのラッパーでは直せない
ラッパー自体の起動にも
/bin/sh(bash) が使われるため、同じ理由でクラッシュする。対処 (暫定モンキーパッチ)
~/.local/bin/gitに C バイナリのラッパーを置く。~/.local/binは PATH で/usr/binより前にあり、apm のshutil.which("git")がこのラッパーを先に発見する。/apm/_internalが含まれる場合のみLD_LIBRARY_PATHを除去し、実 git を exec() する。apm 以外の通常の git 操作では何も変更しない。chezmoi の
run_onchange_スクリプトで C ソースから自動ビルド。ソース変更時はchezmoi applyで再ビルドされる。Linux 専用 ({{ if eq .chezmoi.os "linux" }})。撤去条件
microsoft/apm upstream が
src/apm_cli/utils/git_env.pyのgit_subprocess_env()でLD_LIBRARY_PATHを strip するよう修正した場合、または PyInstaller による配布をやめた場合。確認方法: