lm4f: Add UART echo by interrupt example

Nothing fancy, just a demonstration of the using the UART interrupt service
routine.

Signed-off-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
This commit is contained in:
Alexandru Gagniuc
2013-05-08 11:39:38 -05:00
parent 1a160d794b
commit 5036510da1
3 changed files with 136 additions and 0 deletions

View File

@@ -0,0 +1,25 @@
##
## This file is part of the libopencm3 project.
##
## Copyright (C) 2012 Alexandru Gagniuc <mr.nuke.me@gmail.com>
##
## This library is free software: you can redistribute it and/or modify
## it under the terms of the GNU Lesser General Public License as published by
## the Free Software Foundation, either version 3 of the License, or
## (at your option) any later version.
##
## This library is distributed in the hope that it will be useful,
## but WITHOUT ANY WARRANTY; without even the implied warranty of
## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
## GNU Lesser General Public License for more details.
##
## You should have received a copy of the GNU Lesser General Public License
## along with this library. If not, see <http://www.gnu.org/licenses/>.
##
BINARY = uart_echo_interrupt
LDSCRIPT = ../ek-lm4f120xl.ld
include ../../Makefile.include

View File

@@ -0,0 +1,18 @@
------------------------------------------------------------------------------
README
------------------------------------------------------------------------------
This example demonstrates the ease of setting up the UART with libopencm3, and
using UART interrupts. UART echo is achieved by echoing back received characters
from within the interrupt service routine. This has the advantage over using
blocking reads and writes that the main program loop is freed for other tasks.
The UART is set up as 921600-8N1.
PA0 is the Rx pin, and PA1 is the Tx pin (from the LM4F perspective). These
pins are connected to the CDCACM interface on the debug chip, so no hardware is
necessary to test this example. Just connect the debug USB cable and use a
terminal program to open the ACM port with 921600-8N1.
For example:
$ picocom /dev/ttyACM0 -b921600

View File

@@ -0,0 +1,93 @@
/*
* This file is part of the libopencm3 project.
*
* Copyright (C) 2011 Gareth McMullin <gareth@blacksphere.co.nz>
* Copyright (C) 2012 Alexandru Gagniuc <mr.nuke.me@gmail.com>
*
* This library is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this library. If not, see <http://www.gnu.org/licenses/>.
*/
#include <libopencm3/lm4f/systemcontrol.h>
#include <libopencm3/lm4f/gpio.h>
#include <libopencm3/lm4f/uart.h>
#include <libopencm3/lm4f/nvic.h>
static void uart_setup(void)
{
u32 pins;
/* Enable GPIOA in run mode. */
periph_clock_enable(RCC_GPIOA);
/* Configure PA0 and PA1 as alternate function pins */
pins = GPIO0 | GPIO1;
GPIO_AFSEL(GPIOA) |= pins;
GPIO_DEN(GPIOA) |= pins;
/* PA0 and PA1 are muxed to UART0 during power on, by default */
/* Enable the UART clock */
periph_clock_enable(RCC_UART0);
/* We need a brief delay before we can access UART config registers */
__asm__("nop");
/* Disable the UART while we mess with its setings */
uart_disable(UART0);
/* Configure the UART clock source as precision internal oscillator */
uart_clock_from_piosc(UART0);
/* Set communication parameters */
uart_set_baudrate(UART0, 921600);
uart_set_databits(UART0, 8);
uart_set_parity(UART0, UART_PARITY_NONE);
uart_set_stopbits(UART0, 1);
/* Now that we're done messing with the settings, enable the UART */
uart_enable(UART0);
}
static void uart_irq_setup(void)
{
/* Gimme and RX interrupt */
uart_enable_rx_interrupt(UART0);
/* Make sure the interrupt is routed through the NVIC */
nvic_enable_irq(NVIC_UART0_IRQ);
}
/*
* uart0_isr is declared as a weak function. When we override it here, the
* libopencm3 build system takes care that it becomes our UART0 ISR.
*/
void uart0_isr(void)
{
u8 rx;
u32 irq_clear = 0;
if (uart_is_interrupt_source(UART0, UART_INT_RX)) {
rx = uart_recv(UART0);
uart_send(UART0, rx);
irq_clear |= UART_INT_RX;
}
uart_clear_interrupt_flag(UART0, irq_clear);
}
int main(void)
{
uart_setup();
uart_irq_setup();
/*
* Not worrying about the UART here.
*/
while (1) {
/* Do some other task */
}
return 0;
}