2012-02-19 43 views
2

嗨,我是构建使用如下所示的信号处理程序...接受()和SIGUSR1被绊倒意外

struct sigaction pipeIn; 
pipeIn.sa_handler = updateServer; 
sigemptyset(&pipeIn.sa_mask); 
pipeIn.sa_flags = SA_ONESHOT; 

if(sigaction(SIGUSR1, &pipeIn, NULL) == -1){ 

    printf("We have a problem, sigaction is not working.\n"); 
    perror("\n"); 
    exit(1);  

} 

的问题是,当它不应该以这种处理器是越来越跳闸。唯一应该发送SIGUSR1信号的是我的子进程,它存在于一个无限的while循环内,用于侦听传入的连接。子进程分叉,如下所示。我重做pipeIn处理程序来运行父进程不使用的子进程使用的另一个函数。代码如下所示。

while(1){ 

    newSock = accept(listenSock,(struct sockaddr *)&their_addr,&addr_size); 
    printf("A\n"); 
    if(!fork()){ 
    // We want to redefine the interrupt 
     pid_t th; 
     th = getpid(); 
     printf("child pid: %d\n",th); 
     pipeIn.sa_handler = setFlag; 
     if(sigaction(SIGUSR1, &pipeIn, NULL) == -1){ 

      printf("We have a problem, sigaction is not working.\n"); 
      perror("\n"); 
      exit(1);  

     } 

     close(listenSock); 
     kill(getppid(),SIGUSR1); 
     waitForP(); 
     }*/ 
     close(newSock);   
     exit(0); 
    } 
    close(newSock); 
    //waitForP(); 
    //break; 
} 

当我运行这段代码,我会从另一台计算机的呼叫连接到你在这里看到我的服务器程序。它将accept()从该计算机的一个请求就好了,但然后子进程最终将发送SIGUSR1到父进程。然而,父进程甚至在子进程发送信号之前接收到SIGUSR1信号。处理程序在它应该......之前就会跳过该函数......然后子进程终于获得了信号并且处理程序第二次关闭。最后accept()功能再次关闭,即使没有新的连接正在生成,并且传入的IP地址来自随机的奇怪的ipv6地址。我不知道发生了什么事。任何帮助都会很棒。

+0

你是否接受EINTR和接受呼叫的错误?它看起来像你没有检查返回值 – Flexo 2012-02-19 10:52:53

+0

雅我没有实现这个代码的版本,我检查了newSock的返回值。无论出于何种原因第二个触发,accept()返回-1。所以我用我的fork()语句过滤了它。接受的第一次被触发,它似乎得到正确的套接字。 – 2012-02-19 13:05:16

回答

1

重复:从system call(这accept(2)总是检查返回错误 - 你得到-1的,而不是套接字描述符,EINTRerrno和未定义的连接地址)。

+0

是的,我确实有一个检查这种错误的代码版本,但我想知道为什么它甚至会尝试在没有其他人尝试连接时首先返回套接字fd。 – 2012-02-24 22:29:53

+0

嗯,所以你不要无限期地等待。信号是“软件中断” - 它们允许您摆脱阻塞系统调用。 – 2012-02-25 22:05:37

1

这看起来很明显,但是您是否已经编写了带有完整警告的代码,并确保您没有?神秘的行为往往是由由C编译器,如果你问它只提到错误引起的...我以后