如何从父进程获取子进程


77

是否可以从Shell脚本中的父进程ID获取子进程ID?

我有一个要使用Shell脚本执行的文件,这会导致一个新进程process1(父进程)。这个过程1已经分叉的另一个进程过程2(子进程)。使用脚本,我可以使用以下命令获取process1的pid :

cat /path/of/file/to/be/executed

但我无法获取子进程的pid。


1
您在说哪个孩子和哪个父母程序?根据定义,shell脚本由shell进程执行!你为什么要问?请显示您的脚本!
Basile Starynkevitch

3
等待...该cat命令如何为您提供PID?
Miklos Aubert

2
看来您真的很困惑!
Basile Starynkevitch

1
我第二个@BasileStarynkevitch:请向我们显示您的脚本,或者至少显示相关部分。
Miklos Aubert

2
@ y_159。在类似于您的程序(例如或上使用strace(1)找出涉及的syscalls(2),或从githubgitlab上类似于您的现有项目中汲取灵感pstop
Basile Starynkevitch

Answers:



58

我不确定我是否理解正确,这有帮助吗?

ps --ppid <pid of the parent>

13
标记为“ linux”的问题
Kent

22

我已经编写了一个脚本来获取父进程的所有子进程pid。这是代码。希望它会有所帮助。

function getcpid() {
    cpids=`pgrep -P $1|xargs`
#    echo "cpids=$cpids"
    for cpid in $cpids;
    do
        echo "$cpid"
        getcpid $cpid
    done
}

getcpid $1

15

Shell过程是$$因为它是一个特殊参数

在Linux上, proc(5)文件系统提供了许多有关进程的信息。也许 pgrep(1)(访问/proc)也可能有帮助。

因此,请尝试cat /proc/$$/status获取shell进程的状态。

因此,它的父进程ID可以用例如

  parpid=$(awk '/PPid:/{print $2}' /proc/$$/status)

然后$parpid在脚本中使用以引用父进程pid(shell的父进程)。

但我认为您不需要它!

阅读一些Bash指南(或谨慎使用高级bash脚本指南,该指南有误)和高级linux编程

请注意,某些服务器守护进程(通常需要唯一)通常将其pid写入/var/run,例如,  sshd服务器守护进程正在将其pid写入文本文件/var/run/sshd.pid)。您可能希望将这种功能添加到自己的类似于服务器的程序中(以C,C ++,Ocaml,Go,Rust或其他某种编译语言编码)。


在chat.freenode.net的greybot上的#bash中:应该避免使用臭名昭著的“高级” Bash脚本指南,除非您知道如何过滤掉垃圾。它会教您编写错误,而不是脚本。有鉴于此,BashGuide被编写为:mywiki.wooledge.org/BashGuide ; 只是以为我会提到它!
vktec

11

要获取子进程和线程, pstree -p PID。它还显示了层次树


9
ps -axf | grep parent_pid 

上面的命令打印从中生成的各个过程parent_pid,希望对您有所帮助。+++++++++++++++++++++++++++++++++++++++++++++

root@root:~/chk_prgrm/lp#

 parent...18685

 child... 18686


root@root:~/chk_prgrm/lp# ps axf | grep frk

 18685 pts/45   R      0:11  |       \_ ./frk

 18686 pts/45   R      0:11  |       |   \_ ./frk

 18688 pts/45   S+     0:00  |       \_ grep frk

3

您可以通过阅读条目来获取pids给定父流程的所有子流程。<pid>/proc/<pid>/task/<tid>/children

该文件包含一级子进程的pid。

有关更多信息,请访问https://lwn.net/Articles/475688/


为<children pids>递归地执行此操作
y_159 '20

0

对于感兴趣的过程树具有两个以上级别的情况(例如,Chromium生成了4个级别的深层过程树),pgrep则没有太大用处。就像其他人在上面提到的那样,procfs文件包含有关进程的所有信息,只需要读取它们即可。我构建了一个称为Procpath的CLI工具,正是此工具。它读取所有/proc/N/stat文件,将内容表示为JSON树,并将其公开给JSONPath查询。

要获取非根进程的所有后代进程的逗号分隔的PID(对于根,为..stat.pid),它是:

$ procpath query -d, "..children[?(@.stat.pid == 24243)]..pid"
24243,24259,24284,24289,24260,24262,24333,24337,24439,24570,24592,24606,...

-3
#include<stdio.h>
#include <sys/types.h>
#include <unistd.h>

int main()
{
    // Create a child process     
    int pid = fork();

    if (pid > 0)
    {

            int j=getpid();

            printf("in parent process %d\n",j);
    }
    // Note that pid is 0 in child process
    // and negative if fork() fails
    else if (pid == 0)
    {





            int i=getppid();
            printf("Before sleep %d\n",i);

            sleep(5);
            int k=getppid();

            printf("in child process %d\n",k);
    }

    return 0;

}


此代码可帮助您从init()处将一个孤立进程作为其子进程
user7329527 2016年
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.