timeout for service discovery
This commit is contained in:
parent
9c0aa54e6b
commit
0582fe0326
3 changed files with 34 additions and 11 deletions
|
@ -7,6 +7,8 @@ import info.nightscout.androidaps.logging.LTag
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.callbacks.BleCommCallbacks
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.callbacks.BleCommCallbacks
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.exceptions.ConnectException
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.exceptions.ConnectException
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.io.CharacteristicType
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.io.CharacteristicType
|
||||||
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.session.Connection.Companion.STOP_CONNECTING_CHECK_INTERVAL_MS
|
||||||
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.session.ConnectionWaitCondition
|
||||||
import java.math.BigInteger
|
import java.math.BigInteger
|
||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
|
@ -19,14 +21,23 @@ class ServiceDiscoverer(
|
||||||
/***
|
/***
|
||||||
* This is first step after connection establishment
|
* This is first step after connection establishment
|
||||||
*/
|
*/
|
||||||
fun discoverServices(): Map<CharacteristicType, BluetoothGattCharacteristic> {
|
fun discoverServices(connectionWaitCond: ConnectionWaitCondition): Map<CharacteristicType, BluetoothGattCharacteristic> {
|
||||||
logger.debug(LTag.PUMPBTCOMM, "Discovering services")
|
logger.debug(LTag.PUMPBTCOMM, "Discovering services")
|
||||||
bleCallbacks.startServiceDiscovery()
|
bleCallbacks.startServiceDiscovery()
|
||||||
val discover = gatt.discoverServices()
|
val discover = gatt.discoverServices()
|
||||||
if (!discover) {
|
if (!discover) {
|
||||||
throw ConnectException("Could not start discovering services`")
|
throw ConnectException("Could not start discovering services`")
|
||||||
}
|
}
|
||||||
bleCallbacks.waitForServiceDiscovery(DISCOVER_SERVICES_TIMEOUT_MS)
|
connectionWaitCond.timeoutMs?.let {
|
||||||
|
bleCallbacks.waitForServiceDiscovery(it)
|
||||||
|
}
|
||||||
|
connectionWaitCond.stopConnection?.let {
|
||||||
|
while (!bleCallbacks.waitForConnection(STOP_CONNECTING_CHECK_INTERVAL_MS)) {
|
||||||
|
if (it.count == 0L) {
|
||||||
|
throw ConnectException("stopConnecting called")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
logger.debug(LTag.PUMPBTCOMM, "Services discovered")
|
logger.debug(LTag.PUMPBTCOMM, "Services discovered")
|
||||||
val service = gatt.getService(SERVICE_UUID.toUuid())
|
val service = gatt.getService(SERVICE_UUID.toUuid())
|
||||||
?: throw ConnectException("Service not found: $SERVICE_UUID")
|
?: throw ConnectException("Service not found: $SERVICE_UUID")
|
||||||
|
@ -34,11 +45,10 @@ class ServiceDiscoverer(
|
||||||
?: throw ConnectException("Characteristic not found: ${CharacteristicType.CMD.value}")
|
?: throw ConnectException("Characteristic not found: ${CharacteristicType.CMD.value}")
|
||||||
val dataChar = service.getCharacteristic(CharacteristicType.DATA.uuid)
|
val dataChar = service.getCharacteristic(CharacteristicType.DATA.uuid)
|
||||||
?: throw ConnectException("Characteristic not found: ${CharacteristicType.DATA.value}")
|
?: throw ConnectException("Characteristic not found: ${CharacteristicType.DATA.value}")
|
||||||
var chars = mapOf(
|
return mapOf(
|
||||||
CharacteristicType.CMD to cmdChar,
|
CharacteristicType.CMD to cmdChar,
|
||||||
CharacteristicType.DATA to dataChar
|
CharacteristicType.DATA to dataChar
|
||||||
)
|
)
|
||||||
return chars
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun String.toUuid(): UUID = UUID(
|
private fun String.toUuid(): UUID = UUID(
|
||||||
|
@ -49,6 +59,5 @@ class ServiceDiscoverer(
|
||||||
companion object {
|
companion object {
|
||||||
|
|
||||||
private const val SERVICE_UUID = "1a7e-4024-e3ed-4464-8b7e-751e03d0dc5f"
|
private const val SERVICE_UUID = "1a7e-4024-e3ed-4464-8b7e-751e03d0dc5f"
|
||||||
private const val DISCOVER_SERVICES_TIMEOUT_MS = 5000
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -66,9 +66,9 @@ class BleCommCallbacks(
|
||||||
serviceDiscoveryComplete = CountDownLatch(1)
|
serviceDiscoveryComplete = CountDownLatch(1)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun waitForServiceDiscovery(timeoutMs: Int) {
|
fun waitForServiceDiscovery(timeoutMs: Long) {
|
||||||
try {
|
try {
|
||||||
serviceDiscoveryComplete.await(timeoutMs.toLong(), TimeUnit.MILLISECONDS)
|
serviceDiscoveryComplete.await(timeoutMs, TimeUnit.MILLISECONDS)
|
||||||
} catch (e: InterruptedException) {
|
} catch (e: InterruptedException) {
|
||||||
aapsLogger.warn(LTag.PUMPBTCOMM, "Interrupted while waiting for ServiceDiscovery")
|
aapsLogger.warn(LTag.PUMPBTCOMM, "Interrupted while waiting for ServiceDiscovery")
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,6 +5,7 @@ import android.bluetooth.BluetoothGatt
|
||||||
import android.bluetooth.BluetoothManager
|
import android.bluetooth.BluetoothManager
|
||||||
import android.bluetooth.BluetoothProfile
|
import android.bluetooth.BluetoothProfile
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
|
import android.os.SystemClock
|
||||||
import info.nightscout.androidaps.extensions.toHex
|
import info.nightscout.androidaps.extensions.toHex
|
||||||
import info.nightscout.androidaps.logging.AAPSLogger
|
import info.nightscout.androidaps.logging.AAPSLogger
|
||||||
import info.nightscout.androidaps.logging.LTag
|
import info.nightscout.androidaps.logging.LTag
|
||||||
|
@ -23,6 +24,7 @@ import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.comm.message.
|
||||||
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.state.OmnipodDashPodStateManager
|
import info.nightscout.androidaps.plugins.pump.omnipod.dash.driver.pod.state.OmnipodDashPodStateManager
|
||||||
import java.lang.IllegalArgumentException
|
import java.lang.IllegalArgumentException
|
||||||
import java.util.concurrent.CountDownLatch
|
import java.util.concurrent.CountDownLatch
|
||||||
|
import kotlin.math.absoluteValue
|
||||||
|
|
||||||
sealed class ConnectionState
|
sealed class ConnectionState
|
||||||
|
|
||||||
|
@ -31,7 +33,7 @@ object Handshaking: ConnectionState()
|
||||||
object Connected : ConnectionState()
|
object Connected : ConnectionState()
|
||||||
object NotConnected : ConnectionState()
|
object NotConnected : ConnectionState()
|
||||||
|
|
||||||
data class ConnectionWaitCondition(val timeoutMs: Long?=null, val stopConnection: CountDownLatch?=null) {
|
data class ConnectionWaitCondition(var timeoutMs: Long?=null, val stopConnection: CountDownLatch?=null) {
|
||||||
init {
|
init {
|
||||||
if (timeoutMs == null && stopConnection == null) {
|
if (timeoutMs == null && stopConnection == null) {
|
||||||
throw IllegalArgumentException("One of timeoutMs or stopConnection has to be non null")
|
throw IllegalArgumentException("One of timeoutMs or stopConnection has to be non null")
|
||||||
|
@ -73,14 +75,24 @@ class Connection(
|
||||||
if (!gatt.connect()) {
|
if (!gatt.connect()) {
|
||||||
throw FailedToConnectException("connect() returned false")
|
throw FailedToConnectException("connect() returned false")
|
||||||
}
|
}
|
||||||
|
val before = SystemClock.elapsedRealtime()
|
||||||
if (waitForConnection(connectionWaitCond) !is Connected) {
|
if (waitForConnection(connectionWaitCond) !is Connected) {
|
||||||
podState.bluetoothConnectionState = OmnipodDashPodStateManager.BluetoothConnectionState.DISCONNECTED
|
podState.bluetoothConnectionState = OmnipodDashPodStateManager.BluetoothConnectionState.DISCONNECTED
|
||||||
throw FailedToConnectException(podDevice.address)
|
throw FailedToConnectException(podDevice.address)
|
||||||
}
|
}
|
||||||
|
val waitedMs = SystemClock.elapsedRealtime() - before
|
||||||
|
val timeoutMs = connectionWaitCond.timeoutMs
|
||||||
|
if (timeoutMs != null) {
|
||||||
|
var newTimeout = timeoutMs - waitedMs
|
||||||
|
if (newTimeout < MIN_DISCOVERY_TIMEOUT_MS) {
|
||||||
|
newTimeout = MIN_DISCOVERY_TIMEOUT_MS
|
||||||
|
}
|
||||||
|
connectionWaitCond.timeoutMs = newTimeout
|
||||||
|
}
|
||||||
podState.bluetoothConnectionState = OmnipodDashPodStateManager.BluetoothConnectionState.CONNECTED
|
podState.bluetoothConnectionState = OmnipodDashPodStateManager.BluetoothConnectionState.CONNECTED
|
||||||
|
|
||||||
val discoverer = ServiceDiscoverer(aapsLogger, gatt, bleCommCallbacks)
|
val discoverer = ServiceDiscoverer(aapsLogger, gatt, bleCommCallbacks)
|
||||||
val discovered = discoverer.discoverServices()
|
val discovered = discoverer.discoverServices(connectionWaitCond)
|
||||||
val cmdBleIO = CmdBleIO(
|
val cmdBleIO = CmdBleIO(
|
||||||
aapsLogger,
|
aapsLogger,
|
||||||
discovered[CharacteristicType.CMD]!!,
|
discovered[CharacteristicType.CMD]!!,
|
||||||
|
@ -121,9 +133,9 @@ class Connection(
|
||||||
bleCommCallbacks.waitForConnection(it)
|
bleCommCallbacks.waitForConnection(it)
|
||||||
}
|
}
|
||||||
connectionWaitCond.stopConnection?.let {
|
connectionWaitCond.stopConnection?.let {
|
||||||
while (!bleCommCallbacks.waitForConnection(300)) {
|
while (!bleCommCallbacks.waitForConnection(STOP_CONNECTING_CHECK_INTERVAL_MS)) {
|
||||||
if (it.count == 0L) {
|
if (it.count == 0L) {
|
||||||
return NotConnected
|
ConnectException("stopConnecting called")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -180,5 +192,7 @@ class Connection(
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
const val BASE_CONNECT_TIMEOUT_MS = 10000L
|
const val BASE_CONNECT_TIMEOUT_MS = 10000L
|
||||||
|
const val MIN_DISCOVERY_TIMEOUT_MS = 10000L
|
||||||
|
const val STOP_CONNECTING_CHECK_INTERVAL_MS = 500L
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue