| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 1 | /* | 
 | 2 |  * Copyright (C) 2015 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 | #define LOG_TAG "APM::AudioPolicyEngine/PFWWrapper" | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 18 | //#define LOG_NDEBUG 0 | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 19 |  | 
 | 20 | #include "ParameterManagerWrapper.h" | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 21 | #include "ParameterManagerWrapperConfig.h" | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 22 | #include <ParameterMgrPlatformConnector.h> | 
 | 23 | #include <SelectionCriterionTypeInterface.h> | 
 | 24 | #include <SelectionCriterionInterface.h> | 
| Mikhail Naganov | 913d06c | 2016-11-01 12:49:22 -0700 | [diff] [blame] | 25 | #include <media/convert.h> | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 26 | #include <algorithm> | 
 | 27 | #include <cutils/config_utils.h> | 
 | 28 | #include <cutils/misc.h> | 
 | 29 | #include <fstream> | 
 | 30 | #include <limits> | 
 | 31 | #include <sstream> | 
 | 32 | #include <string> | 
 | 33 | #include <vector> | 
 | 34 | #include <stdint.h> | 
 | 35 | #include <cmath> | 
 | 36 | #include <utils/Log.h> | 
 | 37 |  | 
 | 38 | using std::string; | 
 | 39 | using std::map; | 
 | 40 | using std::vector; | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 41 | using CriterionTypes = std::map<std::string, ISelectionCriterionTypeInterface *>; | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 42 |  | 
 | 43 | /// PFW related definitions | 
 | 44 | // Logger | 
 | 45 | class ParameterMgrPlatformConnectorLogger : public CParameterMgrPlatformConnector::ILogger | 
 | 46 | { | 
 | 47 | public: | 
 | 48 |     ParameterMgrPlatformConnectorLogger() {} | 
 | 49 |  | 
| François Gaffie | c1391f9 | 2015-12-10 09:43:48 +0100 | [diff] [blame] | 50 |     virtual void info(const string &log) | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 51 |     { | 
| Liu Changcheng | 30cf41f | 2016-12-07 18:58:19 +0800 | [diff] [blame] | 52 |         ALOGV("policy-parameter-manager: %s", log.c_str()); | 
| François Gaffie | c1391f9 | 2015-12-10 09:43:48 +0100 | [diff] [blame] | 53 |     } | 
 | 54 |     virtual void warning(const string &log) | 
 | 55 |     { | 
 | 56 |         ALOGW("policy-parameter-manager: %s", log.c_str()); | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 57 |     } | 
 | 58 | }; | 
 | 59 |  | 
| François Gaffie | f19cf79 | 2018-05-30 17:22:17 +0200 | [diff] [blame] | 60 | namespace android { | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 61 |  | 
 | 62 | using utilities::convertTo; | 
 | 63 |  | 
| François Gaffie | f19cf79 | 2018-05-30 17:22:17 +0200 | [diff] [blame] | 64 | namespace audio_policy { | 
 | 65 |  | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 66 | const char *const ParameterManagerWrapper::mPolicyPfwDefaultConfFileName = | 
 | 67 |     "/etc/parameter-framework/ParameterFrameworkConfigurationPolicy.xml"; | 
| Mingwei Shi | c41dc11 | 2017-07-26 10:02:40 +0800 | [diff] [blame^] | 68 | const char *const ParameterManagerWrapper::mPolicyPfwVendorConfFileName = | 
 | 69 |     "/vendor/etc/parameter-framework/ParameterFrameworkConfigurationPolicy.xml"; | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 70 |  | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 71 | static const char *const gInputDeviceCriterionName = "AvailableInputDevices"; | 
 | 72 | static const char *const gOutputDeviceCriterionName = "AvailableOutputDevices"; | 
 | 73 | static const char *const gPhoneStateCriterionName = "TelephonyMode"; | 
 | 74 | static const char *const gOutputDeviceAddressCriterionName = "AvailableOutputDevicesAddresses"; | 
 | 75 | static const char *const gInputDeviceAddressCriterionName = "AvailableInputDevicesAddresses"; | 
 | 76 |  | 
 | 77 | /** | 
 | 78 |  * Order MUST be align with defintiion of audio_policy_force_use_t within audio_policy.h | 
 | 79 |  */ | 
 | 80 | static const char *const gForceUseCriterionTag[AUDIO_POLICY_FORCE_USE_CNT] = | 
 | 81 | { | 
 | 82 |     [AUDIO_POLICY_FORCE_FOR_COMMUNICATION] =        "ForceUseForCommunication", | 
 | 83 |     [AUDIO_POLICY_FORCE_FOR_MEDIA] =                "ForceUseForMedia", | 
 | 84 |     [AUDIO_POLICY_FORCE_FOR_RECORD] =               "ForceUseForRecord", | 
 | 85 |     [AUDIO_POLICY_FORCE_FOR_DOCK] =                 "ForceUseForDock", | 
 | 86 |     [AUDIO_POLICY_FORCE_FOR_SYSTEM] =               "ForceUseForSystem", | 
 | 87 |     [AUDIO_POLICY_FORCE_FOR_HDMI_SYSTEM_AUDIO] =    "ForceUseForHdmiSystemAudio", | 
 | 88 |     [AUDIO_POLICY_FORCE_FOR_ENCODED_SURROUND] =     "ForceUseForEncodedSurround", | 
 | 89 |     [AUDIO_POLICY_FORCE_FOR_VIBRATE_RINGING] =      "ForceUseForVibrateRinging" | 
 | 90 | }; | 
 | 91 |  | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 92 | template <> | 
 | 93 | struct ParameterManagerWrapper::parameterManagerElementSupported<ISelectionCriterionInterface> {}; | 
 | 94 | template <> | 
 | 95 | struct ParameterManagerWrapper::parameterManagerElementSupported<ISelectionCriterionTypeInterface> {}; | 
 | 96 |  | 
 | 97 | ParameterManagerWrapper::ParameterManagerWrapper() | 
 | 98 |     : mPfwConnectorLogger(new ParameterMgrPlatformConnectorLogger) | 
 | 99 | { | 
 | 100 |     // Connector | 
| Mingwei Shi | c41dc11 | 2017-07-26 10:02:40 +0800 | [diff] [blame^] | 101 |     if (access(mPolicyPfwVendorConfFileName, R_OK) == 0) { | 
 | 102 |         mPfwConnector = new CParameterMgrPlatformConnector(mPolicyPfwVendorConfFileName); | 
 | 103 |     } else { | 
 | 104 |         mPfwConnector = new CParameterMgrPlatformConnector(mPolicyPfwDefaultConfFileName); | 
 | 105 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 106 |  | 
 | 107 |     // Logger | 
 | 108 |     mPfwConnector->setLogger(mPfwConnectorLogger); | 
 | 109 |  | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 110 |     status_t loadResult = loadConfig(); | 
 | 111 |     if (loadResult < 0) { | 
 | 112 |         ALOGE("Policy Wrapper configuration is partially invalid."); | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 113 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 114 | } | 
 | 115 |  | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 116 | status_t ParameterManagerWrapper::loadConfig() | 
 | 117 | { | 
 | 118 |     auto result = wrapper_config::parse(); | 
 | 119 |     if (result.parsedConfig == nullptr) { | 
 | 120 |         return -ENOENT; | 
 | 121 |     } | 
 | 122 |     ALOGE_IF(result.nbSkippedElement != 0, "skipped %zu elements", result.nbSkippedElement); | 
 | 123 |  | 
 | 124 |     CriterionTypes criterionTypes; | 
 | 125 |     for (auto criterionType : result.parsedConfig->criterionTypes) { | 
 | 126 |         ALOG_ASSERT(criterionTypes.find(criterionType.name) == criterionTypes.end(), | 
 | 127 |                           "CriterionType %s already added", criterionType.name.c_str()); | 
 | 128 |         ALOGV("%s: Adding new criterionType %s", __FUNCTION__, criterionType.name.c_str()); | 
 | 129 |  | 
 | 130 |         auto criterionTypePfw = | 
 | 131 |                 mPfwConnector->createSelectionCriterionType(criterionType.isInclusive); | 
 | 132 |  | 
 | 133 |         for (auto pair : criterionType.valuePairs) { | 
 | 134 |             std::string error; | 
 | 135 |             ALOGV("%s: Adding pair %d,%s for criterionType %s", __FUNCTION__, pair.first, | 
 | 136 |                   pair.second.c_str(), criterionType.name.c_str()); | 
 | 137 |             criterionTypePfw->addValuePair(pair.first, pair.second, error); | 
 | 138 |         } | 
 | 139 |         criterionTypes[criterionType.name] = criterionTypePfw; | 
 | 140 |     } | 
 | 141 |  | 
 | 142 |     for (auto criterion : result.parsedConfig->criteria) { | 
 | 143 |         ALOG_ASSERT(mPolicyCriteria.find(criterion.name) == mPolicyCriteria.end(), | 
 | 144 |                     "%s: Criterion %s already added", __FUNCTION__, criterion.name.c_str()); | 
 | 145 |  | 
 | 146 |         auto criterionType = | 
 | 147 |                 getElement<ISelectionCriterionTypeInterface>(criterion.typeName, criterionTypes); | 
 | 148 |         ALOG_ASSERT(criterionType != nullptr, "No %s Criterion type found for criterion %s", | 
 | 149 |                     criterion.typeName.c_str(), criterion.name.c_str()); | 
 | 150 |  | 
 | 151 |         auto criterionPfw = mPfwConnector->createSelectionCriterion(criterion.name, criterionType); | 
 | 152 |         mPolicyCriteria[criterion.name] = criterionPfw; | 
 | 153 |  | 
 | 154 |         if (not criterion.defaultLiteralValue.empty()) { | 
 | 155 |             int numericalValue = 0; | 
 | 156 |             if (not criterionType->getNumericalValue(criterion.defaultLiteralValue.c_str(), | 
 | 157 |                                                      numericalValue)) { | 
 | 158 |                 ALOGE("%s; trying to apply invalid default literal value (%s)", __FUNCTION__, | 
 | 159 |                       criterion.defaultLiteralValue.c_str()); | 
 | 160 |                 continue; | 
 | 161 |             } | 
 | 162 |             criterionPfw->setCriterionState(numericalValue); | 
 | 163 |         } | 
 | 164 |     } | 
 | 165 |     return result.nbSkippedElement == 0? NO_ERROR : BAD_VALUE; | 
 | 166 | } | 
 | 167 |  | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 168 | ParameterManagerWrapper::~ParameterManagerWrapper() | 
 | 169 | { | 
 | 170 |     // Unset logger | 
 | 171 |     mPfwConnector->setLogger(NULL); | 
 | 172 |     // Remove logger | 
 | 173 |     delete mPfwConnectorLogger; | 
 | 174 |     // Remove connector | 
 | 175 |     delete mPfwConnector; | 
 | 176 | } | 
 | 177 |  | 
 | 178 | status_t ParameterManagerWrapper::start() | 
 | 179 | { | 
 | 180 |     ALOGD("%s: in", __FUNCTION__); | 
 | 181 |     /// Start PFW | 
 | 182 |     std::string error; | 
 | 183 |     if (!mPfwConnector->start(error)) { | 
 | 184 |         ALOGE("%s: Policy PFW start error: %s", __FUNCTION__, error.c_str()); | 
 | 185 |         return NO_INIT; | 
 | 186 |     } | 
 | 187 |     ALOGD("%s: Policy PFW successfully started!", __FUNCTION__); | 
 | 188 |     return NO_ERROR; | 
 | 189 | } | 
 | 190 |  | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 191 | template <typename T> | 
 | 192 | T *ParameterManagerWrapper::getElement(const string &name, std::map<string, T *> &elementsMap) | 
 | 193 | { | 
 | 194 |     parameterManagerElementSupported<T>(); | 
 | 195 |     typename std::map<string, T *>::iterator it = elementsMap.find(name); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 196 |     ALOG_ASSERT(it != elementsMap.end(), "Element %s not found", name.c_str()); | 
 | 197 |     return it != elementsMap.end() ? it->second : NULL; | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 198 | } | 
 | 199 |  | 
 | 200 | template <typename T> | 
 | 201 | const T *ParameterManagerWrapper::getElement(const string &name, const std::map<string, T *> &elementsMap) const | 
 | 202 | { | 
 | 203 |     parameterManagerElementSupported<T>(); | 
 | 204 |     typename std::map<string, T *>::const_iterator it = elementsMap.find(name); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 205 |     ALOG_ASSERT(it != elementsMap.end(), "Element %s not found", name.c_str()); | 
 | 206 |     return it != elementsMap.end() ? it->second : NULL; | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 207 | } | 
 | 208 |  | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 209 | bool ParameterManagerWrapper::isStarted() | 
 | 210 | { | 
 | 211 |     return mPfwConnector && mPfwConnector->isStarted(); | 
 | 212 | } | 
 | 213 |  | 
 | 214 | status_t ParameterManagerWrapper::setPhoneState(audio_mode_t mode) | 
 | 215 | { | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 216 |     ISelectionCriterionInterface *criterion = | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 217 |             getElement<ISelectionCriterionInterface>(gPhoneStateCriterionName, mPolicyCriteria); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 218 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 219 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gPhoneStateCriterionName); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 220 |         return BAD_VALUE; | 
 | 221 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 222 |     if (!isValueValidForCriterion(criterion, static_cast<int>(mode))) { | 
 | 223 |         return BAD_VALUE; | 
 | 224 |     } | 
 | 225 |     criterion->setCriterionState((int)(mode)); | 
 | 226 |     applyPlatformConfiguration(); | 
 | 227 |     return NO_ERROR; | 
 | 228 | } | 
 | 229 |  | 
 | 230 | audio_mode_t ParameterManagerWrapper::getPhoneState() const | 
 | 231 | { | 
 | 232 |     const ISelectionCriterionInterface *criterion = | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 233 |             getElement<ISelectionCriterionInterface>(gPhoneStateCriterionName, mPolicyCriteria); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 234 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 235 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gPhoneStateCriterionName); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 236 |         return AUDIO_MODE_NORMAL; | 
 | 237 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 238 |     return static_cast<audio_mode_t>(criterion->getCriterionState()); | 
 | 239 | } | 
 | 240 |  | 
 | 241 | status_t ParameterManagerWrapper::setForceUse(audio_policy_force_use_t usage, | 
 | 242 |                                               audio_policy_forced_cfg_t config) | 
 | 243 | { | 
 | 244 |     // @todo: return an error on a unsupported value | 
 | 245 |     if (usage > AUDIO_POLICY_FORCE_USE_CNT) { | 
 | 246 |         return BAD_VALUE; | 
 | 247 |     } | 
 | 248 |  | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 249 |     ISelectionCriterionInterface *criterion = | 
 | 250 |             getElement<ISelectionCriterionInterface>(gForceUseCriterionTag[usage], mPolicyCriteria); | 
 | 251 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 252 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gForceUseCriterionTag[usage]); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 253 |         return BAD_VALUE; | 
 | 254 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 255 |     if (!isValueValidForCriterion(criterion, static_cast<int>(config))) { | 
 | 256 |         return BAD_VALUE; | 
 | 257 |     } | 
 | 258 |     criterion->setCriterionState((int)config); | 
 | 259 |     applyPlatformConfiguration(); | 
 | 260 |     return NO_ERROR; | 
 | 261 | } | 
 | 262 |  | 
 | 263 | audio_policy_forced_cfg_t ParameterManagerWrapper::getForceUse(audio_policy_force_use_t usage) const | 
 | 264 | { | 
 | 265 |     // @todo: return an error on a unsupported value | 
 | 266 |     if (usage > AUDIO_POLICY_FORCE_USE_CNT) { | 
 | 267 |         return AUDIO_POLICY_FORCE_NONE; | 
 | 268 |     } | 
 | 269 |     const ISelectionCriterionInterface *criterion = | 
 | 270 |             getElement<ISelectionCriterionInterface>(gForceUseCriterionTag[usage], mPolicyCriteria); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 271 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 272 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gForceUseCriterionTag[usage]); | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 273 |         return AUDIO_POLICY_FORCE_NONE; | 
 | 274 |     } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 275 |     return static_cast<audio_policy_forced_cfg_t>(criterion->getCriterionState()); | 
 | 276 | } | 
 | 277 |  | 
 | 278 | bool ParameterManagerWrapper::isValueValidForCriterion(ISelectionCriterionInterface *criterion, | 
 | 279 |                                                        int valueToCheck) | 
 | 280 | { | 
 | 281 |     const ISelectionCriterionTypeInterface *interface = criterion->getCriterionType(); | 
 | 282 |     string literalValue; | 
 | 283 |     return interface->getLiteralValue(valueToCheck, literalValue); | 
 | 284 | } | 
 | 285 |  | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 286 | status_t ParameterManagerWrapper::setDeviceConnectionState(const sp<DeviceDescriptor> devDesc, | 
 | 287 |                                                            audio_policy_dev_state_t state) | 
 | 288 | { | 
 | 289 |     std::string criterionName = audio_is_output_device(devDesc->type()) ? | 
 | 290 |                 gOutputDeviceAddressCriterionName : gInputDeviceAddressCriterionName; | 
 | 291 |  | 
 | 292 |     ALOGV("%s: device with address %s %s", __FUNCTION__, devDesc->mAddress.string(), | 
 | 293 |           state != AUDIO_POLICY_DEVICE_STATE_AVAILABLE? "disconnected" : "connected"); | 
 | 294 |     ISelectionCriterionInterface *criterion = | 
 | 295 |             getElement<ISelectionCriterionInterface>(criterionName, mPolicyCriteria); | 
 | 296 |  | 
 | 297 |     if (criterion == NULL) { | 
 | 298 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, criterionName.c_str()); | 
 | 299 |         return DEAD_OBJECT; | 
 | 300 |     } | 
 | 301 |  | 
 | 302 |     auto criterionType = criterion->getCriterionType(); | 
 | 303 |     int deviceAddressId; | 
