Quality RTOS & Embedded Software

 Real time embedded FreeRTOS RSS feed 
Real time embedded FreeRTOS mailing list 
Quick Start Supported MCUs PDF Books Trace Tools Ecosystem TCP & FAT Training




Loading

Use of ISR - STM32 - Freeze

Posted by alexgamo on June 8, 2015

Dear all,

I'm trying to use FreeRTOS 6.0.4 on an STM32F3 Discovery Board, but I encounter some problems.

I want to give a mutex by ISR when I receive a CAN bus message, to wake up another task. I have a second task which permit a LED to blink.

My problem is before the CAN trame is received, the program runs normally, and I see the LED blinks. But when a CAN trame arrives, the ISR wakes up and the program blocks in it. Tasks are stop running, and the LED stops to blink.

Sending and receiving CAN trames are working without use of ISR, only problem is when I try to use ISR. I thought the problem is because of I set wrong priorities but it seems OK for me..

Here's a part of code in FreeRTOSConfig.h :

~~~~~~ :::C

define configUSE_PREEMPTION 1
define configUSEIDLEHOOK 0
define configUSETICKHOOK 0
define configCPUCLOCKHZ ( ( unsigned long ) 72000000 )
define configTICKRATEHZ ( ( portTickType ) 1000 )
define configMAXPRIORITIES ( ( unsigned portBASETYPE ) 10 )
define configMINIMALSTACKSIZE ( ( unsigned short ) 128 )
define configMAXIMALSTACKSIZE ( ( unsigned short ) 8192)
define configTOTALHEAPSIZE ( 30000 )
define configMAXTASKNAME_LEN ( 16 )
define configUSETRACEFACILITY 0
define configUSE16BIT_TICKS 0
define configIDLESHOULDYIELD 1

...

define configKERNELINTERRUPTPRIORITY 255 // 15
define configMAXSYSCALLINTERRUPT_PRIORITY 191 // 11

~~~~~~

The function below is used to configure ISR parameters :

~~~~~~ :::C void CANinitIT(void){ NVICPriorityGroupConfig(NVICPriorityGroup4); NVICInitTypeDef NVICInitStructure; NVICInitStructure.NVICIRQChannel = USBLPCAN1RX0IRQn; NVICInitStructure.NVICIRQChannelPreemptionPriority = 13; NVICInitStructure.NVICIRQChannelSubPriority = 0; NVICInitStructure.NVICIRQChannelCmd = ENABLE; NVICInit(&NVICInitStructure); CANITConfig(CAN1, CANITFMP0, ENABLE); }

~~~~~~

The ISR and the associated task, and the main function, are here :

~~~~~~ :::C xSemaphoreHandle ACKmessageCAN; xSemaphoreHandle message_CAN;

void USBLPCAN1RX0IRQHandler(void) { long yield = 0;

xSemaphoreGiveFromISR(message_CAN, &yield);

    // Only use to debug
/*GPIO_SetBits(GPIOE, GPIO_Pin_11 | GPIO_Pin_10 | GPIO_Pin_9 | GPIO_Pin_8);
vTaskDelay(250);
GPIO_ResetBits(GPIOE, GPIO_Pin_11 | GPIO_Pin_10 | GPIO_Pin_9 | GPIO_Pin_8);
vTaskDelay(250);*/

portEND_SWITCHING_ISR(yield);

}

void RXCAN(void *p) { CANinit(); CANinitIT();

CanRxMsg RxMessage;
RxMessage.Data[0] = 0;

while(1)
{
	if(xSemaphoreTake(message_CAN, (portTickType)0 ))
	{
		CAN_Receive(CAN1, CAN_FIFO0, &RxMessage);
		if(RxMessage.Data[0] == 0x05)
		{
			...
		}
	}
}

}

int main() { SystemInit(); SystemCoreClockUpdate(); // SysTick end of count event each 1ms RCCClocksTypeDef RCCClocks; RCCGetClocksFreq(&RCCClocks); SysTickConfig(RCCClocks.HCLK_Frequency / 1000);

    ...

vSemaphoreCreateBinary(message_CAN);		// Create the semaphore
xSemaphoreTake(message_CAN, 0);        		// Take semaphore after creating it.

    xTaskCreate(RX_CAN,(signed char *) "receive_CAN_task", 20*configMINIMAL_STACK_SIZE, NULL, 1, NULL);
    xTaskCreate(Blink, (signed char *) "blink", 20*configMINIMAL_STACK_SIZE, NULL, 1, NULL);


    vTaskStartScheduler();

    while(1); // the program should never comes here
    return -1;

}

~~~~~~

Maybe I forgot something ? I searched in this forum before to post but I didn't find anything.

Sorry for this long post and my bad English, I'm a french student. Thanks for your help.


Use of ISR - STM32 - Freeze

Posted by rtel on June 8, 2015

Yikes that is an old version. Normally the advice would be to define configASSERT() to have the assert check the interrupt configuration for you - but I don't think that will help in V6.x code. That said, I cannot see anything wrong with what you have posted (thanks for posting useful information!) provided the STM32 in use has 4 priority bits defined.

