diff --git a/CMakeLists.txt b/CMakeLists.txt index 6711474b..eada4f53 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -26,7 +26,7 @@ if (HALST_STANDALONE) FetchContent_Declare( emil GIT_REPOSITORY https://github.com/philips-software/amp-embedded-infra-lib.git - GIT_TAG f38e0ac947cf81a1d48ffd79b079ac3f8c20ccac # unreleased + GIT_TAG 0d8f096330aca30e935f84caf6b3c76c176cec34 # unreleased ) FetchContent_MakeAvailable(emil) diff --git a/hal_st/middlewares/ble_middleware/GapSt.cpp b/hal_st/middlewares/ble_middleware/GapSt.cpp index 2f360668..7ee29c71 100644 --- a/hal_st/middlewares/ble_middleware/GapSt.cpp +++ b/hal_st/middlewares/ble_middleware/GapSt.cpp @@ -62,17 +62,6 @@ namespace hal SVCCTL_Init(); } - uint16_t GapSt::EffectiveMaxAttMtuSize() const - { - return maxAttMtu; - } - - void GapSt::MtuExchange() - { - auto status = aci_gatt_exchange_config(this->connectionContext.connectionHandle); - assert(status == BLE_STATUS_SUCCESS); - } - void GapSt::RemoveAllBonds() { bondStorageSynchronizer.RemoveAllBonds(); @@ -229,11 +218,11 @@ namespace hal void GapSt::HandleMtuExchangeResponseEvent(const aci_att_exchange_mtu_resp_event_rp0& event) { really_assert(event.Connection_Handle == connectionContext.connectionHandle); - maxAttMtu = event.Server_RX_MTU; + SetAttMtu(event.Server_RX_MTU); - AttMtuExchange::NotifyObservers([](auto& observer) + services::AttMtuExchange::NotifyObservers([](auto& observer) { - observer.ExchangedMaxAttMtuSize(); + observer.ExchangedAttMtuSize(); }); } @@ -385,7 +374,7 @@ namespace hal void GapSt::SetConnectionContext(uint16_t connectionHandle, services::GapDeviceAddressType peerAddressType, const uint8_t* peerAddress) { - maxAttMtu = defaultMaxAttMtuSize; + SetAttMtu(defaultAttMtuSize); connectionContext.connectionHandle = connectionHandle; connectionContext.peerAddressType = peerAddressType; std::copy_n(peerAddress, connectionContext.peerAddress.size(), std::begin(connectionContext.peerAddress)); diff --git a/hal_st/middlewares/ble_middleware/GapSt.hpp b/hal_st/middlewares/ble_middleware/GapSt.hpp index acedf3f7..f65c61a1 100644 --- a/hal_st/middlewares/ble_middleware/GapSt.hpp +++ b/hal_st/middlewares/ble_middleware/GapSt.hpp @@ -12,7 +12,7 @@ namespace hal { class GapSt - : public services::AttMtuExchange + : public services::AttMtuExchangeImpl , public services::GapBonding , public services::GapPairing , private HciEventSink @@ -51,10 +51,6 @@ namespace hal bool privacy; }; - // Implementation of AttMtuExchange - uint16_t EffectiveMaxAttMtuSize() const override; - void MtuExchange() override; - // Implementation of GapBonding void RemoveAllBonds() override; void RemoveOldestBond() override; @@ -142,7 +138,6 @@ namespace hal private: services::BondStorageSynchronizer& bondStorageSynchronizer; - uint16_t maxAttMtu = defaultMaxAttMtuSize; }; } diff --git a/hal_st/middlewares/ble_middleware/GattClientSt.cpp b/hal_st/middlewares/ble_middleware/GattClientSt.cpp index 544cab5a..bde03179 100644 --- a/hal_st/middlewares/ble_middleware/GattClientSt.cpp +++ b/hal_st/middlewares/ble_middleware/GattClientSt.cpp @@ -18,7 +18,7 @@ namespace hal void GattClientSt::StartServiceDiscovery() { - onDiscoveryCompletion = [this](services::OperationStatus status) + onOperationDone = [this](services::OperationStatus status) { infra::Subject::NotifyObservers([status](auto& observer) { @@ -27,13 +27,12 @@ namespace hal }; auto ret = aci_gatt_disc_all_primary_services(connectionHandle); - if (ret != BLE_STATUS_SUCCESS) - onDiscoveryCompletion(services::OperationStatus::error); + HandleBleStatusError(ret); } void GattClientSt::StartCharacteristicDiscovery(services::AttAttribute::Handle handle, services::AttAttribute::Handle endHandle) { - onDiscoveryCompletion = [this](services::OperationStatus status) + onOperationDone = [this](services::OperationStatus status) { infra::Subject::NotifyObservers([status](auto& observer) { @@ -42,13 +41,12 @@ namespace hal }; auto ret = aci_gatt_disc_all_char_of_service(connectionHandle, handle, endHandle); - if (ret != BLE_STATUS_SUCCESS) - onDiscoveryCompletion(services::OperationStatus::error); + HandleBleStatusError(ret); } void GattClientSt::StartDescriptorDiscovery(services::AttAttribute::Handle handle, services::AttAttribute::Handle endHandle) { - onDiscoveryCompletion = [this](services::OperationStatus status) + onOperationDone = [this](services::OperationStatus status) { infra::Subject::NotifyObservers([status](auto& observer) { @@ -57,41 +55,32 @@ namespace hal }; auto ret = aci_gatt_disc_all_char_desc(connectionHandle, handle, endHandle); - if (ret != BLE_STATUS_SUCCESS) - onDiscoveryCompletion(services::OperationStatus::error); + HandleBleStatusError(ret); } void GattClientSt::Read(services::AttAttribute::Handle handle, const infra::Function& onResponse, const infra::Function& onDone) { - this->onReadResponse = onResponse; - this->onCharacteristicOperationsDone = [this, onDone](services::OperationStatus result) - { - onDone(result); - }; + onReadResponse = onResponse; + onOperationDone = onDone; auto ret = aci_gatt_read_char_value(connectionHandle, handle); - if (ret != BLE_STATUS_SUCCESS) - this->onCharacteristicOperationsDone(services::OperationStatus::error); + HandleBleStatusError(ret); } void GattClientSt::Write(services::AttAttribute::Handle handle, infra::ConstByteRange data, const infra::Function& onDone) { - this->onCharacteristicOperationsDone = [this, onDone](services::OperationStatus result) - { - onDone(result); - }; + onOperationDone = onDone; auto ret = aci_gatt_write_char_value(connectionHandle, handle, data.size(), data.cbegin()); - if (ret != BLE_STATUS_SUCCESS) - this->onCharacteristicOperationsDone(services::OperationStatus::error); + HandleBleStatusError(ret); } void GattClientSt::WriteWithoutResponse(services::AttAttribute::Handle handle, infra::ConstByteRange data, const infra::Function& onDone) { - auto var = aci_gatt_write_without_resp(connectionHandle, handle, data.size(), data.cbegin()); - if (var == BLE_STATUS_SUCCESS) + auto ret = aci_gatt_write_without_resp(connectionHandle, handle, data.size(), data.cbegin()); + if (ret == BLE_STATUS_SUCCESS) onDone(services::OperationStatus::success); - else if (var == BLE_STATUS_INSUFFICIENT_RESOURCES) + else if (ret == BLE_STATUS_INSUFFICIENT_RESOURCES) onDone(services::OperationStatus::retry); else onDone(services::OperationStatus::error); @@ -216,10 +205,9 @@ namespace hal void GattClientSt::HandleGattCompleteResponse(const aci_gatt_proc_complete_event_rp0& event) { - if (this->onDiscoveryCompletion) - this->onDiscoveryCompletion(event.Error_Code == BLE_STATUS_SUCCESS ? services::OperationStatus::success : services::OperationStatus::error); // Does this conflict with other operations? If not, why do we even get a GattComplete for discovery? - else if (this->onCharacteristicOperationsDone) - this->onCharacteristicOperationsDone(event.Error_Code == BLE_STATUS_SUCCESS ? services::OperationStatus::success : services::OperationStatus::error); + really_assert(onOperationDone); + + onOperationDone(event.Error_Code == BLE_STATUS_SUCCESS ? services::OperationStatus::success : services::OperationStatus::error); } void GattClientSt::HandleHciLeConnectionCompleteEvent(const hci_le_connection_complete_event_rp0& event) @@ -262,7 +250,7 @@ namespace hal { observer.IndicationReceived(event.Attribute_Handle, data, [this]() { - this->HandleGattConfirmIndication(); + HandleGattConfirmIndication(); }); }); } @@ -358,7 +346,31 @@ namespace hal const uint16_t offsetCccd = 1; auto ret = aci_gatt_write_char_desc(connectionHandle, handle + offsetCccd, sizeof(characteristicValue), reinterpret_cast(&characteristicValue)); - if (ret != BLE_STATUS_SUCCESS) - onCharacteristicOperationsDone(services::OperationStatus::error); + HandleBleStatusError(ret); + } + + void GattClientSt::MtuExchange(const infra::Function& onDone) + { + onOperationDone = onDone; + + auto status = aci_gatt_exchange_config(connectionHandle); + HandleBleStatusError(status); + } + + void GattClientSt::HandleAttExchangeMtuResponse(const aci_att_exchange_mtu_resp_event_rp0& event) + { + really_assert(event.Connection_Handle == connectionHandle); + SetAttMtu(event.Server_RX_MTU); + + AttMtuExchange::NotifyObservers([](auto& observer) + { + observer.ExchangedAttMtuSize(); + }); + } + + void GattClientSt::HandleBleStatusError(tBleStatus status) + { + if (status != BLE_STATUS_SUCCESS) + onOperationDone(services::OperationStatus::error); } } diff --git a/hal_st/middlewares/ble_middleware/GattClientSt.hpp b/hal_st/middlewares/ble_middleware/GattClientSt.hpp index 7eef58dd..57a60a3d 100644 --- a/hal_st/middlewares/ble_middleware/GattClientSt.hpp +++ b/hal_st/middlewares/ble_middleware/GattClientSt.hpp @@ -7,6 +7,7 @@ #include "infra/util/AutoResetFunction.hpp" #include "infra/util/BoundedVector.hpp" #include "infra/util/Function.hpp" +#include "services/ble/Gatt.hpp" #include "services/ble/GattClient.hpp" namespace hal @@ -14,6 +15,7 @@ namespace hal class GattClientSt : public services::GattClient , public hal::HciEventSink + , public services::AttMtuExchangeImpl { public: explicit GattClientSt(hal::HciEventSource& hciEventSource); @@ -29,6 +31,7 @@ namespace hal void DisableNotification(services::AttAttribute::Handle handle, const infra::Function& onDone) override; void EnableIndication(services::AttAttribute::Handle handle, const infra::Function& onDone) override; void DisableIndication(services::AttAttribute::Handle handle, const infra::Function& onDone) override; + void MtuExchange(const infra::Function& onDone) override; // Implementation of hal::HciEventSink void HciEvent(hci_event_pckt& event) override; @@ -50,6 +53,7 @@ namespace hal virtual void HandleAttReadByGroupTypeResponse(const aci_att_read_by_group_type_resp_event_rp0& event); virtual void HandleAttReadByTypeResponse(const aci_att_read_by_type_resp_event_rp0& event); virtual void HandleAttFindInfoResponse(const aci_att_find_info_resp_event_rp0& event); + virtual void HandleAttExchangeMtuResponse(const aci_att_exchange_mtu_resp_event_rp0& event); virtual void HandleServiceDiscovered(infra::DataInputStream& stream, bool isUuid16); void HandleUuidFromDiscovery(infra::DataInputStream& stream, bool isUuid16, services::AttAttribute::Uuid& type); @@ -59,11 +63,12 @@ namespace hal void HandleDescriptorDiscovered(infra::DataInputStream& stream, bool isUuid16); void WriteCharacteristicDescriptor(services::AttAttribute::Handle handle, services::GattCharacteristic::PropertyFlags property, services::GattDescriptor::ClientCharacteristicConfiguration::CharacteristicValue characteristicValue); + void HandleBleStatusError(tBleStatus status); template void WriteCharacteristicDescriptor(services::AttAttribute::Handle handle, const infra::Function& onDone) { - this->onCharacteristicOperationsDone = [this, onDone](services::OperationStatus result) + this->onOperationDone = [this, onDone](services::OperationStatus result) { onDone(result); }; @@ -85,9 +90,8 @@ namespace hal static constexpr uint16_t invalidConnection = 0xffff; - infra::AutoResetFunction onDiscoveryCompletion; infra::AutoResetFunction onReadResponse; - infra::AutoResetFunction)> onCharacteristicOperationsDone; + infra::AutoResetFunction)> onOperationDone; }; } diff --git a/hal_st/middlewares/ble_middleware/GattServerSt.hpp b/hal_st/middlewares/ble_middleware/GattServerSt.hpp index b0d0388e..dd352e2d 100644 --- a/hal_st/middlewares/ble_middleware/GattServerSt.hpp +++ b/hal_st/middlewares/ble_middleware/GattServerSt.hpp @@ -3,6 +3,7 @@ #include "ble/ble.h" #include "hal_st/middlewares/ble_middleware/HciEventObserver.hpp" +#include "services/ble/Gatt.hpp" #include "services/ble/GattServer.hpp" namespace hal @@ -11,6 +12,8 @@ namespace hal : public services::GattServer , public services::GattServerCharacteristicOperations , public hal::HciEventSink + , public services::AttMtuExchangeImpl + { public: explicit GattServerSt(hal::HciEventSource& hciEventSource); diff --git a/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.cpp b/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.cpp index 20afaa5f..408be575 100644 --- a/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.cpp +++ b/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.cpp @@ -99,8 +99,8 @@ namespace void ShciCore2Init(const hal::SystemTransportLayerWb::Configuration& configuration) { const uint8_t maxNumberOfBleLinks = 0x01; - const uint8_t prepareWriteListSize = BLE_PREP_WRITE_X_ATT(configuration.maxAttMtuSize); - const uint8_t numberOfBleMemoryBlocks = BLE_MBLOCKS_CALC(prepareWriteListSize, configuration.maxAttMtuSize, maxNumberOfBleLinks); + const uint8_t prepareWriteListSize = BLE_PREP_WRITE_X_ATT(configuration.attMtuSize); + const uint8_t numberOfBleMemoryBlocks = BLE_MBLOCKS_CALC(prepareWriteListSize, configuration.attMtuSize, maxNumberOfBleLinks); const uint8_t bleStackOptions = (SHCI_C2_BLE_INIT_OPTIONS_LL_HOST | SHCI_C2_BLE_INIT_OPTIONS_WITH_SVC_CHANGE_DESC | SHCI_C2_BLE_INIT_OPTIONS_DEVICE_NAME_RO | SHCI_C2_BLE_INIT_OPTIONS_NO_EXT_ADV | SHCI_C2_BLE_INIT_OPTIONS_NO_CS_ALGO2 | SHCI_C2_BLE_INIT_OPTIONS_FULL_GATTDB_NVM | SHCI_C2_BLE_INIT_OPTIONS_GATT_CACHING_NOTUSED | SHCI_C2_BLE_INIT_OPTIONS_POWER_CLASS_2_3 | SHCI_C2_BLE_INIT_OPTIONS_APPEARANCE_READONLY | SHCI_C2_BLE_INIT_OPTIONS_ENHANCED_ATT_NOTSUPPORTED); @@ -130,7 +130,7 @@ namespace 0x01, // Enable or disable the Extended Packet length feature prepareWriteListSize, numberOfBleMemoryBlocks, - configuration.maxAttMtuSize, + configuration.attMtuSize, 0x1FA, // Sleep clock accuracy in Slave mode 0x00, // Sleep clock accuracy in Master mode ToLowSpeedClock(configuration.rfWakeupClock), // Source for the low speed clock for RF wake-up @@ -163,8 +163,8 @@ namespace hal , configuration(configuration) , onInitialized(onInitialized) { - really_assert(configuration.maxAttMtuSize >= BLE_DEFAULT_ATT_MTU && configuration.maxAttMtuSize <= 251); - // BLE middleware supported maxAttMtuSize = 512. Current usage of library limits maxAttMtuSize to 251 (max HCI buffer size) + really_assert(configuration.attMtuSize >= BLE_DEFAULT_ATT_MTU && configuration.attMtuSize <= 251); + // BLE middleware supported attMtuSize = 512. Current usage of library limits attMtuSize to 251 (max HCI buffer size) TL_Init(); ShciInit(); diff --git a/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.hpp b/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.hpp index b66991b1..0aa8f5b1 100644 --- a/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.hpp +++ b/hal_st/middlewares/ble_middleware/SystemTransportLayerWb.hpp @@ -24,7 +24,7 @@ namespace hal struct Configuration { - uint16_t maxAttMtuSize; + uint16_t attMtuSize; RfWakeupClock rfWakeupClock; }; diff --git a/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.cpp b/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.cpp index 7bd8e706..945baed8 100644 --- a/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.cpp +++ b/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.cpp @@ -2,8 +2,8 @@ #include extern "C" { -#include "ble_common.h" #include "ble_bufsize.h" +#include "ble_common.h" #include "blestack.h" } @@ -21,7 +21,7 @@ extern "C" tBleStatus ProcessEventPacket(const uint8_t* data) { - SVCCTL_UserEvtRx(const_cast(data)); + SVCCTL_UserEvtRx(const_cast(data)); return BLE_STATUS_SUCCESS; } @@ -50,18 +50,18 @@ namespace std::array bleGattBuffer; const uint8_t bleStackOptions = 0; - constexpr uint8_t PrepareWriteListSize(uint16_t maxAttMtuSize) + constexpr uint8_t PrepareWriteListSize(uint16_t attMtuSize) { - return static_cast(BLE_PREP_WRITE_X_ATT(maxAttMtuSize)); + return static_cast(BLE_PREP_WRITE_X_ATT(attMtuSize)); } } namespace hal { - SystemTransportLayerWba::SystemTransportLayerWba(uint16_t maxAttMtuSize) + SystemTransportLayerWba::SystemTransportLayerWba(uint16_t attMtuSize) { - really_assert(maxAttMtuSize >= BLE_DEFAULT_ATT_MTU && maxAttMtuSize <= 251); - // BLE middleware supported maxAttMtuSize = 512. Current usage of library limits maxAttMtuSize to 251 (max HCI buffer size) + really_assert(attMtuSize >= BLE_DEFAULT_ATT_MTU && attMtuSize <= 251); + // BLE middleware supported attMtuSize = 512. Current usage of library limits attMtuSize to 251 (max HCI buffer size) BleStack_init_t bleStackInitParameters = { reinterpret_cast(bleBuffer.begin()), @@ -72,9 +72,9 @@ namespace hal numAttrServ, attrValueArrSize, maxNumberOfBleLinks, - PrepareWriteListSize(maxAttMtuSize), + PrepareWriteListSize(attMtuSize), mblockCount, - maxAttMtuSize, + attMtuSize, 248, 64, maxNumberOfConnectionOrientedChannels, diff --git a/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.hpp b/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.hpp index b6692244..8a280b7d 100644 --- a/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.hpp +++ b/hal_st/middlewares/ble_middleware/SystemTransportLayerWba.hpp @@ -11,7 +11,7 @@ namespace hal , public HciEventSource { public: - explicit SystemTransportLayerWba(uint16_t maxAttMtuSize); + explicit SystemTransportLayerWba(uint16_t attMtuSize); // Implementation of HciEventSource void HciEventHandler(hci_event_pckt& event) override; diff --git a/hal_st/middlewares/ble_middleware/TracingGattClientSt.cpp b/hal_st/middlewares/ble_middleware/TracingGattClientSt.cpp index 8cf6a1ae..d20fa971 100644 --- a/hal_st/middlewares/ble_middleware/TracingGattClientSt.cpp +++ b/hal_st/middlewares/ble_middleware/TracingGattClientSt.cpp @@ -69,6 +69,12 @@ namespace hal GattClientSt::DisableIndication(handle, onDone); } + void TracingGattClientSt::MtuExchange(const infra::Function& onDone) + { + tracer.Trace() << "TracingGattClientSt::MtuExchange"; + GattClientSt::MtuExchange(onDone); + } + void TracingGattClientSt::HandleGattIndicationEvent(const aci_gatt_indication_event_rp0& event) { infra::ConstByteRange data(&event.Attribute_Value[0], &event.Attribute_Value[0] + event.Attribute_Value_Length); diff --git a/hal_st/middlewares/ble_middleware/TracingGattClientSt.hpp b/hal_st/middlewares/ble_middleware/TracingGattClientSt.hpp index 53cea2b3..6a341a0e 100644 --- a/hal_st/middlewares/ble_middleware/TracingGattClientSt.hpp +++ b/hal_st/middlewares/ble_middleware/TracingGattClientSt.hpp @@ -23,6 +23,7 @@ namespace hal void DisableNotification(services::AttAttribute::Handle handle, const infra::Function& onDone) override; void EnableIndication(services::AttAttribute::Handle handle, const infra::Function& onDone) override; void DisableIndication(services::AttAttribute::Handle handle, const infra::Function& onDone) override; + void MtuExchange(const infra::Function& onDone) override; protected: void HandleGattIndicationEvent(const aci_gatt_indication_event_rp0& event) override;