Ejemplo n.º 1
0
void evalcmd(char *argv[], int bg) {
  int status;
  pid_t pid;
  if ((pid = Fork()) == 0) // run cmd as child
    Execve(argv[0], argv, environ);
  if (!bg)
    Waitpid(pid, &status, 0);
  else {
    Waitpid(pid, &status, WNOHANG);
    printf("%d %s\n", pid, argv[0]);
  }
  return;
}
Ejemplo n.º 2
0
int
main(int argc, char **argv)
{
	int		pipe1[2], pipe2[2];
	pid_t	childpid;

	Pipe(pipe1);	/* create two pipes */
	Pipe(pipe2);

	if ( (childpid = Fork()) == 0) {		
		/* child: write pipe2, read pipe1 */
		Close(pipe1[1]);
		Close(pipe2[0]);

		server(pipe1[0], pipe2[1]);
		exit(0);
	}
	/* parent , read pipe2 , write pipe1*/
	Close(pipe1[0]);
	Close(pipe2[1]);

	client(pipe2[0], pipe1[1]);

	Waitpid(childpid, NULL, 0);		/* wait for child to terminate */
	exit(0);
}
Ejemplo n.º 3
0
int my_open(const char* pathname, int mode)
{
    int fd, sockfd[2], status;
    pid_t childpid;
    char c, argsockfd[10], argmode[10];

    Socketpair(AF_LOCAL, SOCK_STREAM, 0, sockfd);

    if ((childpid = Fork()) == 0) { /* child process */
        Close(sockfd[0]);
        snprintf(argsockfd, sizeof(argsockfd), "%d", sockfd[1]);
        snprintf(argmode, sizeof(argmode), "%d", mode);
        execl("./openfile", "openfile", argsockfd, pathname, argmode,
              (char*)NULL);
        err_sys("execl error");
    }

    /* parent process - wait for the child to terminate */
    Close(sockfd[1]); /* close the end we don't use */

    Waitpid(childpid, &status, 0);
    if (WIFEXITED(status) == 0) err_quit("child did not terminate");
    if ((status = WEXITSTATUS(status)) == 0)
        Read_fd(sockfd[0], &c, 1, &fd);
    else {
        errno = status; /* set errno value from child's status */
        fd = -1;
    }

    Close(sockfd[0]);
    return (fd);
}
Ejemplo n.º 4
0
int my_open(const char *pathname, int mode)
{
	int fd, sockfd[2], status;
	pid_t childpid;
	char c, argsockfd[10], argmode[10];

	Socketpair(AF_LOCAL, SOCK_STREAM, 0, sockfd);

	//child process
	if ((childpid = Fork()) == 0)
	{
		Close(sockfd[0]);
		snprintf(argsockfd, sizeof(argsockfd), "%d", sockfd[1]); /* what is in sockfd[1] */
		snprintf(argmode, sizeof(argmode), "%d", mode);
		execl("./openfile", "openfile", argsockfd, pathname, argmode, (char *)NULL);
		err_sys("execl error");
	}

	//parent process
	Close(sockfd[1]);

	Waitpid(childpid, &status, 0);
	if (WIFEXITED(status) == 0)
		err_quit("child did not terminate");
	if ((status = WEXITSTATUS(status)) == 0)
		read_fd(sockfd[0], &c, 1, &fd);
	else
	{
		errno = status;
		fd = -1;
	}

    Close(sockfd[0]);
	return (fd);
}
Ejemplo n.º 5
0
int main(int argc, char **argv)
{
	int fd1, fd2, *ptr1, *ptr2;
	pid_t childpid;
	struct stat stat;

	if (argc != 2)
		err_quit("Usage: test2 <name>");

	Shm_unlink(Px_ipc_name(argv[1]));
	fd1 = Shm_open(Px_ipc_name(argv[1]), O_RDWR | O_CREAT | O_EXCL, FILE_MODE);
    Ftruncate(fd1, sizeof(int));
	fd2 = Open("./shm", O_RDONLY);
	Fstat(fd2, &stat);

	if ((childpid = Fork()) == 0) {
		ptr2 = Mmap(NULL, stat.st_size, PROT_READ, MAP_SHARED, fd2, 0);
		ptr1 = Mmap(NULL, sizeof(int), PROT_READ | PROT_WRITE, MAP_SHARED, fd1, 0);
		printf("child: shm ptr = %p, motd ptr = %p\n", ptr1, ptr2);

		sleep(5);
		printf("shared memory integer = %d\n", *ptr1);
		exit(0);
	}
	
	//parent: map in reverse order from child
	ptr1 = Mmap(NULL, sizeof(int), PROT_READ | PROT_WRITE, MAP_SHARED, fd1, 0);
	ptr2 = Mmap(NULL, stat.st_size, PROT_READ, MAP_SHARED, fd2, 0);
	*ptr1 = 777;
	Waitpid(childpid, NULL, 0);
	
	exit(0);
}
int main()
{
    unsigned int pid;
    int val;

    pid = ForkExec("run2");
    if (pid < 0)
    {
        PutString("Error while Fork\n");
        return -1;
    }

    Waitpid(pid, &val);

    PutString("Child exit code was ");
    PutInt(val);
    PutChar('\n');

    return 0;
}
Ejemplo n.º 7
0
int
main(int argc, char **argv)
{
	int		i, nprocs;
	pid_t	childpid[MAXNPROC];

	if (argc != 3)
		err_quit("usage: incr_rwlock5 <#loops> <#processes>");
	nloop = atoi(argv[1]);
	nprocs = min(atoi(argv[2]), MAXNPROC);

		/* 4get shared memory for parent and children */
	shared = My_shm(sizeof(struct shared));

		/* 4initialize the read-write lock and obtain write lock */
	Rwlock_init(&shared->rwlock, USYNC_PROCESS, NULL);
	Rw_wrlock(&shared->rwlock);

		/* 4create all the children */
	for (i = 0; i < nprocs; i++) {
		if ( (childpid[i] = Fork()) == 0) {
			incr(NULL);
			exit(0);
		}
	}
		/* 4parent: start the timer and release the write lock */
	Start_time();
	Rw_unlock(&shared->rwlock);

		/* 4wait for all the children */
	for (i = 0; i < nprocs; i++) {
		Waitpid(childpid[i], NULL, 0);
	}
	printf("microseconds: %.0f usec\n", Stop_time());
	if (shared->counter != nloop * nprocs)
		printf("error: counter = %ld\n", shared->counter);

	exit(0);
}
Ejemplo n.º 8
0
int
main(int argc, char **argv)
{
	int		i, nprocs;
	pid_t	childpid[MAXNPROC];

	if (argc != 3)
		err_quit("usage: incr_pxsem9 <#loops> <#processes>");
	nloop = atoi(argv[1]);
	nprocs = min(atoi(argv[2]), MAXNPROC);

		/* 4get shared memory for parent and children */
	shared = My_shm(sizeof(struct shared));

		/* 4initialize memory-based semaphore to 0 */
	Sem_init(&mutex, 1, 0);

		/* 4create all the children */
	for (i = 0; i < nprocs; i++) {
		if ( (childpid[i] = Fork()) == 0) {
			incr(NULL);
			exit(0);
		}
	}
		/* 4parent: start the timer and release the semaphore */
	Start_time();
	Sem_post(&mutex);

		/* 4wait for all the children */
	for (i = 0; i < nprocs; i++) {
		Waitpid(childpid[i], NULL, 0);
	}
	printf("microseconds: %.0f usec\n", Stop_time());
	if (shared->counter != nloop * nprocs)
		printf("error: counter = %ld\n", shared->counter);

	exit(0);
}
Ejemplo n.º 9
0
int
main(int argc, char **argv)
{
	int		rc;
	pid_t	childpid;
	mymqd_t	mqd;
	unsigned int	prio;
	struct sigevent	sigev;
	struct mymq_attr	attr, info;

	if (argc != 2)
		err_quit("usage: testmymq <pathname>");

		/***************************************************************/
		/* test mq_unlink() error return */
	mymq_unlink(argv[1]);
	if ( ( rc = mymq_unlink(argv[1])) == 0 || errno != ENOENT)
		err_sys("mq_unlink returned %d", rc);

		/***************************************************************/
		/* create a queue with default attributes */
	mqd = Mymq_open(argv[1], O_CREAT | O_EXCL | O_RDWR, FILE_MODE, NULL);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 128 || info.mq_msgsize != 1024 ||
		info.mq_flags != 0 || info.mq_curmsgs != 0)
		err_msg("message queue defaults:\n"
				"maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld",
		   		info.mq_maxmsg, info.mq_msgsize,
				info.mq_flags, info.mq_curmsgs);
	Mymq_close(mqd);

		/***************************************************************/
		/* check O_EXCL */
	mqd = mymq_open(argv[1], O_CREAT | O_EXCL | O_RDWR, FILE_MODE, NULL);
	if (mqd != (mqd_t) -1 || errno != EEXIST)
		err_sys("mq_open returned %d", rc);
	Mymq_unlink(argv[1]);

		/***************************************************************/
		/* create with attributes */
	attr.mq_maxmsg = 4;
	attr.mq_msgsize = 7;
	mqd = Mymq_open(argv[1], O_CREAT | O_EXCL | O_RDWR, FILE_MODE, &attr);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 0)
		err_quit("1: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);

		/***************************************************************/
		/* send/receive 1 message */
	Mymq_send(mqd, msg1, 1, 1);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);

		/* send/receive 1 0-byte message */
	Mymq_send(mqd, msg0, 0, 0);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 0)
		err_quit("mq_receive returned %d, expected 0", rc);
	if (prio != 0)
		err_quit("mq_receive returned prio %d, expected 0", prio);


		/* send 2 messages/receive in reverse order */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg2, 2, 2);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);

		/* send 3 messages/receive in reverse order */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg3, 3, 3);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);

		/* send 4 messages/receive in reverse order */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg3, 3, 3);
	Mymq_send(mqd, msg4, 4, 4);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);

		/***************************************************************/
		/* send/receive 1 message */
	Mymq_send(mqd, msg4, 4, 4);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);

		/* send 2 messages/receive in order */
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_send(mqd, msg3, 3, 3);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);

		/* send 3 messages/receive in order */
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_send(mqd, msg3, 3, 3);
	Mymq_send(mqd, msg2, 2, 2);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);

		/* send 4 messages/receive in order */
		/* first check EMSGSIZE */
	if ( (rc = mymq_send(mqd, msg4, 8, 4)) == 0 || errno != EMSGSIZE)
		err_sys("mq_send returned %d, expected EMSGSIZE", rc);
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_send(mqd, msg3, 3, 3);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg1, 1, 1);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
		/* first check EMSGSIZE */
	if ( (rc = mymq_receive(mqd, msg, 6, &prio)) == 0 || errno != EMSGSIZE)
		err_sys("mq_receive returned %d, expected EMSGSIZE", rc);
	if ( (rc = Mymq_receive(mqd, msg, BUFFLEN, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);

		/* fill queue then close it */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_send(mqd, msg3, 3, 3);
	Mymq_close(mqd);
		/* open existing queue nonblocking and read */
	mqd = Mymq_open(argv[1], O_RDWR | O_NONBLOCK);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != O_NONBLOCK || info.mq_curmsgs != 4)
		err_quit("2: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);
		/* check nonblockiing receive */
	if ( (rc = mymq_receive(mqd, msg, info.mq_msgsize, &prio)) == 0 ||
		errno != EAGAIN)
		err_sys("mq_receive returned %d, expected EAGAIN", rc);

		/* fill queue then close it */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg3, 3, 3);
		/* first check nonblocking send */
	if ( (rc = mymq_send(mqd, msg5, 5, 5)) == 0 || errno != EAGAIN)
		err_sys("mq_send returned %d, expected EAGAIN", rc);
	Mymq_close(mqd);

		/* open existing queue and read */
	mqd = Mymq_open(argv[1], O_RDWR);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 4)
		err_quit("mq_receive returned %d, expected 4", rc);
	if (prio != 4)
		err_quit("mq_receive returned prio %d, expected 4", prio);
		/* now set nonblocking with mq_setattr */
	attr.mq_flags = O_NONBLOCK;
	Mymq_setattr(mqd, &attr, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 3)
		err_quit("3: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != O_NONBLOCK || info.mq_curmsgs != 3)
		err_quit("4: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);
		/* check nonblocking receive */
	if ( (rc = mymq_receive(mqd, msg, info.mq_msgsize, &prio)) == 0 ||
		errno != EAGAIN)
		err_sys("mq_receive returned %d, expected EAGAIN", rc);

		/* now clear nonblocking with mq_setattr */
	attr.mq_flags = 0;
	Mymq_setattr(mqd, &attr, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != O_NONBLOCK || info.mq_curmsgs != 0)
		err_quit("5: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 0)
		err_quit("6: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
#ifdef	notdef
		/* queue is empty; check that mymq_receive is interruptable */
	Signal(SIGALRM, sig_alrm);
	blocked = 1;
	alarm(4);
	if ( (rc = mymq_receive(mqd, msg, info.mq_msgsize, &prio)) == 0 ||
		errno != EINTR)
		err_sys("mq_receive returned %d, expected EINTR", rc);
	alarm(0);
	printf("mymq_receive interrupted, as expected\n");

		/* fill queue */
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg2, 2, 2);
	Mymq_send(mqd, msg3, 3, 3);
	Mymq_send(mqd, msg4, 4, 4);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 4)
		err_quit("7: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);
		/* queue is full; check that mymq_send is interruptable */
	Signal(SIGALRM, sig_alrm);
	blocked = 1;
	alarm(4);
printf("about to call mymq_send\n");
	if ( (rc = mymq_send(mqd, msg5, 5, 5)) == 0 || errno != EINTR)
		err_sys("mq_send returned %d, expected EINTR", rc);
	alarm(0);
	printf("mymq_send interrupted, as expected\n");
#endif

		/* queue is empty, register for notification */
	sigev.sigev_notify = SIGEV_SIGNAL;
	sigev.sigev_signo = SIGUSR1;
	Signal(SIGUSR1, sig_usr1);
	Mymq_notify(mqd, &sigev);
		/* verify we cannot register twice */
	if ( (rc = mymq_notify(mqd, &sigev)) == 0 || errno != EBUSY)
		err_sys("mq_notify returned %d, expected EBUSY", rc);
		/* now unregister, then reregister */
	Mymq_notify(mqd, NULL);
	Mymq_notify(mqd, &sigev);
		/* verify we cannot register twice */
	if ( (rc = mymq_notify(mqd, &sigev)) == 0 || errno != EBUSY)
		err_sys("mq_notify returned %d, expected EBUSY", rc);

		/* make certain child cannot register if we are registered */
	if ( (childpid = Fork()) == 0) {
		if ( (rc = mymq_notify(mqd, &sigev)) == 0 || errno != EBUSY)
			err_sys("mq_notify returned %d, expected EBUSY", rc);
		exit(0);
	}
	Waitpid(childpid, NULL, 0);

		/* send a message and verify SIGUSR1 is delivered */
	sigusr1 = 0;
	Mymq_send(mqd, msg5, 5, 5);
	sleep(1);
	if (sigusr1 != 1)
		err_quit("sigusr1 = %d, expected 1", sigusr1);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 5)
		err_quit("mq_receive returned %d, expected 5", rc);
	if (prio != 5)
		err_quit("mq_receive returned prio %d, expected 5", prio);

		/* send another and make certain another signal is not sent */
	Mymq_send(mqd, msg2, 2, 2);
	sleep(1);
	if (sigusr1 != 1)
		err_quit("sigusr1 = %d, expected 1", sigusr1);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 2)
		err_quit("mq_receive returned %d, expected 2", rc);
	if (prio != 2)
		err_quit("mq_receive returned prio %d, expected 2", prio);

		/* reregister */
	Mymq_notify(mqd, &sigev);
	if ( (childpid = Fork()) == 0) {
			/* child calls mq_receive, which prevents notification */
		if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 6)
			err_quit("mq_receive returned %d, expected 6", rc);
		if (prio != 6)
			err_quit("mq_receive returned prio %d, expected 6", prio);
		exit(0);
	}
	sleep(2);		/* let child block in mq_receive() */
	Mymq_send(mqd, msg6, 6, 6);
	Waitpid(childpid, NULL, 0);
	if (sigusr1 != 1)
		err_quit("sigusr1 = %d, expected 1", sigusr1);

		/* make certain parent can send messages to child, and vice versa */
	if ( (childpid = Fork()) == 0) {
		sleep(2);		/* let parent send two messages */
		if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 3)
			err_quit("mq_receive returned %d, expected 3", rc);
		if (prio != 3)
			err_quit("mq_receive returned prio %d, expected 3", prio);
		if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 1)
			err_quit("mq_receive returned %d, expected 1", rc);
		if (prio != 1)
			err_quit("mq_receive returned prio %d, expected 1", prio);
		exit(0);
	}
	Mymq_send(mqd, msg1, 1, 1);
	Mymq_send(mqd, msg3, 3, 3);
	Waitpid(childpid, NULL, 0);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 0)
		err_quit("8: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);

	if ( (childpid = Fork()) == 0) {
		Mymq_send(mqd, msg3, 3, 3);
		Mymq_send(mqd, msg5, 5, 5);
		Mymq_send(mqd, msg1, 1, 1);
		exit(0);
	}
	sleep(2);		/* let child send 3 messages */
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 5)
		err_quit("mq_receive returned %d, expected 5", rc);
	if (prio != 5)
		err_quit("mq_receive returned prio %d, expected 5", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 3)
		err_quit("mq_receive returned %d, expected 3", rc);
	if (prio != 3)
		err_quit("mq_receive returned prio %d, expected 3", prio);
	if ( (rc = Mymq_receive(mqd, msg, info.mq_msgsize, &prio)) != 1)
		err_quit("mq_receive returned %d, expected 1", rc);
	if (prio != 1)
		err_quit("mq_receive returned prio %d, expected 1", prio);
	Waitpid(childpid, NULL, 0);
	Mymq_getattr(mqd, &info);
	if (info.mq_maxmsg != 4 || info.mq_msgsize != 7 ||
		info.mq_flags != 0 || info.mq_curmsgs != 0)
		err_quit("9: maxmsg = %ld, msgsize = %ld, flags = %ld, curmsgs = %ld\n",
		   		 info.mq_maxmsg, info.mq_msgsize,
				 info.mq_flags, info.mq_curmsgs);

	printf("done\n");
	exit(0);
}
Ejemplo n.º 10
0
static int sigChildHandler(int sig)
{
	int status;
	Waitpid(-1, &status, 0);
	printf("handler has successful reap a child\n");
}
Ejemplo n.º 11
0
/* the current socat/xio implementation knows two kinds of children:
   exec/system addresses perform a fork: their children are registered and
   their death's influence the parents' flow;
   listen-socket with fork children: these children are "anonymous" and their
   death does not affect the parent process (now; maybe we have a child
   process counter later) */
