prashanthks
asked on
Signal handling in Unix
I have a test.cgi executable which has a link and then i have an infinite while loop.Now if i click on the link provided, the cgi receives a SIGTERM and then SIGPIPE.I have written handlers for these signals and i have not exited in these handlers.But still the test.cgi is terminating.Whether it received SIGKILL after this.If it receives SIGKILL how do I handle it? I dont want my test.cgi to be terminated by a signal.I want a normal termination for it.
Here is the code
#include<stdio.h>
#include<signal.h>
int flag=0;
void handlerterm() {
system("echo \"SIGTERM\n\" >> /home/prashantk/sigpipe.tx t");
}
void handlerpipe() {
system("echo \"SIGPIPE\n\" >> /home/prashantk/sigpipe.tx t");
flag=1;
}
main() {
long count = 0,pid =1;
char counttemp[512];
system("echo \" \" > /home/prashantk/sigpipe.tx t");
signal(SIGTERM,handlerterm );
signal(SIGPIPE,handlerpipe );
printf("Content-type:text/ html\n\n") ;
printf("<HTML><HEAD><BODY> \n");
printf("<a href=\"/cgi-bin/test1.cgi\ ">testlink </a>\n");
while(1) {
if(!flag)
printf(" ");
}
printf("</BODY></HTML>\n") ;
}
Here First SIGTERM is received,then SIGPIPE is received.I handle both.But still the process get killed.
The program given above creates my test.cgi
Here is the code
#include<stdio.h>
#include<signal.h>
int flag=0;
void handlerterm() {
system("echo \"SIGTERM\n\" >> /home/prashantk/sigpipe.tx
}
void handlerpipe() {
system("echo \"SIGPIPE\n\" >> /home/prashantk/sigpipe.tx
flag=1;
}
main() {
long count = 0,pid =1;
char counttemp[512];
system("echo \" \" > /home/prashantk/sigpipe.tx
signal(SIGTERM,handlerterm
signal(SIGPIPE,handlerpipe
printf("Content-type:text/
printf("<HTML><HEAD><BODY>
printf("<a href=\"/cgi-bin/test1.cgi\
while(1) {
if(!flag)
printf(" ");
}
printf("</BODY></HTML>\n")
}
Here First SIGTERM is received,then SIGPIPE is received.I handle both.But still the process get killed.
The program given above creates my test.cgi
ASKER
Edited text of question.
I think once the signal handler is invoked, the signal behaviour
becomes the default.
Try adding the code:
signal(SIGTERM,handlerterm );
to the end of handlerterm() and
signal(SIGPIPE,handlerpipe );
to end of handlerpipe.
Also if you have truss in your machine. Run the program under
truss and find out what caused the program to exit.
becomes the default.
Try adding the code:
signal(SIGTERM,handlerterm
to the end of handlerterm() and
signal(SIGPIPE,handlerpipe
to end of handlerpipe.
Also if you have truss in your machine. Run the program under
truss and find out what caused the program to exit.
OOPS I overlooked the code part.Yes as doubted by me earlier it is signal behaviour which is resetting the signal handler to default.Try using the
sigaction
if available on your computer.
To Meerak:
Adding the signal handler install code
signal(SIGTERM,handlerterm );
to the end of handlerterm() and
signal(SIGPIPE,handlerpipe );
to end of handlerpipe.
will not work as there can be delivery of a signal between start and end of handlerterm().
Let us see if it helps prsanthks.
sigaction
if available on your computer.
To Meerak:
Adding the signal handler install code
signal(SIGTERM,handlerterm
to the end of handlerterm() and
signal(SIGPIPE,handlerpipe
to end of handlerpipe.
will not work as there can be delivery of a signal between start and end of handlerterm().
Let us see if it helps prsanthks.
hi prashanthks ... where are you ?
ASKER
I am sorry. I am busy with my work.I have not been able to check your suggestion .I will check it sooner and reply.
ASKER
Hi ufolk,
I am sorry for the delayed response.I tried out sigaction as told by you. But the behaviour is same.Ths signal is handle once. After that the process gets killed. In the struct sigaction I set the sa_handler to the function name i.e,
pipeact.sa_handler = handlerpipe; and
termact.sa_handler = handlerterm;
Then I made
pipeact.sa_flags = 0; and
termact.sa_flags = 0;
Then I called
sigaction(SIGPIPE,&pipeact ,NULL);
sigaction(SIGTERM,&termact ,NULL);
But still the thing seems not to be working.
I am sorry for the delayed response.I tried out sigaction as told by you. But the behaviour is same.Ths signal is handle once. After that the process gets killed. In the struct sigaction I set the sa_handler to the function name i.e,
pipeact.sa_handler = handlerpipe; and
termact.sa_handler = handlerterm;
Then I made
pipeact.sa_flags = 0; and
termact.sa_flags = 0;
Then I called
sigaction(SIGPIPE,&pipeact
sigaction(SIGTERM,&termact
But still the thing seems not to be working.
On some systems ( specifically QNX etc) the system() function call also modifies the signal state of a program.You try to remove system from your handlers and instead keep the file desc open of sigpipe.txt and try to write the text using file i/o calls.
void handlerterm() {
system("echo \"SIGTERM\n\" >> /home/prashantk/sigpipe.tx t");
}
as
void handlerterm() {
fputs(fd,"SIGTERM\n\" );
}
where fd=fopen of /home/prashantk/sigpipe.tx t in main code.
void handlerterm() {
system("echo \"SIGTERM\n\" >> /home/prashantk/sigpipe.tx
}
as
void handlerterm() {
fputs(fd,"SIGTERM\n\" );
}
where fd=fopen of /home/prashantk/sigpipe.tx
ASKER
It is not working out ufolk. I tried commenting out the "system" system call in both the handlers.
Hello,
The problem is that you dont let signals comming in.
you need to use pause() somewhere.
I modified your version and i use pause() and it worked well.
If you want to do processing in the same time then use pause() and alarm() with an action for alarm.
I hope this helps.
The problem is that you dont let signals comming in.
you need to use pause() somewhere.
I modified your version and i use pause() and it worked well.
If you want to do processing in the same time then use pause() and alarm() with an action for alarm.
I hope this helps.
Hi again, watch-out, on some systems (unix),
the system function can block signals also.
This can create loops ! and loops and loops and ...
the system function can block signals also.
This can create loops ! and loops and loops and ...
Hi again, again,
your:
int flag=0;
watch out, you should use and atomic version of it.
ex:
sig_atomic_t flag=0; this will ensure that only one guy (child) will update at one time.
you dont have any childs in your example but this is a good practice.
;-)
your:
int flag=0;
watch out, you should use and atomic version of it.
ex:
sig_atomic_t flag=0; this will ensure that only one guy (child) will update at one time.
you dont have any childs in your example but this is a good practice.
;-)
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
Hi fredos could you please send your version of code so that I can know where to put the pause.
ASKER
I tried with pause and alarm.But it did not work.Could you please send me the code.
yes sure tonight !
OK this is the basic of it, once you get a signal
it will be executed (the handler), but if you want to do something in the same time, use threads/fork or same task with alarm (in seconds) or there is a fine one in milliseconds (see ginfo libc there is also an example)
hope this helps
#include<stdio.h>
#include<signal.h>
int flag=0;
void handlerterm() {
printf("in the term handler\n");
system("echo \"SIGTERM\n\" >> ./sigpipe.txt");
}
void handlerpipe() {
printf("in the pipe handler\n");
system("echo \"SIGPIPE\n\" >> ./sigpipe.txt");
flag=1;
}
main()
{
long count = 0,pid =1;
char counttemp[512];
system("echo \" \" > ./sigpipe.txt");
signal(SIGTERM,handlerterm );
signal(SIGPIPE,handlerpipe );
printf("Content-type:text/ html\n\n") ;
printf("<HTML><HEAD><BODY> \n");
printf("<a href=\"/cgi-bin/test1.cgi\ ">testlink </a>\n");
pause();
printf("</BODY></HTML>\n") ;
}
it will be executed (the handler), but if you want to do something in the same time, use threads/fork or same task with alarm (in seconds) or there is a fine one in milliseconds (see ginfo libc there is also an example)
hope this helps
#include<stdio.h>
#include<signal.h>
int flag=0;
void handlerterm() {
printf("in the term handler\n");
system("echo \"SIGTERM\n\" >> ./sigpipe.txt");
}
void handlerpipe() {
printf("in the pipe handler\n");
system("echo \"SIGPIPE\n\" >> ./sigpipe.txt");
flag=1;
}
main()
{
long count = 0,pid =1;
char counttemp[512];
system("echo \" \" > ./sigpipe.txt");
signal(SIGTERM,handlerterm
signal(SIGPIPE,handlerpipe
printf("Content-type:text/
printf("<HTML><HEAD><BODY>
printf("<a href=\"/cgi-bin/test1.cgi\
pause();
printf("</BODY></HTML>\n")
}
Also you can not handle SIGKILL.There seems to be no source of SIGKILL unless you send it yourself ( unix will never send it to your program internally )so problem is somewhere else