cancel
Showing results for 
Search instead for 
Did you mean: 

Inserting Breakpoint after Execution hangs when initializing Mutex or Semaphore in FreeRTOS

victor.b
Associate II

Hi,

I am using the STM32MP157C-DK2 and so far i manged to make FREERTOS work flawlessly with OpenAMP and the tracing printf functions. I can insert breakpoint at any point without a problem. However, i start having issues when i declare a semaphore or a mutex in the function MX_FREERTOS_Init().

Here is my main.c file:

/**
  ******************************************************************************
  * @file           : main.c
  * @brief          : Main program body
  ******************************************************************************
 */
/* Includes ------------------------------------------------------------------*/
#include "main.h"
#include "cmsis_os.h"
#include "ipcc.h"
#include "openamp.h"
#include "gpio.h"
 
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "stm32mp15xx_disco.h"
#include "log.h"
 
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
void MX_FREERTOS_Init(void);
 
/**
  * @brief  The application entry point.
  * @retval int
  */
int main(void)
{
  /* MCU Configuration--------------------------------------------------------*/
  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();
 
  if(IS_ENGINEERING_BOOT_MODE())
	{
	  SystemClock_Config();
	}
 
  /* IPCC initialisation */
   MX_IPCC_Init();
 
  /* OpenAmp initialisation ---------------------------------*/
  MX_OPENAMP_Init(RPMSG_REMOTE, NULL);
 
  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  __HAL_RCC_HSEM_CLK_ENABLE();
  BSP_LED_Init(LED7);
  BSP_LED_Init(LED5);
 
  /* Call init function for freertos objects (in freertos.c) */
  MX_FREERTOS_Init(); 
 
  /* Start scheduler */
  osKernelStart();
  
  /* We should never get here as control is now taken by the scheduler */
 
  /* Infinite loop */
  while (1)
  {
  }
}
 
/**
  * @brief System Clock Configuration
  * @retval None
  */
