forked from enlightenment/efl
efl/ecore exe - more paranoia - block sig handlers between fork + exec
in theory signal handlers could kick in after fork and before exec... so block them until we're exec'd or exited so they don't change any program state.
This commit is contained in:
parent
49662fcb49
commit
31c343b77c
|
@ -300,6 +300,45 @@ _impl_ecore_exe_efl_object_finalize(Eo *obj, Ecore_Exe_Data *exe)
|
||||||
}
|
}
|
||||||
else if (pid == 0) /* child */
|
else if (pid == 0) /* child */
|
||||||
{
|
{
|
||||||
|
sigset_t newset;
|
||||||
|
|
||||||
|
sigemptyset(&newset);
|
||||||
|
sigaddset(&newset, SIGPIPE);
|
||||||
|
sigaddset(&newset, SIGALRM);
|
||||||
|
sigaddset(&newset, SIGCHLD);
|
||||||
|
sigaddset(&newset, SIGUSR1);
|
||||||
|
sigaddset(&newset, SIGUSR2);
|
||||||
|
sigaddset(&newset, SIGHUP);
|
||||||
|
sigaddset(&newset, SIGQUIT);
|
||||||
|
sigaddset(&newset, SIGINT);
|
||||||
|
sigaddset(&newset, SIGTERM);
|
||||||
|
sigaddset(&newset, SIGBUS);
|
||||||
|
sigaddset(&newset, SIGCONT);
|
||||||
|
sigaddset(&newset, SIGWINCH);
|
||||||
|
#ifdef SIGEMT
|
||||||
|
sigaddset(&newset, SIGEMT);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGIO
|
||||||
|
sigaddset(&newset, SIGIO);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGTSTP
|
||||||
|
sigaddset(&newset, SIGTSTP);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGTTIN
|
||||||
|
sigaddset(&newset, SIGTTIN);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGTTOU
|
||||||
|
sigaddset(&newset, SIGTTOU);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGVTALRM
|
||||||
|
sigaddset(&newset, SIGVTALRM);
|
||||||
|
#endif
|
||||||
|
#ifdef SIGPWR
|
||||||
|
sigaddset(&newset, SIGPWR);
|
||||||
|
#endif
|
||||||
|
// block all those nasty signals we don't want messing with things
|
||||||
|
// in signal handlers while we go from fork to exec in the child
|
||||||
|
pthread_sigmask(SIG_BLOCK, &newset, NULL);
|
||||||
#ifdef HAVE_SYSTEMD
|
#ifdef HAVE_SYSTEMD
|
||||||
char **env = NULL, **e;
|
char **env = NULL, **e;
|
||||||
|
|
||||||
|
@ -326,16 +365,16 @@ _impl_ecore_exe_efl_object_finalize(Eo *obj, Ecore_Exe_Data *exe)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
if (run_pri != ECORE_EXE_PRIORITY_INHERIT)
|
if (run_pri != ECORE_EXE_PRIORITY_INHERIT)
|
||||||
{
|
{
|
||||||
#ifdef PRIO_PROCESS
|
#ifdef PRIO_PROCESS
|
||||||
if ((run_pri >= -20) && (run_pri <= 19))
|
if ((run_pri >= -20) && (run_pri <= 19))
|
||||||
setpriority(PRIO_PROCESS, 0, run_pri);
|
setpriority(PRIO_PROCESS, 0, run_pri);
|
||||||
#else
|
#else
|
||||||
#warning "Your OS/libc does not provide PRIO_PROCESS (and possibly setpriority())"
|
#warning "Your OS/libc does not provide PRIO_PROCESS (and possibly setpriority())"
|
||||||
#warning "This is a POSIX-1.2001 standard and it is highly encouraged that you"
|
#warning "This is a POSIX-1.2001 standard and it is highly encouraged that you"
|
||||||
#warning "Have support for this"
|
#warning "Have support for this"
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
if (ok && (flags & ECORE_EXE_ISOLATE_IO))
|
if (ok && (flags & ECORE_EXE_ISOLATE_IO))
|
||||||
{
|
{
|
||||||
int devnull;
|
int devnull;
|
||||||
|
|
|
@ -467,6 +467,45 @@ _efl_exe_efl_task_run(Eo *obj, Efl_Exe_Data *pd)
|
||||||
}
|
}
|
||||||
// this code is in the child here, and is temporary setup until we
|
// this code is in the child here, and is temporary setup until we
|
||||||
// exec() the child to replace everything.
|
// exec() the child to replace everything.
|
||||||
|
sigset_t newset;
|
||||||
|
|
||||||
|
sigemptyset(&newset);
|
||||||
|
sigaddset(&newset, SIGPIPE);
|
||||||
|
sigaddset(&newset, SIGALRM);
|
||||||
|
sigaddset(&newset, SIGCHLD);
|
||||||
|
sigaddset(&newset, SIGUSR1);
|
||||||
|
sigaddset(&newset, SIGUSR2);
|
||||||
|
sigaddset(&newset, SIGHUP);
|
||||||
|
sigaddset(&newset, SIGQUIT);
|
||||||
|
sigaddset(&newset, SIGINT);
|
||||||
|
sigaddset(&newset, SIGTERM);
|
||||||
|
sigaddset(&newset, SIGBUS);
|
||||||
|
sigaddset(&newset, SIGCONT);
|
||||||
|
sigaddset(&newset, SIGWINCH);
|
||||||
|
# ifdef SIGEMT
|
||||||
|
sigaddset(&newset, SIGEMT);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGIO
|
||||||
|
sigaddset(&newset, SIGIO);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGTSTP
|
||||||
|
sigaddset(&newset, SIGTSTP);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGTTIN
|
||||||
|
sigaddset(&newset, SIGTTIN);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGTTOU
|
||||||
|
sigaddset(&newset, SIGTTOU);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGVTALRM
|
||||||
|
sigaddset(&newset, SIGVTALRM);
|
||||||
|
# endif
|
||||||
|
# ifdef SIGPWR
|
||||||
|
sigaddset(&newset, SIGPWR);
|
||||||
|
# endif
|
||||||
|
// block all those nasty signals we don't want messing with things
|
||||||
|
// in signal handlers while we go from fork to exec in the child
|
||||||
|
pthread_sigmask(SIG_BLOCK, &newset, NULL);
|
||||||
|
|
||||||
if (td->flags & EFL_TASK_FLAGS_USE_STDIN) close(pipe_stdin[1]);
|
if (td->flags & EFL_TASK_FLAGS_USE_STDIN) close(pipe_stdin[1]);
|
||||||
if (td->flags & EFL_TASK_FLAGS_USE_STDOUT) close(pipe_stdout[0]);
|
if (td->flags & EFL_TASK_FLAGS_USE_STDOUT) close(pipe_stdout[0]);
|
||||||
|
@ -523,7 +562,7 @@ _efl_exe_efl_task_run(Eo *obj, Efl_Exe_Data *pd)
|
||||||
close(devnull);
|
close(devnull);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!tdl) exit(1);
|
if (!tdl) _exit(1);
|
||||||
|
|
||||||
// clear systemd notify socket... only relevant for systemd world,
|
// clear systemd notify socket... only relevant for systemd world,
|
||||||
// otherwise shouldn't be trouble
|
// otherwise shouldn't be trouble
|
||||||
|
@ -599,8 +638,8 @@ _efl_exe_efl_task_run(Eo *obj, Efl_Exe_Data *pd)
|
||||||
// we couldn't exec... uh oh. HAAAAAAAALP!
|
// we couldn't exec... uh oh. HAAAAAAAALP!
|
||||||
if ((errno == EACCES) || (errno == EINVAL) || (errno == ELOOP) ||
|
if ((errno == EACCES) || (errno == EINVAL) || (errno == ELOOP) ||
|
||||||
(errno == ENOEXEC) || (errno == ENOMEM))
|
(errno == ENOEXEC) || (errno == ENOMEM))
|
||||||
exit(126);
|
_exit(126);
|
||||||
exit(127);
|
_exit(127);
|
||||||
return EINA_FALSE;
|
return EINA_FALSE;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue