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

There's something I don't understand about LED timer.

Hello,


I have a question because there is a problem with writing code using timer.

I wrote the following code to avoid using the LED timer when I first ran it.

However, All_Stop() will not function properly the first time the code below is executed (that is, when the upload or when the pressed reset button).

void All_Start()
{
  uint32_t err_code;

  CenterLED_timers_start();
  //err_code = app_button_enable();
  //APP_ERROR_CHECK(err_code);
}

void All_Stop()
{
  uint32_t err_code;

  //err_code = app_button_disable();
  //APP_ERROR_CHECK(err_code);
  CenterLED_timers_stop();
  nrf_gpio_pin_clear(BAT_LED_1); //LED Off
  nrf_gpio_pin_clear(BAT_LED_2);
  nrf_gpio_pin_clear(BAT_LED_3);
}  
.
.
.
.
int charging_state = 0; //Used to prevent repeated output of CenterLED_timers_start.
.
.
.
    else //no charging
    {
      //charging_state = 0;
      
      if(charging_state == 0)
      {
        nrf_gpio_pin_clear(BAT_LED_1); //LED Off
        nrf_gpio_pin_clear(BAT_LED_2);
        nrf_gpio_pin_clear(BAT_LED_3);

        CenterLED_timers_start(); //LED1,2,3 toggle repeate timer

        charging_state = 1; //Used to prevent repeated output of CenterLED_timers_start.
        //nrf_delay_ms(100);
        printf("%d\n", charging_state); //check charging_state

        if(charging_state == 1) //No LED activity before Bluetooth connection
        {
          printf("All_Stop\n");
          //CenterLED_timers_stop();
          All_Stop(); //center timer stop & LED Off
        }
      }
    }

The timer starts because the charging_state was initially defined as zero, but the timer must be cancelled via All_Stop() immediately after.

This issue only occurs the first time I run it, and it will work normally after that (after a single change in the value of the charging_state).

When checked at the terminal, All_Stop seemed to have been executed properly.

Can you tell me the reason for this problem?

Thank you in advance.