void SystemClock_Config(void)
{
  RCC_OscInitTypeDef RCC_OscInitStruct = {0};
  RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
  RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};
 
  /** Configure LSE Drive Capability 
  */
  HAL_PWR_EnableBkUpAccess();
  __HAL_RCC_LSEDRIVE_CONFIG(RCC_LSEDRIVE_MEDIUMHIGH);
  /** Initializes the CPU, AHB and APB busses clocks 
  */
  RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI|RCC_OSCILLATORTYPE_LSI
                              |RCC_OSCILLATORTYPE_HSE|RCC_OSCILLATORTYPE_LSE;
  RCC_OscInitStruct.HSEState = RCC_HSE_BYPASS_DIG;
  RCC_OscInitStruct.LSEState = RCC_LSE_ON;
  RCC_OscInitStruct.HSIState = RCC_HSI_ON;
  RCC_OscInitStruct.HSICalibrationValue = 16;
  RCC_OscInitStruct.HSIDivValue = RCC_HSI_DIV1;
  RCC_OscInitStruct.LSIState = RCC_LSI_ON;
  RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL.PLLSource = RCC_PLL12SOURCE_HSE;
  RCC_OscInitStruct.PLL.PLLM = 3;
  RCC_OscInitStruct.PLL.PLLN = 81;
  RCC_OscInitStruct.PLL.PLLP = 1;
  RCC_OscInitStruct.PLL.PLLQ = 2;
  RCC_OscInitStruct.PLL.PLLR = 2;
  RCC_OscInitStruct.PLL.PLLFRACV = 0x800;
  RCC_OscInitStruct.PLL.PLLMODE = RCC_PLL_FRACTIONAL;
  RCC_OscInitStruct.PLL.RPDFN_DIS = RCC_RPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL.TPDFN_DIS = RCC_TPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL2.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL2.PLLSource = RCC_PLL12SOURCE_HSE;
  RCC_OscInitStruct.PLL2.PLLM = 3;
  RCC_OscInitStruct.PLL2.PLLN = 66;
  RCC_OscInitStruct.PLL2.PLLP = 2;
  RCC_OscInitStruct.PLL2.PLLQ = 1;
  RCC_OscInitStruct.PLL2.PLLR = 1;
  RCC_OscInitStruct.PLL2.PLLFRACV = 0x1400;
  RCC_OscInitStruct.PLL2.PLLMODE = RCC_PLL_FRACTIONAL;
  RCC_OscInitStruct.PLL2.RPDFN_DIS = RCC_RPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL2.TPDFN_DIS = RCC_TPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL3.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL3.PLLSource = RCC_PLL3SOURCE_HSE;
  RCC_OscInitStruct.PLL3.PLLM = 2;
  RCC_OscInitStruct.PLL3.PLLN = 34;
  RCC_OscInitStruct.PLL3.PLLP = 2;
  RCC_OscInitStruct.PLL3.PLLQ = 17;
  RCC_OscInitStruct.PLL3.PLLR = 37;
  RCC_OscInitStruct.PLL3.PLLRGE = RCC_PLL3IFRANGE_1;
  RCC_OscInitStruct.PLL3.PLLFRACV = 6660;
  RCC_OscInitStruct.PLL3.PLLMODE = RCC_PLL_FRACTIONAL;
  RCC_OscInitStruct.PLL3.RPDFN_DIS = RCC_RPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL3.TPDFN_DIS = RCC_TPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL4.PLLState = RCC_PLL_ON;
  RCC_OscInitStruct.PLL4.PLLSource = RCC_PLL4SOURCE_HSE;
  RCC_OscInitStruct.PLL4.PLLM = 4;
  RCC_OscInitStruct.PLL4.PLLN = 99;
  RCC_OscInitStruct.PLL4.PLLP = 6;
  RCC_OscInitStruct.PLL4.PLLQ = 8;
  RCC_OscInitStruct.PLL4.PLLR = 8;
  RCC_OscInitStruct.PLL4.PLLRGE = RCC_PLL4IFRANGE_0;
  RCC_OscInitStruct.PLL4.PLLFRACV = 0;
  RCC_OscInitStruct.PLL4.PLLMODE = RCC_PLL_INTEGER;
  RCC_OscInitStruct.PLL4.RPDFN_DIS = RCC_RPDFN_DIS_DISABLED;
  RCC_OscInitStruct.PLL4.TPDFN_DIS = RCC_TPDFN_DIS_DISABLED;
  if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
  /** RCC Clock Config 
  */
  RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_ACLK
                              |RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2
                              |RCC_CLOCKTYPE_PCLK3|RCC_CLOCKTYPE_PCLK4
                              |RCC_CLOCKTYPE_PCLK5|RCC_CLOCKTYPE_MPU;
  RCC_ClkInitStruct.MPUInit.MPU_Clock = RCC_MPUSOURCE_PLL1;
  RCC_ClkInitStruct.MPUInit.MPU_Div = RCC_MPU_DIV2;
  RCC_ClkInitStruct.AXISSInit.AXI_Clock = RCC_AXISSOURCE_PLL2;
  RCC_ClkInitStruct.AXISSInit.AXI_Div = RCC_AXI_DIV1;
  RCC_ClkInitStruct.MCUInit.MCU_Clock = RCC_MCUSSOURCE_PLL3;
  RCC_ClkInitStruct.MCUInit.MCU_Div = RCC_MCU_DIV1;
  RCC_ClkInitStruct.APB4_Div = RCC_APB4_DIV2;
  RCC_ClkInitStruct.APB5_Div = RCC_APB5_DIV4;
  RCC_ClkInitStruct.APB1_Div = RCC_APB1_DIV2;
  RCC_ClkInitStruct.APB2_Div = RCC_APB2_DIV2;
  RCC_ClkInitStruct.APB3_Div = RCC_APB3_DIV2;
 
  if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct) != HAL_OK)
  {
    Error_Handler();
  }
  PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_USBO|RCC_PERIPHCLK_DDRPHYC
                              |RCC_PERIPHCLK_SAI2|RCC_PERIPHCLK_RTC
                              |RCC_PERIPHCLK_LTDC|RCC_PERIPHCLK_UART24
                              |RCC_PERIPHCLK_SPI23|RCC_PERIPHCLK_SDMMC12
                              |RCC_PERIPHCLK_I2C12|RCC_PERIPHCLK_ADC
                              |RCC_PERIPHCLK_I2C46|RCC_PERIPHCLK_CEC
                              |RCC_PERIPHCLK_RNG1|RCC_PERIPHCLK_CKPER;
  PeriphClkInit.I2c12ClockSelection = RCC_I2C12CLKSOURCE_HSI;
  PeriphClkInit.I2c46ClockSelection = RCC_I2C46CLKSOURCE_HSI;
  PeriphClkInit.Sai2ClockSelection = RCC_SAI2CLKSOURCE_PLL3_Q;
  PeriphClkInit.Spi23ClockSelection = RCC_SPI23CLKSOURCE_PLL3_Q;
  PeriphClkInit.Uart24ClockSelection = RCC_UART24CLKSOURCE_HSI;
  PeriphClkInit.EthClockSelection = RCC_ETHCLKSOURCE_PLL4;
  PeriphClkInit.DsiClockSelection = RCC_DSICLKSOURCE_PHY;
  PeriphClkInit.CkperClockSelection = RCC_CKPERCLKSOURCE_HSE;
  PeriphClkInit.Rng1ClockSelection = RCC_RNG1CLKSOURCE_LSI;
  PeriphClkInit.UsbphyClockSelection = RCC_USBPHYCLKSOURCE_HSE;
  PeriphClkInit.UsboClockSelection = RCC_USBOCLKSOURCE_PHY;
  PeriphClkInit.CecClockSelection = RCC_CECCLKSOURCE_LSE;
  PeriphClkInit.Lptim1ClockSelection = RCC_LPTIM1CLKSOURCE_OFF;
  PeriphClkInit.Lptim23ClockSelection = RCC_LPTIM23CLKSOURCE_OFF;
  PeriphClkInit.Lptim45ClockSelection = RCC_LPTIM45CLKSOURCE_OFF;
  PeriphClkInit.AdcClockSelection = RCC_ADCCLKSOURCE_PER;
  PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSE;
  PeriphClkInit.TIMG1PresSelection = RCC_TIMG1PRES_DEACTIVATED;
  PeriphClkInit.TIMG2PresSelection = RCC_TIMG2PRES_DEACTIVATED;
  if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK)
  {
    Error_Handler();
  }
  /** Set the HSE division factor for RTC clock 
  */
  __HAL_RCC_RTC_HSEDIV(24);
}
 

