cron(8): convert vfork() usage to fork()

vfork() is error-prone, and the usage here definitely grew to not be
clearly OK given vfork-semantics; e.g. setusercontext(3) within the child.

Rip out vfork() and the rest of the references to it. fork is heavier, but
it's unclear that the difference will be all that obvious.

Reported by:	Andrew Gierth and sigsys@gmail.com
This commit is contained in:
Kyle Evans 2020-02-10 02:40:23 +00:00
parent 9ce150463c
commit 9b36723388
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=357714
5 changed files with 8 additions and 31 deletions

View file

@ -76,10 +76,6 @@
/*****************************************************************/
#if !defined(BSD) && !defined(HPUX) && !defined(CONVEX) && !defined(__linux)
# define NEED_VFORK
#endif
#if (!defined(BSD) || (BSD < 198902)) && !defined(__linux) && \
!defined(IRIX) && !defined(NeXT) && !defined(HPUX)
# define NEED_STRCASECMP

View file

@ -58,9 +58,6 @@ do_command(e, u)
/* fork to become asynchronous -- parent process is done immediately,
* and continues to run the normal cron code, which means return to
* tick(). the child and grandchild don't leave this function, alive.
*
* vfork() is unsuitable, since we have much to do, and the parent
* needs to be able to run off and fork other processes.
*/
switch ((pid = fork())) {
case -1:
@ -222,13 +219,13 @@ child_process(e, u)
/* fork again, this time so we can exec the user's command.
*/
switch (jobpid = vfork()) {
switch (jobpid = fork()) {
case -1:
log_it("CRON",getpid(),"error","can't vfork");
log_it("CRON",getpid(),"error","can't fork");
exit(ERROR_EXIT);
/*NOTREACHED*/
case 0:
Debug(DPROC, ("[%d] grandchild process Vfork()'ed\n",
Debug(DPROC, ("[%d] grandchild process fork()'ed\n",
getpid()))
if (e->uid == ROOT_UID)
@ -315,24 +312,24 @@ child_process(e, u)
if (setgid(e->gid) != 0) {
log_it(usernm, getpid(),
"error", "setgid failed");
exit(ERROR_EXIT);
_exit(ERROR_EXIT);
}
# if defined(BSD)
if (initgroups(usernm, e->gid) != 0) {
log_it(usernm, getpid(),
"error", "initgroups failed");
exit(ERROR_EXIT);
_exit(ERROR_EXIT);
}
# endif
if (setlogin(usernm) != 0) {
log_it(usernm, getpid(),
"error", "setlogin failed");
exit(ERROR_EXIT);
_exit(ERROR_EXIT);
}
if (setuid(e->uid) != 0) {
log_it(usernm, getpid(),
"error", "setuid failed");
exit(ERROR_EXIT);
_exit(ERROR_EXIT);
}
/* we aren't root after this..*/
#if defined(LOGIN_CAP)

View file

@ -141,7 +141,3 @@ extern int getdtablesize(void);
#ifdef NEED_SETENV
extern int setenv(char *, char *, int);
#endif
#ifdef NEED_VFORK
extern PID_T vfork(void);
#endif

View file

@ -112,7 +112,7 @@ cron_popen(program, type, e, pidptr)
#endif
iop = NULL;
switch(pid = vfork()) {
switch(pid = fork()) {
case -1: /* error */
(void)close(pdes[0]);
(void)close(pdes[1]);

View file

@ -35,18 +35,6 @@ static char rcsid[] = "$FreeBSD$";
#include <paths.h>
/* the code does not depend on any of vfork's
* side-effects; it just uses it as a quick
* fork-and-exec.
*/
#ifdef NEED_VFORK
PID_T
vfork() {
return (fork());
}
#endif
#ifdef NEED_STRDUP
char *
strdup(str)