Hello, I'm working on a modified hurdselect.c, the poll() part, to enable file descriptors being bogus, as allowed by POSIX. That case is now solved, and the revent reported is POLLNVAL. What remains to do to is to return the POLHUP event (and POLLERR).
Using modified code from gnulib, attached, a case to check for is: open a pipe getting both a read and write fs, write, read, close the read fs, and poll. This case should be detected by hurdselect. Currently it does not. The construct used in hurdselect is the mach_msg() function: __mach_msg (&msg.head, MACH_RCV_MSG | options, 0, sizeof msg, portset, to, MACH_PORT_NULL) This function call only has parameters set for reading. Can a subsequent call using MACH_SEND_MSG parameters and messages be used to find out? (or setting both READ and RCV parameters and messages in the same function call above) If not, how to find out that the read part of the pipe has been closed (within hurdselect, not the application) Thanks!
/* File: test_closing a file descriptor */ #include <poll.h> #include <stdio.h> #include <unistd.h> /* Test poll(2) on pipes. */ static int test_pipe (void) { int fd[2]; char buf[3]; pipe (fd); struct pollfd pfd; int nfound = -1; pfd.fd = fd[1]; pfd.events = POLLIN | POLLOUT; pfd.revents = 0; printf ("Pipe created: Read fd[0] = %d, Write fd[1] = %d\n", fd[0], fd[1]); write (fd[1], "foo", 3); read (fd[0], buf, 3); close (fd[0]); printf ("After closing fd[0] = %d\n", fd[0]); printf ("Input: pfd.events = (POLLIN | POLLOUT) = %d\n", pfd.events); nfound = poll (&pfd, 1, -1); printf ("Output: pfd.revents = %d\n", pfd.revents); printf("Result: pfd.revents & (POLLHUP | POLLERR) = %d & %d = %d\n", pfd.revents, (POLLHUP | POLLERR), pfd.revents & (POLLHUP | POLLERR)); if ((pfd.revents & (POLLHUP | POLLERR)) == 0) printf ("ERROR: expecting (POLLHUP | POLLERR) after shutdown\n"); close (fd[1]); return nfound; } int main () { int result = -1; printf ("\npoll parameters:\n"); printf ("POLLIN = %2d, POLLPRI = %2d, POLLOUT = %2d\n", POLLIN, POLLPRI,POLLOUT); printf ("POLLERR = %2d, POLLHUP = %2d, POLLNVAL = %2d\n", POLLERR, POLLHUP, POLLNVAL); printf ("POLLRDNORM = %3d, POLLRDBAND = %3d\n", POLLRDNORM, POLLRDBAND); printf ("POLLWRNORM = %3d, POLLWRBAND = %3d\n", POLLWRNORM, POLLWRBAND); #ifdef __GNU__ #include <hurd/hurd_types.h> #define SELECT_ALL (SELECT_READ | SELECT_WRITE | SELECT_URG) #define SELECT_RETURNED ((SELECT_ALL << 1) & ~SELECT_ALL) printf ("SELECT_READ = %3d, SELECT_WRITE = %3d, SELECT_URG= %3d\n", SELECT_READ, SELECT_WRITE, SELECT_URG); printf ("SELECT_ALL = %3d, SELECT_RETURNED = %3d\n", SELECT_ALL, SELECT_RETURNED); #endif printf("\nPipe test\n=========\n"); result = test_pipe(); return result; }