84
84
#error "Not all bit positions for UART3 are the same as for UART0"
85
85
#endif
86
86
87
- inline void store_char (unsigned char c, HardwareSerial *s)
88
- {
89
- int i = (unsigned int )(s->_rx_buffer_head + 1 ) % SERIAL_BUFFER_SIZE;
90
-
91
- // if we should be storing the received character into the location
92
- // just before the tail (meaning that the head would advance to the
93
- // current location of the tail), we're about to overflow the buffer
94
- // and so we don't write the character or advance the head.
95
- if (i != s->_rx_buffer_tail ) {
96
- s->_rx_buffer [s->_rx_buffer_head ] = c;
97
- s->_rx_buffer_head = i;
98
- }
99
- }
100
-
101
87
#if !defined(USART0_RX_vect) && defined(USART1_RX_vect)
102
88
// do nothing - on the 32u4 the first USART is USART1
103
89
#else
@@ -116,23 +102,7 @@ inline void store_char(unsigned char c, HardwareSerial *s)
116
102
ISR (USART_RXC_vect) // ATmega8
117
103
#endif
118
104
{
119
- #if defined(UDR0)
120
- if (bit_is_clear (UCSR0A, UPE0)) {
121
- unsigned char c = UDR0;
122
- store_char (c, &Serial);
123
- } else {
124
- unsigned char c = UDR0;
125
- };
126
- #elif defined(UDR)
127
- if (bit_is_clear (UCSRA, PE)) {
128
- unsigned char c = UDR;
129
- store_char (c, &Serial);
130
- } else {
131
- unsigned char c = UDR;
132
- };
133
- #else
134
- #error UDR not defined
135
- #endif
105
+ Serial._rx_complete_irq ();
136
106
}
137
107
#endif
138
108
#endif
@@ -143,12 +113,7 @@ inline void store_char(unsigned char c, HardwareSerial *s)
143
113
#define serialEvent1_implemented
144
114
ISR (USART1_RX_vect)
145
115
{
146
- if (bit_is_clear (UCSR1A, UPE1)) {
147
- unsigned char c = UDR1;
148
- store_char (c, &Serial1);
149
- } else {
150
- unsigned char c = UDR1;
151
- };
116
+ Serial1._rx_complete_irq ();
152
117
}
153
118
#endif
154
119
@@ -158,12 +123,7 @@ inline void store_char(unsigned char c, HardwareSerial *s)
158
123
#define serialEvent2_implemented
159
124
ISR (USART2_RX_vect)
160
125
{
161
- if (bit_is_clear (UCSR2A, UPE2)) {
162
- unsigned char c = UDR2;
163
- store_char (c, &Serial2);
164
- } else {
165
- unsigned char c = UDR2;
166
- };
126
+ Serial2._rx_complete_irq ();
167
127
}
168
128
#endif
169
129
@@ -173,12 +133,7 @@ inline void store_char(unsigned char c, HardwareSerial *s)
173
133
#define serialEvent3_implemented
174
134
ISR (USART3_RX_vect)
175
135
{
176
- if (bit_is_clear (UCSR3A, UPE3)) {
177
- unsigned char c = UDR3;
178
- store_char (c, &Serial3);
179
- } else {
180
- unsigned char c = UDR3;
181
- };
136
+ Serial3._rx_complete_irq ();
182
137
}
183
138
#endif
184
139
@@ -215,81 +170,71 @@ ISR(USART0_UDRE_vect)
215
170
ISR (USART_UDRE_vect)
216
171
#endif
217
172
{
218
- if (Serial._tx_buffer_head == Serial._tx_buffer_tail ) {
219
- // Buffer empty, so disable interrupts
220
- #if defined(UCSR0B)
221
- cbi (UCSR0B, UDRIE0);
222
- #else
223
- cbi (UCSRB, UDRIE);
224
- #endif
225
- }
226
- else {
227
- // There is more data in the output buffer. Send the next byte
228
- unsigned char c = Serial._tx_buffer [Serial._tx_buffer_tail ];
229
- Serial._tx_buffer_tail = (Serial._tx_buffer_tail + 1 ) % SERIAL_BUFFER_SIZE;
230
-
231
- #if defined(UDR0)
232
- UDR0 = c;
233
- #elif defined(UDR)
234
- UDR = c;
235
- #else
236
- #error UDR not defined
237
- #endif
238
- }
173
+ Serial._tx_udr_empty_irq ();
239
174
}
240
175
#endif
241
176
#endif
242
177
243
178
#ifdef USART1_UDRE_vect
244
179
ISR (USART1_UDRE_vect)
245
180
{
246
- if (Serial1._tx_buffer_head == Serial1._tx_buffer_tail ) {
247
- // Buffer empty, so disable interrupts
248
- cbi (UCSR1B, UDRIE1);
249
- }
250
- else {
251
- // There is more data in the output buffer. Send the next byte
252
- unsigned char c = Serial1._tx_buffer [Serial1._tx_buffer_tail ];
253
- Serial1._tx_buffer_tail = (Serial1._tx_buffer_tail + 1 ) % SERIAL_BUFFER_SIZE;
254
-
255
- UDR1 = c;
256
- }
181
+ Serial1._tx_udr_empty_irq ();
257
182
}
258
183
#endif
259
184
260
185
#ifdef USART2_UDRE_vect
261
186
ISR (USART2_UDRE_vect)
262
187
{
263
- if (Serial2._tx_buffer_head == Serial2._tx_buffer_tail ) {
264
- // Buffer empty, so disable interrupts
265
- cbi (UCSR2B, UDRIE2);
266
- }
267
- else {
268
- // There is more data in the output buffer. Send the next byte
269
- unsigned char c = Serial2._tx_buffer [Serial2._tx_buffer_tail ];
270
- Serial2._tx_buffer_tail = (Serial2._tx_buffer_tail + 1 ) % SERIAL_BUFFER_SIZE;
271
-
272
- UDR2 = c;
273
- }
188
+ Serial2._tx_udr_empty_irq ();
274
189
}
275
190
#endif
276
191
277
192
#ifdef USART3_UDRE_vect
278
193
ISR (USART3_UDRE_vect)
279
194
{
280
- if (Serial3._tx_buffer_head == Serial3._tx_buffer_tail ) {
281
- // Buffer empty, so disable interrupts
282
- cbi (UCSR3B, UDRIE3);
195
+ Serial3._tx_udr_empty_irq ();
196
+ }
197
+ #endif
198
+
199
+
200
+ // Actual interrupt handlers //////////////////////////////////////////////////////////////
201
+
202
+ void HardwareSerial::_rx_complete_irq (void )
203
+ {
204
+ if (bit_is_clear (*_ucsra, UPE0)) {
205
+ // No Parity error, read byte and store it in the buffer if there is
206
+ // room
207
+ unsigned char c = *_udr;
208
+ int i = (unsigned int )(_rx_buffer_head + 1 ) % SERIAL_BUFFER_SIZE;
209
+
210
+ // if we should be storing the received character into the location
211
+ // just before the tail (meaning that the head would advance to the
212
+ // current location of the tail), we're about to overflow the buffer
213
+ // and so we don't write the character or advance the head.
214
+ if (i != _rx_buffer_tail) {
215
+ _rx_buffer[_rx_buffer_head] = c;
216
+ _rx_buffer_head = i;
217
+ }
218
+ } else {
219
+ // Parity error, read byte but discard it
220
+ unsigned char c = *_udr;
221
+ };
222
+ }
223
+
224
+ void HardwareSerial::_tx_udr_empty_irq (void )
225
+ {
226
+ if (_tx_buffer_head == _tx_buffer_tail) {
227
+ // Buffer empty, so disable interrupts
228
+ cbi (*_ucsrb, UDRIE0);
283
229
}
284
230
else {
285
231
// There is more data in the output buffer. Send the next byte
286
- unsigned char c = Serial3. _tx_buffer [Serial3. _tx_buffer_tail ];
287
- Serial3. _tx_buffer_tail = (Serial3. _tx_buffer_tail + 1 ) % SERIAL_BUFFER_SIZE;
288
-
289
- UDR3 = c;
232
+ unsigned char c = _tx_buffer[_tx_buffer_tail];
233
+ _tx_buffer_tail = (_tx_buffer_tail + 1 ) % SERIAL_BUFFER_SIZE;
234
+
235
+ *_udr = c;
290
236
}
291
237
}
292
- #endif
293
238
294
239
// Constructors ////////////////////////////////////////////////////////////////
295
240
0 commit comments