UART ARM Cortex M4 (Tiva C)
/*
This program configures the UART to work with a bit-rate of 115200 bits/seconds.
The system clock is configured to work at 80MHz assisted by PLL.
We first define all register to configure the UART and then perform functions to send and read characters and strings.
*/
#include "TM4C123.h" // Device header
// configure the system to get its clock from the PLL
#define SYSCTL_RIS_R (*((volatile unsigned long *)0x400FE050))
#define SYSCTL_RCC_R (*((volatile unsigned long *)0x400FE060))
#define SYSCTL_RCC2_R (*((volatile unsigned long *)0x400FE070))
// Define UART registers
#define GPIO_PORTA_AFSEL_R (*((volatile unsigned long *)0x40004420))
#define GPIO_PORTA_DEN_R (*((volatile unsigned long *)0x4000451C))
#define GPIO_PORTA_AMSEL_R (*((volatile unsigned long *)0x40004528))
#define GPIO_PORTA_PCTL_R (*((volatile unsigned long *)0x4000452C))
#define UART0_DR_R (*((volatile unsigned long *)0x4000C000))
#define UART0_FR_R (*((volatile unsigned long *)0x4000C018))
#define UART0_IBRD_R (*((volatile unsigned long *)0x4000C024))
#define UART0_FBRD_R (*((volatile unsigned long *)0x4000C028))
#define UART0_LCRH_R (*((volatile unsigned long *)0x4000C02C))
#define UART0_CTL_R (*((volatile unsigned long *)0x4000C030))
#define UART_FR_TXFF 0x00000020 // UART Transmit FIFO Full
#define UART_FR_RXFE 0x00000010 // UART Receive FIFO Empty
#define SYSCTL_RCGC1_R (*((volatile unsigned long *)0x400FE104))
#define SYSCTL_RCGC2_R (*((volatile unsigned long *)0x400FE108))
void PLL_Init(void);
void UART_Init(void);
void UART_Char_Output(unsigned char data);
unsigned char UART_Char_Input(void);
void UART_Write_String(char *p);
__asm void
Delay(unsigned long n)
{
SUBS R0, #1
BNE Delay
BX LR ;//the link register is providing the address to //branch to.
}
int main(void){
PLL_Init();
UART_Init();
while(1){
UART_Char_Output('a');
Delay(13333333); // delay ~0.5 sec at 80 MHz
while(UART_Char_Input()!='b');
UART_Write_String("you pressed the character b");
}
}
void PLL_Init(void){
// 0) Use RCC2
SYSCTL_RCC2_R |= 0x80000000; // USERCC2
// 1) bypass PLL while initializing
SYSCTL_RCC2_R |= 0x00000800; // BYPASS2, PLL bypass
// 2) select the crystal value and oscillator source
SYSCTL_RCC_R = (SYSCTL_RCC_R &~0x000007C0) // clear XTAL field, bits 10-6
+ 0x00000540; // 10101, configure for 16 MHz crystal
SYSCTL_RCC2_R &= ~0x00000070; // configure for main oscillator source 10001111
// 3) activate PLL by clearing PWRDN
SYSCTL_RCC2_R &= ~0x00002000;
// 4) set the desired system divider
SYSCTL_RCC2_R |= 0x40000000; // use 400 MHz PLL, DIV400
SYSCTL_RCC2_R = (SYSCTL_RCC2_R&~ 0x1FC00000) // clear system clock divider
+ (4<<22); // configure for 80 MHz clock, 400/(4+1) = 80MHz
// 5) wait for the PLL to lock by polling PLLLRIS
while((SYSCTL_RIS_R&0x00000040)==0){}; // wait for PLLRIS bit
// 6) enable use of PLL by clearing BYPASS
SYSCTL_RCC2_R &= ~0x00000800;
}
void UART_Init(void){
SYSCTL_RCGC1_R |= 0x01; // activate UART0
SYSCTL_RCGC2_R |= 0x01; // activate port A
UART0_CTL_R &= ~0x01; // disable UART
UART0_IBRD_R = 43; // IBRD = int(80,000,000 / (16 * 115,200)) = int(43.40278)
UART0_FBRD_R = 26; // FBRD = round(0.40278 * 64) = 26
// 8 bit word length (no parity bits, one stop bit, FIFOs)
UART0_LCRH_R = 0x70;// 0x01110000
//UART0_CTL_R |= UART_CTL_UARTEN; // enable UART, 0x00000001 // UART Enable
UART0_CTL_R |= 0x01; // enable UART, 0x00000001 // UART Enable
GPIO_PORTA_AFSEL_R |= 0x03; // enable alt funct on PA1-0
GPIO_PORTA_DEN_R |= 0x03; // enable digital I/O on PA1-0
// configure PA1-0 as UART
GPIO_PORTA_PCTL_R = (GPIO_PORTA_PCTL_R&0xFFFFFF00)+0x00000011;
GPIO_PORTA_AMSEL_R &= ~0x03; // disable analog functionality on PA
}
void UART_Char_Output(unsigned char data){
while((UART0_FR_R & UART_FR_TXFF) != 0);
UART0_DR_R = data;
}
unsigned char UART_Char_Input(void){
while((UART0_FR_R & UART_FR_RXFE) != 0);
return((unsigned char)(UART0_DR_R & 0xFF));
}
void UART_Write_String(char *p){
while(*p){
UART_Char_Output(*p);
p++;
}
}
No hay comentarios.:
Publicar un comentario