Project

General

Profile

Statistics
| Branch: | Revision:

root / arduino-1.0 / hardware / arduino / cores / arduino / HardwareSerial.cpp @ 58d82c77

History | View | Annotate | Download (11.1 KB)

1
/*
2
  HardwareSerial.cpp - Hardware serial library for Wiring
3
  Copyright (c) 2006 Nicholas Zambetti.  All right reserved.
4

5
  This library is free software; you can redistribute it and/or
6
  modify it under the terms of the GNU Lesser General Public
7
  License as published by the Free Software Foundation; either
8
  version 2.1 of the License, or (at your option) any later version.
9

10
  This library is distributed in the hope that it will be useful,
11
  but WITHOUT ANY WARRANTY; without even the implied warranty of
12
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13
  Lesser General Public License for more details.
14

15
  You should have received a copy of the GNU Lesser General Public
16
  License along with this library; if not, write to the Free Software
17
  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
18
  
19
  Modified 23 November 2006 by David A. Mellis
20
  Modified 28 September 2010 by Mark Sproul
21
*/
22

    
23
#include <stdlib.h>
24
#include <stdio.h>
25
#include <string.h>
26
#include <inttypes.h>
27
#include "Arduino.h"
28
#include "wiring_private.h"
29

    
30
// this next line disables the entire HardwareSerial.cpp, 
31
// this is so I can support Attiny series and any other chip without a uart
32
#if defined(UBRRH) || defined(UBRR0H) || defined(UBRR1H) || defined(UBRR2H) || defined(UBRR3H)
33

    
34
#include "HardwareSerial.h"
35

    
36
// Define constants and variables for buffering incoming serial data.  We're
37
// using a ring buffer (I think), in which head is the index of the location
38
// to which to write the next incoming character and tail is the index of the
39
// location from which to read.
40
#if (RAMEND < 1000)
41
  #define SERIAL_BUFFER_SIZE 16
42
#else
43
  #define SERIAL_BUFFER_SIZE 64
44
#endif
45

    
46
struct ring_buffer
47
{
48
  unsigned char buffer[SERIAL_BUFFER_SIZE];
49
  volatile int head;
50
  volatile int tail;
51
};
52

    
53
#if defined(USBCON)
54
  ring_buffer rx_buffer = { { 0 }, 0, 0};
55
  ring_buffer tx_buffer = { { 0 }, 0, 0};
56
#endif
57
#if defined(UBRRH) || defined(UBRR0H)
58
  ring_buffer rx_buffer  =  { { 0 }, 0, 0 };
59
  ring_buffer tx_buffer  =  { { 0 }, 0, 0 };
60
#endif
61
#if defined(UBRR1H)
62
  ring_buffer rx_buffer1  =  { { 0 }, 0, 0 };
63
  ring_buffer tx_buffer1  =  { { 0 }, 0, 0 };
64
#endif
65
#if defined(UBRR2H)
66
  ring_buffer rx_buffer2  =  { { 0 }, 0, 0 };
67
  ring_buffer tx_buffer2  =  { { 0 }, 0, 0 };
68
#endif
69
#if defined(UBRR3H)
70
  ring_buffer rx_buffer3  =  { { 0 }, 0, 0 };
71
  ring_buffer tx_buffer3  =  { { 0 }, 0, 0 };
72
#endif
73

    
74
inline void store_char(unsigned char c, ring_buffer *buffer)
75
{
76
  int i = (unsigned int)(buffer->head + 1) % SERIAL_BUFFER_SIZE;
77

    
78
  // if we should be storing the received character into the location
79
  // just before the tail (meaning that the head would advance to the
80
  // current location of the tail), we're about to overflow the buffer
81
  // and so we don't write the character or advance the head.
82
  if (i != buffer->tail) {
83
    buffer->buffer[buffer->head] = c;
84
    buffer->head = i;
85
  }
86
}
87

    
88
#if !defined(USART0_RX_vect) && defined(USART1_RX_vect)
89
// do nothing - on the 32u4 the first USART is USART1
90
#else
91
#if !defined(USART_RX_vect) && !defined(SIG_USART0_RECV) && \
92
    !defined(SIG_UART0_RECV) && !defined(USART0_RX_vect) && \
93
        !defined(SIG_UART_RECV)
94
  #error "Don't know what the Data Received vector is called for the first UART"
95
#else
96
  void serialEvent() __attribute__((weak));
