summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlex Blasche <alexander.blasche@theqtcompany.com>2015-04-10 15:13:25 +0200
committerAlex Blasche <alexander.blasche@theqtcompany.com>2015-04-15 08:31:11 +0000
commit0cf802e9dd963e5eb881a3e849beb4143d7c304c (patch)
tree5ff6238e02a0ba777098e746fdf6276d2b5c2c15
parent6bb265e12c1e59078da9e9190bb11f6ac957b2cd (diff)
Android: Fix read/write error reports when failure during initial call
The BluetoothGatt.[read|write][Characteristic|Descriptor]() functions may immediately return under certain circumstances such as writing a read-only characteristic. So far, this "synchronous" form of error reporting was not handled. Any read error during the initial service dioscovery and its related cache population continues to surpress any read errors. Change-Id: I4987f67f4a0d2afe58cd144a577a19e0f0d43b33 Reviewed-by: Timur Pocheptsov <Timur.Pocheptsov@digia.com>
-rw-r--r--src/android/bluetooth/src/org/qtproject/qt5/android/bluetooth/QtBluetoothLE.java32
-rw-r--r--src/bluetooth/qlowenergycontroller_android.cpp6
2 files changed, 38 insertions, 0 deletions
diff --git a/src/android/bluetooth/src/org/qtproject/qt5/android/bluetooth/QtBluetoothLE.java b/src/android/bluetooth/src/org/qtproject/qt5/android/bluetooth/QtBluetoothLE.java
index 40286271..7118ce24 100644
--- a/src/android/bluetooth/src/org/qtproject/qt5/android/bluetooth/QtBluetoothLE.java
+++ b/src/android/bluetooth/src/org/qtproject/qt5/android/bluetooth/QtBluetoothLE.java
@@ -1031,6 +1031,38 @@ public class QtBluetoothLE {
if (skip) {
Log.w(TAG, "Skipping: " + nextJob.entry.type);
+
+ /*
+ BluetoothGatt.[read|write][Characteristic|Descriptor]() immediately
+ return in cases where meta data doesn't match the intended action
+ (e.g. trying to write to read-only char). When this happens
+ we have to report an error back to Qt. This is not required during
+ the initial service discovery though.
+ */
+ final boolean isServiceDiscoveryRun = (runningHandle != -1);
+ if (!isServiceDiscoveryRun) {
+ int handle = -1;
+ if (nextJob.entry.type == GattEntryType.Characteristic)
+ handle = handleForCharacteristic(nextJob.entry.characteristic);
+ else
+ handle = handleForDescriptor(nextJob.entry.descriptor);
+
+ if (handle != -1) {
+ int errorCode = 0;
+
+ // The error codes below must be in sync with QLowEnergyService::ServiceError
+ if (nextJob.jobType == IoJobType.Read) {
+ errorCode = (nextJob.entry.type == GattEntryType.Characteristic) ?
+ 5 : 6; // CharacteristicReadError : DescriptorReadError
+ } else {
+ errorCode = (nextJob.entry.type == GattEntryType.Characteristic) ?
+ 2 : 3; // CharacteristicWriteError : DescriptorWriteError
+ }
+
+ leServiceError(qtObject, handle + 1, errorCode);
+ }
+ }
+
performNextIO();
}
}
diff --git a/src/bluetooth/qlowenergycontroller_android.cpp b/src/bluetooth/qlowenergycontroller_android.cpp
index 992427ff..f48c0e85 100644
--- a/src/bluetooth/qlowenergycontroller_android.cpp
+++ b/src/bluetooth/qlowenergycontroller_android.cpp
@@ -80,6 +80,8 @@ void QLowEnergyControllerPrivate::connectToDevice()
this, &QLowEnergyControllerPrivate::descriptorWritten);
connect(hub, &LowEnergyNotificationHub::characteristicChanged,
this, &QLowEnergyControllerPrivate::characteristicChanged);
+ connect(hub, &LowEnergyNotificationHub::serviceError,
+ this, &QLowEnergyControllerPrivate::serviceError);
}
if (!hub->javaObject().isValid()) {
@@ -563,6 +565,10 @@ void QLowEnergyControllerPrivate::characteristicChanged(
void QLowEnergyControllerPrivate::serviceError(
int attributeHandle, QLowEnergyService::ServiceError errorCode)
{
+ // ignore call if it isn't really an error
+ if (errorCode == QLowEnergyService::NoError)
+ return;
+
QSharedPointer<QLowEnergyServicePrivate> service =
serviceForHandle(attributeHandle);
Q_ASSERT(!service.isNull());