mirror of https://github.com/ipxe/ipxe.git
Terminate cleanly on SIGINT or SIGHUP
parent
e072baeb8c
commit
c5a9c38606
|
@ -40,6 +40,12 @@ struct hijack_options {
|
||||||
|
|
||||||
static int daemonised = 0;
|
static int daemonised = 0;
|
||||||
|
|
||||||
|
static int signalled = 0;
|
||||||
|
|
||||||
|
static void flag_signalled ( int signal __attribute__ (( unused )) ) {
|
||||||
|
signalled = 1;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Log error message
|
* Log error message
|
||||||
*
|
*
|
||||||
|
@ -363,14 +369,22 @@ static int listen_for_hijackers ( struct hijack_listener *listener,
|
||||||
|
|
||||||
logmsg ( LOG_INFO, "Listening on %s\n", listener->sun.sun_path );
|
logmsg ( LOG_INFO, "Listening on %s\n", listener->sun.sun_path );
|
||||||
|
|
||||||
while ( 1 ) {
|
while ( ! signalled ) {
|
||||||
/* Accept new connection */
|
/* Accept new connection, interruptibly */
|
||||||
|
siginterrupt ( SIGINT, 1 );
|
||||||
|
siginterrupt ( SIGHUP, 1 );
|
||||||
fd = accept ( listener->fd, NULL, 0 );
|
fd = accept ( listener->fd, NULL, 0 );
|
||||||
|
siginterrupt ( SIGINT, 0 );
|
||||||
|
siginterrupt ( SIGHUP, 0 );
|
||||||
if ( fd < 0 ) {
|
if ( fd < 0 ) {
|
||||||
|
if ( errno == EINTR ) {
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
logmsg ( LOG_ERR, "accept failed: %s\n",
|
logmsg ( LOG_ERR, "accept failed: %s\n",
|
||||||
strerror ( errno ) );
|
strerror ( errno ) );
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Fork child process */
|
/* Fork child process */
|
||||||
child = fork();
|
child = fork();
|
||||||
|
@ -389,6 +403,8 @@ static int listen_for_hijackers ( struct hijack_listener *listener,
|
||||||
close ( fd );
|
close ( fd );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
logmsg ( LOG_INFO, "Stopped listening on %s\n",
|
||||||
|
listener->sun.sun_path );
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
err:
|
err:
|
||||||
|
@ -527,7 +543,7 @@ static int daemonise ( const char *interface ) {
|
||||||
int main ( int argc, char **argv ) {
|
int main ( int argc, char **argv ) {
|
||||||
struct hijack_options options;
|
struct hijack_options options;
|
||||||
struct hijack_listener listener;
|
struct hijack_listener listener;
|
||||||
struct sigaction sigchld;
|
struct sigaction sa;
|
||||||
|
|
||||||
/* Parse command-line options */
|
/* Parse command-line options */
|
||||||
if ( parse_options ( argc, argv, &options ) < 0 )
|
if ( parse_options ( argc, argv, &options ) < 0 )
|
||||||
|
@ -547,11 +563,25 @@ int main ( int argc, char **argv ) {
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Avoid creating zombies */
|
/* Avoid creating zombies */
|
||||||
memset ( &sigchld, 0, sizeof ( sigchld ) );
|
memset ( &sa, 0, sizeof ( sa ) );
|
||||||
sigchld.sa_handler = SIG_IGN;
|
sa.sa_handler = SIG_IGN;
|
||||||
sigchld.sa_flags = SA_NOCLDWAIT;
|
sa.sa_flags = SA_RESTART | SA_NOCLDWAIT;
|
||||||
if ( sigaction ( SIGCHLD, &sigchld, NULL ) < 0 ) {
|
if ( sigaction ( SIGCHLD, &sa, NULL ) < 0 ) {
|
||||||
logmsg ( LOG_ERR, "Could not set signal handler: %s",
|
logmsg ( LOG_ERR, "Could not set SIGCHLD handler: %s",
|
||||||
|
strerror ( errno ) );
|
||||||
|
exit ( 1 );
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Set 'signalled' flag on SIGINT or SIGHUP */
|
||||||
|
sa.sa_handler = flag_signalled;
|
||||||
|
sa.sa_flags = SA_RESTART | SA_RESETHAND;
|
||||||
|
if ( sigaction ( SIGINT, &sa, NULL ) < 0 ) {
|
||||||
|
logmsg ( LOG_ERR, "Could not set SIGINT handler: %s",
|
||||||
|
strerror ( errno ) );
|
||||||
|
exit ( 1 );
|
||||||
|
}
|
||||||
|
if ( sigaction ( SIGHUP, &sa, NULL ) < 0 ) {
|
||||||
|
logmsg ( LOG_ERR, "Could not set SIGHUP handler: %s",
|
||||||
strerror ( errno ) );
|
strerror ( errno ) );
|
||||||
exit ( 1 );
|
exit ( 1 );
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue