| /* |
| * Copyright 2021 The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| #include "hci/vendor_specific_event_manager.h" |
| |
| #include "hci/controller.h" |
| #include "hci/hci_layer.h" |
| #include "hci/hci_packets.h" |
| |
| namespace bluetooth { |
| namespace hci { |
| |
| const ModuleFactory VendorSpecificEventManager::Factory = |
| ModuleFactory([]() { return new VendorSpecificEventManager(); }); |
| |
| struct VendorSpecificEventManager::impl { |
| impl(Module* module) : module_(module){}; |
| |
| ~impl() {} |
| |
| void start(os::Handler* handler, hci::HciLayer* hci_layer, hci::Controller* controller) { |
| module_handler_ = handler; |
| hci_layer_ = hci_layer; |
| controller_ = controller; |
| hci_layer_->RegisterEventHandler( |
| EventCode::VENDOR_SPECIFIC, handler->BindOn(this, &VendorSpecificEventManager::impl::on_vendor_specific_event)); |
| vendor_capabilities_ = controller->GetVendorCapabilities(); |
| } |
| |
| void stop() {} |
| |
| void register_event(VseSubeventCode event, common::ContextualCallback<void(VendorSpecificEventView)> handler) { |
| ASSERT_LOG( |
| subevent_handlers_.count(event) == 0, |
| "Can not register a second handler for %02hhx (%s)", |
| event, |
| VseSubeventCodeText(event).c_str()); |
| subevent_handlers_[event] = handler; |
| } |
| |
| void unregister_event(VseSubeventCode event) { |
| subevent_handlers_.erase(subevent_handlers_.find(event)); |
| } |
| |
| bool check_event_supported(VseSubeventCode event) { |
| switch (event) { |
| case (VseSubeventCode::BLE_THRESHOLD): { |
| if (vendor_capabilities_.total_scan_results_storage_ > 0) { |
| return true; |
| } |
| } break; |
| case (VseSubeventCode::BLE_TRACKING): { |
| if (vendor_capabilities_.total_num_of_advt_tracked_ > 0) { |
| return true; |
| } |
| } break; |
| case (VseSubeventCode::DEBUG_INFO): { |
| return vendor_capabilities_.debug_logging_supported_; |
| } break; |
| case (VseSubeventCode::BQR_EVENT): { |
| return vendor_capabilities_.bluetooth_quality_report_support_; |
| } break; |
| default: |
| LOG_WARN("Unhandled event %s", VseSubeventCodeText(event).c_str()); |
| } |
| return false; |
| } |
| |
| void on_vendor_specific_event(EventView event_view) { |
| auto vendor_specific_event_view = VendorSpecificEventView::Create(event_view); |
| ASSERT(vendor_specific_event_view.IsValid()); |
| VseSubeventCode vse_subevent_code = vendor_specific_event_view.GetSubeventCode(); |
| if (subevent_handlers_.find(vse_subevent_code) == subevent_handlers_.end()) { |
| LOG_WARN("Unhandled vendor specific event of type 0x%02hhx", vse_subevent_code); |
| return; |
| } |
| subevent_handlers_[vse_subevent_code].Invoke(vendor_specific_event_view); |
| } |
| |
| Module* module_; |
| os::Handler* module_handler_; |
| hci::HciLayer* hci_layer_; |
| hci::Controller* controller_; |
| VendorCapabilities vendor_capabilities_; |
| std::map<VseSubeventCode, common::ContextualCallback<void(VendorSpecificEventView)>> subevent_handlers_; |
| }; |
| |
| VendorSpecificEventManager::VendorSpecificEventManager() { |
| pimpl_ = std::make_unique<impl>(this); |
| } |
| |
| void VendorSpecificEventManager::ListDependencies(ModuleList* list) const { |
| list->add<hci::HciLayer>(); |
| list->add<hci::Controller>(); |
| } |
| |
| void VendorSpecificEventManager::Start() { |
| pimpl_->start(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>()); |
| } |
| |
| void VendorSpecificEventManager::Stop() { |
| pimpl_->stop(); |
| pimpl_.reset(); |
| } |
| |
| std::string VendorSpecificEventManager::ToString() const { |
| return "Vendor Specific Event Manager"; |
| } |
| |
| void VendorSpecificEventManager::RegisterEventHandler( |
| VseSubeventCode event, common::ContextualCallback<void(VendorSpecificEventView)> handler) { |
| CallOn(pimpl_.get(), &impl::register_event, event, handler); |
| } |
| |
| void VendorSpecificEventManager::UnregisterEventHandler(VseSubeventCode event) { |
| CallOn(pimpl_.get(), &impl::unregister_event, event); |
| } |
| |
| } // namespace hci |
| } // namespace bluetooth |