diff options
-rw-r--r-- | cores/arduino/CDC.cpp | 54 | ||||
-rw-r--r-- | cores/arduino/USBAPI.h | 4 | ||||
-rw-r--r-- | cores/arduino/USBCore.cpp | 7 |
3 files changed, 25 insertions, 40 deletions
diff --git a/cores/arduino/CDC.cpp b/cores/arduino/CDC.cpp index aa1275d..9999ca8 100644 --- a/cores/arduino/CDC.cpp +++ b/cores/arduino/CDC.cpp @@ -114,7 +114,6 @@ bool WEAK CDC_Setup(Setup& setup) } -int _serialPeek = -1; void Serial_::begin(unsigned long /* baud_count */) { } @@ -127,51 +126,29 @@ void Serial_::end(void) { } -void Serial_::accept(void) -{ - int i = (unsigned int)(_rx_buffer_head+1) % SERIAL_BUFFER_SIZE; - - // if we should be storing the received character into the location - // just before the tail (meaning that the head would advance to the - // current location of the tail), we're about to overflow the buffer - // and so we don't write the character or advance the head. - - // while we have room to store a byte - while (i != _rx_buffer_tail) { - int c = USB_Recv(CDC_RX); - if (c == -1) - break; // no more data - _rx_buffer[_rx_buffer_head] = c; - _rx_buffer_head = i; - - i = (unsigned int)(_rx_buffer_head+1) % SERIAL_BUFFER_SIZE; - } -} - int Serial_::available(void) { - return (unsigned int)(SERIAL_BUFFER_SIZE + _rx_buffer_head - _rx_buffer_tail) % SERIAL_BUFFER_SIZE; + if (peek_buffer >= 0) { + return 1; + } + return USB_Available(CDC_RX); } int Serial_::peek(void) { - if (_rx_buffer_head == _rx_buffer_tail) { - return -1; - } else { - return _rx_buffer[_rx_buffer_tail]; - } + if (peek_buffer < 0) + peek_buffer = USB_Recv(CDC_RX); + return peek_buffer; } int Serial_::read(void) { - // if the head isn't ahead of the tail, we don't have any characters - if (_rx_buffer_head == _rx_buffer_tail) { - return -1; - } else { - unsigned char c = _rx_buffer[_rx_buffer_tail]; - _rx_buffer_tail = (unsigned int)(_rx_buffer_tail + 1) % SERIAL_BUFFER_SIZE; + if (peek_buffer >= 0) { + int c = peek_buffer; + peek_buffer = -1; return c; - } + } + return USB_Recv(CDC_RX); } void Serial_::flush(void) @@ -181,6 +158,11 @@ void Serial_::flush(void) size_t Serial_::write(uint8_t c) { + return write(&c, 1); +} + +size_t Serial_::write(const uint8_t *buffer, size_t size) +{ /* only try to send bytes if the high-level CDC connection itself is open (not just the pipe) - the OS should set lineState when the port is opened and clear lineState when the port is closed. @@ -191,7 +173,7 @@ size_t Serial_::write(uint8_t c) // open connection isn't broken cleanly (cable is yanked out, host dies // or locks up, or host virtual serial port hangs) if (_usbLineInfo.lineState > 0) { - int r = USB_Send(CDC_TX,&c,1); + int r = USB_Send(CDC_TX,buffer,size); if (r > 0) { return r; } else { diff --git a/cores/arduino/USBAPI.h b/cores/arduino/USBAPI.h index 5a33002..c637fda 100644 --- a/cores/arduino/USBAPI.h +++ b/cores/arduino/USBAPI.h @@ -35,17 +35,19 @@ struct ring_buffer; class Serial_ : public Stream { +private: + int peek_buffer; public: void begin(unsigned long); void begin(unsigned long, uint8_t); void end(void); virtual int available(void); - virtual void accept(void); virtual int peek(void); virtual int read(void); virtual void flush(void); virtual size_t write(uint8_t); + virtual size_t write(const uint8_t*, size_t); using Print::write; // pull in write(str) and write(buf, size) from Print operator bool(); diff --git a/cores/arduino/USBCore.cpp b/cores/arduino/USBCore.cpp index 9eb7b33..39a9530 100644 --- a/cores/arduino/USBCore.cpp +++ b/cores/arduino/USBCore.cpp @@ -289,9 +289,12 @@ int USB_Send(u8 ep, const void* d, int len) if (n > len) n = len; - len -= n; { LockEP lock(ep); + // Frame may have been released by the SOF interrupt handler + if (!ReadWriteAllowed()) + continue; + len -= n; if (ep & TRANSFER_ZERO) { while (n--) @@ -627,8 +630,6 @@ ISR(USB_GEN_vect) { #ifdef CDC_ENABLED USB_Flush(CDC_TX); // Send a tx frame if found - if (USB_Available(CDC_RX)) // Handle received bytes (if any) - Serial.accept(); #endif // check whether the one-shot period has elapsed. if so, turn off the LED |