Tool/software: TI-RTOS
Hey, every one, I'm facing some problems with TI-RTOS. I'm trying to change the state of an LED(an onboard LED) by receiving characters on UART5, so, when some character arrives on UART5 RX the state of the LED is switched(On -->Off and Off --> On). To accomplish this I'm using TI-RTOS, the idea is basically use an HWI to detect the character in RX and use a Swi to switch the LED, here is the code :
/*Tivaware Drivers*/
#include <stdint.h>
#include <stdbool.h>
#include "inc/hw_types.h"
#include "inc/hw_memmap.h"
#include "driverlib/sysctl.h"
#include "driverlib/gpio.h"
#include "inc/hw_ints.h"
#include "driverlib/interrupt.h"
#include "driverlib/uart.h"
#include "driverlib/pin_map.h"
#define WS_UART_BAUD_RATE 115200
/*BIOS include headers*/
#include <xdc/std.h> /*xdc standards*/
#include <ti/sysbios/BIOS.h> /*includes Bios_start*/
#include <xdc/runtime/Log.h> /*includes LogInfo()*/
#include <xdc/runtime/System.h> /*UIA functions*/
#include <ti/sysbios/hal/Hwi.h>
#include <xdc/runtime/Error.h>
#include <ti/sysbios/knl/Swi.h>
/*globals*/
uint32_t g_ui32SysClock;
Swi_Handle uartSwi;
/*Function prototypes*/
void system_start(void);
void uart5_isr(void);
void ledToggle(void);
void create_swi(void);
void ws_init_serial(uint32_t system_clock, void (*pfnHandler) (void));
void main(void){
system_start();
BIOS_start();
}
void system_start(void){
/* Set the clocking to run at 120MHz */
g_ui32SysClock= SysCtlClockFreqSet((SYSCTL_XTAL_25MHZ |
SYSCTL_OSC_MAIN | SYSCTL_USE_PLL |
SYSCTL_CFG_VCO_480), 120000000);
/*Enabling and configuring GPIO PORT*/
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPION);
GPIOPinTypeGPIOOutput(GPIO_PORTN_BASE, GPIO_PIN_1);
/*Turn on the LED*/
GPIOPinWrite(GPIO_PORTN_BASE, GPIO_PIN_1, 0x00);
ws_init_serial(g_ui32SysClock, uart5_isr);
//software interrupt
create_swi();
}
void ws_init_serial(uint32_t system_clock, void (*pfnHandler)(void)){
/*Enabling Peripherals*/
SysCtlPeripheralEnable(SYSCTL_PERIPH_UART5);
SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOC);
/*Setting Up pins*/
GPIOPinConfigure(GPIO_PC6_U5RX);
GPIOPinConfigure(GPIO_PC7_U5TX);
GPIOPinTypeUART(GPIO_PORTC_BASE, GPIO_PIN_6 | GPIO_PIN_7);
/*UART Configurations*/
UARTConfigSetExpClk(UART5_BASE,system_clock,WS_UART_BAUD_RATE,
(UART_CONFIG_WLEN_8 | UART_CONFIG_STOP_ONE | UART_CONFIG_PAR_NONE));
/*Setting up the UART HWI*/
Hwi_Handle myHwi;
Error_Block eb;
/*starting the error block*/
Error_init(&eb);
/*starting the HWI object*/
myHwi = Hwi_create(74, pfnHandler, NULL, &eb);
if (myHwi == NULL) {
System_abort("UART HWI creation failed");
}
/*Enable uart interruptions*/
IntEnable(INT_UART5);
UARTIntEnable(UART5_BASE, (UART_INT_RX | UART_INT_RT));
}
/*This function is used to trigger the swi*/
void uart5_isr(void){
uint32_t ui32Status;
/*Get the interrrupt status.*/
ui32Status = UARTIntStatus(UART5_BASE, true);
/*Clear the asserted interrupts.*/
UARTIntClear(UART5_BASE, ui32Status);
/*posting the Swi*/
Swi_post(uartSwi);
}
void create_swi(void){
Error_Block eb;
Error_init(&eb);
uartSwi = Swi_create(ledToggle,NULL,&eb);
if (uartSwi == NULL) {
System_abort("UART SWI creation failed");
}
}
void ledToggle(void){
if(GPIOPinRead(GPIO_PORTN_BASE, GPIO_PIN_1)) /*if LED is on*/
{
GPIOPinWrite(GPIO_PORTN_BASE, GPIO_PIN_1, 0x00); /*Turn it off*/
}
else
{
GPIOPinWrite(GPIO_PORTN_BASE, GPIO_PIN_1, GPIO_PIN_1); /*turn*/
}
}
The code works well only when I receive the first character, when I send another ones the led doesn't switch.