1 /* 2 * Copyright (C) 2020 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 17 #pragma once 18 19 #include <set> 20 #include <string> 21 22 #include <DeviceDescriptor.h> 23 #include <HwModule.h> 24 #include <Serializer.h> 25 #include <gtest/gtest.h> 26 #include <system/audio_config.h> 27 28 #include "DeviceManager.h" 29 30 using ::android::sp; 31 using ::android::status_t; 32 33 struct PolicyConfigData { 34 android::HwModuleCollection hwModules; 35 android::DeviceVector availableOutputDevices; 36 android::DeviceVector availableInputDevices; 37 sp<android::DeviceDescriptor> defaultOutputDevice; 38 }; 39 40 class PolicyConfig : private PolicyConfigData, public android::AudioPolicyConfig { 41 public: PolicyConfig(const std::string & configFileName)42 explicit PolicyConfig(const std::string& configFileName) 43 : android::AudioPolicyConfig(hwModules, availableOutputDevices, availableInputDevices, 44 defaultOutputDevice), 45 mConfigFileName{configFileName} { 46 for (const auto& location : android::audio_get_configuration_paths()) { 47 std::string path = location + '/' + mConfigFileName; 48 if (access(path.c_str(), F_OK) == 0) { 49 mFilePath = path; 50 break; 51 } 52 } 53 init(); 54 } PolicyConfig(const std::string & configPath,const std::string & configFileName)55 PolicyConfig(const std::string& configPath, const std::string& configFileName) 56 : android::AudioPolicyConfig(hwModules, availableOutputDevices, availableInputDevices, 57 defaultOutputDevice), 58 mConfigFileName{configFileName}, 59 mFilePath{configPath + "/" + mConfigFileName} { 60 init(); 61 } getStatus()62 status_t getStatus() const { return mStatus; } getError()63 std::string getError() const { 64 if (mFilePath.empty()) { 65 return std::string{"Could not find "} + mConfigFileName + 66 " file in: " + testing::PrintToString(android::audio_get_configuration_paths()); 67 } else { 68 return "Invalid config file: " + mFilePath; 69 } 70 } getFilePath()71 const std::string& getFilePath() const { return mFilePath; } getModuleFromName(const std::string & name)72 sp<const android::HwModule> getModuleFromName(const std::string& name) const { 73 return getHwModules().getModuleFromName(name.c_str()); 74 } getPrimaryModule()75 sp<const android::HwModule> getPrimaryModule() const { return mPrimaryModule; } getModulesWithDevicesNames()76 const std::set<std::string>& getModulesWithDevicesNames() const { 77 return mModulesWithDevicesNames; 78 } haveInputProfilesInModule(const std::string & name)79 bool haveInputProfilesInModule(const std::string& name) const { 80 auto module = getModuleFromName(name); 81 return module && !module->getInputProfiles().empty(); 82 } 83 84 private: init()85 void init() { 86 mStatus = android::deserializeAudioPolicyFileForVts(mFilePath.c_str(), this); 87 if (mStatus == android::OK) { 88 mPrimaryModule = getModuleFromName(DeviceManager::kPrimaryDevice); 89 // Available devices are not 'attached' to modules at this moment. 90 // Need to go over available devices and find their module. 91 for (const auto& device : availableOutputDevices) { 92 for (const auto& module : hwModules) { 93 if (module->getDeclaredDevices().indexOf(device) >= 0) { 94 mModulesWithDevicesNames.insert(module->getName()); 95 break; 96 } 97 } 98 } 99 for (const auto& device : availableInputDevices) { 100 for (const auto& module : hwModules) { 101 if (module->getDeclaredDevices().indexOf(device) >= 0) { 102 mModulesWithDevicesNames.insert(module->getName()); 103 break; 104 } 105 } 106 } 107 } 108 } 109 110 const std::string mConfigFileName; 111 status_t mStatus = android::NO_INIT; 112 std::string mFilePath; 113 sp<const android::HwModule> mPrimaryModule = nullptr; 114 std::set<std::string> mModulesWithDevicesNames; 115 }; 116