97
  void serialEvent() {}
98
  #define serialEvent_implemented
99
#if defined(USART_RX_vect)
100
  SIGNAL(USART_RX_vect)
101
#elif defined(SIG_USART0_RECV)
102
  SIGNAL(SIG_USART0_RECV)
103
#elif defined(SIG_UART0_RECV)
104
  SIGNAL(SIG_UART0_RECV)
105
#elif defined(USART0_RX_vect)
106
  SIGNAL(USART0_RX_vect)
107
#elif defined(SIG_UART_RECV)
108
  SIGNAL(SIG_UART_RECV)
109
#endif
110
  {
111
  #if defined(UDR0)
112
    unsigned char c  =  UDR0;
113
  #elif defined(UDR)
114
    unsigned char c  =  UDR;
115
  #else
116
    #error UDR not defined
117
  #endif
118
    store_char(c, &rx_buffer);
119
  }
120
#endif
121
#endif
122

    
123
#if defined(USART1_RX_vect)
124
  void serialEvent1() __attribute__((weak));
125
  void serialEvent1() {}
126
  #define serialEvent1_implemented
127
  SIGNAL(USART1_RX_vect)
128
  {
129
    unsigned char c = UDR1;
130
    store_char(c, &rx_buffer1);
131
  }
132
#elif defined(SIG_USART1_RECV)
133
  #error SIG_USART1_RECV
134
#endif
135

    
136
#if defined(USART2_RX_vect) && defined(UDR2)
137
  void serialEvent2() __attribute__((weak));
138
  void serialEvent2() {}
139
  #define serialEvent2_implemented
140
  SIGNAL(USART2_RX_vect)
141
  {
142
    unsigned char c = UDR2;
143
    store_char(c, &rx_buffer2);
144
  }
145
#elif defined(SIG_USART2_RECV)
146
  #error SIG_USART2_RECV
147
#endif
148

    
149
#if defined(USART3_RX_vect) && defined(UDR3)
150
  void serialEvent3() __attribute__((weak));
151
  void serialEvent3() {}
152
  #define serialEvent3_implemented
153
  SIGNAL(USART3_RX_vect)
154
  {
155
    unsigned char c = UDR3;
156
    store_char(c, &rx_buffer3);
157
  }
158
#elif defined(SIG_USART3_RECV)
159
  #error SIG_USART3_RECV
160
#endif
161

    
162
void serialEventRun(void)
163
{
164
#ifdef serialEvent_implemented
165
  if (Serial.available()) serialEvent();
166
#endif
167
#ifdef serialEvent1_implemented
168
  if (Serial1.available()) serialEvent1();
169
#endif
170
#ifdef serialEvent2_implemented
171
  if (Serial2.available()) serialEvent2();
172
#endif
173
#ifdef serialEvent3_implemented
174
  if (Serial3.available()) serialEvent3();
175
#endif
176
}
177

    
178

    
179
#if !defined(USART0_UDRE_vect) && defined(USART1_UDRE_vect)
180
// do nothing - on the 32u4 the first USART is USART1
181
#else
182
#if !defined(UART0_UDRE_vect) && !defined(UART_UDRE_vect) && !defined(USART0_UDRE_vect) && !defined(USART_UDRE_vect)
183
  #error "Don't know what the Data Register Empty vector is called for the first UART"
