209 lines
8.9 KiB
C++
209 lines
8.9 KiB
C++
/*
|
|
* Copyright (C) 2015 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 "DeviceDescriptor.h"
|
|
#include "AudioRoute.h"
|
|
#include <utils/RefBase.h>
|
|
#include <utils/String8.h>
|
|
#include <utils/Errors.h>
|
|
#include <utils/Vector.h>
|
|
#include <system/audio.h>
|
|
#include <cutils/config_utils.h>
|
|
#include <string>
|
|
|
|
namespace android {
|
|
|
|
class IOProfile;
|
|
class InputProfile;
|
|
class OutputProfile;
|
|
|
|
typedef Vector<sp<IOProfile> > InputProfileCollection;
|
|
typedef Vector<sp<IOProfile> > OutputProfileCollection;
|
|
typedef Vector<sp<IOProfile> > IOProfileCollection;
|
|
|
|
class HwModule : public RefBase
|
|
{
|
|
public:
|
|
explicit HwModule(const char *name, uint32_t halVersionMajor = 0, uint32_t halVersionMinor = 0);
|
|
~HwModule();
|
|
|
|
const char *getName() const { return mName.string(); }
|
|
|
|
const DeviceVector &getDeclaredDevices() const { return mDeclaredDevices; }
|
|
void setDeclaredDevices(const DeviceVector &devices);
|
|
DeviceVector getAllDevices() const
|
|
{
|
|
DeviceVector devices = mDeclaredDevices;
|
|
devices.merge(mDynamicDevices);
|
|
return devices;
|
|
}
|
|
std::string getTagForDevice(audio_devices_t device,
|
|
const String8 &address = String8(),
|
|
audio_format_t codec = AUDIO_FORMAT_DEFAULT);
|
|
void addDynamicDevice(const sp<DeviceDescriptor> &device)
|
|
{
|
|
device->setDynamic();
|
|
mDynamicDevices.add(device);
|
|
}
|
|
|
|
bool removeDynamicDevice(const sp<DeviceDescriptor> &device)
|
|
{
|
|
return mDynamicDevices.remove(device) >= 0;
|
|
}
|
|
DeviceVector getDynamicDevices() const { return mDynamicDevices; }
|
|
|
|
const InputProfileCollection &getInputProfiles() const { return mInputProfiles; }
|
|
const OutputProfileCollection &getOutputProfiles() const { return mOutputProfiles; }
|
|
|
|
void setProfiles(const IOProfileCollection &profiles);
|
|
|
|
void setHalVersion(uint32_t major, uint32_t minor) {
|
|
mHalVersion = (major << 8) | (minor & 0xff);
|
|
}
|
|
uint32_t getHalVersionMajor() const { return mHalVersion >> 8; }
|
|
uint32_t getHalVersionMinor() const { return mHalVersion & 0xff; }
|
|
|
|
sp<DeviceDescriptor> getRouteSinkDevice(const sp<AudioRoute> &route) const;
|
|
DeviceVector getRouteSourceDevices(const sp<AudioRoute> &route) const;
|
|
const AudioRouteVector& getRoutes() const { return mRoutes; }
|
|
void setRoutes(const AudioRouteVector &routes);
|
|
|
|
status_t addOutputProfile(const sp<IOProfile> &profile);
|
|
status_t addInputProfile(const sp<IOProfile> &profile);
|
|
status_t addProfile(const sp<IOProfile> &profile);
|
|
|
|
status_t addOutputProfile(const std::string& name, const audio_config_t *config,
|
|
audio_devices_t device, const String8& address);
|
|
status_t removeOutputProfile(const std::string& name);
|
|
status_t addInputProfile(const std::string& name, const audio_config_t *config,
|
|
audio_devices_t device, const String8& address);
|
|
status_t removeInputProfile(const std::string& name);
|
|
|
|
audio_module_handle_t getHandle() const { return mHandle; }
|
|
void setHandle(audio_module_handle_t handle);
|
|
|
|
sp<PolicyAudioPort> findPortByTagName(const std::string &tagName) const
|
|
{
|
|
return findByTagName(mPorts, tagName);
|
|
}
|
|
|
|
/**
|
|
* @brief supportsPatch checks if an audio patch between 2 ports beloging to this HwModule
|
|
* is supported by a HwModule. The ports and the route shall be declared in the
|
|
* audio_policy_configuration.xml file.
|
|
* @param srcPort (aka the source) to be considered
|
|
* @param dstPort (aka the sink) to be considered
|
|
* @return true if the HwModule supports the connection between the sink and the source,
|
|
* false otherwise
|
|
*/
|
|
bool supportsPatch(const sp<PolicyAudioPort> &srcPort,
|
|
const sp<PolicyAudioPort> &dstPort) const;
|
|
|
|
// TODO remove from here (split serialization)
|
|
void dump(String8 *dst, int spaces) const;
|
|
|
|
private:
|
|
void refreshSupportedDevices();
|
|
|
|
const String8 mName; // base name of the audio HW module (primary, a2dp ...)
|
|
audio_module_handle_t mHandle;
|
|
OutputProfileCollection mOutputProfiles; // output profiles exposed by this module
|
|
InputProfileCollection mInputProfiles; // input profiles exposed by this module
|
|
uint32_t mHalVersion; // audio HAL API version
|
|
DeviceVector mDeclaredDevices; // devices declared in audio_policy configuration file.
|
|
DeviceVector mDynamicDevices; /**< devices that can be added/removed at runtime (e.g. rsbumix)*/
|
|
AudioRouteVector mRoutes;
|
|
PolicyAudioPortVector mPorts;
|
|
};
|
|
|
|
class HwModuleCollection : public Vector<sp<HwModule> >
|
|
{
|
|
public:
|
|
sp<HwModule> getModuleFromName(const char *name) const;
|
|
|
|
/**
|
|
* @brief getModuleForDeviceType try to get a device from type / format on all modules
|
|
* @param device type to consider
|
|
* @param encodedFormat to consider
|
|
* @param[out] tagName if not null, if a matching device is found, will return the tagName
|
|
* of original device from XML file so that audio routes matchin rules work.
|
|
* @return valid module if considered device found, nullptr otherwise.
|
|
*/
|
|
sp<HwModule> getModuleForDeviceType(audio_devices_t device,
|
|
audio_format_t encodedFormat,
|
|
std::string *tagName = nullptr) const;
|
|
|
|
sp<HwModule> getModuleForDevice(const sp<DeviceDescriptor> &device,
|
|
audio_format_t encodedFormat) const;
|
|
|
|
DeviceVector getAvailableDevicesFromModuleName(const char *name,
|
|
const DeviceVector &availableDevices) const;
|
|
|
|
/**
|
|
* @brief getDeviceDescriptor returns a device descriptor associated to the device type and
|
|
* device address (if matchAddress is true).
|
|
* It may loop twice on all modules to check if allowToCreate is true
|
|
* -first loop will check if the device is found on a module since declared in the list
|
|
* of device port in configuration file
|
|
* -(allowToCreate is true)second loop will check if the device is weakly supported by one
|
|
* or more profiles on a given module and will add as a supported device for this module.
|
|
* The device will also be added to the dynamic list of device of this module
|
|
* @param type of the device requested
|
|
* @param address of the device requested
|
|
* @param name of the device that requested
|
|
* @param encodedFormat if not AUDIO_FORMAT_DEFAULT, must match one supported format
|
|
* @param matchAddress true if a strong match is required
|
|
* @param allowToCreate true if allowed to create dynamic device (e.g. hdmi, usb...)
|
|
* @return device descriptor associated to the type (and address if matchAddress is true)
|
|
*/
|
|
sp<DeviceDescriptor> getDeviceDescriptor(const audio_devices_t type,
|
|
const char *address,
|
|
const char *name,
|
|
audio_format_t encodedFormat,
|
|
bool allowToCreate = false,
|
|
bool matchAddress = true) const;
|
|
|
|
/**
|
|
* @brief createDevice creates a new device from the type and address given. It checks that
|
|
* according to the device type, a module is supporting this device (weak check).
|
|
* This concerns only dynamic device, aka device with a specific address and not
|
|
* already supported by module/underlying profiles.
|
|
* @param type of the device to be created
|
|
* @param address of the device to be created
|
|
* @param name of the device to be created
|
|
* @return device descriptor if a module is supporting this type, nullptr otherwise.
|
|
*/
|
|
sp<DeviceDescriptor> createDevice(const audio_devices_t type,
|
|
const char *address,
|
|
const char *name,
|
|
const audio_format_t encodedFormat) const;
|
|
|
|
/**
|
|
* @brief cleanUpForDevice: loop on all profiles of all modules to remove device from
|
|
* the list of supported device. If this device is a dynamic device (aka a device not in the
|
|
* xml file with a runtime address), it is also removed from the module collection of dynamic
|
|
* devices.
|
|
* @param device that has been disconnected
|
|
*/
|
|
void cleanUpForDevice(const sp<DeviceDescriptor> &device);
|
|
|
|
void dump(String8 *dst) const;
|
|
};
|
|
|
|
} // namespace android
|