int WindowsFileIO::read(void *p) { LOG->Trace( "WindowsFileIO::read()" ); /* See if we have a response for our request (which we may * have made on a previous call): */ if(WaitForSingleObjectEx(h, 0, TRUE) == WAIT_TIMEOUT) return -1; return finish_read(p); }
/// read XML stream into XML tree below _pos void XMLReaderBase::read() { if (!parse()) { XMLError error; error._message = "XML parsing error"; //error._line = ; //error._column = ; _errors.push_back(error); } finish_read(); }
int serial_read ( struct serial_channel* _chan, void* _buf, int len) { struct serial_win32* chan = (struct serial_win32*)_chan; char* buf = (char*)_buf; int bytesCopied = 0; int bytesAvail; for (;;) { /* Get the number of bytes remaining in the read buffer. This is * the total number of bytes immediately available without making * the caller wait. */ bytesAvail = chan->rxBufLen - chan->rxRecvLen; if (bytesAvail > 0) { /* If no space remains in the buffer provided by the caller, return * the number of bytes which have been copied into the user's buffer. */ if (0 == len) { /* If there is still more data available in the application buffer, * but no pending IO operation is active, there won't be a pending * operation when this return is made. Therefore manually signal * the eRxReady event. This ensures that the caller will get * the signal immediately and call again to get more data from * the buffer. The later call may start an IO operation. */ if (RXSTATE_NONE == chan->rxState) { SetEvent(chan->eRxReady); } goto ok_return; } if (len < bytesAvail) { /* The rx buffer actually has more data in it than what the * caller asked for. Copy only what the caller asked for. */ memcpy(buf, chan->rxBuf + chan->rxRecvLen, len); chan->rxRecvLen += len; bytesCopied += len; len = 0; } else { /* Copy what's available in the serial port buffer. There may * still be more data imemdiately available from the OS, but we * don't know that yet. This might actually empty the buffer, * but we cannot update rxBufLen or reset rxRecvLen until we know * if a pending operation is outstanding or not. */ memcpy(buf, chan->rxBuf + chan->rxRecvLen, bytesAvail); chan->rxRecvLen += bytesAvail; bytesCopied += bytesAvail; buf += bytesAvail; len -= bytesAvail; } } switch (chan->rxState) { case RXSTATE_NONE: /* No operation is currently pending. If the buffer has been * completely drained by the caller, start up a wait operation. */ if (chan->rxRecvLen == chan->rxBufLen) { /* The buffer is completely empty, so zero out the lengths * so the entire buffer is available for more data. This * is the only way the buffer truncates back to its start. */ chan->rxBufLen = 0; chan->rxRecvLen = 0; /* If start_wait_rx returns FALSE, an IO operation is now * pending and the caller will get signaled with eRxReady * when the pending operation completes. Return the current * number of bytes processed, or -1. */ if ( ! start_wait_rx(chan)) { goto ok_return; } /* No operation is pending. Most likely there is now new * data in the read buffer, and thus the receive loop should * keep running to copy all available data into the user * buffer. */ } /* If the buffer is not empty, don't try to get an operation * started. This allows the caller to completely empty the * application buffer on the next call (which should happen * immediately as SetEvent is used to manually signal eRxReady). * Only after the caller has emptied the buffer will the IO * get started up again. */ break; case RXSTATE_WAIT: /* The serial port needs to finish the wait call. If the wait * call is not finished yet, return the current number of * bytes processed (most likely will be 0, so the actual * return code will be -1). */ if ( ! finish_wait_rx(chan)) { goto ok_return; } /* If we fall through, finish_wait_rx returned TRUE, indicating * that the start_read call put new data into the buffer. Go * through the loop above and try to consume it. */ break; case RXSTATE_READ: /* The serial port read just finished, or maybe not. If the * read is not yet finished, return the number of bytes put into * the user's buffer, or -1 if no data was copied. */ if ( ! finish_read(chan)) { goto ok_return; } /* If we fall through, the read may have put more data into the * buffer, so loop and try to copy it into the user's buffer. */ break; } } ok_return: /* If no bytes were copied, return -1. This is how UNIX read(2) works * when in nonblocking IO mode. We don't however set an error code * to EAGAIN like UNIX systems do. */ return bytesCopied > 0 ? bytesCopied : -1; }