184
#else
185
#if defined(UART0_UDRE_vect)
186
ISR(UART0_UDRE_vect)
187
#elif defined(UART_UDRE_vect)
188
ISR(UART_UDRE_vect)
189
#elif defined(USART0_UDRE_vect)
190
ISR(USART0_UDRE_vect)
191
#elif defined(USART_UDRE_vect)
192
ISR(USART_UDRE_vect)
193
#endif
194
{
195
  if (tx_buffer.head == tx_buffer.tail) {
196
        // Buffer empty, so disable interrupts
197
#if defined(UCSR0B)
198
    cbi(UCSR0B, UDRIE0);
199
#else
200
    cbi(UCSRB, UDRIE);
201
#endif
202
  }
203
  else {
204
    // There is more data in the output buffer. Send the next byte
205
    unsigned char c = tx_buffer.buffer[tx_buffer.tail];
206
    tx_buffer.tail = (tx_buffer.tail + 1) % SERIAL_BUFFER_SIZE;
207
        
208
  #if defined(UDR0)
209
    UDR0 = c;
210
  #elif defined(UDR)
211
    UDR = c;
212
  #else
213
    #error UDR not defined
214
  #endif
215
  }
216
}
217
#endif
218
#endif
219

    
220
#ifdef USART1_UDRE_vect
221
ISR(USART1_UDRE_vect)
222
{
223
  if (tx_buffer1.head == tx_buffer1.tail) {
224
        // Buffer empty, so disable interrupts
225
    cbi(UCSR1B, UDRIE1);
226
  }
227
  else {
228
    // There is more data in the output buffer. Send the next byte
229
    unsigned char c = tx_buffer1.buffer[tx_buffer1.tail];
230
    tx_buffer1.tail = (tx_buffer1.tail + 1) % SERIAL_BUFFER_SIZE;
231
        
232
    UDR1 = c;
233
  }
234
}
235
#endif
236

    
237
#ifdef USART2_UDRE_vect
238
ISR(USART2_UDRE_vect)
239
{
240
  if (tx_buffer2.head == tx_buffer2.tail) {
241
        // Buffer empty, so disable interrupts
242
    cbi(UCSR2B, UDRIE2);
243
  }
244
  else {
245
    // There is more data in the output buffer. Send the next byte
246
    unsigned char c = tx_buffer2.buffer[tx_buffer2.tail];
247
    tx_buffer2.tail = (tx_buffer2.tail + 1) % SERIAL_BUFFER_SIZE;
248
        
249
    UDR2 = c;
250
  }
251
}
252
#endif
253

    
254
#ifdef USART3_UDRE_vect
255
ISR(USART3_UDRE_vect)
256
{
257
  if (tx_buffer3.head == tx_buffer3.tail) {
258
        // Buffer empty, so disable interrupts
259
    cbi(UCSR3B, UDRIE3);
260
  }
261
  else {
262
    // There is more data in the output buffer. Send the next byte
263
    unsigned char c = tx_buffer3.buffer[tx_buffer3.tail];
264
    tx_buffer3.tail = (tx_buffer3.tail + 1) % SERIAL_BUFFER_SIZE;
265
        
266
    UDR3 = c;
267
  }
268
}
269
#endif
270

    
271

    
272
// Constructors ////////////////////////////////////////////////////////////////
273

    
274
HardwareSerial::HardwareSerial(ring_buffer *rx_buffer, ring_buffer *tx_buffer,
275
  volatile uint8_t *ubrrh, volatile uint8_t *ubrrl,
276
  volatile uint8_t *ucsra, volatile uint8_t *ucsrb,
277
  volatile uint8_t *udr,
278
  uint8_t rxen, uint8_t txen, uint8_t rxcie, uint8_t udrie, uint8_t u2x)
