2016-11-22 01:11 PM
Hi guys, I'm facing out some problems and i wonder if some of you can give some of your wisdom.
Here are some inputs:MCU: STM32L053 (Host)
GSM Module: handles GSM network connecctions and notifify via UART the MCU. It also receives MCU commands.
UART-USB converters: They let me monitor what happens in each pin (RX and TX) by means of hiperterminals
UART TX +DMA for transmissions of AT commands
UART RX for reception of messages of different sizes.
I don t use the hal library for the uart IRQ. (unfortunately, ST doesn't provide std firmware neither! So i ve )
My purpose is as follows:
trigger 2 different threads depending on a received buffer pattern. For this, i will use a preemptive scheduler (FreeRTOS V8.2.3+ cmis os interface).Here are some code snippets with brief some brief explanation:static void EmergencyButtonEventProcess(void)
{
DelSMS();
}
void DelSMS(void)
{
Send_AT_Command(eDelete_All_Sms);
}
static void Send_AT_Command(AT_CommandId_tE Cmd_Id_tE)
{
...
U8 source[MAX_SIZE_FOR_BUFFER];
switch(Cmd_Id_tE)
{
case eCheck_Gsm_Module:
strcpy(source, CHECK_GSM_MODULE);
sizeOfBuffer = LibTyp_StrLen(&source);
HUart_Transmit( HUart_eUart2, source,
sizeOfBuffer );
break;
case eRead_SMS:
strcpy(source, READ_SMS_COMAND);
sizeOfBuffer = LibTyp_StrLen(&source);
HUart_Transmit( HUart_eUart2, source,
sizeOfBuffer );
break;
case eDelete_All_Sms:
strcpy(source, DELETE_ALL_SMS_COMAND);
sizeOfBuffer = LibTyp_StrLen(&source);
HUart_Transmit( HUart_eUart2, source,
sizeOfBuffer );
break;
default:
break;
}
}
These functions are called when a button is pressed and after a debounce time has passed. I used the IRQ of a GPIO and IRQ of a timer.When the button is pressed more than 5 seconds a command is sent to the GSM module and this one responds with an OK. The transmition is done with a uart peripheral of the MCU and DMA. All works correctly and as expected. In this case i have not used any of the OS services but maybe in the future, i would sync with a semaphore. I don't think this is necessary.void USART2_IRQHandler (void)
{
//Store DR
//Detect patern and store it in appropiate buffers...
if(TX_RX_Buffer_Flag_tb ==TRUE)
{
... //more pattern tests...
//store TX_RX_Buffer[]
TX_RX_Buffer_Flag_tb =FALSE;
osSignalSet(ThreadId_2, BIT_2 );
}
if(RX_Buffer_Flag_tb==TRUE)
{
... more process
//store RX_Buffer[]
osSignalSet(ThreadId_1, BIT_1);
}
}
In the UART IRQ, i fill up 2 buffers depending on the start of the message. Basically, we have 2 types:TX_RX_Buffer[] = ''AT+something
\n'' pattern corresponds to a answer of the gsm module after a command has been sent.
RX_Buffer[] = ''\r something \n'' pattern corresponds to a notification of the gsm module.
A event flag is set and notified to the OS. A related thread (depending on the buffer patern detected) has to be triggered
static void Thread1_RX_Buffer(void const *argument)
{
osEvent event;
for(;;)
{
event = osSignalWait( BIT_1, osWaitForever);
if(event.value.signals == BIT_1)
{
Send_AT_Command(eRead_SMS); //UART Transmit with DMA is called
}
}
static void Thread2_TX_RX_Buffer (void const *argument)
{
(void) argument;
osEvent event;
RelayId_tE Id_tE;
for(;;)
{
event = osSignalWait( BIT_2 , osWaitForever);
if(event.value.signals == (BIT_2 ))
{
Send_AT_Command(eMakeCall); //UART Transmit with DMA is called
}
}
}
Here the Threads are triggered as expected. The problem is that only 3 characters are transmitted and the rest are incoherent (i.eAT+C����[02][00]).
On the other hand, the same transmission function is called when the button is pressed and all is ok. I think that the tick interrupt related to the OS corrupts the UART DMA transmission. How can i sort this out ? Any suggestions? PS: Any suggestions are welcome concerning the design/implementation. There are still some improvements to do like copy the buffer for deferred processing .... #freertos-+uart-tx-dma+-uart-rx