mirror of
https://github.com/Evolution-X/hardware_interfaces
synced 2026-02-01 22:04:26 +00:00
Add methods 'IModule.connect/disconnectExternalDevice' which inform audio HAL about connection / disconnection of an external non-attached device. Add method 'getAudioRoutesForPort' to retrieve only routes that include the specified port. Update the behavior of 'getAudioPorts' and 'getAudioRoutes' indicating that the result may change due to instantiation of new device ports for connected external devices. Clarify behavior of 'IModule.setAudioPortConfig' that it can not work with device ports with no profiles. Add debug flags structure 'ModuleDebug' and method 'IModule.setModuleDebug' to control the debugging aspects. VTS tests use these flags to test HAL behavior which would otherwise require human intervention. Update the default implementation and VTS for the AIDL changes. Bug: 205884982 Test: atest VtsHalAudioCoreTargetTest Change-Id: Iad5f7009e283729206f88b6278c8992f7f8a92a2
143 lines
7.0 KiB
C++
143 lines
7.0 KiB
C++
/*
|
|
* Copyright (C) 2022 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.
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
#include <optional>
|
|
#include <set>
|
|
#include <utility>
|
|
#include <vector>
|
|
|
|
#include <android/hardware/audio/core/AudioRoute.h>
|
|
#include <android/hardware/audio/core/IModule.h>
|
|
#include <android/media/audio/common/AudioPort.h>
|
|
#include <binder/Status.h>
|
|
|
|
class ModuleConfig {
|
|
public:
|
|
using SrcSinkPair = std::pair<android::media::audio::common::AudioPortConfig,
|
|
android::media::audio::common::AudioPortConfig>;
|
|
using SrcSinkGroup =
|
|
std::pair<android::hardware::audio::core::AudioRoute, std::vector<SrcSinkPair>>;
|
|
|
|
explicit ModuleConfig(android::hardware::audio::core::IModule* module);
|
|
android::binder::Status getStatus() const { return mStatus; }
|
|
std::string getError() const { return mStatus.toString8().c_str(); }
|
|
|
|
std::vector<android::media::audio::common::AudioPort> getAttachedDevicePorts() const;
|
|
std::vector<android::media::audio::common::AudioPort> getExternalDevicePorts() const;
|
|
std::vector<android::media::audio::common::AudioPort> getInputMixPorts() const;
|
|
std::vector<android::media::audio::common::AudioPort> getOutputMixPorts() const;
|
|
std::vector<android::media::audio::common::AudioPort> getMixPorts(bool isInput) const {
|
|
return isInput ? getInputMixPorts() : getOutputMixPorts();
|
|
}
|
|
|
|
std::vector<android::media::audio::common::AudioPort> getAttachedDevicesPortsForMixPort(
|
|
bool isInput, const android::media::audio::common::AudioPort& mixPort) const {
|
|
return isInput ? getAttachedSourceDevicesPortsForMixPort(mixPort)
|
|
: getAttachedSinkDevicesPortsForMixPort(mixPort);
|
|
}
|
|
std::vector<android::media::audio::common::AudioPort> getAttachedSinkDevicesPortsForMixPort(
|
|
const android::media::audio::common::AudioPort& mixPort) const;
|
|
std::vector<android::media::audio::common::AudioPort> getAttachedSourceDevicesPortsForMixPort(
|
|
const android::media::audio::common::AudioPort& mixPort) const;
|
|
std::optional<android::media::audio::common::AudioPort> getSourceMixPortForAttachedDevice()
|
|
const;
|
|
|
|
std::optional<SrcSinkPair> getNonRoutableSrcSinkPair(bool isInput) const;
|
|
std::optional<SrcSinkPair> getRoutableSrcSinkPair(bool isInput) const;
|
|
std::vector<SrcSinkGroup> getRoutableSrcSinkGroups(bool isInput) const;
|
|
|
|
std::vector<android::media::audio::common::AudioPortConfig>
|
|
getPortConfigsForAttachedDevicePorts() const {
|
|
return generateAudioDevicePortConfigs(getAttachedDevicePorts(), false);
|
|
}
|
|
std::vector<android::media::audio::common::AudioPortConfig> getPortConfigsForMixPorts() const {
|
|
auto inputs = generateInputAudioMixPortConfigs(getInputMixPorts(), false);
|
|
auto outputs = generateOutputAudioMixPortConfigs(getOutputMixPorts(), false);
|
|
inputs.insert(inputs.end(), outputs.begin(), outputs.end());
|
|
return inputs;
|
|
}
|
|
std::vector<android::media::audio::common::AudioPortConfig> getPortConfigsForMixPorts(
|
|
bool isInput) const {
|
|
return isInput ? generateInputAudioMixPortConfigs(getInputMixPorts(), false)
|
|
: generateOutputAudioMixPortConfigs(getOutputMixPorts(), false);
|
|
}
|
|
std::vector<android::media::audio::common::AudioPortConfig> getPortConfigsForMixPorts(
|
|
bool isInput, const android::media::audio::common::AudioPort& port) const {
|
|
return isInput ? generateInputAudioMixPortConfigs({port}, false)
|
|
: generateOutputAudioMixPortConfigs({port}, false);
|
|
}
|
|
std::optional<android::media::audio::common::AudioPortConfig> getSingleConfigForMixPort(
|
|
bool isInput) const {
|
|
const auto config = isInput ? generateInputAudioMixPortConfigs(getInputMixPorts(), true)
|
|
: generateOutputAudioMixPortConfigs(getOutputMixPorts(), true);
|
|
// TODO: Avoid returning configs for offload since they require an extra
|
|
// argument to openOutputStream.
|
|
if (!config.empty()) {
|
|
return *config.begin();
|
|
} else {
|
|
return {};
|
|
}
|
|
}
|
|
std::optional<android::media::audio::common::AudioPortConfig> getSingleConfigForMixPort(
|
|
bool isInput, const android::media::audio::common::AudioPort& port) const {
|
|
const auto config = isInput ? generateInputAudioMixPortConfigs({port}, true)
|
|
: generateOutputAudioMixPortConfigs({port}, true);
|
|
if (!config.empty()) {
|
|
return *config.begin();
|
|
} else {
|
|
return {};
|
|
}
|
|
}
|
|
|
|
std::vector<android::media::audio::common::AudioPortConfig> getPortConfigsForDevicePort(
|
|
const android::media::audio::common::AudioPort& port) const {
|
|
return generateAudioDevicePortConfigs({port}, false);
|
|
}
|
|
android::media::audio::common::AudioPortConfig getSingleConfigForDevicePort(
|
|
const android::media::audio::common::AudioPort& port) const {
|
|
const auto config = generateAudioDevicePortConfigs({port}, true);
|
|
return *config.begin();
|
|
}
|
|
|
|
std::string toString() const;
|
|
|
|
private:
|
|
std::vector<android::media::audio::common::AudioPortConfig> generateInputAudioMixPortConfigs(
|
|
const std::vector<android::media::audio::common::AudioPort>& ports,
|
|
bool singleProfile) const;
|
|
std::vector<android::media::audio::common::AudioPortConfig> generateOutputAudioMixPortConfigs(
|
|
const std::vector<android::media::audio::common::AudioPort>& ports,
|
|
bool singleProfile) const;
|
|
|
|
// Unlike MixPorts, the generator for DevicePorts always returns a non-empty
|
|
// vector for a non-empty input port list. If there are no profiles in the
|
|
// port, its initial configs are looked up, if there are none,
|
|
// then an empty config is used, assuming further negotiation via setAudioPortConfig.
|
|
std::vector<android::media::audio::common::AudioPortConfig> generateAudioDevicePortConfigs(
|
|
const std::vector<android::media::audio::common::AudioPort>& ports,
|
|
bool singleProfile) const;
|
|
|
|
android::binder::Status mStatus = android::binder::Status::ok();
|
|
std::vector<android::media::audio::common::AudioPort> mPorts;
|
|
std::vector<android::media::audio::common::AudioPortConfig> mInitialConfigs;
|
|
std::set<int32_t> mAttachedSinkDevicePorts;
|
|
std::set<int32_t> mAttachedSourceDevicePorts;
|
|
std::set<int32_t> mExternalDevicePorts;
|
|
std::vector<android::hardware::audio::core::AudioRoute> mRoutes;
|
|
};
|