279
{
280
  _rx_buffer = rx_buffer;
281
  _tx_buffer = tx_buffer;
282
  _ubrrh = ubrrh;
283
  _ubrrl = ubrrl;
284
  _ucsra = ucsra;
285
  _ucsrb = ucsrb;
286
  _udr = udr;
287
  _rxen = rxen;
288
  _txen = txen;
289
  _rxcie = rxcie;
290
  _udrie = udrie;
291
  _u2x = u2x;
292
}
293

    
294
// Public Methods //////////////////////////////////////////////////////////////
295

    
296
void HardwareSerial::begin(unsigned long baud)
297
{
298
  uint16_t baud_setting;
299
  bool use_u2x = true;
300

    
301
#if F_CPU == 16000000UL
302
  // hardcoded exception for compatibility with the bootloader shipped
303
  // with the Duemilanove and previous boards and the firmware on the 8U2
304
  // on the Uno and Mega 2560.
305
  if (baud == 57600) {
306
    use_u2x = false;
307
  }
308
#endif
309

    
310
try_again:
311
  
312
  if (use_u2x) {
313
    *_ucsra = 1 << _u2x;
314
    baud_setting = (F_CPU / 4 / baud - 1) / 2;
315
  } else {
316
    *_ucsra = 0;
317
    baud_setting = (F_CPU / 8 / baud - 1) / 2;
318
  }
319
  
320
  if ((baud_setting > 4095) && use_u2x)
321
  {
322
    use_u2x = false;
323
    goto try_again;
324
  }
325

    
326
  // assign the baud_setting, a.k.a. ubbr (USART Baud Rate Register)
327
  *_ubrrh = baud_setting >> 8;
328
  *_ubrrl = baud_setting;
329

    
330
  sbi(*_ucsrb, _rxen);
331
  sbi(*_ucsrb, _txen);
332
  sbi(*_ucsrb, _rxcie);
333
  cbi(*_ucsrb, _udrie);
334
}
335

    
336
void HardwareSerial::end()
337
{
338
  // wait for transmission of outgoing data
339
  while (_tx_buffer->head != _tx_buffer->tail)
340
    ;
341

    
342
  cbi(*_ucsrb, _rxen);
343
  cbi(*_ucsrb, _txen);
344
  cbi(*_ucsrb, _rxcie);  
345
  cbi(*_ucsrb, _udrie);
346
  
347
  // clear any received data
348
  _rx_buffer->head = _rx_buffer->tail;
349
}
350

    
351
int HardwareSerial::available(void)
352
{
353
  return (unsigned int)(SERIAL_BUFFER_SIZE + _rx_buffer->head - _rx_buffer->tail) % SERIAL_BUFFER_SIZE;
354
}
355

    
356
int HardwareSerial::peek(void)
357
{
358
  if (_rx_buffer->head == _rx_buffer->tail) {
359
    return -1;
360
  } else {
361
    return _rx_buffer->buffer[_rx_buffer->tail];
362
  }
363
}
364

    
365
int HardwareSerial::read(void)
366
{
367
  // if the head isn't ahead of the tail, we don't have any characters
368
  if (_rx_buffer->head == _rx_buffer->tail) {
369
    return -1;
370
  } else {
371
    unsigned char c = _rx_buffer->buffer[_rx_buffer->tail];
372
    _rx_buffer->tail = (unsigned int)(_rx_buffer->tail + 1) % SERIAL_BUFFER_SIZE;
373
    return c;
374
  }
375
}
376

    
377
void HardwareSerial::flush()
378
{
379
  while (_tx_buffer->head != _tx_buffer->tail)
380
    ;
381
}
382

    
383
size_t HardwareSerial::write(uint8_t c)
384
{
385
  int i = (_tx_buffer->head + 1) % SERIAL_BUFFER_SIZE;
386
        
387
  // If the output buffer is full, there's nothing for it other than to 
388
  // wait for the interrupt handler to empty it a bit
389
  // ???: return 0 here instead?
390
  while (i == _tx_buffer->tail)
391
    ;
392
        
393
  _tx_buffer->buffer[_tx_buffer->head] = c;
394
  _tx_buffer->head = i;
395
        
396
  sbi(*_ucsrb, _udrie);
397
  
398
  return 1;
399
}
400

    
401
// Preinstantiate Objects //////////////////////////////////////////////////////
402

    
403
#if defined(UBRRH) && defined(UBRRL)
404
  HardwareSerial Serial(&rx_buffer, &tx_buffer, &UBRRH, &UBRRL, &UCSRA, &UCSRB, &UDR, RXEN, TXEN, RXCIE, UDRIE, U2X);
405
#elif defined(UBRR0H) && defined(UBRR0L)
406
  HardwareSerial Serial(&rx_buffer, &tx_buffer, &UBRR0H, &UBRR0L, &UCSR0A, &UCSR0B, &UDR0, RXEN0, TXEN0, RXCIE0, UDRIE0, U2X0);
407
#elif defined(USBCON)
408
  // do nothing - Serial object and buffers are initialized in CDC code
409
#else
410
  #error no serial port defined  (port 0)
411
#endif
412

    
413
#if defined(UBRR1H)
414
  HardwareSerial Serial1(&rx_buffer1, &tx_buffer1, &UBRR1H, &UBRR1L, &UCSR1A, &UCSR1B, &UDR1, RXEN1, TXEN1, RXCIE1, UDRIE1, U2X1);
415
#endif
416
#if defined(UBRR2H)
417
  HardwareSerial Serial2(&rx_buffer2, &tx_buffer2, &UBRR2H, &UBRR2L, &UCSR2A, &UCSR2B, &UDR2, RXEN2, TXEN2, RXCIE2, UDRIE2, U2X2);
418
#endif
419
#if defined(UBRR3H)
420
  HardwareSerial Serial3(&rx_buffer3, &tx_buffer3, &UBRR3H, &UBRR3L, &UCSR3A, &UCSR3B, &UDR3, RXEN3, TXEN3, RXCIE3, UDRIE3, U2X3);
421
#endif
422

    
423
#endif // whole file
424