I have an app that has both 16bit standard service UUIDs and custom 128bit service UUIDs (in separate profiles). I can advertise multiple 16bit UUIDs or one and only one 128bit UUID. Both 16bit and 128bit UUIDs cannot be advertised at the same time. If there is a mix, the 128bit UUID is ignored.
Is this by design?
Robin
BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
Re: BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
Howdy Robin,
When we think about advertising what we are saying is that BLE device is continuously broadcasting a "packet" of information over the radio waves. The idea is that some other device may be listening (scanning) and be interested to known of the existence of this device. It is how two BLE devices will find each other. The BLE advertising protocol restricts the maximum amount of data that can be broadcast in an advert. I believe it is about 31 bytes (by default). What this means is that a server advertising its wears is limited in what it can broadcast. The broadcast must include some mandatory information such as the address of the device advertising (otherwise how will a receiver know how to connect to it). Beyond this minimum information, the remainder is configurable by the advertiser. It can include service ids, names, appearance and other goodies ... these goodies are primarily designed to allow the end user to "select" from among possible devices.
Putting this another way, you only have a relatively small amount of space for which an advertiser can advertise content beyond its existence. So ... what if we then want to know "more" about and advertising device? There are two stories.
The first is an active response. In that story, a scanner that receives an advertisement can ask "tell me more" and the advertiser will be prepared to send "another" short packet (usually another 31 bytes) (my numerical facts may be off here). This is considered separate but additional advertisement data and will usually be up to 31 bytes of data that didn't fit in the original advertisement packet.
Further than this, the original scanner can, upon receipt of an advertisement actually form a connection to the advertiser and then, in a conversation, ask for the full details of that device. Since this is a conversation, it is not bounded by broadcast restrictions and the data flow sizes can be unlimited (over time).
This is just a summary overview ... but I am thinking that it will paint a bit of a picture on what I think **might** be happening. If I am close, then you are trying to "stuff" too much data into the original advertisement packet such that it discards what won't fit. You then have further design options based on the "active response" story for an additional 31 bytes worth of quick response or a full connection to learn more about the device.
Do remember, the goal here is to have your BLE client "locate" your BLE server. Your server is known by a 6 byte address. How your client determine it has found the "desired" BLE server is either by:
1) White list (you already knew the address)
2) Advertised name
3) Advertised service
4) Other advertised parameters
5) Detection of a device it doesn't know about (because it hasn't seen the address recently/before) and then calls it up and queries its details to determine if THIS is the device it wants to continue to talk with
When we think about advertising what we are saying is that BLE device is continuously broadcasting a "packet" of information over the radio waves. The idea is that some other device may be listening (scanning) and be interested to known of the existence of this device. It is how two BLE devices will find each other. The BLE advertising protocol restricts the maximum amount of data that can be broadcast in an advert. I believe it is about 31 bytes (by default). What this means is that a server advertising its wears is limited in what it can broadcast. The broadcast must include some mandatory information such as the address of the device advertising (otherwise how will a receiver know how to connect to it). Beyond this minimum information, the remainder is configurable by the advertiser. It can include service ids, names, appearance and other goodies ... these goodies are primarily designed to allow the end user to "select" from among possible devices.
Putting this another way, you only have a relatively small amount of space for which an advertiser can advertise content beyond its existence. So ... what if we then want to know "more" about and advertising device? There are two stories.
The first is an active response. In that story, a scanner that receives an advertisement can ask "tell me more" and the advertiser will be prepared to send "another" short packet (usually another 31 bytes) (my numerical facts may be off here). This is considered separate but additional advertisement data and will usually be up to 31 bytes of data that didn't fit in the original advertisement packet.
Further than this, the original scanner can, upon receipt of an advertisement actually form a connection to the advertiser and then, in a conversation, ask for the full details of that device. Since this is a conversation, it is not bounded by broadcast restrictions and the data flow sizes can be unlimited (over time).
This is just a summary overview ... but I am thinking that it will paint a bit of a picture on what I think **might** be happening. If I am close, then you are trying to "stuff" too much data into the original advertisement packet such that it discards what won't fit. You then have further design options based on the "active response" story for an additional 31 bytes worth of quick response or a full connection to learn more about the device.
Do remember, the goal here is to have your BLE client "locate" your BLE server. Your server is known by a 6 byte address. How your client determine it has found the "desired" BLE server is either by:
1) White list (you already knew the address)
2) Advertised name
3) Advertised service
4) Other advertised parameters
5) Detection of a device it doesn't know about (because it hasn't seen the address recently/before) and then calls it up and queries its details to determine if THIS is the device it wants to continue to talk with
Free book on ESP32 available here: https://leanpub.com/kolban-ESP32
Re: BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
Hi Neil. Thanks for a long explanation that you only have 31 bytes.
I'm hoping for a response from Espressif on the choice of ignoring the 128bit UUID when there are 16bit UUID(s) present, even when the 128bit UUID comes first in the list.
There is a lot of technical knowledge that one needs to implement BLE on the ESP32 (and probably most platforms). The takeaway on this on is that you can advertise one 128bit UUID or multiple (maybe 15?) 16bit UUIDs but not both.
Robin
I'm hoping for a response from Espressif on the choice of ignoring the 128bit UUID when there are 16bit UUID(s) present, even when the 128bit UUID comes first in the list.
There is a lot of technical knowledge that one needs to implement BLE on the ESP32 (and probably most platforms). The takeaway on this on is that you can advertise one 128bit UUID or multiple (maybe 15?) 16bit UUIDs but not both.
Robin
Re: BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
On the "you need a lot of technical knowledge" part ... I'm trying to do my bit to make that easier. We now have some open source C++ classes that try and encapsulate much (and hopefully/eventually) all of the BLE functions into super high level consumables. These classes encapsulate the ESP-IDF BLE.
See:
https://esp32.com/viewtopic.php?f=13&t=2330
and
https://esp32.com/viewtopic.php?f=13&t=2361
As for the length of the post ... I try and practice back story explanations to practice and sound out my own knowledge when I can. The hope is that if I say something that is inaccurate, others may chime in and offer new words that will help me understand better. It wasn't at all meant to suggest that you yourself needed that depth of explanation and great apologies if I came across in any way as condescending in the answer ... it truly wasn't my intent.
See:
https://esp32.com/viewtopic.php?f=13&t=2330
and
https://esp32.com/viewtopic.php?f=13&t=2361
As for the length of the post ... I try and practice back story explanations to practice and sound out my own knowledge when I can. The hope is that if I say something that is inaccurate, others may chime in and offer new words that will help me understand better. It wasn't at all meant to suggest that you yourself needed that depth of explanation and great apologies if I came across in any way as condescending in the answer ... it truly wasn't my intent.
Free book on ESP32 available here: https://leanpub.com/kolban-ESP32
Re: BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
No worries. How will your classes handle the case (related to this thread) where someone issues both 16bit and 128bit (or more than one 128bit) UUID for advertising?
Robin
Robin
Re: BLE: cannot advertise 16bit and 128bit UUIDs (or more than one 128bit) simultaneously
Thats a great question and it will all boil down to the semantics of the underlying ESP-IDF capabilities. As I understand it, today I can use the API called "esp_ble_gap_config_adv_data()" which is an ESP-IDF supplied API that, when called, takes a rich input structure with a subset of the possible things that "can" be advertised. I say a subset because I believe the BLE spec says that our BLE server can advertise many more "things" than are described in the structure supplied by ESP-IDF. It is likely this structure was designed for the "majority of common cases" as opposed to be 100% of everything".
My current C++ wrapper allows the BLE Server author (eg you) to set some of these parameters and then when you start advertising, the C++ classes do all the work of passing that through to "esp_ble_gap_config_adv_data" and ESP-IDF "does what it does". I would assume that it packages up enough of the fields to fill the 31 byte primary advertising. It is the scanning BLE device that indicates whether or not it wishes to receive a second 31 byte packet from an advertiser ... and again, it is ESP-IDF that "auto handles" this.
A second story exists that I haven't looked at yet which is based on the APIs called esp_ble_gap_config_adv_data_raw() and esp_ble_gap_config_scan_rsp_data_raw() and I think THIS is the proper answer to your core question.
First let us trust that a BLE advertisement is either 31 bytes (and thats it) OR
an initial 31 bytes and the opportunity to get a second set of 31 bytes (62 bytes in total). Then we have two stories:
1) We tell ESP-IDF about all the possible advertisement data that ESP-IDF allows and IT controls in which of the two advertisement packets the data is sent.
2) We take control ourselves and WE define what is in which of the 1 (or 2) packets. This later story is achieved by us calling esp_ble_gap_config_adv_data_raw() for the 1st packet and esp_ble_gap_config_scan_rsp_data_raw() for the 2nd packet. Thus we can 100% control what we advertise. Since a full 128 bit UUID is itself 16 bytes, we simply CAN'T advertise more than 1 in either of the two packets (16 + 16 > 31).
What I'll now do is look at exposing some APIs for the C++ classes so that the user of the classes can specify not only the values of the ESP-IDF defined advertisement data but can also supply the other data with full control of order and packet with error handling.
I'm very open to requests for desired function ... but obviously they have to be within the capabilities of what industry spec of BLE says is possible.
My current C++ wrapper allows the BLE Server author (eg you) to set some of these parameters and then when you start advertising, the C++ classes do all the work of passing that through to "esp_ble_gap_config_adv_data" and ESP-IDF "does what it does". I would assume that it packages up enough of the fields to fill the 31 byte primary advertising. It is the scanning BLE device that indicates whether or not it wishes to receive a second 31 byte packet from an advertiser ... and again, it is ESP-IDF that "auto handles" this.
A second story exists that I haven't looked at yet which is based on the APIs called esp_ble_gap_config_adv_data_raw() and esp_ble_gap_config_scan_rsp_data_raw() and I think THIS is the proper answer to your core question.
First let us trust that a BLE advertisement is either 31 bytes (and thats it) OR
an initial 31 bytes and the opportunity to get a second set of 31 bytes (62 bytes in total). Then we have two stories:
1) We tell ESP-IDF about all the possible advertisement data that ESP-IDF allows and IT controls in which of the two advertisement packets the data is sent.
2) We take control ourselves and WE define what is in which of the 1 (or 2) packets. This later story is achieved by us calling esp_ble_gap_config_adv_data_raw() for the 1st packet and esp_ble_gap_config_scan_rsp_data_raw() for the 2nd packet. Thus we can 100% control what we advertise. Since a full 128 bit UUID is itself 16 bytes, we simply CAN'T advertise more than 1 in either of the two packets (16 + 16 > 31).
What I'll now do is look at exposing some APIs for the C++ classes so that the user of the classes can specify not only the values of the ESP-IDF defined advertisement data but can also supply the other data with full control of order and packet with error handling.
I'm very open to requests for desired function ... but obviously they have to be within the capabilities of what industry spec of BLE says is possible.
Free book on ESP32 available here: https://leanpub.com/kolban-ESP32
Who is online
Users browsing this forum: No registered users and 407 guests