Xref: utzoo comp.lang.c:16817 comp.unix.questions:12116 comp.unix.wizards:15002 Path: utzoo!utgpu!jarvis.csri.toronto.edu!mailrus!ncar!gatech!purdue!decwrl!megatest!djones From: djones@megatest.UUCP (Dave Jones) Newsgroups: comp.lang.c,comp.unix.questions,comp.unix.wizards Subject: Re: Interrupt Handler in 'C' Message-ID: <2762@goofy.megatest.UUCP> Date: 9 Mar 89 03:36:21 GMT References: <319@h.cs.wvu.wvnet.edu> Organization: Megatest Corporation, San Jose, Ca Lines: 35 The correspondant poses questions such as, "How can I longjmp to B?" etc.. He was a bit long on describing possible "how"'s, and a bit short on the "what". But I think I understand what he wants. I think the real question is, How do you set up a SIGALRM handler which calls B() in such a way that B() will be aborted and restarted by a subsequent SIGALRM. If B() ever finishes, it should resume normal execution, of course. It's a little tricky. We'll use a volatile flag called "handler_active". SIGALRM must be blocked when it is either set or inspected. The idea is that when there is a signal handler active on the stack, a subsequent signal handler will simply longjmp back to the earlier one. If there is an activation of B() on the stack when that happens, the activation of B() will get popped off along with the second signal-handler activation. (I've neglected comments and white-space for the sake of net.brevity.) sigalrm_handler(){ static int handler_active = 0; static jmp_buf first_handler; int old_mask; if(handler_active) longjmp(first_handler, 1); handler_active = 1; setjmp(first_handler); old_mask = sigsetmask(~0); sigsetmask(old_mask & ~(sigmask(SIGALRM))); B(); sigsetmask(old_mask); handler_active = 0; }