Can you try changing the semaphore from a mutex to a binary semaphore. You only need change the function used to create the semaphore, nothing else. The reason being that various different FreeRTOS versions have had different rules on giving mutexes from interrupt - the reason being that mutexes use priority inheritance, which has little meaning when they are used from an interrupt. Let me know if that helps.

Regards.


Use of ISR - STM32 - Freeze

Posted by alexgamo on June 10, 2015

Hello,

I was already using binary semaphore in my code, I was wrong when I wrote "I want to give a mutex by ISR", sorry. I tried to comment the "void USBLPCAN1RX0IRQHandler(void)" handler, and I saw the same thing : the program froze when a CAN trame is received.

So I upgraded my version of FreeRTOS to v8.2.1 : same problem.

I defined configASSERT like this :

~~~~~~ :::C

define configASSERT( x ) if( ( x ) == pdFALSE ) { taskDISABLE_INTERRUPTS(); for( ;; ); }

~~~~~~

When I debug, the program stops on this line, in the function xQueueGenericReceive, in the file queue.c :

~~~~~~ :::C configASSERT( !( ( pvBuffer == NULL ) && ( pxQueue->uxItemSize != ( UBaseType_t ) 0U ) ) ); ~~~~~~

Values are : - pvBuffer : 0 - uxItemSize : 8

I don't understand what happen and what I'm doing wrong.


Use of ISR - STM32 - Freeze

Posted by rtel on June 10, 2015

Inside that function it is only valid for the buffer to be NULL, if zero bytes are going to be copied into the buffer (i.e. the buffer is not going to be accessed). If pxQueue->uxItemSize is zero, then no data is going to be copied to the buffer. pxQueue->uxItemSize will be zero, and pvBuffer will be NULL, if the queue is actually being used as a semaphore.

In your case it is correctly detecting that, if the assert didn't catch it, the code would attempt to write 8 bytes to a NULL pointer.

When the code stops on that line, look at the function call stack in the debugger. That should tell you the route through the code taken to get to that point, which will help you debug how it came to be.

Did you create the semaphore before using it?

Regards.


Use of ISR - STM32 - Freeze

Posted by alexgamo on June 11, 2015

I solved my problem.

I changed the handler by this :

~~~~~~ :::C void USBLPCAN1RX0IRQHandler(void) { long yield = pdFALSE;

CAN_Receive(CAN1, CAN_FIFO0, &RxMessage);

if((RxMessage.StdId == 0x000) && (RxMessage.IDE == CAN_ID_STD)
     && (RxMessage.DLC == 1) && (RxMessage.Data[0] == 0x05))
  {
	xSemaphoreGiveFromISR(message_CAN, &yield);
  }

portEND_SWITCHING_ISR(yield);

} ~~~~~~

I realized that, when CAN ITs are enabled (CANITConfig(CAN1, CANITFMP0, ENABLE);), you need to clean FIFO with CANreceive() in the IRQ (maybe I am wrong ? but this is what I'm observing). Else program stops working at the first received message.

This problem was a STM32 functionning problem, not a freeRTOS problem.

The program is now working fine. Thanks !


[ Back to the top ]    [ About FreeRTOS ]    [ Sitemap ]    [ ]




Copyright (C) 2004-2010 Richard Barry. Copyright (C) 2010-2016 Real Time Engineers Ltd.
Any and all data, files, source code, html content and documentation included in the FreeRTOSTM distribution or available on this site are the exclusive property of Real Time Engineers Ltd.. See the files license.txt (included in the distribution) and this copyright notice for more information. FreeRTOSTM and FreeRTOS.orgTM are trade marks of Real Time Engineers Ltd.

Latest News:

FreeRTOS V9.0.0 is now available for download.


Free TCP/IP and file system demos for the RTOS


Sponsored Links

⇓ Now With No Code Size Limit! ⇓
⇑ Free Download Without Registering ⇑


FreeRTOS Partners

ARM Connected RTOS partner for all ARM microcontroller cores

Renesas Electronics Gold Alliance RTOS Partner.jpg

Microchip Premier RTOS Partner

RTOS partner of NXP for all NXP ARM microcontrollers

Atmel RTOS partner supporting ARM Cortex-M3 and AVR32 microcontrollers

STMicro RTOS partner supporting ARM7, ARM Cortex-M3, ARM Cortex-M4 and ARM Cortex-M0

Xilinx Microblaze and Zynq partner

Silicon Labs low power RTOS partner

Altera RTOS partner for Nios II and Cortex-A9 SoC

Freescale Alliance RTOS Member supporting ARM and ColdFire microcontrollers

Infineon ARM Cortex-M microcontrollers

Texas Instruments MCU Developer Network RTOS partner for ARM and MSP430 microcontrollers

Cypress RTOS partner supporting ARM Cortex-M3

Fujitsu RTOS partner supporting ARM Cortex-M3 and FM3

Microsemi (previously Actel) RTOS partner supporting ARM Cortex-M3

Atollic Partner

IAR Partner

Keil ARM Partner

Embedded Artists