Skip to main content
Associate II
March 20, 2024
Solved

Custom made ble characteristic updater don't work

Hello everyone!

I just started learning how to use the STM32WB-Chips on the Nucleo-WB55RG and followed this tutorial: 

https://www.youtube.com/watch?v=Zgw3wRpGSRQ&list=PLnMKNibPkDnG9JRe2fbOOpVpWY7E4WbJ-&index=17

After that I tried to make a function (following the steps mentioned in the tutorial above) which I can use in the main.c to send custom data to the PC. However when I call this function in the main loop the advertismenet  disappear and I cannot find the reason why. Can you guys help me with this?

In the app_conf.h I wrote

648 /* USER CODE BEGIN Defines */
649 void ble_updateChar(uint8_t);
650 /* USER CODE END Defines */
...

671 /* USER CODE BEGIN CFG_Task_Id_With_HCI_Cmd_t */
672 CFG_TASK_BLE_UPDATE,
673 /* USER CODE END CFG_Task_Id_With_HCI_Cmd_t */

In the app_ble.c

268 /* USER CODE BEGIN APP_BLE_Init_1 */
269 UTIL_SEQ_RegTask(1<<CFG_TASK_BLE_UPDATE, UTIL_SEQ_RFU, ble_updateChar);
270 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
271 /* USER CODE END APP_BLE_Init_1 */

In the custom_app.h

57 /* External variables --------------------------------------------------------*/
58 /* USER CODE BEGIN EV */
59 extern uint8_t ble_flag;
60 extern uint8_t ble_buffer[247];
70 /* USER CODE END EV */
...
71 /* USER CODE BEGIN EF */
72 void ble_updateChar(uint8_t char_identifier);
73 /* USER CODE END EF */

In the custom_app.c

75 /* USER CODE BEGIN PV */
76 uint8_t ble_flag;
77 uint8_t ble_buffer[247];
78 /* USER CODE END PV */
...
177 /* USER CODE BEGIN FD */
178 void ble_updateChar(uint8_t char_identifier){
179
180 if(char_identifier == NOTIFY_CHARACTERISTICS){
181 		if(ble_flag == 1){
182 			Custom_STM_App_Update_Char(CUSTOM_STM_NOTFIY, (uint8_t *)ble_buffer);
183 			ble_flag = 0;
184 		}
185
186 }
187 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
188 }
189 /* USER CODE END FD */

 

When I want to send data to the PC I set the ble_flag to 1 and place the data in the ble_buffer in the main.c and call the ble_updateChar() function. Like this:

119 while (1)
120 {
121 /* USER CODE END WHILE */
122 MX_APPE_Process();
123
124 /* USER CODE BEGIN 3 */
125 ble_flag = 1;
126 ble_buffer[0] = 0;
127 ble_updateChar(NOTIFY_CHARACTERISTICS);
127 HAL_Delay(100);
128 ble_flag = 1;
129 ble_buffer[0] = 1;
130 ble_updateChar(NOTIFY_CHARACTERISTICS);
131 HAL_Delay(100);
132
133
134 }
135 /* USER CODE END 3 */

As I said above, if the ble_updateChar() function is called it causes the service to disappear, but if I comment them out the service is there again.

 

I'm thankful for and looking forward to your answers!

 

Best regard,

AndrasToth

This topic has been closed for replies.
FDumontKeller
FDumontKellerBest answer
Associate II
March 21, 2024

Hi @AndrasToth, 

I think there are some things mixed up.


remark: If you want to update the value as soon the Server has something new for the client you should use the a characteristic on notification or indication (CHAR_PROP_NOTIFY / CHAR_PROP_INDICATE). 
On the other hand if you want to give the client data when you received a read command from it, then you should use a characteristic with the read property (CHAR_PROP_READ). 

In your code  you are introducing a task for the sequencer to execute ble_updateChar() as soon as the code starts in APP_BLE_Init()

268 /* USER CODE BEGIN APP_BLE_Init_1 */
269 UTIL_SEQ_RegTask(1<<CFG_TASK_BLE_UPDATE, UTIL_SEQ_RFU, ble_updateChar);
270 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
271 /* USER CODE END APP_BLE_Init_1 */

and the function associated with the task introduces again a new task for the execution of the same function.

/* USER CODE BEGIN PV */
76 uint8_t ble_flag;
77 uint8_t ble_buffer[247];
78 /* USER CODE END PV */
...
177 /* USER CODE BEGIN FD */
178 void ble_updateChar(uint8_t char_identifier){
179
180 if(char_identifier == NOTIFY_CHARACTERISTICS){
181 		if(ble_flag == 1){
182 			Custom_STM_App_Update_Char(CUSTOM_STM_NOTFIY, (uint8_t *)ble_buffer);
183 			ble_flag = 0;
184 		}
185
186 }
187 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
188 }
189 /* USER CODE END FD */

 

