この質問には以下が含まれます。この回答。
子プロセスを作成して初期環境変数を確認して、プロセスの現在の(初期ではない)環境変数を取得できますか?
アイデアは、子プロセスの初期環境が親プロセスの現在の環境から継承されることです。
答え1
execve
環境は、引数リストと同様に、システムコールを介して渡される文字列のリストです。期間。アプリケーションが受信した文字列のリストを処理する方法は、アプリケーションによって異なります。
慣例に基づいて、このリストは通常引数リストとは異なります。プログラムは、受信した環境変数のリストを記憶し、他のコマンドを実行するときに同じ環境変数を再利用することがよくあります。
これを行うのに役立つCライブラリ関数があります。環境は変数として提供され、、、、、、、、environ
...getenv
実行コマンド中(追跡中の変数を使用して呼び出されます)setenv
putenv
execvp
execl
system
popen
environ
execve
environ
これで、アプリケーションはこのAPIを使用する必要はありません。彼らは独自の方法を使用して環境変数のリストを管理できます。たとえば、シェルは環境変数をシェル変数にマップし、 putenv/setenv libc 関数を使用しないことがあります。連想配列などがperl
あります。%ENV
常にgdb
プロセスに接続を使用して呼び出すことができますが(libcに動的に接続されていると仮定)、コマンドに接続すると、他のコマンドと同じ環境を取得して独自の方法で実行できるsystem("env > /tmp/some-file")
という保証はありません。env
(例:シェルを考えてください)。 (また、system()
シェルが起動され(コマンドラインが解釈されている)、シェルは起動時に環境を変更できます(例:try env -i sh -c env
)。
$ sleep 100 &
[1] 17098
$ gdb --pid=$! /bin/sleep
[...]
(gdb) p environ[0]
$1 = 0x7fffd722d227 "STY=7498.pts-0.hostname"
(gdb) p environ[1]
$2 = 0x7fffd722d245 "TERM=screen-bce"
(gdb) call system("env > /tmp/some-file")
$4 = 0
(gdb) detach
Detaching from program: /bin/sleep, process 17098
(gdb) quit
$ cat /tmp/some-file
GNOME_KEYRING_PID=6850
SSH_AGENT_PID=6844
SHLVL=1
[...]
答え2
LinuxまたはファイルシステムがあるUnixのいずれかを実行している場合、/proc
プロセス環境はにあります/proc
。現在はSolarisシステムにアクセスできませんが、Linuxでは次のように動作します。
$ tr '\0' '\n' < /proc/$$/environ
現在のシェルの環境変数を印刷しますが、$$
ユーザーIDがアクセスできるすべてのプロセスIDにすることができます。
Solarisではこれを行う方法がありますが、はるかに複雑です。 BSDはLinuxに似ていると思います/proc
。