I am porting some code from MacOS to Windows. MacOS always returns a non-empty local name in advertisement packets while Windows seems to always return an empty local name in an advertisement packet.
No, having a local name is not a requirement as part of sending out adverts. The requirements for BLE adverts depend on the type of advert, but for the simplest and most common advert type (ADV_IND, a.k.a scannable & connectable advert) the only requirement is the device's public or random address. None of the advert types require the local name to be part of the address. You can read more about this in the Bluetooth Specification v5.2, Vol 6, Part B, Section 2.3.1 (Advertising PDUs) [1].
You can also do a scan with nRF Connect on an Android/iOS device and you'll see that many devices don't have the name as part of advert, instead you get N/A as the device's name:-
Related
I have a BLE device that doesn't respond to SCAN_REQ and am working it out with the vendor independently per https://github.com/espressif/esp-idf/issues/10660.
When I use Nordic nRD Connect iphone app as a client I can see that device in the scan list and can connect to it. However, when I use a different client, a python Windows one, that client doesn't show the device in its scan list and doesn't connect to it if I specify the exact address.
My question is, are BLE 4 devices required to respond to SCAN_REQ requests to be discoverable and connectable or is it just optional response to provide additional advertisement data?
EDIT, I believe that Emil's answer below (thanks) refers to this quote
Yes, it's required to reply with a scan response. That is defined in Bluetooth Core v5.3, Vol 6 Part B (Link Layer), section 4.4.2.3, using the word "shall".
There is one exception though. There is a Filter Accept List in the controller which can contain addresses of centrals allowed to scan and/or connect. There are four combinations the host can set (advertising filter policy) that control if this list shall be used for filtering incoming SCAN_REQ and CONNECT_IND packets, respectively. If you don't use this filtering mechanism, then the device must send a scan response to every scan request.
There are two possible approaches to scanning—Passive Scanning or Active Scanning.
Passive Scanning is when Scanners receive advertising packets and process the contents.
In the case of Active Scanning, however, a device may decide it wants to know more about an advertising device and respond to the initial advertising packet by sending a Scan Request GAP protocol data unit (PDU). This basically means ‘Tell me more.’ The device receiving the Scan Request can send back a Scan Response PDU with more information, once again in the form of a collection of AD types.
The above has been extracted from: https://www.bluetooth.com/blog/advertising-works-part-1/ [the emphasis mine].
According to the Bluetooth Specification, each Bluetooth (or more specifically BLE) device can have a public Bluetooth device address which corresponds to the IEEE-assigned MAC address (burned-in MAC address). A device manufacturer has to purchase a range of MAC addresses from IEEE and can then assign these MAC addresses to his devices. However, Bluetooth devices can also randomize their device address to tackle privacy issues. They can use either
a static random address,
a resolvable private random address, or
a non-resolvable private random address.
I am wondering whether it is actually necessary to purchase the Bluetooth device addresses from IEEE. In other words, what would be the benefit of doing so? Is it possible to simply not purchase public device addresses and instead just use random addresses in products in the market. Or would that lead to legal or licensing issues?
I appreciate your help very much!
It's definitely possible to use static random address instead of public address. I guess most people do that.
Theoretically the only down sides are that with a small probability two random addresses might be the same, and you can't benefit from having your device addresses in a certain range (which could sometimes be useful).
Technically, Bluetooth stacks that fail to expose a proper API for connecting to a BLE device using address without prior scanning/bond, can lack the address type bit (public/random) so that the connection attempt does to the wrong address. This issue is currently present on Android.
I was looking for accessing device information like current device WLAN MAC address, IMEI, OS type etc. using Gluon mobile. How can I do it?
Currently the Charm Down Device service provides some of the features you are requesting.
Model: device's model or product
Uuid: device's universally unique identifier
Platform: the platform string that the operating system uses to identify itself
Version: the version number of the device platform
Serial: the device hardware serial number.
Wearable: true if the device is a wearable
In your view, you can call the service like:
Services.get(DeviceService.class).ifPresent(service -> {
System.out.printf("Device Model Name: %s", service.getModel());
});
Also, you can find implementation details for android here and for iOS here.
If there is any other feature you require, and you want to implement it, you can either clone and modify the service (see this question on how to do it), or create a new one (see this sample).
Hello,
The context: I'm currently working on a BLE device that is connected with Just Works connection type to its Master (android tablet).
Since :
Android devices with recent versions of Android do not use the public address when connecting. Rather, they use a random address. This is part of the BLE spec. For the purpose of privacy, in addition to the public device address there are random device addresses. New versions of Android uses a random address when connecting to peripherals. (source of that quote)
I understood that my Android tablet is using a random address. For that, i made a programme to verify this information and it actually works (fortunately).
So my BLE public addressed device can connect to the master by receiving its pairing ask.
The question: First of all, what exactly are BLE addresses (random, static, public(mac) it's a bit confusing from the docs) ?
The MAIN question: Can my master (android tablet) connect to my device when those two are private addressed ?
My specifications:
Using VisualStudio
Using VisualGDB and openOCD
BLE_lib.h and BlueNRG
Ask for more information
The answer: Public BLE address is given by Bluetooth SIG and is guaranteed to unique. Random BLE address does not have this property. In addition random address can be either static or public. Static address cannot be changed while the BT chip is on. Public is divided into resolvable and non-resolvable, both can change whenever and the basic difference is the amount of bytes that change.
The main answer: Yes but you will need a way to identify the device. You could broadcasting specific data (e.g. manufacturer data or a 128b service UUID) and have your tablet scan for it. Then you can connect to whatever address you find provided the device advertises correct data.
And recommendation: You can find a lot of stuff at Nordic semiconductor-related sites. Even if you do not use their stack, their tutorials and explanations are easy to understand and cover pretty much everything.
Edit: I could probably provide better answer if I knew what exactly you intend to do.
Being somewhat of a newbie I was wondering if there is a way to hard-code something on a peripheral that would only allow a single unique central/master to connect.....?
i.e. / eg
I have the ‘simple chat’ Arduino app on a RedBearLab Blend-Micro (which is for all intensive purposes the same as a Arduino Uno with a BLE shield) and I only want one single / unique phone to BE ABLE TO connect with it and therefore work with it.
My understanding is that the GAP handles security features during a BLE connection.
Therefore, is there some way to ‘code’ the peripheral device in / below one of the following includes:
spi.h ?
boards.h ?
EEPROM.h ?
RBL_nRF8001.h (or similar) ?
Other?
Didn't quite get an answer from Restricting the BLE peripheral device to connect to only one Master
OR
Am I stuck with EVERYTHING connecting but coding the peripheral in some other way in a GATT profile (I think) to ONLY do something with a predefined unique central/master (how/where to code?).
Many thanks for thoughts in advance
Being somewhat of a newbie I was wondering if there is a way to hard-code something on a peripheral that would only allow a single unique central/master to connect.....?
Theres the "Advertising Filter Policy" as specified in the Bluetooth Core V4.0 specification. Its a Byte in the Advertising Parameters as specified in Section 7.8.5 LE Set Advertising Parameters Command.
For example the value 0x02 reads Allow Scan Request from Any, Allow Connect Request from White List Only.
Then theres section 7.8.16 LE Add Device To White List Command.
That said, if your device confirms to the Bluetooth 4.0 specification, it should support these HCI commands. However there might be functions that simplify these procedures, wrapping those HCI commands for easier use. Check the Documentation of your device for such methods.
Good Luck!
I was asked to answer this question via email. It's been almost a year since I quit working on BLE. So I only answer this question based on my memories.
Basically #dominik has it right.
If the device is freshly new, it should advertise normally (without setting the whitelist only bit), then any central device could connect and bond. Once it is bonded, you should save this bonded flag and the bonded master's bd_addr to EEPROM. If the next time the master is lost, you will advertise with that white-list-only flag set. If a new central tries to connect, you could verify if its address is the same as your master.
I don't have the BLE spec at hand and I kind of forgot a lot about BLE already. Probably the spec says somewhere that if a central sees a peripheral device is broadcasting with white-list-only flag set, it wouldn't try to connect if it doesn't recognize that peripheral device. This saves both some effort.
But a master could always initiate a connection to your peripheral device regardless the white-list-only flag. So checking if the connecting central device's address is the same as your previously bonded master is the last resort.
[Update]
I used CSR1010 chips. I remembered that the BLE stack actually allows me to insert a list of bd_addr to the white-list data structure maintained by the stack. Then, with the white-list-only flag set, the lower-level stack layer will help you filter devices that are not in that white-list without your knowing.
However, you can always filter bd_addrs from your application code.