asantos wrote on Wednesday, February 06, 2019:
Hi,
I am using the nordic NRF52832 on a custom board.
My program implements a binary semaphore, which is given in the RTC interrupt handler.
My send_data task (this is the only task) waits for this semaphore in the beginning of the loop.
I have been trying to debug it but I have not found the problem.
The portYIELD_WITHIN_API(); line inside xQueueSemaphoreTake() is reached and then my program seems to hang. The code inside void vApplicationIdleHook( void ) is not run though, which should be the code run after the context switch.
I attach the part of the code relative to this issue. Please let me know how to debug this.
Thanks
Code in main.c
void vApplicationIdleHook( void )
{
while(1)
{
NRF_LOG_DEBUG("Idle task");
delay_ms(1000);
}
/* Create task for send_data blinking with priority set to 2 */
UNUSED_VARIABLE(xTaskCreate(send_data, "send_data", configMINIMAL_STACK_SIZE + 200, NULL, 2, &send_data_handle));
Code in task.c
// RTC timer
APP_TIMER_DEF(m_led_a_timer_id);
/**
* @brief RTC instance number
*
*/
#define PERIODIC_RTC 2
/**
* @brief RTC compare channel used
*
*/
#define PERIODIC_RTC_CC 0
/**
* @brief Number of RTC ticks between interrupts
*/
#define PERIODIC_TIMER_US 5000000ULL
#define PERIODIC_RTC_TICKS (RTC_US_TO_TICKS(PERIODIC_TIMER_US, RTC_DEFAULT_CONFIG_FREQUENCY))
/**
* @brief Semaphore set in RTC event
*/
static SemaphoreHandle_t send_data_semaphore = NULL;
/**
* @brief RTC configuration
*/
static nrf_drv_rtc_config_t const m_rtc_config = NRF_DRV_RTC_DEFAULT_CONFIG;
/**
* @brief RTC instance
*
* Instance of the RTC used for led blinking
*/
static nrf_drv_rtc_t const m_rtc = NRF_DRV_RTC_INSTANCE(PERIODIC_RTC);
static void periodic_rtc_handler(nrf_drv_rtc_int_type_t int_type)
{
NRF_LOG_DEBUG("Send data RTC handler");
BaseType_t yield_req = pdFALSE;
BaseType_t ret_val;
ret_code_t err_code;
err_code = nrf_drv_rtc_cc_set(
&m_rtc,
PERIODIC_RTC_CC,
(nrf_rtc_cc_get(m_rtc.p_reg, PERIODIC_RTC_CC) + PERIODIC_RTC_TICKS) & RTC_COUNTER_COUNTER_Msk,
true);
APP_ERROR_CHECK(err_code);
/* The returned value may be safely ignored, if error is returned it only means that
* the semaphore is already given (raised). */
UNUSED_VARIABLE(xSemaphoreGiveFromISR(send_data_semaphore, &yield_req));
// Request a context switch (switch to other task). Interrupt safe verison of taskYIELD()
portYIELD_FROM_ISR(yield_req);
}
/**
* @brief send_data task entry function.
*
* @param[in] pvParameter Pointer that will be used as the parameter for the task.
*/
void send_data(void * pvParameter)
{
NRF_LOG_INFO("---------- SEND DATA TASK ----------");
// Create rtc instance and compare channel
NRF_LOG_DEBUG("Init RTC");
ret_code_t err_code;
err_code = nrf_drv_rtc_init(&m_rtc, &m_rtc_config, periodic_rtc_handler);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_rtc_cc_set(&m_rtc, PERIODIC_RTC_CC, PERIODIC_RTC_TICKS, true);
APP_ERROR_CHECK(err_code);
// Enable RTC instance
nrf_drv_rtc_enable(&m_rtc);
// Create semaphore
send_data_semaphore = xSemaphoreCreateBinary();
UNUSED_PARAMETER(pvParameter);
// Begin task loop
while(1)
{
NRF_LOG_DEBUG("Waiting for semaphore to begin task");
UNUSED_VARIABLE(xSemaphoreTake(send_data_semaphore, portMAX_DELAY));
NRF_LOG_INFO("++++++++++++++++task begin++++++++++++++++\r\n");