131 lines
2.3 KiB
C
131 lines
2.3 KiB
C
#include <libopencm3/stm32/usart.h>
|
|
#include <libopencm3/stm32/gpio.h>
|
|
#include <libopencm3/cm3/nvic.h>
|
|
|
|
#include "pinout.h"
|
|
|
|
#include "uart.h"
|
|
|
|
#define UART_BUFFER_SIZE 128
|
|
static volatile char debugBuffer[UART_BUFFER_SIZE];
|
|
|
|
static volatile uint16_t readPos, writePos;
|
|
static volatile uint8_t bufferFull, bufferEmpty, usartActive;
|
|
|
|
void uart_init(void)
|
|
{
|
|
// initialize the ring buffer
|
|
readPos = 0;
|
|
writePos = 0;
|
|
bufferFull = 0;
|
|
bufferEmpty = 1;
|
|
usartActive = 0;
|
|
|
|
/* Initialize GPIOs */
|
|
|
|
// RX and TX pins
|
|
gpio_mode_setup(UART_PORT, GPIO_MODE_AF, GPIO_PUPD_NONE, UART_TX_PIN | UART_RX_PIN);
|
|
gpio_set_af(UART_PORT, GPIO_AF0, UART_TX_PIN | UART_RX_PIN);
|
|
|
|
// enable interrupt
|
|
nvic_enable_irq(NVIC_USART2_IRQ);
|
|
|
|
/* Setup USART2 parameters. */
|
|
usart_set_baudrate(USART2, 115200);
|
|
usart_set_databits(USART2, 8);
|
|
usart_set_stopbits(USART2, USART_CR2_STOPBITS_1);
|
|
usart_set_mode(USART2, USART_MODE_TX);
|
|
usart_set_parity(USART2, USART_PARITY_NONE);
|
|
usart_set_flow_control(USART2, USART_FLOWCONTROL_NONE);
|
|
|
|
/* Enable the USART. */
|
|
usart_enable(USART2);
|
|
|
|
/* Enable the USART2 TX Interrupt */
|
|
usart_enable_tx_interrupt(USART2);
|
|
usart_enable_tx_complete_interrupt(USART2);
|
|
}
|
|
|
|
|
|
static void uart_transfer(void)
|
|
{
|
|
if(bufferEmpty) {
|
|
usart_disable_tx_interrupt(USART2);
|
|
usartActive = 0;
|
|
return;
|
|
}
|
|
|
|
usart_send(USART2, debugBuffer[readPos]);
|
|
|
|
readPos++;
|
|
if(readPos == UART_BUFFER_SIZE) {
|
|
readPos = 0;
|
|
}
|
|
|
|
if(readPos == writePos) {
|
|
bufferEmpty = 1;
|
|
}
|
|
|
|
bufferFull = 0;
|
|
usart_enable_tx_interrupt(USART2);
|
|
}
|
|
|
|
|
|
void usart2_isr(void)
|
|
{
|
|
if(USART2_ISR & USART_ISR_TXE) {
|
|
uart_transfer();
|
|
}
|
|
|
|
if(USART2_ISR & USART_ISR_TC) {
|
|
USART2_ICR |= USART_ICR_TCCF;
|
|
}
|
|
}
|
|
|
|
|
|
void uart_enqueue(const char *str)
|
|
{
|
|
while(*str) {
|
|
if(bufferFull) {
|
|
break;
|
|
}
|
|
|
|
debugBuffer[writePos] = *str;
|
|
|
|
writePos++;
|
|
if(writePos == UART_BUFFER_SIZE) {
|
|
writePos = 0;
|
|
}
|
|
|
|
if(writePos == readPos) {
|
|
bufferFull = 1;
|
|
}
|
|
|
|
bufferEmpty = 0;
|
|
|
|
str++;
|
|
}
|
|
|
|
if(!usartActive) {
|
|
usartActive = 1;
|
|
//gpio_set(UART_PORT, UART_DE_PIN);
|
|
uart_transfer();
|
|
}
|
|
}
|
|
|
|
|
|
void uart_deepsleep_prepare(void)
|
|
{
|
|
// force the transceiver to RX mode
|
|
//gpio_clear(UART_PORT, UART_DE_PIN);
|
|
}
|
|
|
|
|
|
void uart_deepsleep_resume(void)
|
|
{
|
|
// if a transmission is still in progress, switch to TX mode again
|
|
if(usartActive) {
|
|
//gpio_set(UART_PORT, UART_DE_PIN);
|
|
}
|
|
}
|