void childdied(int signum
#if HAVE_SIGACTION
	       , siginfo_t *siginfo, void *context
#endif /* HAVE_SIGACTION */
	       ) {
   pid_t pid;
   int _errno;
   int status = 0;
   bool wassig = false;
   int i;
   struct _xiosigchld_child *entry;

   _errno = errno;	/* save current value; e.g., select() on Cygwin seems
			   to set it to EINTR _before_ handling the signal, and
			   then passes the value left by the signal handler to
			   the caller of select(), accept() etc. */
   /* is not thread/signal save, but confused messages in rare cases are better
      than no messages at all */
   Info1("childdied(signum=%d)", signum);
   do {
      pid = Waitpid(-1, &status, WNOHANG);
      if (pid == 0) {
	 Msg(wassig?E_INFO:E_WARN,
	     "waitpid(-1, {}, WNOHANG): no child has exited");
	 Info("childdied() finished");
	 errno = _errno;
	 return;
      } else if (pid < 0 && errno == ECHILD) {
	 Msg1(wassig?E_INFO:E_WARN,
	      "waitpid(-1, {}, WNOHANG): %s", strerror(errno));
	 Info("childdied() finished");
	 errno = _errno;
	 return;
      }
      wassig = true;
      if (pid < 0) {
	 Warn2("waitpid(-1, {%d}, WNOHANG): %s", status, strerror(errno));
	 Info("childdied() finished");
	 errno = _errno;
	 return;
      }
#if 0
   /*! indent */
   /* check if it was a registered child process */
   i = 0;
   while (i < XIO_MAXSOCK) {
      if (xio_checkchild(sock[i], i, pid))  break;
      ++i;
   }
   if (i == XIO_MAXSOCK) {
	 Info2("childdied(%d): cannot identify child %d", signum, pid);
	 if (diedunknown1 == 0) {
	    diedunknown1 = pid;
	    Debug("saving pid in diedunknown1");
	 } else if (diedunknown2 == 0) {
	    diedunknown2 = pid;
	    Debug("saving pid in diedunknown2");
	 } else if (diedunknown3 == 0) {
	     diedunknown3 = pid;
	    Debug("saving pid in diedunknown3");
	 } else {
	    diedunknown4 = pid;
	    Debug("saving pid in diedunknown4");
	 }
      }
#else
   entry = _xiosigchld_find(pid);
   if (entry == NULL) {
      Info("dead child "F_pid" died unknown");
   } else {
      (*entry->sigaction)(signum, siginfo, entry->context);
      xiosigchld_unregister(pid);
   }
#endif

   if (WIFEXITED(status)) {
      if (WEXITSTATUS(status) == 0) {
	 Info2("waitpid(): child %d exited with status %d",
	       pid, WEXITSTATUS(status));
      } else {
	 Warn2("waitpid(): child %d exited with status %d",
	       pid, WEXITSTATUS(status));
      }
   } else if (WIFSIGNALED(status)) {
      Info2("waitpid(): child %d exited on signal %d",
	    pid, WTERMSIG(status));
   } else if (WIFSTOPPED(status)) {
      Info2("waitpid(): child %d stopped on signal %d",
	    pid, WSTOPSIG(status));
   } else {
      Warn1("waitpid(): cannot determine status of child %d", pid);
   }

#if !HAVE_SIGACTION
   /* we might need to re-register our handler */
   if (Signal(SIGCHLD, childdied) == SIG_ERR) {
      Warn2("signal(SIGCHLD, %p): %s", childdied, strerror(errno));
   }
#endif /* !HAVE_SIGACTION */
  } while (1);
   Info("childdied() finished");
   errno = _errno;
}
Ejemplo n.º 12
0
void sigchld_handler(int s)
{
    int olderrno = errno;
    pid = Waitpid(-1, NULL, 0);
    errno = olderrno;
}
Ejemplo n.º 13
0
int xioshutdown(xiofile_t *sock, int how) {
   int result = 0;

   if (sock->tag == XIO_TAG_INVALID) {
      Error("xioshutdown(): invalid file descriptor");
      errno = EINVAL;
      return -1;
   }

   if (sock->tag == XIO_TAG_DUAL) {
      if ((how+1)&1) {
	 result = xioshutdown((xiofile_t *)sock->dual.stream[0], 0);
      }
      if ((how+1)&2) {
	 result |= xioshutdown((xiofile_t *)sock->dual.stream[1], 1);
      }
      return result;
   }

   switch (sock->stream.howtoshut) {
      char writenull;
   case XIOSHUT_NONE:
      return 0;
   case XIOSHUT_CLOSE:
      if (Close(sock->stream.fd) < 0) {
	 Info2("close(%d): %s",
	       sock->stream.fd, strerror(errno));
      }
      return 0;
   case XIOSHUT_DOWN:
      if ((result = Shutdown(sock->stream.fd, how)) < 0) {
	 Info3("shutdown(%d, %d): %s",
	       sock->stream.fd, how, strerror(errno));
      }
      return 0;
#if _WITH_SOCKET
   case XIOSHUT_NULL:
      /* send an empty packet; only useful on datagram sockets? */
      xiowrite(sock, &writenull, 0);
      return 0;
#endif /* _WITH_SOCKET */
   default: ;
   }

   if (false) {
      ;
#if WITH_OPENSSL
   } else if ((sock->stream.dtype & XIODATA_MASK) == XIODATA_OPENSSL) {
      sycSSL_shutdown (sock->stream.para.openssl.ssl);
      /*! what about half/full close? */
#endif /* WITH_OPENSSL */

   } else if ((sock->stream.dtype & XIODATA_MASK) == XIODATA_PIPE) {
      if ((how+1)&1) {
	 if (Close(sock->stream.fd) < 0) {
	    Info2("close(%d): %s",
		  sock->stream.fd, strerror(errno));
	 }
      }
      if ((how+1)&2) {
	 if (Close(sock->stream.para.bipipe.fdout) < 0) {
	    Info2("close(%d): %s",
		  sock->stream.para.bipipe.fdout, strerror(errno));
	 } 
      }
      
   } else if ((sock->stream.dtype & XIODATA_MASK) == XIODATA_2PIPE) {
      if ((how+1)&1) {
	 if (Close(sock->stream.fd) < 0) {
	    Info2("close(%d): %s",
		  sock->stream.fd, strerror(errno));
	 }
      }
      if ((how+1)&2) {
	 if (Close(sock->stream.para.exec.fdout) < 0) {
	    Info2("close(%d): %s",
		  sock->stream.para.exec.fdout, strerror(errno));
	 } 
      }
#if _WITH_SOCKET
   } else if (sock->stream.howtoend == END_SHUTDOWN) {
      if ((result = Shutdown(sock->stream.fd, how)) < 0) {
	 Info3("shutdown(%d, %d): %s",
	       sock->stream.fd, how, strerror(errno));
      }
   } else if (sock->stream.howtoend == END_SHUTDOWN_KILL) {
      if ((result = Shutdown(sock->stream.fd, how)) < 0) {
	 Info3("shutdown(%d, %d): %s",
	       sock->stream.fd, how, strerror(errno));
      }
      if ((sock->stream.flags&XIO_ACCMODE) == XIO_WRONLY) {
	 /* the child process might want to flush some data before terminating
	    */
	 int status = 0;

	 /* we wait for the child process to die, but to prevent timeout
	    we raise an alarm after some time.
	    NOTE: the alarm does not terminate waitpid() on Linux/glibc (BUG?),
	    therefore we have to do the kill in the signal handler */
	 {
	    struct sigaction act;
	    sigfillset(&act.sa_mask);
	    act.sa_flags = 0;
	    act.sa_handler = signal_kill_pid;
	    Sigaction(SIGALRM, &act, NULL);
	 }
	 socat_kill_pid = sock->stream.para.exec.pid;
#if HAVE_SETITIMER
	 /*! with next feature release, we get usec resolution and an option */
#else
	 Alarm(1 /*! sock->stream.para.exec.waitdie */);
#endif /* !HAVE_SETITIMER */
	 if (Waitpid(sock->stream.para.exec.pid, &status, 0) < 0) {
	    Warn3("waitpid("F_pid", %p, 0): %s",
		  sock->stream.para.exec.pid, &status, strerror(errno));
	 }
	 Alarm(0);
      }
   } else if ((sock->stream.dtype & XIODATA_MASK) ==
	      (XIODATA_RECVFROM & XIODATA_MASK)) {
      if (how >= 1) {
	 if (Close(sock->stream.fd) < 0) {
	    Info2("close(%d): %s",
		  sock->stream.fd, strerror(errno));
	 }
	 sock->stream.eof = 2;
	 sock->stream.fd = -1;
      }
#endif /* _WITH_SOCKET */
#if 0
   } else {
      Error1("xioshutdown(): bad data type specification %d", sock->stream.dtype);
      return -1;
#endif

   }
#if 0
   else if (sock->stream.howtoend == END_CLOSE &&
Ejemplo n.º 14
0
/*$sigChldHandler to protect zimble process */
static void sigChldHandler(int signo)
{
	Waitpid(-1,NULL,WNOHANG);
	return;
}