Mailing-List: contact cygwin-help AT cygwin DOT com; run by ezmlm List-Subscribe: List-Archive: List-Post: List-Help: , Sender: cygwin-owner AT cygwin DOT com Mail-Followup-To: cygwin AT cygwin DOT com Delivered-To: mailing list cygwin AT cygwin DOT com From: "Vankemmel Rudi" To: Subject: Problem: SIGCONT handler is not called (Cygwin or Bash problem ?) Date: Mon, 6 Sep 2004 08:18:40 +0200 Message-ID: MIME-Version: 1.0 Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 7bit Hi, in the process of porting some software to the Cygwin environment i came across a problem when trying to install a signal SIGCONT handler. This is needed as the program puts the terminal into certain states that need to be reset/set again when SIGTSTP/SIGCONT signals are received. My problem is that the SIGCONT handler is never triggered (as it seems to me). I could reduce the problem into the following code snippets. Note that i have also a testversion using only the Posix calls (sigprocmask, sigaction) but it behaves identically: the SIGCONT handler is never called. I can (in the Posix version) remove the sigaction(SIGCONT,..) after which the test routine stops at the kill() command after a SIGTSTP. Sending a SIGCONT resumes the program after the kill and there i could continue with the SIGCONT code but this is not really what i want to do (because i want the SIGCONT also to work after a SIGTERM). Questions: 1) is there a problem with the SIGCONT handling in CYGWIN ? Why is it never called or is SIGCONT not delivered ? 2) what is the signal delivery scheme in Cygwin for SIGCONT i.e. what is called first after issueing a shell - fg command ? 3) or do i miss something in my code here that would be specific for Cygwin (i tested it on various other Unix platforms with success) ? I'm on Cygwin 1.5.10-3, gcc 3.3.1-3 gcc-core 3.3.3-3, bash 2.05b-16, platform = Win2000 Professional V5.0 Build 2195 SP4 Testsequence: gcc prog.c -o prog prog ^Z fg --> bash types prog but the program blocks. Classic signal version: ---------------------------------------------------------------------------- ------------------- #include #include /* IO functions */ #include /* strlen functions*/ #include /* file errors */ #include /* emulate signals */ /* =================================================================== */ void signal_handler(); void (*Tstp) (), (*Cont) (); /* ================================================================ */ int main() { int input; char buf[3]; int i; Tstp = signal(SIGTSTP, signal_handler); /* ctrl-Z, kill -18 */ Cont = signal(SIGCONT, SIG_DFL); /* fg after ^Z, kill -19 */ /* first get the char in the selected mode */ printf("Give a char:\n "); input = getc(stdin); if (input == EOF) printf("Input error\n"); /* reset signals */ signal(SIGTSTP, Tstp); /* ctrl-Z */ signal(SIGCONT, Cont); /* fg after ^Z */ } /* ================================================================ */ void signal_handler(int sig) { int send_sig=0; /* signal to be sent */ sigset_t mask; printf("\nSIGTSTP = %d, SIGCONT = %d, signal = %d \n",SIGTSTP,SIGCONT,sig); switch (sig) { case SIGTSTP: printf("catching the SIGTSTP\n"); send_sig = SIGTSTP ;/*STOP; /* send a suspend signal */ signal(sig, SIG_DFL); /* load default signal mode */ /* now we will install the SIGCONT handler */ if(signal(SIGCONT, signal_handler)==SIG_ERR) printf("Error loading SIGCONT handler... \n"); kill(getpid(),send_sig); printf("now after the kill....\n"); break; /* this is resumed after a suspend: */ case SIGCONT: printf("catching the SIGCONT\n"); printf(" Continuing ..... (my_raw.c)\n"); fflush(stdout); signal(sig, signal_handler); /* keep same signal mode */ break; } } ---------------------------------------------------------------------------- --------------------- Posix call version: ---------------------------------------------------------------------------- --------------------- #include #include /* IO functions */ #include /* strlen functions */ #include /* file errors */ #include /* emulate signals */ /* =================================================================== */ sigset_t mask_old, mask_new; struct sigaction Tstp_old, Tstp_new; struct sigaction Cont_old, Cont_new; void signal_handler (); void (*Tstp) (), (*Cont) (); /* ================================================================ */ int main () { int input; char buf[3]; int i; sigemptyset (&mask_new); sigaddset (&mask_new, SIGCONT); sigaddset (&mask_new, SIGTSTP); sigprocmask (SIG_SETMASK, &mask_new, &mask_old); /* block signals */ sigemptyset (&mask_new); Tstp_new.sa_handler = signal_handler; Tstp_new.sa_mask = mask_new; Tstp_new.sa_flags = 0; sigaction (SIGTSTP, &Tstp_new, &Tstp_old); /* install SIGTSTP handler */ sigprocmask (SIG_SETMASK, &mask_old, NULL); /*unblock signals again */ /* first get the char in the selected mode */ printf ("Give a char:\n "); input = getc (stdin); if (input == EOF) printf ("Input error\n"); /* reset signals */ } /* ================================================================ */ void signal_handler (int sig) { int send_sig = 0; /* signal to be sent */ sigset_t mask; printf ("\nSIGTSTP = %d, SIGCONT = %d, signal = %d \n", SIGTSTP, SIGCONT, sig); switch (sig) { case SIGTSTP: printf ("catching the SIGTSTP\n"); send_sig = SIGTSTP; /*STOP; /* send a suspend signal */ // /* now we will install the SIGCONT handler */ sigemptyset (&mask_new); sigaddset (&mask_new, SIGTSTP); sigaddset (&mask_new, SIGCONT); sigprocmask (SIG_SETMASK, &mask_new, NULL); /* block again */ sigaction (SIGTSTP, &Tstp_old, NULL); sigemptyset (&mask_new); Cont_new.sa_handler = signal_handler; Cont_new.sa_mask = mask_new; Cont_new.sa_flags = 0; if (sigaction (SIGCONT, &Cont_new, &Cont_old) != 0) /* install SIGCONT handler */ printf ("Error loading SIGCONT handler\n"); sigprocmask (SIG_SETMASK, &mask_old, NULL); /* unblock signals again */ kill (getpid (), send_sig); printf ("now after the kill....\n"); break; case SIGCONT: /* this is resumed after a suspend: */ printf ("catching the SIGCONT\n"); printf (" Continuing ..... (my_raw.c)\n"); printf ("Don't mind the input error: there comes a longjmp here\n"); fflush (stdout); break; } } ---------------------------------------------------------------------------- ----------------- Rudi Vankemmel -- Unsubscribe info: http://cygwin.com/ml/#unsubscribe-simple Problem reports: http://cygwin.com/problems.html Documentation: http://cygwin.com/docs.html FAQ: http://cygwin.com/faq/