特定のプロセスの名前空間を見つける方法


回答:


39

これらと関連する以前の質問の両方に答えてみます

名前空間への扉は、内のファイルです/proc/*/ns/*/proc/*/task/*/ns/*

名前空間は、その名前空間の共有を解除するプロセスによって作成されます。名前空間は、それまでに永久的にすることができますバインドマウントnsいくつかの他の場所にファイルを。

これip netnsは、たとえば、ネット名前空間に対して行われます。net名前空間を共有解除し、にバインドマウント/proc/self/ns/netします。/run/netns/netns-name

/procルートPID名前空間に取り付けられた、あなたがやってそれらの処理が持っているすべての名前空間を一覧表示することができます。

# readlink /proc/*/task/*/ns/* | sort -u
ipc:[4026531839]
mnt:[4026531840]
mnt:[4026531856]
mnt:[4026532469]
net:[4026531956]
net:[4026532375]
pid:[4026531836]
pid:[4026532373]
uts:[4026531838]

角括弧内の数字はiノード番号です。

特定のプロセスでそれを取得するには:

# ls -Li /proc/1/ns/pid
4026531836 /proc/1/ns/pid

現在、プロセスを持たない永続的な名前空間が存在する場合があります。それらを見つけることは、はるかにトリッキーなAFAICTになる可能性があります。

最初に、いくつかのマウント名前空間が存在する可能性があることに留意する必要があります。

# awk '$9 == "proc" {print FILENAME,$0}' /proc/*/task/*/mountinfo | sort -k2 -u
/proc/1070/task/1070/mountinfo 15 19 0:3 / /proc rw,nosuid,nodev,noexec,relatime - proc proc rw
/proc/19877/task/19877/mountinfo 50 49 0:3 / /run/netns/a rw,nosuid,nodev,noexec,relatime shared:2 - proc proc rw
/proc/19877/task/19877/mountinfo 57 40 0:3 / /proc rw,nosuid,nodev,noexec,relatime - proc proc rw
/proc/1070/task/1070/mountinfo 66 39 0:3 / /run/netns/a rw,nosuid,nodev,noexec,relatime shared:2 - proc proc rw
/proc/19877/task/19877/mountinfo 68 67 0:3 / /mnt/1/a rw,nosuid,nodev,noexec,relatime unbindable - proc proc rw

それら/mnt/1/a/run/netns/a名前空間ファイルかもしれません。

iノード番号を取得できます。

# nsenter --mount=/proc/19877/task/19877/ns/mnt -- ls -Li /mnt/1/a
4026532471 /mnt/1/a

しかし、それは、上記で計算されたリストに含まれていないことを除けば、他のことをほとんど教えてくれません。

さまざまなタイプのいずれかとして入力してみることができます。

# nsenter --mount=/proc/19877/task/19877/ns/mnt -- nsenter --pid=/mnt/1/a true
nsenter: reassociate to namespace 'ns/pid' failed: Invalid argument
# nsenter --mount=/proc/19877/task/19877/ns/mnt -- nsenter --mount=/mnt/1/a true
nsenter: reassociate to namespace 'ns/mnt' failed: Invalid argument
# nsenter --mount=/proc/19877/task/19877/ns/mnt -- nsenter --net=/mnt/1/a true
#

OK、net名前空間ファイルでした。

したがって、名前空間を一覧表示する方法があるように見えます。nsすべてのタスクのディレクトリを一覧表示してから、すべてのタスクのすべてのprocマウントポイントを見つけ、/proc/*/task/*/mountinfoそれらを入力してタイプを判断します。


19

あなたは持っている場合のutil-linuxのv2.28または上にあなたが使用できるのLSNを

# lsns
        NS TYPE  NPROCS   PID USER             COMMAND
4026531836 pid       78     1 root             /sbin/init
4026531837 user      79     1 root             /sbin/init
4026531838 uts       78     1 root             /sbin/init
4026531839 ipc       78     1 root             /sbin/init
4026531840 mnt       75     1 root             /sbin/init
4026531857 mnt        1    12 root             kdevtmpfs
4026531957 net       79     1 root             /sbin/init
4026532393 mnt        1  1214 root             /lib/systemd/systemd-udevd
4026532415 mnt        1  2930 systemd-timesync /lib/systemd/systemd-timesyncd
4026532477 mnt        1 32596 root             -bash
4026532478 uts        1 32596 root             -bash
4026532479 ipc        1 32596 root             -bash
4026532480 pid        1 32596 root             -bash

修正:lsnsは、この回答が言っていたように、util-linux v2.27では使用できません。https://www.kernel.org/pub/linux/utils/util-linux/v2.28/v2.28-ReleaseNotesを参照してください


古いLinuxを使用している人のために見つけた素晴らしいPythonスクリプトもあります。opencloudblog.com/?p=251
ニールマクギル

lsnsは非常に便利ですが、各ネームスペースで最も低いPIDのみを表示します。つまり、任意のPIDのネームスペースを示すことはできません。とにかく+1。質問に直接回答しなくても、これはまだ有用な回答であるためです。
cas

9
$ ip netns identify $PID

ここ$PIDで、プロセスのプロセスIDは、さまざまな方法で取得できます。

http://man7.org/linux/man-pages/man8/ip-netns.8.html


1
これは、ネットワーク名前空間のみを使用してip netns作成されたものであることに注意してください(または、少なくとも/ run / netnsで名前空間のドアをバインドマウントするものによって作成されますip netns)。基本的には/ run / netnsで、と同じファイルを探します /proc/$PID/ns/net
ステファンシャゼラス

何?/run/netns私のコンピューターにも存在しません。
ケンシャープ

/run/netnsまたはip、名前空間特殊ファイルをバインドマウントする場所。findmnt -t nsfsシステム上のどこにあるかを教えてくれるかもしれません。あなたがそうするならunshare -n sleep 1000 & ip netns identify "$!"、あなたは何も手に入れません。
ステファンシャゼル

findmnt -t nsfs-何もない。unshare -n sleep 1000 & ip netns identify "$!"-共有解除:共有解除に失敗しました:操作は許可されていません
ケンシャープ

新しいネットワークを作成するには、スーパーユーザー権限(CAP_SYS_ADMIN機能)が必要です。findmnt -t nsfs何も返さないということは、マシンATMにネットがないことを意味します。
ステファンシャゼラス

9

ps今のプロセスに関連付けられている名前空間のさまざまな種類の出力オプションがあります:ipcnsmntnsnetnspidnsuserns、とutsns。この質問の場合、関連するのはPID名前空間、またはpidnsです。

したがって、たとえばpid 459のPID名前空間IDを確認する場合:

# ps -h -o pidns -p 459
4026532661

そして、その名前空間内のすべてのプロセスをリストするには:

ps -o pidns,pid,cmd | awk '$1==4026532661'

またはを使用してpgrep、PIDから同じPID名前空間を共有するすべてのプロセスのリストに直接移動できます。

pgrep -a --ns 459

とは異なりpspgrep出力を特定のネームスペースに制限できます(そのプロセスの1つのPIDがわかっている場合)が、出力フォーマット機能は非常に限られています(PIDのみ、またはPIDとそのコマンドライン)

プロセスに対して必要な情報を取得するために、常にpgrep --ns 459to の出力をパイプxargs ps -f処理できます。


0

名前空間リスター

listns.pyを使用できます

使用法:./listns.pyまたはpython2 listns.pyこの質問に正確に答えるpython2 listns.py | grep $PIDために、このような結果をgrepできます(pid変数を置き換えます)

出典:github-mirrorおよび記事は すべてラルフ・トレゼシアクに帰属

ネットワーク名前空間

ネットワーク名前空間にip netns identify $PIDは、使用できます。

Nsutils

提供pidnslistそのリターン・プロセスのpid名前空間を

$ pidnslist -ss 8782
pid:[4026531836] 
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.