And here is my app_freertos.c

1 ACCEPTED SOLUTION

Accepted Solutions
PatrickF
ST Employee

Hello,

could you please precise if you are using SW4STM32 (i.e. GDB/OpenOCD debug) or another debugger ?

There is a separate thread which sound similar : https://community.st.com/s/question/0D50X0000B422in/stm32mp1-freertos-debug-issue

Is reducing the optimization level solve your issue ?

Seems linked to the way GDB manage the debug and the way FreeRTOS manage the stack pointers.

In order to give better visibility on the answered topics, please click on 'Accept as Solution' on the reply which solved your issue or answered your question.

View solution in original post

5 REPLIES 5
victor.b
Associate II

And here is my app_freertos.c:

/**
  ******************************************************************************
  * File Name          : app_freertos.c
  * Description        : Code for freertos applications
  ******************************************************************************
*/
/* Includes ------------------------------------------------------------------*/
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include "cmsis_os.h"
 
/* Private includes ----------------------------------------------------------*/  
#include "stm32mp15xx_disco.h"
#include "log.h"
#include "openamp.h"
#include <stdio.h>
 
/* Private define ------------------------------------------------------------*/
#define MAX_BUFFER_SIZE RPMSG_BUFFER_SIZE
 
/* Private variables ---------------------------------------------------------*/
VIRT_UART_HandleTypeDef hvuart0;
 
__IO FlagStatus VirtUart0RxMsg = RESET;
uint8_t VirtUart0ChannelBuffRx[MAX_BUFFER_SIZE];
uint16_t VirtUart0ChannelRxSize = 0;
 
osThreadId TaskIdleHandle;
osThreadId TaskLedBlinkHandle;
osThreadId TaskVUART0Handle;
osMessageQId QueueTxMP1Handle;
osMessageQId QueueRxMP1Handle;
osMutexId myMutex01Handle;
osSemaphoreId myBinarySem01Handle;
 
