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

Stuck Timer Value always reading Zero!

Hi,

I am using Timer0 to measure external pulse width. Using GPIOTE, PPI task and events. The problem here is, I am reading Timer0 Capture register as Zero always. Here I am giving PWM externally (10% duty cycle). Am I missing something here, does it need a read time interval? Kindly do the needful.

Code Snippets:

void in_pin_handler(nrf_drv_gpiote_pin_t pin, nrf_gpiote_polarity_t action)
{

if(pin == PIN_IN_2)
{
printf("Timer value: %d\r\n",(nrf_drv_timer_capture_get(&m_timer, NRF_TIMER_CC_CHANNEL0)));
nrf_drv_timer_clear(&m_timer);
}
}

static void gpiote_init(void)
{
ret_code_t err_code;

err_code = nrf_drv_gpiote_init();
APP_ERROR_CHECK(err_code);
nrf_drv_gpiote_in_config_t in_config = GPIOTE_CONFIG_IN_SENSE_LOTOHI(true);
in_config.pull = NRF_GPIO_PIN_PULLDOWN;
err_code = nrf_drv_gpiote_in_init(PIN_IN_2, &in_config, in_pin_handler);
APP_ERROR_CHECK(err_code);

}

void timer_init()
{
ret_code_t err_code;

nrf_drv_timer_config_t timer_cfg = NRF_DRV_TIMER_DEFAULT_CONFIG;
timer_cfg.bit_width = NRF_TIMER_BIT_WIDTH_32;
err_code = nrf_drv_timer_init(&m_timer, &timer_cfg, timer_handler);
APP_ERROR_CHECK(err_code);
}

void ppi_init()
{
ret_code_t err_code;

err_code = nrf_drv_ppi_init();
APP_ERROR_CHECK(err_code);

err_code = nrf_drv_ppi_channel_alloc(&ppi_channel_1);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_ppi_channel_alloc(&ppi_channel_2);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_ppi_channel_alloc(&ppi_channel_3);
APP_ERROR_CHECK(err_code);

uint32_t gpiote_evt_addr_2 = nrf_drv_gpiote_in_event_addr_get(PIN_IN_2);

uint32_t timer_start_task_addr = nrf_drv_timer_task_address_get(&m_timer, NRF_TIMER_TASK_START);
uint32_t timer_stop_task_addr = nrf_drv_timer_task_address_get(&m_timer, NRF_TIMER_TASK_STOP);
uint32_t timer_compare_task_addr = nrf_drv_timer_task_address_get(&m_timer, NRF_TIMER_TASK_CAPTURE2);

if(LATCH_GPIOTE==0){
err_code = nrf_drv_ppi_channel_assign(ppi_channel_1, gpiote_evt_addr_2, timer_start_task_addr);
APP_ERROR_CHECK(err_code);
LATCH_GPIOTE++;
}
else if (LATCH_GPIOTE==1){
err_code = nrf_drv_ppi_channel_assign(ppi_channel_2, gpiote_evt_addr_2, timer_compare_task_addr);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_ppi_channel_assign(ppi_channel_3, gpiote_evt_addr_2, timer_stop_task_addr);
APP_ERROR_CHECK(err_code);
LATCH_GPIOTE-=1;
}

err_code = nrf_drv_ppi_channel_enable(ppi_channel_1);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_ppi_channel_enable(ppi_channel_2);
APP_ERROR_CHECK(err_code);
err_code = nrf_drv_ppi_channel_enable(ppi_channel_3);
APP_ERROR_CHECK(err_code);
}

int main(void)
{
APP_ERROR_CHECK(NRF_LOG_INIT(NULL));

gpiote_init();
timer_init();
ppi_init();
printf("Example started\r\n");
NRF_LOG_INFO("Example start\r\n");


while(true){
__WFE();
}
}

Parents Reply
  • Ok, the timer is started via PPI if "LATCH_GPIOTE" is set to 0, and you get a in event for PIN2. Where are you setting LATCH_GPIOTE ? and why do you need LATCH_GPIOTE ?

    And the timer_compare_task_addr is using CC[2] register, but in the in_pin_handler() you are reading the CC[0] register. So try using NRF_TIMER_TASK_CAPTURE0 for the timer_compare_task_addr instead.

Children
  • Hi, Well LATCH_GPIOTE is integer declared as global and initialized to value 0. I am using it if(Latch_GPIOTE==0) then start the timer on LoToHi on PIN_IN2 and increment Latch_GPIOTE++, else if(Latch_GPIOTE==1) stop the timer and reset Latch_GPIOTE to 0. And this else If(Latch_GPIOTE==1) is executed on next LoToHi pulse on PIN_IN2. 

    I did try to read CC[0] reg somehow nothing came out. But eventually, I have added 

    if(pin==PIN_IN2)&&(action==NRF_GPIOTE_POLARITY_LOTOHI)  this worked for it. 


    But got a new problem here. when I give 2microsecond pulse to PIN_IN2, the timer ticks value I am getting is 513 which is 32.0625 microseconds. Hence the scale is way off.

    What could be the problem here? I have got the range to measure from 2us to 135us.

    Here is the Output on debugging terminal for 2us pulse with 50% duty cycle.

    time in us: 33.062500
    Timer Ticks: 529
    time in us: 33.187500
    Timer Ticks: 531

  • What prescaler do you use for the timer ?

    Are you using the projects found in this post?

Related