簡體   English   中英

父進程在收到信號后運行兩次

[英]Parent process runs twice after receiving signal

我編寫了一個程序,其中父進程從參數列表中打印出5個(彩票)號碼。 然后,子進程生成5個隨機數,如果這些數字之一等於參數,則它將SIGUSR1或SIGUSR2信號發送給父進程。 如果我不使用信號,只需簡單地打印孩子的答案,代碼就可以正常工作。 但是有了這些信號,父進程將運行兩次,或者至少將其內容打印兩次。 能否請您向我解釋這種行為? 提前致謝!

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h> 
#include <sys/wait.h> 
#include <errno.h> 
#include <signal.h>

void handler(int signumber){
        printf("The child got a hit, my pid: %i\n", getpid());
}

void handler2(int signumber){
        printf("The child had no hit!\n");
}

int main(int argc, char* argv[])
{
    signal(SIGUSR1,handler);
    signal(SIGUSR2,handler2);

    int status, child;
    int num1 = atoi(argv[1]);
    int num2 = atoi(argv[2]);
    int num3 = atoi(argv[3]);
    int num4 = atoi(argv[4]);
    int num5 = atoi(argv[5]);

    if ( num1<0 || num1>45 || num2<0 || num2>45 || num3<0 || num3>45 || num4<0 || num4>45 || num5<0 || num5>45 ){
        perror("We need 5 numbers in range of 0 and 45");
        exit(1);
    }

    child = fork();

    if(child>0){ //parent
        printf("The numbers: %i, %i, %i, %i, %i. my pid: %i \n", num1,num2,num3,num4,num5,getpid());
    } else{
        int rnd,i,isAnyHit;
        isAnyHit = 0;
        srand(time(NULL) * (getpid())); 
        for ( i=0;i<5;i++ ){
            rnd = ((rand()%45)+1);
            if ( rnd == num1 || rnd == num2 || rnd == num3 || rnd == num4 || rnd == num5 ){
                kill(getppid(),SIGUSR1);
                isAnyHit++;
            }   
        }
        if ( isAnyHit == 0 )
            kill(getppid(),SIGUSR2);
    }
    return 0; 
}

我做了一些代碼更改,它似乎對我有用。

#include <stdio.h>    
#include <stdlib.h>    
#include <unistd.h>     
#include <sys/wait.h>     
#include <errno.h>     
#include <signal.h>    
#include <time.h>    


void handler(int signumber){    
  printf("Got signal %d at %i\n", signumber, getpid());    
}    

int main(int argc, char* argv[])    
{    
  signal(SIGUSR1,handler);    
  signal(SIGUSR2,handler);    

  int status, child;    
  int num1 = atoi(argv[1]);    
  int num2 = atoi(argv[2]);    
  int num3 = atoi(argv[3]);    
  int num4 = atoi(argv[4]);    
  int num5 = atoi(argv[5]);    

  if ( num1<0 || num1>45 || num2<0 || num2>45 || num3<0 || num3>45 || num4<0 || num4>45 || num5<0 || num5>45 ){    
    perror("Invalid numbers\n");    
    exit(1);    
  }    

  child = fork();    

  if(child>0){ //szülő    
    printf("In the parent - child pid is %i, parent pid is %i\n", child, getpid());    
    sleep(1000);    
  } else{    
    printf("In the child - child pid is %i, parent pid is %i\n", getpid(), getppid());    
    int rnd,i,isAnyHit;    
    isAnyHit = 0;    
    srand(time(NULL) * (getpid()));     
    for ( i=0;i<5;i++ ){    
      rnd = ((rand()%45)+1);    
      printf("Checking %i against numbers\n", rnd);    
      if ( rnd == num1 || rnd == num2 || rnd == num3 || rnd == num4 || rnd == num5)){    
        printf("Matched %i\n", rnd);    
        kill(getppid(),SIGUSR1);    
        isAnyHit++;    
      }       
    }    
    if ( isAnyHit == 0 )    
      kill(getppid(),SIGUSR2);    
  }    

  printf("PID %i is ending\n", getpid());    
  return 0;     
}  

以下輸出:

$ ./a.out 1 2 3 4 5
In the parent - child pid is 20401, parent pid is 20400
In the child - child pid is 20401, parent pid is 20400
Checking 6 against numbers
Checking 18 against numbers
Checking 15 against numbers
Checking 42 against numbers
Checking 4 against numbers
Matched 4
PID 20401 is ending
Got signal 10 at 20400
PID 20400 is ending

但是如果兩個數字匹配:

$ ./a.out 1 2 3 4 5
In the parent - child pid is 20493, parent pid is 20492
In the child - child pid is 20493, parent pid is 20492
Checking 2 against numbers
Matched 2
Checking 5 against numbers
Matched 5
Checking 13 against numbers
Got signal 10 at 20492
Checking 36 against numbers
Checking 19 against numbers
Got signal 10 at 20492
PID 20493 is ending
PID 20492 is ending

我得到2 SIGUSR1(10)。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM