Is it safe to send SIGUSR1 to a program, and why? [on hold]

The name of the pictureThe name of the pictureThe name of the pictureClash Royale CLAN TAG#URR8PPP











up vote
0
down vote

favorite












When you send SIGUSR1 signal (say the signal handler has been set in advance) to a program while it is executing sleep(100), the signal is caught correctly but sleep(100) is terminated just after the catch. This may mean sending a signal can forcedly terminate the internal some function.



For example, in a scientific calculation program, I would like to catch SIGUSR1 and print the progress. But what if I happen to send the signal while statements like has_error_occured = true or should_break_this_roop = true are in execution? I think this may cause unexpected behavior.



How can I use SIGUSR1 (and SIGUSR2) safely? It is known that the shell command dd print the progress when it catches SIGUSR1. Why is this safe?




Sample program (I executed kill -SIGUSR1 xxxxx):



#include <iostream>
#include <csignal>
#include <unistd.h>

void my_handler(int signal)
; //some instructions


void just_sleep()
std::cout << "sleep() starts.n";
sleep(100); //not wait for 100s if a signal caught
std::cout << "sleep() ends.n"; //executed even if a signal caught


int main()

signal(SIGUSR1, my_handler);
just_sleep();











share|improve this question















put on hold as off-topic by Kusalananda, Thomas Dickey, RalfFriedl, Romeo Ninov, muru 1 hour ago



  • This question does not appear to be about Unix or Linux within the scope defined in the help center.
