The Problem:
The bluetooth connection between the android app(GATT client) and two TI boards(CC2640R2F, GATT server) is unstable. When the android app connects to the two boards, the bluetooth connection state of the two boards toggle rapidly between connected and disconnected states. As a result the service discovery process is affected and sometimes there are no GATT characteristics discovered(The GATT service is just empty). The problem occurs with only android devices running marshmallow(6.0+) and above.
This issue also occurs on other third-party apps available in the play store such as BLE scanner, sensorTag and nrf connect running on those android devices.
Fixes attempted on Android side:
The following fixes were attempted on the Android side but these were unsuccessful.
a time delay(tried upto 2000ms) was set between connection successful event and gatt.discoverServices() request.
Have separate device.gattConnect(...) methods for devices below and above marshmallow(6.0). Devices above marshmallow require a TRANSPORT parameter.
Switch connection between the GATT servers to ensure that only one server is connected at a given time.
Created separate Gatt callbacks for the two servers and separate threads for all the operations that took place involving the two servers.
The only fix that was successful is connecting only one server to the client. To connect another server, the app needs to be reopened. If another device is connected at the same time, the issue still occurs.
Data Collected:
The bluetooth sniffer logs were collected from the android side and are attached.
The 'btsnoop_hci_success.log' file deals with the successful BLE connection between an android device(Samsung galaxy s7 edge) running marshmallow(6.0.1) and just one server(a purifier).
The 'btsnoop_hci_fail.log' file deals with the problematic BLE connection between the same android device and two servers(a sensor and a purifier).
Related
I have an Android app acting as a peripheral server sending accelerometer data via notifications to the central client (an RN4871 module).
Things work fine if I manually initiate the connection from the RN4871 using the phone's randomized MAC address, but I would like to pair the two to make connection easier so I can do it through software instead of manually.
I send the bonding request from the RN4871 on the phone and the phone allows me to accept it.
%INDI,0003,0100FFFF%%INDI,0003,0100FFFF%%SECURED%%BONDED%
There seem to be some handshake messages which are sent: %CONN_PARAM,0006,0000,01F4%%CONN_PARAM,0016,0000,0200%
I think maybe these are updating the connection parameters to the following:
2021-03-08 10:01:26.932 16804-17751/ece558.bthornhill.edu.jumprope D/BluetoothGattServer: onConnectionUpdated() - Device=D8:80:39:F8:B2:77 interval=6 latency=0 timeout=500 status=0
2021-03-08 10:01:27.599 16804-17751/ece558.bthornhill.edu.jumprope D/BluetoothGattServer: onConnectionUpdated() - Device=D8:80:39:F8:B2:77 interval=22 latency=0 timeout=512 status=0
But then the app seems to freeze. I can disconnect the connection on both sides by exiting the app, and running the connection kill command on the RN4871, but when I set the app in advertising mode again, and try to connect to the newly listed bonded device, the connection never happens and it just cycles.
I can get things working again only when I unpair the device from the phone, remove the phone as a bonded item from the RN4871, and restart the RN4871 and the app.
I can't seem to pinpoint what the exact issue is. Any help would be appreciated.
I want to connect and stream the multiple Bluetooth low energy sensors by matching their gatt profiles. All the sensors devices are of the same type but different mac address. So I want to connect those sensors to my mobile application and stream those data to our other application through the serial port. I know the Bluetooth can connect to 7 devices at a time.
But for connectivity with Android devices, it is not stated properly and still in a dilemma. Or else is it possible to connect external Bluetooth module to the android box to connect it to multiple devices? If yes then to do this what are the changes I need to perform on my system? How many devices can be used to communicate with the Android device at the same time? Can the android box act as a master that collects all the data from the peripherals and stream via the serial port. We have completed our process for a single sensor. Or is there any other possibility to stream multiple ble sensor data to another device through serial port write. please guide me through this process.
Execute connectGatt one time for every device, which will then give you one BluetoothGatt object per device. The callback object can be the same, or a separate instance per device, it depends on the use-case but most probably the devices serve different purposes so you'll have separate specific instances per device.
As long as you have a BluetoothDevice object, you can make a GATT connection to it. You can get it either using Bluetooth device address (which can sometimes be problematic since the API misses the random / public address type bit) or by a scan. You can have one outstanding GATT operation at a time, per BluetoothGatt object, so yes you can read / write characteristics to both devices simultaneously.
Feel free to post some source code for more analysis.
I'm developing android applications which shows real-time data via UDP using WIFI connection on static IP addresses. I'm using AsyncTask class which is executed in one second period.
My problem is that the communication via UDP is interrupted by other applications (for example Facebook - ARP requests) because the WIFI is connected to the IP local device without internet connection.
The interruption is during execution method: socket.receive();
Is there a way to use wifi only for my developed application and has it disabled for other apps?
How to detect if Android wear switched the connection from bluetooth to wifi or vice versa? And is there a way to force it to connect via bluetooth?
Being an Android framework, you can register a broadcast receiver to be notified when connectivity status changes. In general, when your watch is connected to a phone directly (which only happens via BT), wifi connection is dropped and when it is not connected, if your phone is wifi capable and if a wifi network is available, it gets connected to the cloud node. In that case, you cannot force it to connect through BT since, most likely, it is not possible (might be due to distance or many other reasons). What exactly are you trying to accomplish?
I have been running into an issue with my product that has a rooted tablet (iball 3G 7271,running on 4.1.2) which is trying to communicate with an RN42 Bluetooth module.As per my project requirement the android app, which initiates the BT connectivity to the RN42 must have capability to:
Be updated remotely
Should restart itself in case if it crashes.Both these functionality
have been coded and found working.
However as you know in both these cases the Bluetooth connectivity is disrupted and lost,and has to be re-established between the tablet and the RN42.
The problem I am facing is that,when the app which was connected via Bluetooth to RN42(is either updated/restarted as per case 1 or case2) leaves the bluetooth socket/port in the connected/open state itself,whilst the new app is re-installed/restarted respectively.Hence the newly re-installed/restarted app, when it initiates a bluetooth connection with the RN42, the device OS allocates it a new bluetooth socket/port(and not the older one since it is still occupied). But after a couple of re-installs/restarts(20 to be precise) the device runs out of any available socket port which it can allocate to the app and I get repeated exception stating 'Connection not created(failed or aborted)'.
Is there a way that I can close the bluetooth socket/port which was left open by an app prior to its reinstall/restart?
I had such issues with different BT chipset (mainly from lowcost tablet) and switching on/off the Bluetooth adapter did the job, through .enable() or .disabled().
Notice it is a bad idea, bad practice, but in the scope of my mockup it was usefull for debug :)
BluetoothAdapter mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
mBluetoothAdapter.disable();
while(mBluetoothAdapter.isEnabled());
mBluetoothAdapter.enable();
while(!mBluetoothAdapter.isEnabled());