1 /****************************************************************************** 2 * 3 * Copyright 2019 The Android Open Source Project 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at: 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 * 17 ******************************************************************************/ 18 #pragma once 19 20 #include <map> 21 #include <mutex> 22 23 #include "hci/classic_device.h" 24 #include "hci/device.h" 25 #include "hci/dual_device.h" 26 #include "hci/le_device.h" 27 #include "os/log.h" 28 29 namespace bluetooth::hci { 30 31 /** 32 * Stores all of the paired or connected devices in the database. 33 * 34 * <p>If a device is stored here it is actively being used by the stack. 35 * 36 * <p>This database is not meant for scan results. 37 */ 38 class DeviceDatabase { 39 public: DeviceDatabase()40 DeviceDatabase() : classic_device_map_(), le_device_map_(), dual_device_map_() { 41 if (!ReadFromDisk()) { 42 LOG_WARN("First boot or missing data!"); 43 } 44 } 45 46 /** 47 * Adds a device to the internal memory map and triggers a WriteToDisk. 48 * 49 * @param address private address for device 50 * @return weak pointer to the device or empty pointer if device already exists 51 */ 52 std::shared_ptr<ClassicDevice> CreateClassicDevice(Address address); 53 54 /** 55 * Adds a device to the internal memory map and triggers a WriteToDisk. 56 * 57 * @param address private address for device 58 * @return weak pointer to the device or empty pointer if device already exists 59 */ 60 std::shared_ptr<LeDevice> CreateLeDevice(Address address); 61 62 /** 63 * Adds a device to the internal memory map and triggers a WriteToDisk. 64 * 65 * @param address private address for device 66 * @return weak pointer to the device or empty pointer if device already exists 67 */ 68 std::shared_ptr<DualDevice> CreateDualDevice(Address address); 69 70 /** 71 * Fetches a Classic Device matching the given uuid. 72 * 73 * @param uuid generated uuid from a Device 74 * @return a weak reference to the matching Device or empty shared_ptr (nullptr) 75 */ 76 std::shared_ptr<ClassicDevice> GetClassicDevice(const std::string& uuid); 77 78 /** 79 * Fetches a Le Device matching the given uuid. 80 * 81 * @param uuid generated uuid from a Device 82 * @return a weak reference to the matching Device or empty shared_ptr (nullptr) 83 */ 84 std::shared_ptr<LeDevice> GetLeDevice(const std::string& uuid); 85 86 /** 87 * Fetches a Dual Device matching the given uuid. 88 * 89 * @param uuid generated uuid from a Device 90 * @return a weak reference to the matching Device or empty shared_ptr (nullptr) 91 */ 92 std::shared_ptr<DualDevice> GetDualDevice(const std::string& uuid); 93 94 /** 95 * Removes a device from the internal database. 96 * 97 * @param device weak pointer to device to remove from the database 98 * @return <code>true</code> if the device is removed 99 */ 100 bool RemoveDevice(const std::shared_ptr<Device>& device); 101 102 /** 103 * Changes an address for a device. 104 * 105 * Also fixes the key mapping for the device. 106 * 107 * @param new_address this will replace the existing address 108 * @return <code>true</code> if updated 109 */ 110 bool UpdateDeviceAddress(const std::shared_ptr<Device>& device, Address new_address); 111 112 // TODO(optedoblivion): Make interfaces for device modification 113 // We want to keep the device modification encapsulated to the DeviceDatabase. 114 // Pass around shared_ptr to device, device metadata only accessible via Getters. 115 // Choices: 116 // a) Have Getters/Setters on device object 117 // b) Have Getters/Setters on device database accepting a device object 118 // c) Have Getters on device object and Setters on device database accepting a device object 119 // I chose to go with option c for now as I think it is the best option. 120 121 /** 122 * Fetches a list of classic devices. 123 * 124 * @return vector of weak pointers to classic devices 125 */ 126 std::vector<std::shared_ptr<Device>> GetClassicDevices(); 127 128 /** 129 * Fetches a list of le devices 130 * 131 * @return vector of weak pointers to le devices 132 */ 133 std::vector<std::shared_ptr<Device>> GetLeDevices(); 134 135 private: 136 std::mutex device_map_mutex_; 137 std::map<std::string, std::shared_ptr<ClassicDevice>> classic_device_map_; 138 std::map<std::string, std::shared_ptr<LeDevice>> le_device_map_; 139 std::map<std::string, std::shared_ptr<DualDevice>> dual_device_map_; 140 141 bool AddDeviceToMap(ClassicDevice&& device); 142 bool AddDeviceToMap(LeDevice&& device); 143 bool AddDeviceToMap(DualDevice&& device); 144 145 bool WriteToDisk(); 146 bool ReadFromDisk(); 147 }; 148 149 } // namespace bluetooth::hci 150