| Francois Gaffie | 716e143 | 2019-01-14 16:58:59 +0100 | [diff] [blame] | 304 |     if (not criterionType->getNumericalValue(devDesc->address().string(), deviceAddressId)) { | 
 | 305 |         ALOGW("%s: unknown device address reported (%s)", __FUNCTION__, devDesc->address().c_str()); | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 306 |         return BAD_TYPE; | 
 | 307 |     } | 
 | 308 |     int currentValueMask = criterion->getCriterionState(); | 
 | 309 |     if (state == AUDIO_POLICY_DEVICE_STATE_AVAILABLE) { | 
 | 310 |         currentValueMask |= deviceAddressId; | 
 | 311 |     } | 
 | 312 |     else { | 
 | 313 |         currentValueMask &= ~deviceAddressId; | 
 | 314 |     } | 
 | 315 |     criterion->setCriterionState(currentValueMask); | 
 | 316 |     return NO_ERROR; | 
 | 317 | } | 
 | 318 |  | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 319 | status_t ParameterManagerWrapper::setAvailableInputDevices(audio_devices_t inputDevices) | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 320 | { | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 321 |     ISelectionCriterionInterface *criterion = | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 322 |             getElement<ISelectionCriterionInterface>(gInputDeviceCriterionName, mPolicyCriteria); | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 323 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 324 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gInputDeviceCriterionName); | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 325 |         return DEAD_OBJECT; | 
 | 326 |     } | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 327 |     criterion->setCriterionState(inputDevices & ~AUDIO_DEVICE_BIT_IN); | 
 | 328 |     applyPlatformConfiguration(); | 
 | 329 |     return NO_ERROR; | 
 | 330 | } | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 331 |  | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 332 | status_t ParameterManagerWrapper::setAvailableOutputDevices(audio_devices_t outputDevices) | 
 | 333 | { | 
| François Gaffie | 814ce80 | 2016-01-18 11:23:47 +0100 | [diff] [blame] | 334 |     ISelectionCriterionInterface *criterion = | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 335 |             getElement<ISelectionCriterionInterface>(gOutputDeviceCriterionName, mPolicyCriteria); | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 336 |     if (criterion == NULL) { | 
| François Gaffie | a56b5c2 | 2018-02-21 18:04:39 +0100 | [diff] [blame] | 337 |         ALOGE("%s: no criterion found for %s", __FUNCTION__, gOutputDeviceCriterionName); | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 338 |         return DEAD_OBJECT; | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 339 |     } | 
| François Gaffie | a3e696d | 2015-12-18 09:38:43 +0100 | [diff] [blame] | 340 |     criterion->setCriterionState(outputDevices); | 
| François Gaffie | 20f06f9 | 2015-03-24 09:01:14 +0100 | [diff] [blame] | 341 |     applyPlatformConfiguration(); | 
 | 342 |     return NO_ERROR; | 
 | 343 | } | 
 | 344 |  | 
 | 345 | void ParameterManagerWrapper::applyPlatformConfiguration() | 
 | 346 | { | 
 | 347 |     mPfwConnector->applyConfigurations(); | 
 | 348 | } | 
 | 349 |  | 
 | 350 | } // namespace audio_policy | 
 | 351 | } // namespace android |