コンピュータのシステム パスを変更しようとしています。
何らかの理由で、実行経由で cmd を開くと、パスは期待どおりに正しくなります。
ただし、ディレクトリ内で Shift キーを押しながら右クリックし、ここで cmd ウィンドウを開くと、USER でも SYSTEM でも Path 変数に表示されない古い/異なるパスが表示されます。
例:
RUNからのCMD:
C:\Users\PERSON>python
Python 2.7.7 (default, Jun 1 2014, 14:17:13) [MSC v.1500 32 bit (Intel)] on win32
Type "help", "copyright", "credits" or "license" for more information.
C:\Users\PERSON>pip
Usage:
pip <command> [options]
Shift+右クリックからCMD:
C:\Users\PERSON>python
'python' is not recognized as an internal or external command,
operable program or batch file.
C:\Users\PERSON>pip
'pip' is not recognized as an internal or external command,
operable program or batch file.
システムとユーザーの両方のパスを変更して、そこに何か奇妙な問題があるかどうかを確認しましたが、問題は解決しません。
さらに情報が必要な場合はお知らせください。
編集: パスを変更する間に、すべてのコマンド プロンプトを再起動しました。
編集2: パスは次のとおりです
RUNからのCMD:
C:\Users\PERSON>echo %path%
C:\ProgramData\Oracle\Java\javapath;
C:\Windows\system32;
C:\Windows;
C:\Windows\System32\Wbem;
C:\Windows\System32\WindowsPowerShell\v1.0\;
C:\EASE\Cygwin\Bin;
C:\bin;
C:\bin\Hardware;
C:\bin\OpenCV;
C:\bin\Qt;
C:\Program Files\Microsoft SQL Server\110\Tools\Binn\;
C:\Program Files (x86)\Microsoft Visual Studio\VC98\Bin;
C:\Program Files (x86)\Microsoft Visual Studio\Common\MSDev98\Bin;
C:\Python27\;
C:\Python27\Scripts;
C:\Program Files (x86)\Skype\Phone\;
C:\Program Files\SlikSvn\bin;
C:\Program Files (x86)\GNU Tools ARM Embedded\4.7 2012q4\bin;
Shift+右クリックからCMD:
C:\Users\PERSON\Desktop>echo %path%
C:\ProgramData\Oracle\Java\javapath;
C:\Windows\system32;
C:\Windows;
C:\Windows\System32\Wbem;
C:\Windows\System32\WindowsPowerShell\v1.0\;
C:\bin;
C:\bin\Hardware;
C:\bin\OpenCV;
C:\bin\Qt;
C:\Program Files\Microsoft SQL Server\110\Tools\Binn\;
C:\Program Files (x86)\Microsoft Visual Studio\VC98\Bin;
C:\Program Files (x86)\Microsoft Visual Studio\Common\MSDev98\Bin;
C:\Program Files (x86)\Skype\Phone\;
C:\Program Files (x86)\GNU ToolsARM Embedded\4.7 2012q4\bin;
答え1
プロセスが開始されると、デフォルトで環境変数はコピーしました親プロセス (新しいプロセスの作成を要求しているプロセス) から新しく作成されたプロセスへ。
メソッドを使用するとRun
、explorer.exe
デスクトップを処理するインスタンスがインスタンスを作成しますcmd
が、 + 右クリック メソッドを使用するとShift、別のexplorer
インスタンス、svchost.exe
( の子services.exe
、 の子wininit.exe
) の子がインスタンスを作成しますcmd
。
両方のエクスプローラー バージョンに同じ環境ブロックがない場合、cmd
インスタンスには同じ変数が含まれません。
環境変数の構成がシステム プロパティから変更されると、OS はWM_SETTINGCHANGE
すべてのトップ ウィンドウにメッセージを送信します。explorer
デスクトップを処理するインスタンスはそれを受信し、環境ブロックを更新しますが、ファイル参照を処理するインスタンス ( の下にあるインスタンスsvchost.exe
) はメッセージを処理せず (いいえ、現時点では理由はわかりません)、環境ブロックは更新されません (これらはすべて、sysinternal によるプロセス環境のチェックでテスト済みですProcExp
)。
解決方法は?わかりません。おそらく(いいえ、テストしていません。現在コンパイラが手元にないので、単なるアイデアです)、メッセージHWND_BROADCAST
を送信する代わりにWM_SETTINGCHANGE
、ファイルブラウザプロセスに直接メッセージを送信すると解決できるかもしれません(またはできないかもしれません)。
どのように対処しますか?explorer
親プロセスが であるインスタンスを強制終了しますsvchost.exe
。新しいファイル ブラウザーが要求されると、正しい環境ブロックで新しいインスタンスが開始されます。
大まかなアプローチとしては、コマンドラインから実行してみるといいでしょう。
wmic process where "name='explorer.exe' and CommandLine like '%/factory%'" call Terminate
ファイル ブラウザを終了します。新しいファイル ブラウザが要求されると、新しいプロセスが作成され (環境が更新されます)、新しいcmd
インスタンスに変更が反映されます。
編集済み
API モニターでいくつかのテストを行った後、 API 呼び出しを介してプロセスsvchost.exe
が作成されていることがわかりました。この呼び出しでは、引数は null ではありません (null の場合、環境は親から子にコピーされます)。そのため、新しいプロセスの環境が作成されます。しかし、新しい環境を作成するために使用されているソースは何ですか?explorer
CreateProcessAsUserW
lpEnvironment
svchost.exe
そこで、レジストリの変数(regedit
)を直接変更して、メッセージが送信されないようにしWM_SETTINGSCHANGE
、ファイルブラウザexplorer
インスタンスを強制終了して、2つのcmd
インスタンスを作成しました。結果は次のようになります。
Run
メソッド:cmd
インスタンスは変更を認識しません。親へのメッセージがなかったため、その環境は変更されず、新しく開始されたプロセスはexplorer.exe
デスクトップを処理するものから変更されていないバージョンを継承します。Shift+クリック方式: レジストリの変更が有効になります。
したがって、svchost.exe
レジストリから情報を取得して、新しく作成されたプロセスに渡す環境ブロックを作成します。
答え2
パスを変更した後は、エクスプローラを再起動すべての端末を再度開こうとする前に、この手順を実行してください。こうすることで、Explorer プロセスは新しい PATH を取り込み、実行する新しいプログラムにその新しい PATH を送信できるようになります。