/* Private function prototypes -----------------------------------------------*/
void VIRT_UART0_RxCpltCallback(VIRT_UART_HandleTypeDef *huart);
 
void StartTaskIdle(void const * argument);
void StartTaskLedBlink(void const * argument);
void StartTaskVUART0(void const * argument);
 
void MX_FREERTOS_Init(void); /* (MISRA C 2004 rule 8.1) */
 
/* GetIdleTaskMemory prototype (linked to static allocation support) */
void vApplicationGetIdleTaskMemory( StaticTask_t **ppxIdleTaskTCBBuffer, StackType_t **ppxIdleTaskStackBuffer, uint32_t *pulIdleTaskStackSize );
 
static StaticTask_t xIdleTaskTCBBuffer;
static StackType_t xIdleStack[configMINIMAL_STACK_SIZE];
  
void vApplicationGetIdleTaskMemory( StaticTask_t **ppxIdleTaskTCBBuffer, StackType_t **ppxIdleTaskStackBuffer, uint32_t *pulIdleTaskStackSize )
{
  *ppxIdleTaskTCBBuffer = &xIdleTaskTCBBuffer;
  *ppxIdleTaskStackBuffer = &xIdleStack[0];
  *pulIdleTaskStackSize = configMINIMAL_STACK_SIZE;
  /* place for user code */
}                   
 
/**
  * @brief  FreeRTOS initialization
  * @param  None
  * @retval None
  */
void MX_FREERTOS_Init(void) {
  osStatus status;
 
  /* Create the mutex(es) */
  /* definition and creation of myMutex01 */
  osMutexDef(myMutex01);
  myMutex01Handle = osMutexCreate(osMutex(myMutex01));
  //status = osMutexDelete (myMutex01Handle);
  //if(status != osOK)
  //{
  //	  log_err("Mutex delete failed");
  //}
 
  /* Create the semaphores(s) */
  /* definition and creation of myBinarySem01 */
  osSemaphoreDef(myBinarySem01);
  myBinarySem01Handle = osSemaphoreCreate(osSemaphore(myBinarySem01), 1);
  //status = osSemaphoreDelete (myBinarySem01Handle);
  //if(status != osOK)
  //{
  //	  log_err("Semaphore delete failed");
  //}
 
  /* Create the queue(s) */
  /* definition and creation of QueueTxMP1 */
  osMessageQDef(QueueTxMP1, 128, uint8_t);
  QueueTxMP1Handle = osMessageCreate(osMessageQ(QueueTxMP1), NULL);
 
  /* definition and creation of QueueRxMP1 */
  osMessageQDef(QueueRxMP1, 128, uint8_t);
  QueueRxMP1Handle = osMessageCreate(osMessageQ(QueueRxMP1), NULL);
 
  /* Create the thread(s) */
  /* definition and creation of TaskIdle */
  osThreadDef(TaskIdle, StartTaskIdle, osPriorityIdle, 0, 128);
  TaskIdleHandle = osThreadCreate(osThread(TaskIdle), NULL);
 
  /* definition and creation of TaskLedBlink */
  osThreadDef(TaskLedBlink, StartTaskLedBlink, osPriorityNormal, 0, 128);
  TaskLedBlinkHandle = osThreadCreate(osThread(TaskLedBlink), NULL);
 
  /* definition and creation of TaskVUART0 */
  osThreadDef(TaskVUART0, StartTaskVUART0, osPriorityNormal, 0, 128);
  TaskVUART0Handle = osThreadCreate(osThread(TaskVUART0), NULL);
}
 
/**
  * @brief  Function implementing the TaskIdle thread.
  * @param  argument: Not used 
  * @retval None
  */
void StartTaskIdle(void const * argument)
{
  /* Infinite loop */
  for(;;)
  {
    osDelay(1);
  }
}
 
/**
* @brief Function implementing the TaskLedBlink thread.
* @param argument: Not used
* @retval None
*/
void StartTaskLedBlink(void const * argument)
{
  log_info("TaskLedBlink Started");
 
  log_info("TaskLedBlink Initialization Complete");
  /* Infinite loop */
  for(;;)
  {
	  BSP_LED_Toggle(LED7);
	  osDelay(100);
  }
}
 