This will result in the sequencer constantly entering the ble_updateChar() in MX_APPE_Proccess() once the BLE stack is ready. If no additional code is in main the application will send Advertising normally since the calling of ble_updateChar() does not do anything given that ble_flag is 0.

But if you put the extra code in main(). The application will try to send something to a non existent client since there has not been any connection established. 

If this is your first time using the Custom_service, you can follow this example of provided by ST: 
https://wiki.stmicroelectronics.cn/stm32mcu/wiki/Connectivity:STM32WB_BLE_STM32CubeMX

And information about how the sequencer for the BLE application can be found here: 
https://www.st.com/resource/en/application_note/an5289-how-to-build-wireless-applications-with-stm32wb-mcus-stmicroelectronics.pdf

 

Hope this helps.

 

8 replies

FDumontKeller
FDumontKellerBest answer
Associate II
March 21, 2024

Hi @AndrasToth, 

I think there are some things mixed up.


remark: If you want to update the value as soon the Server has something new for the client you should use the a characteristic on notification or indication (CHAR_PROP_NOTIFY / CHAR_PROP_INDICATE). 
On the other hand if you want to give the client data when you received a read command from it, then you should use a characteristic with the read property (CHAR_PROP_READ). 

In your code  you are introducing a task for the sequencer to execute ble_updateChar() as soon as the code starts in APP_BLE_Init()

268 /* USER CODE BEGIN APP_BLE_Init_1 */
269 UTIL_SEQ_RegTask(1<<CFG_TASK_BLE_UPDATE, UTIL_SEQ_RFU, ble_updateChar);
270 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
271 /* USER CODE END APP_BLE_Init_1 */

and the function associated with the task introduces again a new task for the execution of the same function.

/* USER CODE BEGIN PV */
76 uint8_t ble_flag;
77 uint8_t ble_buffer[247];
78 /* USER CODE END PV */
...
177 /* USER CODE BEGIN FD */
178 void ble_updateChar(uint8_t char_identifier){
179
180 if(char_identifier == NOTIFY_CHARACTERISTICS){
181 		if(ble_flag == 1){
182 			Custom_STM_App_Update_Char(CUSTOM_STM_NOTFIY, (uint8_t *)ble_buffer);
183 			ble_flag = 0;
184 		}
185
186 }
187 UTIL_SEQ_SetTask(1<<CFG_TASK_BLE_UPDATE, CFG_SCH_PRIO_0);
188 }
189 /* USER CODE END FD */

 

This will result in the sequencer constantly entering the ble_updateChar() in MX_APPE_Proccess() once the BLE stack is ready. If no additional code is in main the application will send Advertising normally since the calling of ble_updateChar() does not do anything given that ble_flag is 0.

But if you put the extra code in main(). The application will try to send something to a non existent client since there has not been any connection established. 

If this is your first time using the Custom_service, you can follow this example of provided by ST: 
https://wiki.stmicroelectronics.cn/stm32mcu/wiki/Connectivity:STM32WB_BLE_STM32CubeMX

And information about how the sequencer for the BLE application can be found here: 
https://www.st.com/resource/en/application_note/an5289-how-to-build-wireless-applications-with-stm32wb-mcus-stmicroelectronics.pdf

 

Hope this helps.

 

Associate II
March 21, 2024

Thank you very much! I removed the parts which uses the sequencer and it started working.

268 /* USER CODE BEGIN APP_BLE_Init_1 */
269 
270 /* USER CODE END APP_BLE_Init_1 */
/* USER CODE BEGIN PV */
76 uint8_t ble_flag;
77 uint8_t ble_buffer[247];
78 /* USER CODE END PV */
...
177 /* USER CODE BEGIN FD */
178 void ble_updateChar(uint8_t char_identifier){
179
180 if(char_identifier == NOTIFY_CHARACTERISTICS){
181 		if(ble_flag == 1){
182 			Custom_STM_App_Update_Char(CUSTOM_STM_NOTFIY, (uint8_t *)ble_buffer);
183 			ble_flag = 0;
184 		}
185 }
186 }
187 /* USER CODE END FD */

However I run into an other problem where the program is running when I'm debugging and after I stopped debugging, but not when I depower and repower the devboard after the debug or I use the run configuration on it. Did you ever run into this kind of problem?

 

FDumontKeller
Associate II
March 21, 2024

Just to understand your problem better: 
the only way you get your application to work is to press the debug option. If you reset the dev board or you use the run option, you do not see any advertising from the server?