If this question can be reworded to fit the rules in the help center, please edit the question.
















    up vote
    0
    down vote

    favorite












    When you send SIGUSR1 signal (say the signal handler has been set in advance) to a program while it is executing sleep(100), the signal is caught correctly but sleep(100) is terminated just after the catch. This may mean sending a signal can forcedly terminate the internal some function.



    For example, in a scientific calculation program, I would like to catch SIGUSR1 and print the progress. But what if I happen to send the signal while statements like has_error_occured = true or should_break_this_roop = true are in execution? I think this may cause unexpected behavior.



    How can I use SIGUSR1 (and SIGUSR2) safely? It is known that the shell command dd print the progress when it catches SIGUSR1. Why is this safe?




    Sample program (I executed kill -SIGUSR1 xxxxx):



    #include <iostream>
    #include <csignal>
    #include <unistd.h>

    void my_handler(int signal)
    ; //some instructions


    void just_sleep()
    std::cout << "sleep() starts.n";
    sleep(100); //not wait for 100s if a signal caught
    std::cout << "sleep() ends.n"; //executed even if a signal caught


    int main()

    signal(SIGUSR1, my_handler);
    just_sleep();











    share|improve this question















    put on hold as off-topic by Kusalananda, Thomas Dickey, RalfFriedl, Romeo Ninov, muru 1 hour ago



    • This question does not appear to be about Unix or Linux within the scope defined in the help center.
    If this question can be reworded to fit the rules in the help center, please edit the question.














      up vote
      0
      down vote

      favorite









      up vote
      0
      down vote

      favorite











      When you send SIGUSR1 signal (say the signal handler has been set in advance) to a program while it is executing sleep(100), the signal is caught correctly but sleep(100) is terminated just after the catch. This may mean sending a signal can forcedly terminate the internal some function.



      For example, in a scientific calculation program, I would like to catch SIGUSR1 and print the progress. But what if I happen to send the signal while statements like has_error_occured = true or should_break_this_roop = true are in execution? I think this may cause unexpected behavior.



      How can I use SIGUSR1 (and SIGUSR2) safely? It is known that the shell command dd print the progress when it catches SIGUSR1. Why is this safe?




      Sample program (I executed kill -SIGUSR1 xxxxx):



      #include <iostream>
      #include <csignal>
      #include <unistd.h>

      void my_handler(int signal)
      ; //some instructions


      void just_sleep()
      std::cout << "sleep() starts.n";
      sleep(100); //not wait for 100s if a signal caught
      std::cout << "sleep() ends.n"; //executed even if a signal caught


      int main()

      signal(SIGUSR1, my_handler);
      just_sleep();











      share|improve this question















      When you send SIGUSR1 signal (say the signal handler has been set in advance) to a program while it is executing sleep(100), the signal is caught correctly but sleep(100) is terminated just after the catch. This may mean sending a signal can forcedly terminate the internal some function.



      For example, in a scientific calculation program, I would like to catch SIGUSR1 and print the progress. But what if I happen to send the signal while statements like has_error_occured = true or should_break_this_roop = true are in execution? I think this may cause unexpected behavior.



      How can I use SIGUSR1 (and SIGUSR2) safely? It is known that the shell command dd print the progress when it catches SIGUSR1. Why is this safe?




      Sample program (I executed kill -SIGUSR1 xxxxx):



      #include <iostream>
      #include <csignal>
      #include <unistd.h>

      void my_handler(int signal)
      ; //some instructions


      void just_sleep()
      std::cout << "sleep() starts.n";
      sleep(100); //not wait for 100s if a signal caught
      std::cout << "sleep() ends.n"; //executed even if a signal caught


      int main()

      signal(SIGUSR1, my_handler);
      just_sleep();








      c signals c++






      share|improve this question















      share|improve this question













      share|improve this question




      share|improve this question








      edited 12 hours ago

























      asked 13 hours ago









      ynn

      747




      747




      put on hold as off-topic by Kusalananda, Thomas Dickey, RalfFriedl, Romeo Ninov, muru 1 hour ago



      • This question does not appear to be about Unix or Linux within the scope defined in the help center.
      If this question can be reworded to fit the rules in the help center, please edit the question.




      put on hold as off-topic by Kusalananda, Thomas Dickey, RalfFriedl, Romeo Ninov, muru 1 hour ago



      • This question does not appear to be about Unix or Linux within the scope defined in the help center.
      If this question can be reworded to fit the rules in the help center, please edit the question.




















          1 Answer
          1






          active

          oldest

          votes

















          up vote
          5
          down vote



          accepted










          You should set your signal handler using sigaction(2) instead of signal(2), and set SA_RESTART in sa_flags if you don't want it to interrupt a blocking system call.



          struct sigaction sa;
          sa.sa_handler = your_handler;
          sa.sa_flags = SA_RESTART;
          sigemptyset(&sa.sa_mask);
          sigaction(SIGUSR1, &sa, 0);


          Or, even better than that, just handle the interrupt yourself.



          If nanosleep(), etc. has returned -1, check if errno == EINTR, and print the progress and then redo the call (sleep() is just a wrapper for nanosleep() on linux). You will have to do this anyway if your program grows to something more complex — there's not much you can do safely from a signal handler — see the signal-safety(7) man page on Linux.






          share|improve this answer






















          • Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
            – ynn
            7 hours ago

















          1 Answer
          1






          active

          oldest

          votes








          1 Answer
          1






          active

          oldest

          votes









          active

          oldest

          votes






          active

          oldest

          votes








          up vote
          5
          down vote



          accepted










          You should set your signal handler using sigaction(2) instead of signal(2), and set SA_RESTART in sa_flags if you don't want it to interrupt a blocking system call.



          struct sigaction sa;
          sa.sa_handler = your_handler;
          sa.sa_flags = SA_RESTART;
          sigemptyset(&sa.sa_mask);
          sigaction(SIGUSR1, &sa, 0);


          Or, even better than that, just handle the interrupt yourself.



          If nanosleep(), etc. has returned -1, check if errno == EINTR, and print the progress and then redo the call (sleep() is just a wrapper for nanosleep() on linux). You will have to do this anyway if your program grows to something more complex — there's not much you can do safely from a signal handler — see the signal-safety(7) man page on Linux.






          share|improve this answer






















          • Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
            – ynn
            7 hours ago














          up vote
          5
          down vote



          accepted










          You should set your signal handler using sigaction(2) instead of signal(2), and set SA_RESTART in sa_flags if you don't want it to interrupt a blocking system call.



          struct sigaction sa;
          sa.sa_handler = your_handler;
          sa.sa_flags = SA_RESTART;
          sigemptyset(&sa.sa_mask);
          sigaction(SIGUSR1, &sa, 0);


          Or, even better than that, just handle the interrupt yourself.



          If nanosleep(), etc. has returned -1, check if errno == EINTR, and print the progress and then redo the call (sleep() is just a wrapper for nanosleep() on linux). You will have to do this anyway if your program grows to something more complex — there's not much you can do safely from a signal handler — see the signal-safety(7) man page on Linux.






          share|improve this answer






















          • Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
            – ynn
            7 hours ago












          up vote
          5
          down vote



          accepted







          up vote
          5
          down vote



          accepted






          You should set your signal handler using sigaction(2) instead of signal(2), and set SA_RESTART in sa_flags if you don't want it to interrupt a blocking system call.



          struct sigaction sa;
          sa.sa_handler = your_handler;
          sa.sa_flags = SA_RESTART;
          sigemptyset(&sa.sa_mask);
          sigaction(SIGUSR1, &sa, 0);


          Or, even better than that, just handle the interrupt yourself.



          If nanosleep(), etc. has returned -1, check if errno == EINTR, and print the progress and then redo the call (sleep() is just a wrapper for nanosleep() on linux). You will have to do this anyway if your program grows to something more complex — there's not much you can do safely from a signal handler — see the signal-safety(7) man page on Linux.






          share|improve this answer














          You should set your signal handler using sigaction(2) instead of signal(2), and set SA_RESTART in sa_flags if you don't want it to interrupt a blocking system call.



          struct sigaction sa;
          sa.sa_handler = your_handler;
          sa.sa_flags = SA_RESTART;
          sigemptyset(&sa.sa_mask);
          sigaction(SIGUSR1, &sa, 0);


          Or, even better than that, just handle the interrupt yourself.



          If nanosleep(), etc. has returned -1, check if errno == EINTR, and print the progress and then redo the call (sleep() is just a wrapper for nanosleep() on linux). You will have to do this anyway if your program grows to something more complex — there's not much you can do safely from a signal handler — see the signal-safety(7) man page on Linux.







          share|improve this answer














          share|improve this answer



          share|improve this answer








          edited 12 hours ago









          Stephen Kitt

          155k23341413




          155k23341413










          answered 12 hours ago









          qubert

          5566




          5566











          • Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
            – ynn
            7 hours ago
















          • Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
            – ynn
            7 hours ago















          Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
          – ynn
          7 hours ago




          Thank you. This is exactly what I wanted. I've read all of the links you gave me and I'll check some additional references.
          – ynn
          7 hours ago


          Popular posts from this blog

          How to check contact read email or not when send email to Individual?

          Displaying single band from multi-band raster using QGIS

          How many registers does an x86_64 CPU actually have?