Bluez not reading advertisement packet - bluetooth

I'm trying to build a small program that reads the BLE beacons around my devices and parses the ones that I'm interested in to publish on MQTT. I'm using Raspberry Pis to run the code, I develop using my mac. The language is JS (Node 10.x), my Pis are running latest Buster, that is Bluez 5.50 and a fork of Noble to interface with the bluetooth layer.
For some reason, on one of the Pis that I moved to an open area (in order to get clear readings), I only receive the Scan Response Packets. I never receive the Advertisement Packet. I do sometimes receive the Advertisement packet for one of the device that is quite far away, making me suspect that signal comes in play here. From the Pis in the network cabinet (small Faraday cage) I do get inconsistently both packets every now and then (reason for dedicating a Pi in an open location).
Is there any way to force Bluez to always receive the Advertisement packet? Is there a bug somehow or a feature that I am not using properly?
EDIT
I installed tshark to monitor closely, and I do see the advertisement packet reaching my device. This means that BlueZ is ignoring them. Is there some complete documentation on how to use bluetoothctl and how to configure the bluetooth deamon/tool in order for these packets to be read?

After many days investigating, I manage to get the desired result for my project. I first thought of using the bluewalker project to access the raw packets. With this you can scan in passive mode, meaning only the advertising packet is retrieved.
By looking more in depth into noble project, the one I actually use to interface with, there is a workaround to scan in passive mode (https://github.com/noble/noble/issues/701), but also a variable to capture both advertising and response packets: NOBLE_REPORT_ALL_HCI_EVENTS. Setting this to 1 will give me exactly what I need, both the scan request which contains the data that changes more frequently, and the scan response that contains more data, such as min/max 24h values. And as a matter of fact, combining this setting with duplicates=false seems to give me only the scan request data, just like in passive mode.
Question still opened:
Having this, I still don't know how to use bluetoothctl to display both scan request data along with the scan response. Nor did I find a way to force the scan mode to passive. I could investigate more hcitool hciconfig, but they are deprecated (although every article on the internet refers to them).

Related

Resources for field data on BLE transfer speeds

I'm currently working on a research project which revolves around me getting to know the transfer speeds of BLE in a simple setting. To be specific, I'll be working with an Arduino Nano 33 BLE board. I'm well aware that BLE v5 is capable of reaching speeds of up to 1Mb/s (Mega-bits/s) but is unrealistic in real-world applications. Are there any resources that I can get the transfer speeds of BLE? If not, I'm guessing I will have to work with an experimental setup for finding the speeds for my specific use-case. Thank you in advance!
The Bluetooth Radio on the Arduino Nano 33 BLE is built into the NRF52840 MCU.
More information on the Radio is found here:
https://infocenter.nordicsemi.com/topic/ps_nrf52840/radio.html?cp=4_0_0_5_19
There are definitely ways to determine real throughput of this peripheral, you just need a packet sniffer (link below) or have a transmitter/receiver board-to-board setup.
Packet Sniffer:
https://www.nordicsemi.com/Products/Development-tools/nRF-Sniffer-for-Bluetooth-LE
The board-to-board setup will have the relay serially send the number of packets received to a PC for analysis. You could configure the relay board to send the number of packets received within a certain interval (using the Timers in the NRF52840 with <microsecond precision).
If your project changes and you no longer need to use BLE and you would like to increase throughput to ~1.5Mbps, I developed and tested a working configuration of the NRF52840's Radio on the Arduino Nano 33 BLE. Link below.
https://forum.arduino.cc/t/stream-binary-data-from-arduino-nano-33-ble-to-pc-via-ble/917206

Has anyone used bleak to connect multiple BLE devices and receive notifications from all of them simultaneously?

I am able to use bleak and get data from all 5 BLE sensors. But the problem is that I am unable to identify which data is from which device. I mean i need a string representing the address of the device alongwith the data itself.
I was able to get data simultaneously from all the BLE modules using bleak in Windows, as well as on raspberry pi.
The only problem with Windows is that if you use Bluetooth 4.2 adapter & above. It will be much better for the high speed data rate, and proper devices connection handling. As with the 4.0 adapter, I have always gone through one or two exceptions each time i started the script, and the maximum number of connections I got was 3.
When i tried this script on Raspberry pi 3b+, it has on-board chip of Bluetooth 4.2. It was able to give high speed data rate, and my 5 sensors were connected to it simultaneously.
Also, The two_devices examples in bleak source code on Github, is very good example for starting with further coding.
And if you run the script and found the data on console, but you were unable to get that which data is from device. Then you need to use functools, (what it does is it will inject the client you're connected to at present, with the callback function, and it will make the work much easier).
Check this out on Github: https://github.com/hbldh/bleak/issues/601

Constant Delay in Bluetooth Low Energy (BLE) data transmission

I am trying to evaluate the suitability of some different wireless interfaces for our project on 2xRaspberry Pi 4 and currently I’m evaluating Bluetooth Low Energy. Therefore I have written an Central and Peripheral device application with the Qt framework (5.15). In my case the latency time between messages is important, because of some security aspects. The message size of each command is around 80-100 Bytes. In one of my tests I have sent 80 Bytes commands every 80ms. Ideally the messages should be received on the other device in 80ms interval as well. For the LAN (TCP) interface this test works well.
For Bluetooth Low Energy I observed that messages, which are sent from Peripheral to Central work quite good and I measured no big delay. Different results I got for the Central to Peripheral direction. Here, I have received the messages in the interval of 100ms to 150ms really exactly. It seems that there couldn’t be a very big magic behind it, so is there any plausible explanation for this? I tested it with a Python script as well and I observed the same results. So it seems that the Qt implementation shouldn’t be the problem.
During research I found out, that the connection interval may influence this, but in Qt the QLowEnergyConnectionParameterRequest (QLowEnergyConnectionParameters Class | Qt Bluetooth 5.15.4) doesn’t work for me. Is there any command, where I can set the connection interval for test purposes at the command line on Linux?
Kind regards,
BenFR
It is possible that your code is slower from central to peripheral because WRITE is used instead of WRITE WITHOUT RESPONSE. The difference is that WRITE waits for an acknowledgement, therefore slowing the communication down, while WRITE WITHOUT RESPONSE is very much like how notifications/indications work in that there's no ACK at the ATT layer. You can change this by changing the write mode of your application and ensuring that the peripheral's characteristic supports WriteNoResponse.
Regarding changing the connection interval, the change needs to be accepted from the remote side in order for it to take effect. In other words, if you are requesting the connection parameter change from the peripheral, then the central needs to have code to receive this connection parameter change request and accept it.
Have a look at the links below for more information:-
How does BLE parameter negotiation work
Understand BLE connection intervals and events
The different types of BLE write

Why is my iBeacon signal not detected every time it should send according to the interval?

I have a small BLE beacon which is configured to send iBeacon packets every 1000ms.
In my usecase i want to detect the signal on multiple recievers every time it is sent. However the detection is not reliable no matter which receiving device and software i use (phone, computer, raspberry). The signal is sometimes detected after 2 seconds, another time 5, 6 or whatever. It seems like there is no pattern behind it.
Also it seems that sometimes the signal is received on one receiver but not on the others while definetly being in range! Also the area i am testing in is not "problematic".
What could be the problem?
Not 100% of beacon packets transmitted are ever received. There are a number of reasons for this, including radio noise, packet collisions and channel hopping. That said, the typical detection rate in a quiet radio environment is around 90 percent.
If you are seeing a much lower rate than this on multiple receivers I would check the transmitter. First, use one of.your devices to transmit a software beacon (Android and iOS have free apps like Locate Beacon that do this.) If you get a higher detection rate with a different device transmitting, the issue may be your transmitter.
A few possible issues with it:
Bad antenna sending out a very weak signal. (Measure the received RSSI when you do get a detection and verify it is over -60 dBm)
Weak transmitter power setting. See if you can configure this higher.
Advertising on wrong channels
Advertising is stopped before packet can go out. Try to leave the advertiser on for at least 2x the transmission rate to ensure at least on packet gets out.
I assume you use a large enough scan window for your scan interval so your receiver radio is actually turned on most of the time.
You could try to send advertising packets of the type ADV_NONCONN_IND (non-connectable and no scan response packet). That way if the receiver radio scans with 100% duty it should see the packet.
Otherwise if you use normal ADV_IND packets, then at least Android always waits for the SCAN_RSP packet before it sends anything to the scanning app. But if the are multiple scanners nearby, your peripheral can only respond to a single scanner's SCAN_REQ for each advertising packet. To avoid collisions of SCAN_REQ packets in the air, Bluetooth controllers also back off if they don't get a SCAN_RSP in return. If you use a BLE sniffer you can see all three kinds of packets and what happens when you have multiple scanners nearby.
Read the BLE Link Layer part of the Bluetooth Core specification for more details.

Linux "connectionless" wlan

I'm currently planning to do cheap wireless video transmission from mobile, battery powered devices to a base station.
To be clear, I did not do any tests so far, but because the required range will be quite large (>2000ft/600m) and by my experience on wifi I'm quite sure this won't work using a standard wifi connection using standard german wifi cards (max 100mW power). Wifi requires a two-way connection to keep associated with each other.
However, I don't really care if my device can receive data from my base station.
I can use large antennas on the receiving side (base station) but not on the device. So I thought what is not there can't break. So my intention is to send 802.11 packets without beeing connected.
How can I send and receive 802.11 frames in Linux without the network stack adding or removing any data (or even dropping the packet because it does not know how to handle it) ?
An 802.11 frame at it's lowest level consists of the following fields:
Preamble | PLCP header | MPDU (MAC PDU)
My intent is to control anything that's inside the MPDU.
Thanks in advance.

Resources