I have put together some test code to read a child processes stdout, stderr and to write data to the child's stdin. Moreover, I've managed to do this using C++ streams.
The input streambuffer class was written by Frank B. Brokken and can be found in C++ Annotations http://www.icce.rug.nl/documents/cplusplus/ See section 19.4.2.2: Using an n-character buffer ifdnstreambuf uses the file descriptor returned by pipe (2) so is perfect for my needs. Indeed, everything works perfectly. Well almost. Here's the code doing the reading: int underflow() { if (gptr() < egptr()) return *gptr(); int nread = read(d_fd, d_buffer, d_bufsize); if (nread <= 0) return EOF; setg(d_buffer, d_buffer, d_buffer + nread); return *gptr(); } I'm using select (2) to inform me when data becomes available to read. That works. The question is, how do I know when to stop reading? Clearly, if (nread < d_bufsize) then I shouldn't call read (2) again until select (2) informs me that there's something to read. However, what should I do if (nread == d_bufsize)? Either I got lucky and my buffer was exactly the right size to store the data, or there's more data to read. The problem is, if I call read (2) again, it'll block awaiting input if there's none to be had. Ok, so I invoke fcntl(d_fd[READ], F_SETFL, O_NONBLOCK); so that read runs non-blocking. Still no good. An EAGAIN error breaks the pipe. I think that I've reached the limits of my knowledge. Can anyone help me out? Is it possible to re-open the pipe again? -- Angus
