diff options
| -rw-r--r-- | include/unistd.h | 2 | ||||
| -rw-r--r-- | libc/unistd/Makefile.in | 2 | ||||
| -rw-r--r-- | libc/unistd/daemon.c | 39 | 
3 files changed, 26 insertions, 17 deletions
| diff --git a/include/unistd.h b/include/unistd.h index d59f049e5..71c1934db 100644 --- a/include/unistd.h +++ b/include/unistd.h @@ -956,12 +956,10 @@ extern void endusershell (void) __THROW; /* Discard cached info.  */  extern void setusershell (void) __THROW; /* Rewind and re-read the file.  */ -#ifdef __ARCH_USE_MMU__  /* Put the program in the background, and dissociate from the controlling     terminal.  If NOCHDIR is zero, do `chdir ("/")'.  If NOCLOSE is zero,     redirects stdin, stdout, and stderr to /dev/null.  */  extern int daemon (int __nochdir, int __noclose) __THROW __wur; -#endif  #endif /* Use BSD || X/Open.  */ diff --git a/libc/unistd/Makefile.in b/libc/unistd/Makefile.in index f6ef98cf0..b4c5130a9 100644 --- a/libc/unistd/Makefile.in +++ b/libc/unistd/Makefile.in @@ -14,8 +14,6 @@ CSRC := $(filter-out exec.c,$(CSRC))  ifeq ($(ARCH_USE_MMU),y)  CSRC := $(filter-out __exec_alloc.c,$(CSRC)) -else -CSRC := $(filter-out daemon.c,$(CSRC))  endif  ifeq ($(UCLIBC_HAS_GNU_GETOPT),y) diff --git a/libc/unistd/daemon.c b/libc/unistd/daemon.c index 5bd6f39ed..19332cca1 100644 --- a/libc/unistd/daemon.c +++ b/libc/unistd/daemon.c @@ -56,27 +56,40 @@  /* libc_hidden_proto(chdir) */  /* libc_hidden_proto(fork) */ +#ifndef __ARCH_USE_MMU__ +#include <sys/syscall.h> +/* use clone() to get fork() like behavior here -- we just want to disassociate + * from the controlling terminal + */ +static inline pid_t fork_parent(void) +{ +	register unsigned long ret = INTERNAL_SYSCALL(clone, wtf, 2, CLONE_VM, 0); +	if (ret != -1 && ret != 0) +		/* parent needs to die now w/out touching stack */ +		INTERNAL_SYSCALL(exit, wtf, 0); +	return ret; +} +#else +static inline pid_t fork_parent(void) +{ +	switch (fork()) { +		case -1: return -1; +		case 0:  return 0; +		default: _exit(0); +	} +} +#endif +  int daemon( int nochdir, int noclose )  {  	int fd; -	switch (fork()) { -		case -1: -			return(-1); -		case 0: -			break; -		default: -			_exit(0); -	} +	if (fork_parent() == -1) +		return -1;  	if (setsid() == -1)  		return(-1); -	/* Make certain we are not a session leader, or else we -	 * might reacquire a controlling terminal */ -	if (fork()) -		_exit(0); -  	if (!nochdir)  		chdir("/"); | 
