How does the advertise with timeout function work?
static const struct default_handlers_configuration user_default_hnd_conf = { // Configure the advertise operation used by the default handlers // Possible values: // - DEF_ADV_FOREVER // - DEF_ADV_WITH_TIMEOUT .adv_scenario = DEF_ADV_WITH_TIMEOUT,
// Configure the advertise period in case of DEF_ADV_WITH_TIMEOUT. // It is measured in timer units (3 min). Use MS_TO_TIMERUNITS macro to convert // from milliseconds (ms) to timer units. .advertise_period = MS_TO_TIMERUNITS(5000),
I have defined the above configuration. Advertisement timeout shall happen after 5 seconds.
After the timeout, which callback shall get called?
I want to advertise for 5 seconds then have a timeout and go to deep sleep mode. Then upon pressing a GPIO, my dialog will wake up and restart advertising. How shall I do?
Which callback/function shall I put the button wakeup press function so that when I press SW2 in dialog board, my system wakes up?
When will the below callback function be called?
Hi Satakshi,Thank you for posting your question online.You can either use the DEF_ADV_WITH_TIMEOUT option as your adv_scenario or you can implement it with a timer yourself, please refer on this ticket: Advertising with timeout in loop - Bluetooth Low Energy - Wireless Connectivity - Renesas Engineering Community
Satakshi_R said:I have defined the above configuration. Advertisement timeout shall happen after 5 seconds. After the timeout, which callback shall get called?
When you have set the DEF_ADV_WITH_TIMEOUT as your adv_scenario, the default advertise operation is going to call the app_easy_gap_undirected_advertise_with_timeout_start API:void default_advertise_operation(void) { if (user_default_hnd_conf.adv_scenario == DEF_ADV_FOREVER) { app_easy_gap_undirected_advertise_start(); } else if (user_default_hnd_conf.adv_scenario == DEF_ADV_WITH_TIMEOUT) { app_easy_gap_undirected_advertise_with_timeout_start(user_default_hnd_conf.advertise_period, adv_timeout_callback); //static void (*adv_timeout_callback)(void) } } /** **************************************************************************************** * @brief Start advertising for undirected connection with timeout start. * @param[in] delay Delay of the timer * @param[in] timeout_callback Timeout callback function **************************************************************************************** */ void app_easy_gap_undirected_advertise_with_timeout_start(uint32_t delay, void (*timeout_callback)(void)); /** **************************************************************************************** * @brief Stop advertising with timeout stop. **************************************************************************************** */ void app_easy_gap_advertise_with_timeout_stop(void);After the period of advertising you had set has passed, then the app_easy_gap_advertise_stop_handler will be executed to terminate the advertising. After that one of the callback functions for advertising is going to be executed:
void default_advertise_operation(void) { if (user_default_hnd_conf.adv_scenario == DEF_ADV_FOREVER) { app_easy_gap_undirected_advertise_start(); } else if (user_default_hnd_conf.adv_scenario == DEF_ADV_WITH_TIMEOUT) { app_easy_gap_undirected_advertise_with_timeout_start(user_default_hnd_conf.advertise_period, adv_timeout_callback); //static void (*adv_timeout_callback)(void) } } /** **************************************************************************************** * @brief Start advertising for undirected connection with timeout start. * @param[in] delay Delay of the timer * @param[in] timeout_callback Timeout callback function **************************************************************************************** */ void app_easy_gap_undirected_advertise_with_timeout_start(uint32_t delay, void (*timeout_callback)(void)); /** **************************************************************************************** * @brief Stop advertising with timeout stop. **************************************************************************************** */ void app_easy_gap_advertise_with_timeout_stop(void);
.app_on_adv_nonconn_complete = NULL, .app_on_adv_undirect_complete = NULL, .app_on_adv_direct_complete = NULL,
Thanks a lot for the reply.
As per the ticket shared by you, I defined my own timer and after 10 seconds, I called the following callback function:
void stop_adv_cb(void) { arch_printf("stop function called"); //Check if Timer for Advertising is unitiliazed and initialize him again if( app_adv_timeout_timer_used != EASY_TIMER_INVALID_TIMER) { app_adv_timeout_timer_used = EASY_TIMER_INVALID_TIMER; } //app_easy_gap_advertise_stop(); #if defined (CFG_EXT_SLEEP_WAKEUP_RTC) || defined (CFG_EXT_SLEEP_WAKEUP_TIMER1) || \ defined (CFG_DEEP_SLEEP_WAKEUP_RTC) || defined (CFG_DEEP_SLEEP_WAKEUP_TIMER1) // Ensure PD_TIM is open SetBits16(PMU_CTRL_REG, TIM_SLEEP, 0); // Wait until PD_TIM is opened while ((GetWord16(SYS_STAT_REG) & TIM_IS_UP) != TIM_IS_UP); #else // Close PD_TIM SetBits16(PMU_CTRL_REG, TIM_SLEEP, 1); // Wait until PD_TIM is closed while ((GetWord16(SYS_STAT_REG) & TIM_IS_DOWN) != TIM_IS_DOWN); #endif spi_flash_power_down(); put_system_into_deep_sleep(); }
After the timeout, I am making the system go to deep sleep mode.
From this, I want GPIO wakeup of the dialog board and upon wake up, it shall resume the advertisement. For that I have defined the folllwoing functions and I am using SW2 for wakeup.
static void app_wakeup_cb(void) { // If state is not idle, ignore the message if (ke_state_get(TASK_APP) == APP_CONNECTABLE) { //default_advertise_operation(); user_app_adv_start(); } } static void app_resume_system_from_sleep(void) { #if !defined (__DA14531__) if (GetBits16(SYS_STAT_REG, PER_IS_DOWN)) { periph_init(); } #endif if (arch_ble_ext_wakeup_get()) { arch_set_sleep_mode(app_default_sleep_mode); arch_ble_force_wakeup(); arch_ble_ext_wakeup_off(); app_easy_wakeup(); } default_advertise_operation(); } static void app_button_press_cb(void) { app_resume_system_from_sleep(); app_button_enable(); } void app_button_enable(void) { app_easy_wakeup_set(app_wakeup_cb); wkupct_register_callback(app_button_press_cb); if (GPIO_GetPinStatus(GPIO_BUTTON_PORT, GPIO_BUTTON_PIN)) { wkupct_enable_irq(WKUPCT_PIN_SELECT(GPIO_BUTTON_PORT, GPIO_BUTTON_PIN), // select pin (GPIO_BUTTON_PORT, GPIO_BUTTON_PIN) WKUPCT_PIN_POLARITY(GPIO_BUTTON_PORT, GPIO_BUTTON_PIN, WKUPCT_PIN_POLARITY_LOW), // polarity low 1, // 1 event 0); // debouncing time = 0 } } void user_app_adv_undirect_complete(uint8_t status) { // If advertising was canceled then update advertising data and start advertising again if (status == GAP_ERR_CANCELED) { arch_ble_ext_wakeup_on(); // Configure wakeup button app_button_enable(); // app_adv_timeout_timer_used = app_easy_timer(START_ADV_IN_SEC, user_app_adv_start); } }
Is this correct, because my system is entering sleep mode after 10 seconds but when I press SW2, it is not waking up as I am not able to scan the device again. What could be the issue for the same?
Hi Satakshi,Thank you for the reply.From the code snippet you shared I saw that you have commented out the app_easy_gap_advertise_stop API to stop the advertising. So you are not actually stopping the advertising, you are going straight into the Deep Sleep Mode. I would personally suggest to call the app_easy_gap_advertise_stop API and then do the Deep Sleep implementation inside the user_app_adv_undirect_complete custom callback function which is going to be executed after that.
Satakshi_R said:Is this correct, because my system is entering sleep mode after 10 seconds but when I press SW2, it is not waking up as I am not able to scan the device again. What could be the issue for the same?
Please refer on the ble_app_sleepmode example inside the SDK, it has the same functionalities as the one you want to do, but it has Extended Sleep Mode instead of Deep Sleep. If you are working with our Dev Kit Pro, you can also check the Power Profiler to make sure that the device is actually in Deep Sleep mode or Advertising. Inside the app_button_enable function, it is not necessary to call the if statement that checks the GPIO_GetPinStatus API. You can just configure the wake up controller for the GPIO you have configured in order to wake up the DA14531.Best Regards,OV_Renesas
In the function void_stop_adv_cb() I have made the system go into sleep mode. You are suggesting to put the sleep mode function inside the user_app_undirect_complete() function??
Also I have defined app_resume_system_from_sleep(). Whether that is required for deep sleep or not required ? Is there anything else required for deep sleep?
I have called the app_button_enable() inside usee_app_undirect_complete(). Is that correct? Where exactly do I have to call the app_button_enable callback? I am a bit confused and what are the exact configuration needed for waking up from deep sleep. Can u please help me?
Hi Satakshi,Thank you for the reply.Please find attached the ble_app_peripheral_adv_timeout_deep_sleep.zip file. I worked on SDK v6.0.18 with Dev Kit Pro and the DA14531MOD DB. I worked on a ble_app_peripheral example and I copied the Deep Sleep configuration from the prox_reporter example.After 5 seconds, the Advertising Stops and the DA14531 goes into Deep Sleep, then I press SW2 (P0_11) and I wake up the device, it automatically starts advertising for another 5 seconds and goes to Deep Sleep again. Please see the screenshots captured from the Power Profiler:It works on my side as expected. Please share any feedback. ble_app_peripheral_adv_timeout_deep_sleep.zipBest Regards,OV_Renesas
Thanks a lot for sharing the answer. I have updated my code as per your instructions. And now I am getting something as below.
After 10 seconds, dialog is going to sleep. Then when I press SW2 again I am getting the graph as shown above. Is 10 seconds a very short time because I am not able to scan it in the nrf connect in my mobile phone.
After 10 seconds if I press SW2 again, it is advertising but why am I not able to scan it in my mobile phone?
Also one more thing, if I am advertising continuously without any sleep mode implementation, then why is the average current constantly reducing?
Before:
After:
You can see in the before and after images, that average current value has decreased.
Hi Satakshi,Thank you for the reply.The Screenshot you shared shows that it took the DA14531 187ms to download the source code into SRAM. With the project I shared I was able to see a similar time between the Wake up controller interrupt and the DA14531 going back into Extended Sleep.
Satakshi_R said:After 10 seconds if I press SW2 again, it is advertising but why am I not able to scan it in my mobile phone?
I am only advertising for 5 seconds, and I am able to see my DA14531 advertising with the SmartBond App.Could you please test the project I shared on my previous answer?
Satakshi_R said:Also one more thing, if I am advertising continuously without any sleep mode implementation, then why is the average current constantly reducing?
If you want to measure the current measurement, you should enable the Power Profiler (Initialize-Start) after the FW has been downloaded into the DA14531. Ideally you should let the DA14531 for 2-10minutes running on the Power Profiler in order to see the Average Current Measurements. Best Regards,OV_Renesas
Apart from using the power profiler, I am trying to measure the average current with multimeter. I programmed and burned the code in OTP from smart snippets toolbox. After that, I removed the J9 jumper but when I am trying to calculate the value, multimeter shows 0. What could be the issue?
Hi Satakshi,Thank you for the reply.Is your Multimeter capable of measuring uA? You should be able to see the current measurement from the J9 Jumpers.Best Regards,OV_Renesas
Yes the multimeter is capable of measuring uA also. When I remove the shorted J9 jumper, the blue LED goes off in the dev kit pro. After that, I start measuring it but it shows 0 in mA mode also and uA mode also. Is there any additional step I should do in smart snippets toolbox ?
I forgot to change the macros like below:
#undef CFG_CODE_LOCATION_EXT #define CFG_CODE_LOCATION_OTP
#undef CFG_DEVELOPMENT_DEBUGAnd I burned the OTP image and header. After that my board is not getting detected. Did the wrong flashingdcaused some issue to the board?