(I think my explanation is complicated, but I'm sorry if the English interpretation is a little weird.)

Parents
  • Hello,

    I wrote the following code to avoid using the LED timer when I first ran it.

    Please share the actual code you used. Where is the timer configuration and initialization? Which function is used as the timers expiration callback?
    Where is your GPIO configuration and initialization?
    Which function contains the if and else code you have pasted at the bottom?

    However, All_Stop() will not function properly the first time the code below is executed (that is, when the upload or when the pressed reset button).

    Please elaborate on this, what are you seeing and how is it different from what you would have expected?
    Does your All_stop function not work without power-cycling or resetting your device first?

    This issue only occurs the first time I run it, and it will work normally after that (after a single change in the value of the charging_state).

    Your last conditional is inside the if( .. == 0) conditional.
    Is this intentional? With the current design, the last conditional will always be true, when the function is entered with (charging == 0).
    Please review this part of the code, and tell me if this is the intended behavior. If not, could you have meant to place the last part as a separate conditional check?
    As it stands right now the conditional is redundant, since charging is set to 1 right before it is checked.

    Best regards,
    Karl

  • Hello, Karl.
    Thank you for your answer.

    I use one internal LED on the board and three external LEDs.
    External LEDs have several operating routines.

    1. When Bluetooth is connected, CenterLED_timers_start() is called.

    (CenterLED_timers_stop() is called before connection).

    2. When the battery charging connector is connected, the three LEDs stop working and print the battery value to the LED.

    3. If the battery charging connector is not connected, the CenterLED Timer starts or stops as shown in 1.

    void gpio_init(void)
    {
      nrf_gpio_cfg_output(APP_LED_1); //board_led1
      nrf_gpio_pin_set(APP_LED_1);
    
      nrf_gpio_cfg_output(APP_LED_2); //board_led2
      nrf_gpio_pin_set(APP_LED_2);
    
      nrf_gpio_cfg_output(APP_LED_3); //board_led3
      nrf_gpio_pin_set(APP_LED_3);
    
      nrf_gpio_cfg_output(APP_LED_4); //board_led4
      nrf_gpio_pin_set(APP_LED_4);
    
      nrf_gpio_cfg_output(BAT_LED_1); 
      nrf_gpio_pin_set(BAT_LED_1);
    
      nrf_gpio_cfg_output(BAT_LED_2); 
      nrf_gpio_pin_set(BAT_LED_2);
    
      nrf_gpio_cfg_output(BAT_LED_3); 
      nrf_gpio_pin_set(BAT_LED_3);
    
      nrf_gpio_cfg_input(APP_BTN_1,NRF_GPIO_PIN_PULLUP);
      nrf_gpio_cfg_input(bat_state, NRF_GPIO_PIN_PULLDOWN);
    }
    
    
    static void CenterLED_timer_handler(void * p_context)
    {
      nrf_gpio_pin_toggle(BAT_LED_1);
      nrf_gpio_pin_toggle(BAT_LED_2);
      nrf_gpio_pin_toggle(BAT_LED_3);
    }
    
    
    static void PairLED_timer_handler(void * p_context)
    {
      nrf_gpio_pin_toggle(APP_LED_1); //toggle led
      //printf("Pairing LED....\n");
    }
    
    
    /**@brief Function for the Timer initialization.
     *
     * @details Initializes the timer module. This creates and starts application timers.
     */
    static void timers_init(void)
    {
        ret_code_t err_code;
    
        // Initialize timer module.
        err_code = app_timer_init();
        APP_ERROR_CHECK(err_code);
    
        //Create Center LED timers
        err_code = app_timer_create(&m_CenterLED_timerid,
                                    APP_TIMER_MODE_REPEATED,
                                    CenterLED_timer_handler);
        APP_ERROR_CHECK(err_code);
    
    
       //Create Pairing LED timers
        err_code = app_timer_create(&m_PairLED_timerid,
                                    APP_TIMER_MODE_REPEATED,
                                    PairLED_timer_handler);
        APP_ERROR_CHECK(err_code);
    }
    
    
    static void CenterLED_timers_start() //Bat_LED1,2,3 toggle start
    {
      ret_code_t err_code;
    
      err_code = app_timer_start(m_CenterLED_timerid, APP_TIMER_TICKS(1000), NULL); //Toggle 1sec
      APP_ERROR_CHECK(err_code);
      printf("Center Led Start\n");
    }
    
    
    static void PairLED_timers_start() //APP_LED1 toggle start (advertising)
    {
      ret_code_t err_code;
    
      err_code = app_timer_start(m_PairLED_timerid, APP_TIMER_TICKS(1000), NULL); //Toggle 1sec
      APP_ERROR_CHECK(err_code);
      printf("Scanning Start\n");
    }
    
    
    static void CenterLED_timers_stop() //Stop Center Timer
    {
        ret_code_t err_code;
        
        err_code = app_timer_stop(m_CenterLED_timerid); 
        APP_ERROR_CHECK(err_code);
        printf("Center Led Stop\n");
    }
    
    static void PairLED_timers_stop() //Stop pairing LED Timer
    {
        ret_code_t err_code;
        
        err_code = app_timer_stop(m_PairLED_timerid); 
        APP_ERROR_CHECK(err_code);
    }
    
    
    void All_Start()
    {
      uint32_t err_code;
    
      CenterLED_timers_start();
      //err_code = app_button_enable();
      //APP_ERROR_CHECK(err_code);
    }
    
    void All_Stop()
    {
      uint32_t err_code;
    
      //err_code = app_button_disable();
      //APP_ERROR_CHECK(err_code);
      CenterLED_timers_stop();
      nrf_gpio_pin_clear(BAT_LED_1); //LED Off
      nrf_gpio_pin_clear(BAT_LED_2);
      nrf_gpio_pin_clear(BAT_LED_3);
    }  
    .
    .
    .
    .
    //battery level range
    #define BAT_ADC_100 465
    #define BAT_ADC_75  350 
    #define BAT_ADC_50  230 
    #define BAT_ADC_0   0
    
    int charging_state = 0; //Used to prevent repeated output of CenterLED_timers_start.
    
    void turn_on_batter_level_led(int16_t bat_level) //battery LED
    { 
       //int charging_state = 0;
       ret_code_t err_code;
    
       int charge_state = nrf_gpio_pin_read(bat_state); //read battery charge state
       printf("%d\n", charge_state); //charging : 1, no charging : 0 (TP4056 Charge IC)
    
       if(charge_state == 1) //charging
       {
          charging_state = 0; //Used to prevent repeated output of CenterLED_timers_start.
    
          //stop center LED, start Battery LED
          CenterLED_timers_stop();
          
          printf("battery : %u \n", bat_level); //%u : unsigned decimal number
    
          if(bat_level >= BAT_ADC_75) { // over 75%
            printf("over 75persent \n"); //led1,2,3 on
    
            nrf_gpio_pin_toggle(BAT_LED_1);
            nrf_gpio_pin_toggle(BAT_LED_2);
            nrf_gpio_pin_toggle(BAT_LED_3);
          }
    
          else if (BAT_ADC_75 > bat_level >= BAT_ADC_50) { //over 50%
            printf("over 50persent \n"); //led1,2 on
    
            nrf_gpio_pin_toggle(BAT_LED_1);
            nrf_gpio_pin_toggle(BAT_LED_2);
    
            nrf_gpio_pin_clear(BAT_LED_3); //bat_led3 off
    
            char bat_array2[] = "over 50";
            uint16_t bat_length2 = sizeof(bat_array2);
          }
      
          else if (bat_level < BAT_ADC_50) { //under 50%
           printf("under 50persent \n"); //led1 on
    
           nrf_gpio_pin_toggle(BAT_LED_1);
    
           nrf_gpio_pin_clear(BAT_LED_2); //bat_led2 off
           nrf_gpio_pin_clear(BAT_LED_3);  //bat_led3 off
          }
       }
       
    /*When first executed, Bluetooth is before connection and the battery charging connector is also before connection. 
    Therefore, the CenterLED must be turned off. */
        else //no charging
        {
          //charging_state = 0;
          
          if(charging_state == 0)
          {
            nrf_gpio_pin_clear(BAT_LED_1); //LED Off
            nrf_gpio_pin_clear(BAT_LED_2);
            nrf_gpio_pin_clear(BAT_LED_3);
    
            CenterLED_timers_start(); //LED1,2,3 toggle repeate timer
    
            charging_state = 1; //Used to prevent repeated output of CenterLED_timers_start.
            //nrf_delay_ms(100);
            printf("charging_state : %d\n", charging_state); //check charging_state
    
            if(charging_state == 1) //No LED activity before bluetooth connection
            {
              printf("All_Stop\n");
              //CenterLED_timers_stop();
              All_Stop(); //center timer stop & LED Off
            }
          }
        }

    The reason why I used 'if(charging_state == 0)' is that 'CenterLED_timers_start()' is continuously called when the battery charging connector is not connected. If it continues to be called, the LED behavior becomes strange, so I only printed it once.

    The output on the serial terminal indicates that All_Stop is called.
    But the LEDs are working without stopping.
    (No Bluetooth connection when upload or reset Therefore, the LED should be turned off.)

    Please feel free to let me know if I lack explanation or need anything else.

    Thank you.

  • I'm modified it.

    After further testing, I connected the battery charge connection when there was no Bluetooth connection. CenterLED_timers_start is called when battery charging removed, and the LED turns on.

Reply Children
No Data
Related