diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/avr/Kconfig | 4 | ||||
-rw-r--r-- | src/avr/serial.c | 65 |
2 files changed, 38 insertions, 31 deletions
diff --git a/src/avr/Kconfig b/src/avr/Kconfig index 77f002e2..2d3074a3 100644 --- a/src/avr/Kconfig +++ b/src/avr/Kconfig @@ -110,6 +110,10 @@ config SERIAL_BAUD_U2X depends on AVR_SERIAL && !SIMULAVR bool default y +config SERIAL_PORT + int + default 1 if MACH_at90usb1286 || MACH_at90usb646 + default 0 config SIMULAVR depends on MACH_atmega168 || MACH_atmega328 || MACH_atmega644p || MACH_atmega1284p diff --git a/src/avr/serial.c b/src/avr/serial.c index 4b72bf76..4cc2ebc8 100644 --- a/src/avr/serial.c +++ b/src/avr/serial.c @@ -4,66 +4,69 @@ // // This file may be distributed under the terms of the GNU GPLv3 license. -#include <avr/interrupt.h> // USART0_RX_vect +#include <avr/interrupt.h> // USART_RX_vect #include "autoconf.h" // CONFIG_SERIAL_BAUD #include "board/serial_irq.h" // serial_rx_byte #include "sched.h" // DECL_INIT -// Define serial port registers on AT90USB1286 -#if !defined(UCSR0A) && defined(UCSR1A) -#define UCSR0A UCSR1A -#define UCSR0B UCSR1B -#define UCSR0C UCSR1C -#define UBRR0 UBRR1 -#define UDR0 UDR1 -#define UCSZ01 UCSZ11 -#define UCSZ00 UCSZ10 -#define U2X0 U2X1 -#define RXEN0 RXEN1 -#define TXEN0 TXEN1 -#define RXCIE0 RXCIE1 -#define UDRIE0 UDRIE1 -#define USART0_RX_vect USART1_RX_vect -#define USART0_UDRE_vect USART1_UDRE_vect -#endif +// Helper macros for defining serial port aliases +#define AVR_SERIAL_REG1(prefix, id, suffix) prefix ## id ## suffix +#define AVR_SERIAL_REG(prefix, id, suffix) AVR_SERIAL_REG1(prefix, id, suffix) + +// Serial port register aliases +#define UCSRxA AVR_SERIAL_REG(UCSR, CONFIG_SERIAL_PORT, A) +#define UCSRxB AVR_SERIAL_REG(UCSR, CONFIG_SERIAL_PORT, B) +#define UCSRxC AVR_SERIAL_REG(UCSR, CONFIG_SERIAL_PORT, C) +#define UBRRx AVR_SERIAL_REG(UBRR, CONFIG_SERIAL_PORT,) +#define UDRx AVR_SERIAL_REG(UDR, CONFIG_SERIAL_PORT,) +#define UCSZx1 AVR_SERIAL_REG(UCSZ, CONFIG_SERIAL_PORT, 1) +#define UCSZx0 AVR_SERIAL_REG(UCSZ, CONFIG_SERIAL_PORT, 0) +#define U2Xx AVR_SERIAL_REG(U2X, CONFIG_SERIAL_PORT,) +#define RXENx AVR_SERIAL_REG(RXEN, CONFIG_SERIAL_PORT,) +#define TXENx AVR_SERIAL_REG(TXEN, CONFIG_SERIAL_PORT,) +#define RXCIEx AVR_SERIAL_REG(RXCIE, CONFIG_SERIAL_PORT,) +#define UDRIEx AVR_SERIAL_REG(UDRIE, CONFIG_SERIAL_PORT,) -// Define serial port registers on atmega168 / atmega328 #if defined(USART_RX_vect) -#define USART0_RX_vect USART_RX_vect -#define USART0_UDRE_vect USART_UDRE_vect +// The atmega168 / atmega328 doesn't have an ID in the irq names +#define USARTx_RX_vect USART_RX_vect +#define USARTx_UDRE_vect USART_UDRE_vect +#else +#define USARTx_RX_vect AVR_SERIAL_REG(USART, CONFIG_SERIAL_PORT, _RX_vect) +#define USARTx_UDRE_vect AVR_SERIAL_REG(USART, CONFIG_SERIAL_PORT, _UDRE_vect) #endif void serial_init(void) { - UCSR0A = CONFIG_SERIAL_BAUD_U2X ? (1<<U2X0) : 0; + UCSRxA = CONFIG_SERIAL_BAUD_U2X ? (1<<U2Xx) : 0; uint32_t cm = CONFIG_SERIAL_BAUD_U2X ? 8 : 16; - UBRR0 = DIV_ROUND_CLOSEST(CONFIG_CLOCK_FREQ, cm * CONFIG_SERIAL_BAUD) - 1UL; - UCSR0C = (1<<UCSZ01) | (1<<UCSZ00); - UCSR0B = (1<<RXEN0) | (1<<TXEN0) | (1<<RXCIE0) | (1<<UDRIE0); + UBRRx = DIV_ROUND_CLOSEST(CONFIG_CLOCK_FREQ, cm * CONFIG_SERIAL_BAUD) - 1UL; + UCSRxC = (1<<UCSZx1) | (1<<UCSZx0); + UCSRxB = (1<<RXENx) | (1<<TXENx) | (1<<RXCIEx) | (1<<UDRIEx); } DECL_INIT(serial_init); // Rx interrupt - data available to be read. -ISR(USART0_RX_vect) +ISR(USARTx_RX_vect) { - serial_rx_byte(UDR0); + serial_rx_byte(UDRx); } // Tx interrupt - data can be written to serial. -ISR(USART0_UDRE_vect) +ISR(USARTx_UDRE_vect) { uint8_t data; int ret = serial_get_tx_byte(&data); if (ret) - UCSR0B &= ~(1<<UDRIE0); + UCSRxB &= ~(1<<UDRIEx); else - UDR0 = data; + UDRx = data; } // Enable tx interrupts void serial_enable_tx_irq(void) { - UCSR0B |= 1<<UDRIE0; + UCSRxB |= 1<<UDRIEx; } |