/**
* @brief Function implementing the TaskVUART0 thread.
* @param argument: Not used
* @retval None
*/
void StartTaskVUART0(void const * argument)
{
	log_info("TaskVUART0 Started");
	if (VIRT_UART_Init(&hvuart0) != VIRT_UART_OK) {
		log_err("VIRT_UART_Init UART0 failed");
		Error_Handler();
	}
	/*Need to register callback for message reception by channels*/
	if (VIRT_UART_RegisterCallback(&hvuart0, VIRT_UART_RXCPLT_CB_ID,
			VIRT_UART0_RxCpltCallback) != VIRT_UART_OK) {
		log_err("VIRT_UART_RegisterCallback UART0 failed");
		Error_Handler();
	}
	log_info("TaskVUART0 Initialization Complete");
  /* Infinite loop */
  for(;;)
  {
	OPENAMP_check_for_message();
	if (VirtUart0RxMsg) {
		VirtUart0RxMsg = RESET;
		VIRT_UART_Transmit(&hvuart0, VirtUart0ChannelBuffRx, VirtUart0ChannelRxSize);
	}
    osDelay(1);
  }
}
 
/* Private application code --------------------------------------------------*/
void VIRT_UART0_RxCpltCallback(VIRT_UART_HandleTypeDef *huart)
{
    log_info("Msg received on VIRTUAL UART0 channel:  %s", (char *) huart->pRxBuffPtr);
    /* copy received msg in a variable to sent it back to master processor in main infinite loop*/
    VirtUart0ChannelRxSize = huart->RxXferSize < MAX_BUFFER_SIZE? huart->RxXferSize : MAX_BUFFER_SIZE-1;
    memcpy(VirtUart0ChannelBuffRx, huart->pRxBuffPtr, VirtUart0ChannelRxSize);
    VirtUart0RxMsg = SET;
}

victor.b
Associate II

Here is some images showing what i am experiencing:

This image shows what i see when I initialize the mutex (but do not use it, as seen in the app_freertos.c file in the previous post) and i am stepping inside the function MX_FREERTOS_Init before the scheduler is called. We can see that i placed a break point inside the Led blink task and that the dissasembly seems ok for that part of the code:

0690X000009ZdCdQAK.png

Then, when i hit the "resume", it hits the breakpoint and the disassembly seems ok. But when i press resume again, it should hit back the same break point 100ms later...but it hangs there and its over.

0690X000009ZdCYQA0.png

The board is now bricked and has to be reset before i can launch a new debug session. Here in this last image, i launch the debug session with no breakpoint. The code is running fine (the led is blinking), but when i place a breakpoint at the same place, i get a weird disassembly. Also i cannot "resume" because it hangs there.

0690X000009ZdCOQA0.png

I tried declaring the mutex/semaphone, and delete them immediately after, and it does the same thing. The only wait to be able to debug with break points is to not initialize any semaphone or mutex.

I cannot continue my projet without mutex or semaphore...as i need task synchronisation.

Also i observed the same problem when using Queues. There are using semaphore under the hood and when ever i insert a breakpoint, it hangs.

PatrickF
ST Employee

Hello,

could you please precise if you are using SW4STM32 (i.e. GDB/OpenOCD debug) or another debugger ?

There is a separate thread which sound similar : https://community.st.com/s/question/0D50X0000B422in/stm32mp1-freertos-debug-issue

Is reducing the optimization level solve your issue ?

Seems linked to the way GDB manage the debug and the way FreeRTOS manage the stack pointers.

In order to give better visibility on the answered topics, please click on 'Accept as Solution' on the reply which solved your issue or answered your question.
victor.b
Associate II

Hi Patrick,

I am using SW4STM32 and it looks like it works when i remove the option "optimize for debugging" and set it to "None":

0690X000009ZdOUQA0.png

I will move foward and see if it still works when i start using the declared mutex and semaphore.

Thanks!

victor.b
Associate II

Ok so here is the sad part:

When i use "None" in Optimization level, OpenAMP works erratically and end up crashing!

0690X000009Zdg4QAC.png

But when i use "Optimize for Debug", everything works (OpenAmp, semaphores, mutexes, queues, etc.) but i cannot insert a breakpoint!0690X000009ZdfzQAC.png

This is a major issue for debugging!