【问题标题】:Program with fork() and signal handling in c在 c 中使用 fork() 和信号处理的程序
【发布时间】:2016-11-09 00:31:38
【问题描述】:

嗨,我在这里要做的是一个程序,它首先在文件 server.lock 中注册它的 pid,然后它应该执行一个 fork()。儿子应该说它开始工作而不是被动等待并武装信号SIGUSR2,当它收到它时,它应该终止它的执行并写下“再见残酷世界”。父母应该写它开始并做一个被动等待,然后武装信号 SIGUSR1 和 SIGINT。如果它收到 SIGUSR1 它自己应该发送信号 SIGUSR2 给儿子,如果它收到信号 SIGINT 如果它是第一次收到它应该说它收到信号,如果它是第二次它应该发送信号 SIGUSR2 到儿子,所以它终止了儿子的处决。现在我的问题出在父母身上,我不知道为什么,但是第二次收到信号时,它说错误“用户定义的信号 2”并离开,如果有人可以向我解释我在这里做错了什么,我会非常感谢。这是代码。谢谢。

int p = 1;
int son;

void handle_SIGINT(int signal){
  if ( p==1 ) {
     p = 2;
     printf("The authentication module received the signal SIGINT\n");
  }else{
     kill( son, SIGUSR2);
     exit(0);
  }
}

void handle_SIGUSR1(int signal){
  kill( son, SIGUSR2);
}

void handle_SIGUSR2(int signal){
  printf("Goodbye cruel world\n");
  exit(0);
}

void main(){


    int pid = getpid();
    FILE *f = fopen("server.lock", "w");
    fprintf( f, "%d", pid );
    fclose(f);

int n = fork();

    if ( n==0 ) {
        printf("The message handling module has started\n");
        signal(SIGUSR2, handle_SIGUSR2);
        while(1)
                pause();
    }else{
        printf("The authentication module has started\n");

        son = getpid();

        signal(SIGUSR1, handle_SIGUSR1);

        signal(SIGINT, handle_SIGINT);

        while(1)
            pause();
   }
}

【问题讨论】:

  • IIRC 信号处理程序在被调用时未设置,这意味着它需要重新设置自己。
  • 很抱歉,不是所有 3 个信号处理程序都应该在 main 之前定义吗?我的意思是第一次(对于信号 SIGINT)父母完美地工作,问题是第二次。
  • 哈!而且,刚刚注意到您命名为son 的变量实际上是父变量!你的名字让我很困惑。
  • @j.DOH 我刚才所说的与他们在程序中定义的顺序无关。

标签: c signals fork


【解决方案1】:

你的名字让我很困惑。看来您的问题是您的变量名为son。那不是儿子又名子进程。那是父母。

fork 调用返回两次。一次在父母身上,一次在孩子身上。在父节点中,它返回子节点的 PID。它在孩子中返回 0。你把它们颠倒了!

您使用的是signal 而不是sigaction。我推荐使用sigaction。它要复杂得多,但也提供了更多选择。

signal 遇到的问题是,在调用处理程序后,它会将信号重置为默认行为。但这也不能保证。 GNU C 库的行为会有所不同,具体取决于是否定义了 _BSD_SOURCE_GNU_SOURCE 或未定义任何内容。那是为了模拟它在 BSD UNIX 或 SYSV UNIX 上的行为。这就是为什么sigaction 是更好的选择,它在每个 POSIX 系统上的作用都是一样的。

【讨论】:

  • 我很抱歉,但不是在父级调用 getpid() 返回儿子的 pid 并在儿子返回 0 时调用它?这就是为什么我在 main 的 else 上调用 getpid()。(对不起,如果这是一个愚蠢的问题)
  • @j.DOH:你自己很容易看到。打印出pidson 的值。
  • @Zan Lynx 好的,非常感谢您的帮助,非常感谢。
猜你喜欢
  • 2023-03-15
  • 1970-01-01
  • 2017-05-06
  • 1970-01-01
  • 2011-09-25
  • 1970-01-01
  • 2010-12-29
  • 2014-02-06
  • 1970-01-01
相关资源
最近更新 更多