dotnet-bluetooth-le icon indicating copy to clipboard operation
dotnet-bluetooth-le copied to clipboard

Cannot disconnect ble device, device state is limited

Open xxeasterxx opened this issue 7 years ago • 9 comments

Steps to reproduce

  1. Connect to BLE device

  2. Disconnect BLE device

Expected behavior

Show device is disconnected from system setting and not able to transmit data to mobile

Actual behavior

System setting still showing device connected and able to transmit data to mobile. device.State is limited before disconnecting, and after DisconnectDeviceAsync() is called, state is still limited.

Configuration

Version of the Plugin: Tried 1.0.3 and 2.0.0

Platform: Android 7.0

Device: Samsung J7

Below is my code for connecting and disconnecting:

Connect

                _bluetoothGatt = _device.ConnectGatt(this, false, new BGattCallback(this));
                Plugin.BLE.Android.Device device = new Plugin.BLE.Android.Device(
                    (Plugin.BLE.Android.Adapter)Plugin.BLE.CrossBluetoothLE.Current.Adapter,
                    _device, _bluetoothGatt, Rssi);

   
   Plugin.BLE.CrossBluetoothLE.Current.Adapter.GetSystemConnectedOrPairedDevices().FirstOrDefault(x => x.Id == Id);

                await Plugin.BLE.CrossBluetoothLE.Current.Adapter.ConnectToDeviceAsync(device);
                return device != null && device.State == Plugin.BLE.Abstractions.DeviceState.Connected || device.State == Plugin.BLE.Abstractions.DeviceState.Limited ? true : false;

Disconnect

                var device = Plugin.BLE.CrossBluetoothLE.Current.Adapter.GetSystemConnectedOrPairedDevices().FirstOrDefault(x => x.Id == Id);
                if (device != null)
                {
                    await Plugin.BLE.CrossBluetoothLE.Current.Adapter.DisconnectDeviceAsync(device);
                }

xxeasterxx avatar Jun 08 '18 07:06 xxeasterxx

Hi @xxeasterxx,

I'm the friendly issue checker. Thanks for using the issue template :star2: I appreciate it very much. I'm sure, the maintainers of this repository will answer, soon.

smsissuechecker avatar Jun 08 '18 07:06 smsissuechecker

The problem seems to lie in the TaskBuilder.FromEvent pattern in AdapterBase. DisconnectDeviceAsync and a missing DeviceDisconnected event in the case of _gatt == null in the Android Device implementation of Disconnect. This method doesn't do anything if there's no GATT.

            if (_gatt != null)
            {
                IsOperationRequested = true;

                ClearServices();

                _gatt.Disconnect();
            }
            else
            {
                Trace.Message("[Warning]: Can't disconnect {0}. Gatt is null.", Name);
            }

The Task returned from DisconnectDeviceAsync seems to never finish. Any await is hanging forever. One is able to circumvent this by leveraging Device. State and only disconnect in case of DeviceState. Connected.

In my opinion the library should handle this case more gracefully. Androids Device.Disconnect implementation should finish the Task correctly. I'd propose a fix and a Pull Request, but am not sure how to get this into the TaskBuilder.FromEvent pattern…

MKuckert avatar Dec 02 '19 06:12 MKuckert

Any update with this/workaround? experiencing the same issue :/ halting app from being production ready

smmutlu avatar Apr 01 '20 19:04 smmutlu

You can workaround by checking Device.State == DeviceState.Connected before disconnecting.

MKuckert avatar Apr 01 '20 20:04 MKuckert

Thank you Martin! I realized my problem was involved with trying to share a connected device across pages. Essentially I was connecting the device on one page, but upon fetching it from another page came back with DeviceState.Limited. After reconnecting disconnect did not work.

smmutlu avatar Apr 02 '20 01:04 smmutlu

Thank you, Martin! I realized my problem was involved with trying to share a connected device across pages. Essentially I was connecting the device on one page, but upon fetching it from another page came back with DeviceState.Limited. After reconnecting disconnect did not work.

I am facing this issue too. But instead of view pages, I am using a service class and the App class holds a static reference to it. When I try to disconnect it waits forever and Device State = Limited.

djad442 avatar Jul 06 '21 12:07 djad442

It appears to occur on paired devices only, disconnecting a non-paired device returns DeviceState.Disconnected as expected, but a paired device returns DeviceState.Limited.

Any workarounds other than checking for DeviceState.Connected as this is not working in my case when the device is paired.

jp54l avatar Aug 31 '21 12:08 jp54l

I was connecting twice on the same device

nictoul avatar Aug 31 '21 14:08 nictoul

Hi Reviving an old issue - i am facing the same problem on Android Could this check in AdapterBase.cs work?

if (device.State == DeviceState.Connecting)
                return;

I am thinking about preventing "connecting" multiple times to the BLE product. By "connecting" i mean issuing multiple Connect commands

narciszait avatar Apr 11 '23 21:04 narciszait