2828
2929// Constructors ////////////////////////////////////////////////////////////////
3030
31- Uart::Uart (XMC_UART_t *xmc_uart_config, RingBuffer *rx_buffer, RingBuffer *tx_buffer ) {
31+ Uart::Uart (XMC_UART_t *xmc_uart_config, RingBuffer *rx_buffer) {
3232 _XMC_UART_config = xmc_uart_config;
3333 _rx_buffer = rx_buffer;
34- _tx_buffer = tx_buffer;
3534}
3635
3736// Public Methods //////////////////////////////////////////////////////////////
@@ -103,7 +102,7 @@ void Uart::end(void) {
103102 // Disable UART interrupt in NVIC
104103 NVIC_DisableIRQ (_XMC_UART_config->irq_num );
105104 // Clear any received data after stopping interrupts
106- _rx_buffer->_iHead = _rx_buffer-> _iTail ;
105+ _rx_buffer->clear () ;
107106}
108107
109108void Uart::setInterruptPriority (uint32_t priority) {
@@ -112,96 +111,31 @@ void Uart::setInterruptPriority(uint32_t priority) {
112111
113112uint32_t Uart::getInterruptPriority () { return NVIC_GetPriority (_XMC_UART_config->irq_num ); }
114113
115- int Uart::available (void ) {
116- int head = _rx_buffer->_iHead ; // Snapshot index affected by irq
117- if (head >= _rx_buffer->_iTail )
118- return head - _rx_buffer->_iTail ;
119- return SERIAL_BUFFER_SIZE - _rx_buffer->_iTail + head;
120- }
114+ int Uart::available (void ) { return _rx_buffer->available (); }
121115
122116int Uart::availableForWrite (void ) {
123- int tail = _tx_buffer->_iTail ; // Snapshot index affected by irq
124- if (_tx_buffer->_iHead >= tail)
125- return SERIAL_BUFFER_SIZE - 1 - _tx_buffer->_iHead + tail;
126- return tail - _tx_buffer->_iHead - 1 ;
127- }
128-
129- int Uart::peek (void ) {
130- if (_rx_buffer->_iHead == _rx_buffer->_iTail )
131- return -1 ;
132- return _rx_buffer->_aucBuffer [_rx_buffer->_iTail ];
133- }
117+ return 1 ;
118+ } // TODO: there are no tx buffer so we awaly have 1 byte available
134119
135- int Uart::read (void ) {
136- // if the head isn't ahead of the tail, we don't have any characters
137- if (_rx_buffer->_iHead == _rx_buffer->_iTail )
138- return -1 ;
120+ int Uart::peek (void ) { return _rx_buffer->peek (); }
139121
140- uint8_t uc = _rx_buffer->_aucBuffer [_rx_buffer->_iTail ];
141- _rx_buffer->_iTail ++;
142- if (_rx_buffer->_iTail >= SERIAL_BUFFER_SIZE)
143- _rx_buffer->_iTail = 0 ;
144- return uc;
145- }
122+ int Uart::read (void ) { return _rx_buffer->read_char (); }
146123
147124void Uart::flush (void ) {
148- while (_tx_buffer->_iHead != _tx_buffer->_iTail )
149- ; // wait for transmit data to be sent
150-
151125 while (XMC_USIC_CH_GetTransmitBufferStatus (_XMC_UART_config->channel ) ==
152- XMC_USIC_CH_TBUF_STATUS_BUSY)
153- ;
126+ XMC_USIC_CH_TBUF_STATUS_BUSY) {
127+ } ;
154128}
155129
156130size_t Uart::write (const uint8_t uc_data) {
157- // Is the hardware currently busy?
158- #if defined(SERIAL_USE_U1C1)
159- if (_tx_buffer->_iTail != _tx_buffer->_iHead )
160- #else
161- if ((XMC_USIC_CH_GetTransmitBufferStatus (_XMC_UART_config->channel ) ==
162- XMC_USIC_CH_TBUF_STATUS_BUSY) ||
163- (_tx_buffer->_iTail != _tx_buffer->_iHead ))
164- #endif
165- {
166- // If busy we buffer
167- int nextWrite = _tx_buffer->_iHead + 1 ;
168- if (nextWrite >= SERIAL_BUFFER_SIZE)
169- nextWrite = 0 ;
170-
171- // This should always be false but in case transmission is completed before buffer, we need
172- // to reenable IRQ
173- if (XMC_USIC_CH_GetTransmitBufferStatus (_XMC_UART_config->channel ) !=
174- XMC_USIC_CH_TBUF_STATUS_BUSY) {
175- XMC_UART_CH_EnableEvent (_XMC_UART_config->channel , XMC_UART_CH_EVENT_TRANSMIT_BUFFER);
176- XMC_UART_CH_Transmit (_XMC_UART_config->channel ,
177- _tx_buffer->_aucBuffer [_tx_buffer->_iTail ]);
178- _tx_buffer->_iTail ++;
179- if (_tx_buffer->_iTail >= SERIAL_BUFFER_SIZE)
180- _tx_buffer->_iTail %= SERIAL_BUFFER_SIZE; // If iTail is larger than Serial Buffer
181- // Size calculate the correct index value
182- }
183-
184- unsigned long startTime = millis ();
185- while (_tx_buffer->_iTail == nextWrite) {
186- if (millis () - startTime > 1000 ) {
187- return 0 ; // Spin locks if we're about to overwrite the buffer. This continues once
188- // the data is
189- // sent
190- }
191- }
192-
193- _tx_buffer->_aucBuffer [_tx_buffer->_iHead ] = uc_data;
194- _tx_buffer->_iHead = nextWrite;
195- } else {
196- // Make sure TX interrupt is enabled
197- XMC_UART_CH_EnableEvent (_XMC_UART_config->channel , XMC_UART_CH_EVENT_TRANSMIT_BUFFER);
198- // Bypass buffering and send character directly
199- XMC_UART_CH_Transmit (_XMC_UART_config->channel , uc_data);
200- }
131+ // For sending, write immediately
132+ // This API already have a check for available buffer
133+ XMC_UART_CH_Transmit (_XMC_UART_config->channel , uc_data);
201134 return 1 ;
202135}
203136
204137void Uart::IrqHandler (void ) {
138+ // Receive data Interrupt handler
205139 uint32_t status = XMC_UART_CH_GetStatusFlag (_XMC_UART_config->channel );
206140
207141 // Did we receive data?
@@ -215,24 +149,6 @@ void Uart::IrqHandler(void) {
215149 (USIC_CH_RBUFSR_RDV0_Msk | USIC_CH_RBUFSR_RDV1_Msk))
216150 _rx_buffer->store_char (XMC_UART_CH_GetReceivedData (_XMC_UART_config->channel ));
217151 }
218-
219- // Do we need to keep sending data?
220- if ((status & XMC_UART_CH_STATUS_FLAG_TRANSMIT_BUFFER_INDICATION) != 0U ) {
221- XMC_UART_CH_ClearStatusFlag (_XMC_UART_config->channel ,
222- XMC_UART_CH_STATUS_FLAG_TRANSMIT_BUFFER_INDICATION);
223-
224- if (_tx_buffer->_iTail != _tx_buffer->_iHead ) {
225- XMC_UART_CH_Transmit (_XMC_UART_config->channel ,
226- _tx_buffer->_aucBuffer [_tx_buffer->_iTail ]);
227- _tx_buffer->_iTail ++;
228- if (_tx_buffer->_iTail >= SERIAL_BUFFER_SIZE)
229- _tx_buffer->_iTail %= SERIAL_BUFFER_SIZE; // If iTail is larger than Serial Buffer
230- // Size calculate the correct index value
231- } else {
232- // Mask off transmit interrupt so we don't get it any more
233- XMC_UART_CH_DisableEvent (_XMC_UART_config->channel , XMC_UART_CH_EVENT_TRANSMIT_BUFFER);
234- }
235- }
236152}
237153
238154// ****************************************************************************
0 commit comments