All pastes #537869 Raw Edit

running an external program

public c v1 · immutable
·published 2007-06-04 21:39 UTC
rendered paste body
#include <stdio.h>#include <unistd.h>#include <fcntl.h>#include <errno.h>#include <sys/select.h>#include <sys/wait.h>enum{	BUF_SIZE     = 4096,	BUF_MAX_READ = BUF_SIZE - 1,	LOOP_CONT = 0,	LOOP_EXIT = 1,	LOOP_KILL = 2};intmain (int argc, char *argv[]){	int	pfd[2];	pid_t	cpid;	if (pipe (pfd) == -1)		err (1, "pipe");	if ((cpid = fork()) == -1)		err (1, "fork");	else if (cpid == 0)	/* the child */	{		/* Replace the child's stdin with /dev/null to prevent any funny stuff. */		int devNull;		if ((devNull = open ("/dev/null", O_RDONLY)) == -1)			err (1, "open");		if (dup2 (devNull, 0) == -1)			err (1, "dup2");		/* Close the reading end of the child's pipe. */		if (close (pfd[0]) == -1)			err (1, "close");		if (dup2 (pfd[1], 1) == -1)			err (1, "dup2");		/* Fire the rockets! */		if (execl ("/bin/zcat", "zcat", "/proc/config.gz", (char *) NULL) == -1)			err (1, "execl");	}	else	/* the parent */	{		int 		status, loop = LOOP_CONT, retval, s;		char		buf[BUF_SIZE];		ssize_t		n;		fd_set		rfds;		struct timeval	tv;		/* Close the writing end of the parent's pipe. */		if (close (pfd[1]) == -1)			err (1, "close");		FD_ZERO (&rfds);		FD_SET  (pfd[0], &rfds);		tv.tv_sec  = 0;		tv.tv_usec = 0;		while (loop == LOOP_CONT)		{			/* Monitor the child and schedule to kill it and/or break out of the loop if necessary. */			if (waitpid (cpid, &status, WUNTRACED) == -1)				err (1, "waitpid");			else if (WIFSTOPPED (status) != 0)			{				fprintf (stderr, "Child received SIGSTOP, sending SIGKILL...\n");				loop = LOOP_KILL;			}			else if (WIFSIGNALED (status) != 0)			{				printf ("Child was terminated with signal %i\n", WTERMSIG (status));				loop = LOOP_EXIT;			}			else if (WIFEXITED (status) != 0)			{				retval = WEXITSTATUS (status);				loop = LOOP_EXIT;			}			/* Read from the pipe if possible, but don't wait. */			while (((s = select (pfd[0] + 1, &rfds, NULL, NULL, &tv)) > 0)			       && ((n = read (pfd[0], &buf, BUF_MAX_READ)) != 0))			{				if (n == -1)					err (1, "read");				buf[n] = '\0';				printf ("%s", buf);			}			if (s == -1)				err (1, "select");			/* The infant must perish. */			if (loop == LOOP_KILL)				if (kill (cpid, SIGKILL) == -1)					err (1, "kill");		}	}	return 0;}