это способ ожидания сигнала того же типа на языке C? - PullRequest
2 голосов
/ 19 мая 2019

Мне действительно нужно сделать сигнал ожидающим, когда в обработчике находится другой сигнал того же типа.

Предположим, что SIGUSR2 находится в обработчике, а SIGUSR1 является членом sa_mask.если теперь процесс получит SIGUSR1, он будет заблокирован и будет доставлен после того, как SIGUSR2 выйдет из обработчика, что является разумным.

Но если процесс получит SIGUSR2, когда он обрабатывает другой SIGUSR2 в обработчике, второй сигнал будет проигнорированнавсегда.

Я хочу, чтобы SIGUSR2 был отложен и доставлен позже.как я могу это сделать?

Примечание: приведенные ниже коды являются всего лишь двумя примерами, если вы поняли мой вопрос, нет необходимости читать их

первый сценарий: дочерний процесс посылает два сигнала (SIGUSR1& SIGUSR2) к родителю.в то время как SIGUSR1 находится в обработчике, SIGUSR2 будет в ожидании и будет доставлен позже:

    #define MAXCHILD 1
    void handler1(int signo)
      {
        switch(signo)
        {
          /* handling SIGUSR1 takes one second
          during this time if SIGUSR2 will be blocked on delivery. */
          case SIGUSR1:
          write(1,"SIGUSR1 received \n",strlen("SIGUSR1 received \n"));
          sleep(5);
          break;
          case SIGUSR2:
          write(1,"SIGUSR2 received \n",strlen("SIGUSR2 received \n"));
          break;
        }
      }
    int main()
    {
      struct sigaction action1;
      sigset_t set1;
      sigemptyset(&set1);
      sigaddset(&set1, SIGUSR2);//adding SIGUSR2 to set1
      sigaddset(&set1,SIGUSR1);
      action1.sa_handler = handler1;
      action1.sa_mask = set1;
      action1.sa_flags = 0;
      int inchild=0;
      sigaction(SIGUSR1,(struct sigaction *) &action1,NULL);
      sigaction(SIGUSR2,(struct sigaction *) &action1,NULL);
      pid_t parent=getpid();
      pid_t pid[MAXCHILD];
      for ( int i=0;i<MAXCHILD;i++)
      {
        pid[i]=fork();
        if( pid[i]==0)
        {
          inchild=1;
          break;
        }
      }
      while(inchild==0);
      if(inchild==1)
      {
        //child sends SIGUSR1 and immediately SIGUSR2 to parent
        kill(parent,SIGUSR1);
        kill(parent,SIGUSR2);
        sleep(1);
      }
      printf("end\n");
      return 0;
    }

вывод кода выше:

SIGUSR1 received 
end
SIGUSR2 received 

, что в порядке.

, нодавайте поговорим о втором сценарии: ребенок посылает два сигнала (SIGUSR1) родителю.пока SIGUSR1 находится в обработчике, второй SIGUSR1 не будет ожидающим и будет игнорироваться навсегда:

    #define MAXCHILD 1
    void handler1(int signo)
      {
        switch(signo)
        {
          /* handling SIGUSR1 takes one second
          during this time if SIGUSR2 will be blocked on delivery. */
          case SIGUSR1:
          write(1,"SIGUSR1 received \n",strlen("SIGUSR1 received \n"));
          sleep(5);
          break;
          case SIGUSR2:
          write(1,"SIGUSR2 received \n",strlen("SIGUSR2 received \n"));
          break;
        }
      }
    int main()
    {
      struct sigaction action1;
      sigset_t set1;
      sigemptyset(&set1);
      sigaddset(&set1, SIGUSR2);//adding SIGUSR2 to set1
      sigaddset(&set1,SIGUSR1);
      action1.sa_handler = handler1;
      action1.sa_mask = set1;
      action1.sa_flags = 0;
      int inchild=0;
      sigaction(SIGUSR1,(struct sigaction *) &action1,NULL);
      sigaction(SIGUSR2,(struct sigaction *) &action1,NULL);
      pid_t parent=getpid();
      pid_t pid[MAXCHILD];
      for ( int i=0;i<MAXCHILD;i++)
      {
        pid[i]=fork();
        if( pid[i]==0)
        {
          inchild=1;
          break;
        }
      }
      while(inchild==0);
      if(inchild==1)
      {
        //child sends SIGUSR1 and immediately SIGUSR1 to parent
        kill(parent,SIGUSR1);
        kill(parent,SIGUSR1);
        sleep(1);
      }
      printf("end\n");
      return 0;
    }

я ожидаю, что результат будет:

SIGUSR1 received
end
SIGUSR1 received

, но вывод:

SIGUSR1 received
end

, который показывает, что второй сигнал был проигнорирован навсегда.

как я могу достичь ожидаемого результата при отправке двух сигналов одного типа?я просто хочу иметь возможность получить второй сигнал как ожидающий сигнал, есть ли способ сделать это?

согласно этой ссылке нет способа сделать это, но я надеюсь, что кто-топредложить поддельный способ сделать это или, по крайней мере, имитировать это (но я хочу, чтобы функции write () оставались в обработчике).

...