This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Using app timer in sdk13

Hi all,

I am using a nRF52832 with SD S132 V4.0.2 ion SDK13.

My application currently uses TWI, SPI and BLE and also 1 wire (which is based on delays). Everything works fine. The 1 wire is used before the SD is enabled and after it is done it will not be used anymore, so it wouldn't interfere with the SD.

On my custom board I have an ADC conected through SPI. I want to take a sample every 100ms based on a app timer timeout. However the timeout interrupt is not fired.

I use the following code in main start:

NRF_LOG_INIT(NULL); // Initialize the logging module

err_code = app_timer_init();
APP_ERROR_CHECK(err_code);


/* Initialize peripherals */
adc_init();
twi_init();
press_init();
batt_init();
ds2431_getprofile();
measurement_init();
NRF_LOG_FLUSH();

/* Initialize bluetooth */
ble_stack_init();
peer_manager_init(erase_bonds);
gap_params_init();
gatt_init();
advertising_init();
ble_services_init();
conn_params_init();

/* Start advertising on start-up */
err_code = ble_advertising_start(BLE_ADV_MODE_FAST);
APP_ERROR_CHECK(err_code); 

measurement_start();

The timer is started in measurement_start and created in measurement_create:

APP_TIMER_DEF(m_pt100_timer_id);

void measurement_init(void)
{
	uint32_t time_base;
	ret_code_t err_code;

	/* Define a timer id used for 10Hz sample rate */
	err_code = app_timer_create(&m_pt100_timer_id, APP_TIMER_MODE_REPEATED, measurement_handler);
	APP_ERROR_CHECK(err_code);
}

void measurement_start(void)
{
	/* Start timer */
	app_timer_start(&m_pt100_timer_id, MEAS_TIMER_INTERVAL, NULL);

	/* Clear previous measurement in flash */

}

void measurement_handler(void * p_context) // this code is not fired
{
	float 	temperature = 0, pressure = 0;

	// do measurement, code currently not included
}

I have the following questions:

  1. Does app_timer module enable RTC1 or do I need to enable it?
  2. Do I need to initialize the LF clk?
  3. Should I first enable the softdevice and then the timer, or the other way around?
  4. Do you guys know why my timeout is not fired?
  • Okay, this helped me. Not in an expected way. I missed a reset. i put a breakpoint in the measurement start function. No error code is returned but i can see it resetting. I'll try to investigate this further.

    EDIT 1: Strange things are happening. I also placed a breakpoint in the RTC1_IRQHandler in app_timer.c . Another breakpoint is in measurement_start() just after

    err_code = app_timer_start(m_pt100_timer_id, APP_TIMER_TICKS(5000), NULL);
    

    btw app_timer_start does not like to get a address of the timer id, but would rather like a copy.

    ret_code_t app_timer_start(app_timer_id_t timer_id, uint32_t timeout_ticks, void * p_context);
    

    This change allows me to enter the RTC1_IRQHandler() however I still do not enter my own handler and it still resets.

    Also it only enters the RTC1_IRQhandler if I wait a a few seconds, if I just continue it resets without entering the RTC1_IRQHandler(). I will continue..

    EDIT 2: If I change the timeout value from 5s to 100ms it fires RTC1_IRQHandler a few times before restting. Is something else resetting my program? Further investigation.. EDIT 3: I fixed it. I will update the question with an answer. The reset was probably induced by adding the breakpoints, after the SD was enabled.

  • With help from @Sigurd I managed to find the problem. It was a problem all programmers will experience in their careers and one of my finest "d'oh" moments.

    You should create the timer with the following function:

    ret_code_t app_timer_create(app_timer_id_t const *      p_timer_id,
                                app_timer_mode_t            mode,
                                app_timer_timeout_handler_t timeout_handler)
    

    And start the timer with the following function:

    ret_code_t app_timer_start(app_timer_id_t timer_id, uint32_t timeout_ticks, void * p_context)
    

    Notice the difference in the first argument. The init requires an address of your timer id, and when you start a timer it only needs a copy. So when I changed my call from:

    err_code = app_timer_start(&m_pt100_timer_id, APP_TIMER_TICKS(1000), NULL);
    

    to

    err_code = app_timer_start(m_pt100_timer_id, APP_TIMER_TICKS(1000), NULL);
    

    It worked like a charm! Oh and btw, do not try to debug after the softdevice was enabled, it can get quirky.

Related