在两个相互跟踪的进程中捕获int3

时间:2019-07-16 13:02:12

标签: c

我在Linux中围绕ptrace进行了一些实验,不知道为什么下面的代码不起作用。这个问题与calling ptrace inside a ptraced Linux process有关。

目标如下:分叉该进程,然后父进程P和子进程C彼此运行ptrace(PTRACE_SEIZE, ...),以便从int3 P(分别是C)可以捕获C(分别来自P)。

下面的代码试图实现这一点,但是当父过程Pint3函数中的sleep(1)之后引发do_loop时,它将挂起:我相​​信孩子进程C被while循环中的waitpid阻塞。

是否可以修补代码以达到预期的行为?

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

#define DO_INT3(who) do {                      \
    printf("%s: raising an int3\n", who);      \
    __asm__("int $3");                         \
    printf("%s: raised int3\n", who);          \
} while(0);

void do_loop(char *who, pid_t pid) {

    int status;

    printf("%s: waiting...\n", who);
    while( waitpid(pid, &status, 0) != -1) {

        switch (WSTOPSIG(status)) {
            case SIGTRAP: printf("%s: **** CATCHED SIGTRAP ****\n", who); break;
            case SIGSTOP: printf("%s: **** CATCHED SIGSTOP ****\n", who); break;
            default:      printf("%s: **** CATCHED EVENT %d ****\n", who, WSTOPSIG(status));
        }

        /* Continue the execution*/
        ptrace(PTRACE_CONT, pid, NULL, NULL);

        /* Next action */
        sleep(1); /* wait for child to attach */
        DO_INT3(who);

    } /*while*/

}

int main() {

    pid_t pid = fork();

    if (pid) {
        printf("parent: child pid is %d\n", pid);

        ptrace(PTRACE_SEIZE, pid, NULL, NULL);
        printf("parent: attached to child\n");

        do_loop("parent", pid);

    } else {

        pid_t parent = getppid();
        printf("child: parent pid is %d\n", parent);

        sleep(1); /* wait for parent to attach */
        DO_INT3("child");

        ptrace(PTRACE_SEIZE, parent, NULL, NULL);
        printf("child: attached to parent\n");

        do_loop("child", parent);
    }

    return 0;
}

0 个答案:

没有答案