1 /* 2 * Copyright (C) 2019 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 #ifndef CONFIG_MANAGER_H 17 #define CONFIG_MANAGER_H 18 19 #include <vector> 20 #include <string> 21 #include <unordered_map> 22 #include <unordered_set> 23 24 #include <tinyxml2.h> 25 26 #include <system/camera_metadata.h> 27 #include <android/hardware/automotive/evs/1.1/types.h> 28 #include <android-base/logging.h> 29 30 #include "ConfigManagerUtil.h" 31 32 using namespace std; 33 using namespace tinyxml2; 34 35 using ::android::hardware::hidl_vec; 36 using ::android::hardware::camera::device::V3_2::Stream; 37 using ::android::hardware::automotive::evs::V1_1::CameraParam; 38 39 /* 40 * Plese note that this is different from what is defined in 41 * libhardware/modules/camera/3_4/metadata/types.h; this has one additional 42 * field to store a framerate. 43 */ 44 const size_t kStreamCfgSz = 6; 45 typedef std::array<int32_t, kStreamCfgSz> RawStreamConfiguration; 46 47 class ConfigManager { 48 public: 49 static std::unique_ptr<ConfigManager> Create(); 50 ConfigManager(const ConfigManager&) = delete; 51 ConfigManager& operator=(const ConfigManager&) = delete; 52 53 virtual ~ConfigManager(); 54 55 /* Camera device's capabilities and metadata */ 56 class CameraInfo { 57 public: CameraInfo()58 CameraInfo() : 59 characteristics(nullptr) { 60 /* Nothing to do */ 61 } 62 63 virtual ~CameraInfo(); 64 65 /* Allocate memory for camera_metadata_t */ allocate(size_t entry_cap,size_t data_cap)66 bool allocate(size_t entry_cap, size_t data_cap) { 67 if (characteristics != nullptr) { 68 LOG(ERROR) << "Camera metadata is already allocated"; 69 return false; 70 } 71 72 characteristics = allocate_camera_metadata(entry_cap, data_cap); 73 return characteristics != nullptr; 74 } 75 76 /* 77 * List of supported controls that the primary client can program. 78 * Paraemters are stored with its valid range 79 */ 80 unordered_map<CameraParam, 81 tuple<int32_t, int32_t, int32_t>> controls; 82 83 /* 84 * List of supported output stream configurations; each array stores 85 * format, width, height, and direction values in the order. 86 */ 87 unordered_map<int32_t, RawStreamConfiguration> streamConfigurations; 88 89 /* 90 * Internal storage for camera metadata. Each entry holds a pointer to 91 * data and number of elements 92 */ 93 unordered_map<camera_metadata_tag_t, 94 pair<void *, size_t>> cameraMetadata; 95 96 /* Camera module characteristics */ 97 camera_metadata_t *characteristics; 98 }; 99 100 class CameraGroupInfo : public CameraInfo { 101 public: CameraGroupInfo()102 CameraGroupInfo() {} 103 104 /* ID of member camera devices */ 105 unordered_set<string> devices; 106 107 /* The capture operation of member camera devices are synchronized */ 108 int32_t synchronized = 0; 109 }; 110 111 class SystemInfo { 112 public: 113 /* number of available cameras */ 114 int32_t numCameras = 0; 115 }; 116 117 class DisplayInfo { 118 public: 119 /* 120 * List of supported input stream configurations; each array stores 121 * format, width, height, and direction values in the order. 122 */ 123 unordered_map<int32_t, RawStreamConfiguration> streamConfigurations; 124 }; 125 126 /* 127 * Return system information 128 * 129 * @return SystemInfo 130 * Constant reference of SystemInfo. 131 */ getSystemInfo()132 const SystemInfo &getSystemInfo() { 133 unique_lock<mutex> lock(mConfigLock); 134 mConfigCond.wait(lock, [this] { return mIsReady; }); 135 return mSystemInfo; 136 } 137 138 /* 139 * Return a list of camera identifiers 140 * 141 * This function assumes that it is not being called frequently. 142 * 143 * @return vector<string> 144 * A vector that contains unique camera device identifiers. 145 */ getCameraIdList()146 vector<string> getCameraIdList() { 147 unique_lock<mutex> lock(mConfigLock); 148 mConfigCond.wait(lock, [this] { return mIsReady; }); 149 150 vector<string> aList; 151 for (auto&& v : mCameraInfo) { 152 aList.emplace_back(v.first); 153 } 154 155 return aList; 156 } 157 158 /* 159 * Return a list of camera group identifiers 160 * 161 * This function assumes that it is not being called frequently. 162 * 163 * @return vector<string> 164 * A vector that contains unique camera device identifiers. 165 */ getCameraGroupIdList()166 vector<string> getCameraGroupIdList() { 167 unique_lock<mutex> lock(mConfigLock); 168 mConfigCond.wait(lock, [this] { return mIsReady; }); 169 170 vector<string> aList; 171 for (auto&& v : mCameraGroups) { 172 aList.emplace_back(v.first); 173 } 174 175 return aList; 176 } 177 178 /* 179 * Return a pointer to the camera group 180 * 181 * @return CameraGroup 182 * A pointer to a camera group identified by a given id. 183 */ getCameraGroupInfo(const string & gid)184 unique_ptr<CameraGroupInfo>& getCameraGroupInfo(const string& gid) { 185 unique_lock<mutex> lock(mConfigLock); 186 mConfigCond.wait(lock, [this] { return mIsReady; }); 187 188 return mCameraGroups[gid]; 189 } 190 191 /* 192 * Return a camera metadata 193 * 194 * @param cameraId 195 * Unique camera node identifier in string 196 * 197 * @return unique_ptr<CameraInfo> 198 * A pointer to CameraInfo that is associated with a given camera 199 * ID. This returns a null pointer if this does not recognize a 200 * given camera identifier. 201 */ getCameraInfo(const string cameraId)202 unique_ptr<CameraInfo>& getCameraInfo(const string cameraId) noexcept { 203 unique_lock<mutex> lock(mConfigLock); 204 mConfigCond.wait(lock, [this] { return mIsReady; }); 205 206 return mCameraInfo[cameraId]; 207 } 208 209 /* 210 * Tell whether the configuration data is ready to be used 211 * 212 * @return bool 213 * True if configuration data is ready to be consumed. 214 */ isReady()215 bool isReady() const { 216 return mIsReady; 217 } 218 219 private: 220 /* Constructors */ ConfigManager()221 ConfigManager() : 222 mBinaryFilePath("") { 223 } 224 225 static const char* CONFIG_DEFAULT_PATH; 226 static const char* CONFIG_OVERRIDE_PATH; 227 228 /* System configuration */ 229 SystemInfo mSystemInfo; 230 231 /* Internal data structure for camera device information */ 232 unordered_map<string, unique_ptr<CameraInfo>> mCameraInfo; 233 234 /* Internal data structure for camera device information */ 235 unordered_map<string, unique_ptr<DisplayInfo>> mDisplayInfo; 236 237 /* Camera groups are stored in <groud id, CameraGroup> hash map */ 238 unordered_map<string, unique_ptr<CameraGroupInfo>> mCameraGroups; 239 240 /* 241 * Camera positions are stored in <position, camera id set> hash map. 242 * The position must be one of front, rear, left, and right. 243 */ 244 unordered_map<string, unordered_set<string>> mCameraPosition; 245 246 /* Configuration data lock */ 247 mutex mConfigLock; 248 249 /* 250 * This condition is signalled when it completes a configuration data 251 * preparation. 252 */ 253 condition_variable mConfigCond; 254 255 /* A path to a binary configuration file */ 256 const char *mBinaryFilePath; 257 258 /* Configuration data readiness */ 259 bool mIsReady = false; 260 261 /* 262 * Parse a given EVS configuration file and store the information 263 * internally. 264 * 265 * @return bool 266 * True if it completes parsing a file successfully. 267 */ 268 bool readConfigDataFromXML() noexcept; 269 270 /* 271 * read the information of the vehicle 272 * 273 * @param aSysElem 274 * A pointer to "system" XML element. 275 */ 276 void readSystemInfo(const XMLElement * const aSysElem); 277 278 /* 279 * read the information of camera devices 280 * 281 * @param aCameraElem 282 * A pointer to "camera" XML element that may contain multiple 283 * "device" elements. 284 */ 285 void readCameraInfo(const XMLElement * const aCameraElem); 286 287 /* 288 * read display device information 289 * 290 * @param aDisplayElem 291 * A pointer to "display" XML element that may contain multiple 292 * "device" elements. 293 */ 294 void readDisplayInfo(const XMLElement * const aDisplayElem); 295 296 /* 297 * read camera device information 298 * 299 * @param aCamera 300 * A pointer to CameraInfo that will be completed by this 301 * method. 302 * aDeviceElem 303 * A pointer to "device" XML element that contains camera module 304 * capability info and its characteristics. 305 * 306 * @return bool 307 * Return false upon any failure in reading and processing camera 308 * device information. 309 */ 310 bool readCameraDeviceInfo(CameraInfo *aCamera, 311 const XMLElement *aDeviceElem); 312 313 /* 314 * read camera metadata 315 * 316 * @param aCapElem 317 * A pointer to "cap" XML element. 318 * @param aCamera 319 * A pointer to CameraInfo that is being filled by this method. 320 * @param dataSize 321 * Required size of memory to store camera metadata found in this 322 * method. This is calculated in this method and returned to the 323 * caller for camera_metadata allocation. 324 * 325 * @return size_t 326 * Number of camera metadata entries 327 */ 328 size_t readCameraCapabilities(const XMLElement * const aCapElem, 329 CameraInfo *aCamera, 330 size_t &dataSize); 331 332 /* 333 * read camera metadata 334 * 335 * @param aParamElem 336 * A pointer to "characteristics" XML element. 337 * @param aCamera 338 * A pointer to CameraInfo that is being filled by this method. 339 * @param dataSize 340 * Required size of memory to store camera metadata found in this 341 * method. 342 * 343 * @return size_t 344 * Number of camera metadata entries 345 */ 346 size_t readCameraMetadata(const XMLElement * const aParamElem, 347 CameraInfo *aCamera, 348 size_t &dataSize); 349 350 /* 351 * construct camera_metadata_t from camera capabilities and metadata 352 * 353 * @param aCamera 354 * A pointer to CameraInfo that is being filled by this method. 355 * @param totalEntries 356 * Number of camera metadata entries to be added. 357 * @param totalDataSize 358 * Sum of sizes of camera metadata entries to be added. 359 * 360 * @return bool 361 * False if either it fails to allocate memory for camera metadata 362 * or its size is not large enough to add all found camera metadata 363 * entries. 364 */ 365 bool constructCameraMetadata(CameraInfo *aCamera, 366 const size_t totalEntries, 367 const size_t totalDataSize); 368 369 /* 370 * Read configuration data from the binary file 371 * 372 * @return bool 373 * True if it succeeds to read configuration data from a binary 374 * file. 375 */ 376 bool readConfigDataFromBinary(); 377 378 /* 379 * Store configuration data to the file 380 * 381 * @return bool 382 * True if it succeeds to serialize mCameraInfo to the file. 383 */ 384 bool writeConfigDataToBinary(); 385 386 /* 387 * debugging method to print out all XML elements and their attributes in 388 * logcat message. 389 * 390 * @param aNode 391 * A pointer to the root XML element to navigate. 392 * @param prefix 393 * A prefix to XML string. 394 */ 395 void printElementNames(const XMLElement *aNode, string prefix = "") const; 396 }; 397 #endif // CONFIG_MANAGER_H 398 399