1 #include <avr/interrupt.h>
3 #include "ringbuffer.h"
6 #define BIT(n) (1<<(n))
9 #define SERIAL_BUFSIZE 16
13 static RINGBUFFER(rx, SERIAL_BUFSIZE);
14 static RINGBUFFER(tx, SERIAL_BUFSIZE);
15 static uint8_t rx_overrun;
16 #define INTERRUPTS BIT(RXCIE0)
21 void serial_init(uint16_t baud)
23 DDRD = (DDRD&~0x03) | 0x02;
26 baud = (F_CPU/16+baud/2)/baud-1;
30 UCSR0C = BIT(UCSZ00) | BIT(UCSZ01); // 8N1
31 UCSR0B = BIT(RXEN0) | BIT(TXEN0) | INTERRUPTS;
37 return ringbuffer_blocking_pop(rx);
39 while(!(UCSR0A&BIT(RXC0))) ;
44 uint8_t serial_read_available()
47 return ringbuffer_fill(rx);
49 return (UCSR0A&BIT(RXC0))!=0;
53 uint8_t serial_read_overrun()
56 uint8_t o = rx_overrun;
60 return (UCSR0A&BIT(DOR0))!=0;
64 void serial_write(uint8_t c)
67 ringbuffer_blocking_push(tx, c);
68 UCSR0B |= BIT(UDRIE0);
70 while(!(UCSR0A&BIT(UDRE0))) ;
75 uint8_t serial_write_space()
78 return ringbuffer_space(tx);
80 return (UCSR0A&BIT(UDRE0))!=0;
87 if(ringbuffer_fill(tx))
88 UDR0 = ringbuffer_pop(tx);
90 UCSR0B &= ~BIT(UDRIE0);
96 if(!ringbuffer_space(rx))
99 ringbuffer_push(rx, c);