linux - 父进程的追踪

标签 linux fork trace ptrace

子进程可以使用ptrace系统调用来跟踪它的父进程吗?

操作系统是linux 2.6

谢谢。

更新1: 我想从“自身”追踪 process1。这是不可能的,所以我 fork 并尝试从子进程执行 ptrace(process1_pid, PTRACE_ATTACH)。但是我不能,有一个奇怪的错误,比如内核禁止子进程跟踪他们的父进程

UPD2:安全策略可以禁止此类跟踪。哪些警察这样做?内核中的校验代码在哪里?

UPD3:在我的嵌入式 Linux 上,PEEKDATA 没有错误,但 GETREGS 没有:

child: getregs parent: -1
errno is 1, strerror is Operation not permitted 

错误号 = EPERM

最佳答案

这个问题让我很感兴趣。所以我写了一些代码来尝试一下。

首先请记住,在跟踪进程时,跟踪进程成为大多数目的的父进程,名称除外(即 getppid())。首先,手册的 PTRACE_ATTACH 部分的片段很有帮助:

   PTRACE_ATTACH
          Attaches to the process specified in pid,  making  it  a  traced
          "child"  of the calling process; the behavior of the child is as
          if it had done a PTRACE_TRACEME.  The calling  process  actually
          becomes the parent of the child process for most purposes (e.g.,
          it will receive notification of  child  events  and  appears  in
          ps(1)  output  as  the  child's parent), but a getppid(2) by the
          child will still return the PID of  the  original  parent.   The
          child  is  sent a SIGSTOP, but will not necessarily have stopped
          by the completion of this call; use  wait(2)  to  wait  for  the
          child to stop.  (addr and data are ignored.)

现在这是我编写的代码,用于测试和验证您实际上可以 ptrace() 您的父级(您可以通过将其转储到名为 blah.c< 的文件中来构建它 并运行 make blah:

#include <assert.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/ptrace.h>

int main()
{
    pid_t pid = fork();
    assert(pid != -1);
    int status;
    long readme = 0;
    if (pid)
    {
        readme = 42;
        printf("parent: child pid is %d\n", pid);
        assert(pid == wait(&status));
        printf("parent: child terminated?\n");
        assert(0 == status);
    }
    else
    {
        pid_t tracee = getppid();
        printf("child: parent pid is %d\n", tracee);
        sleep(1); // give parent time to set readme
        assert(0 == ptrace(PTRACE_ATTACH, tracee));
        assert(tracee == waitpid(tracee, &status, 0));
        printf("child: parent should be stopped\n");
        printf("child: peeking at parent: %ld\n", ptrace(PTRACE_PEEKDATA, tracee, &readme));
    }
    return 0;
}

请注意,我正在利用父虚拟地址空间的复制来了解查找位置。另请注意,当 child 随后终止时,我怀疑存在必须允许 parent 继续的隐式分离,我没有进一步调查。

关于linux - 父进程的追踪,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2216035/

相关文章:

linux - 使用perl脚本在linux中杀死多个进程

使用多个 fork() 子项计算表达式?

javascript - JavaScript 中如何获取调用函数的行?

clojure - 当参数是大映射时跟踪函数

c# - wcf 休息服务消息记录

linux - Docker init Daemon最佳实践(PID 1僵尸收割)

mysql - 从 shell 脚本将表导出为 mysql 中的 csv

c - C 中的魔法与 malloc、fork 和 open

linux - 使用管道和文件进行进程间通信

linux - Linux 打印命令中的数学表达式