Skip to content

Commit

Permalink
Improvements to HardwareSerial.cpp
Browse files Browse the repository at this point in the history
  • Loading branch information
MCUdude committed Jan 19, 2023
1 parent 4543713 commit c8bef0b
Showing 1 changed file with 22 additions and 12 deletions.
34 changes: 22 additions & 12 deletions HardwareSerial.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#include <stdio.h>
#include <string.h>
#include <inttypes.h>
#include <util/atomic.h>
#include "Arduino.h"

#include "HardwareSerial.h"
Expand Down Expand Up @@ -76,6 +77,13 @@ void serialEventRun(void)
#endif
}

// macro to guard critical sections when needed for large TX buffer sizes
#if (SERIAL_TX_BUFFER_SIZE>256)
#define TX_BUFFER_ATOMIC ATOMIC_BLOCK(ATOMIC_RESTORESTATE)
#else
#define TX_BUFFER_ATOMIC
#endif

// Actual interrupt handlers //////////////////////////////////////////////////////////////

void HardwareSerial::_tx_udr_empty_irq(void)
Expand Down Expand Up @@ -174,15 +182,13 @@ int HardwareSerial::read(void)

int HardwareSerial::availableForWrite(void)
{
#if (SERIAL_TX_BUFFER_SIZE>256)
uint8_t oldSREG = SREG;
cli();
#endif
tx_buffer_index_t head = _tx_buffer_head;
tx_buffer_index_t tail = _tx_buffer_tail;
#if (SERIAL_TX_BUFFER_SIZE>256)
SREG = oldSREG;
#endif
tx_buffer_index_t head;
tx_buffer_index_t tail;

TX_BUFFER_ATOMIC {
head = _tx_buffer_head;
tail = _tx_buffer_tail;
}
if (head >= tail) return SERIAL_TX_BUFFER_SIZE - 1 - head + tail;
return tail - head - 1;
}
Expand Down Expand Up @@ -237,9 +243,13 @@ size_t HardwareSerial::write(uint8_t c)
}

_tx_buffer[_tx_buffer_head] = c;
_tx_buffer_head = i;

*_ucsrb |= _BV(UDRIE0);
// make atomic to prevent execution of ISR between setting the
// head pointer and setting the interrupt flag resulting in buffer
// retransmission
ATOMIC_BLOCK(ATOMIC_RESTORESTATE) {
_tx_buffer_head = i;
*_ucsrb |= _BV(UDRIE0);
}

return 1;
}
Expand Down

0 comments on commit c8bef0b

Please sign in to comment.