经过以上三篇对AudioTrack,AudioFlinger, AudioPolicy的分析,发现音频数据经过AudioTrack,通过AudioPolicy路由,由AudioFlinger的各路线程混合输出到合适的Audio设备去。我们再分析AudioFlinger构造函数的时候涉及到音频硬件抽象层但是没有深入研究,现在,我们回过头来继续看看。
1. Audio系统设备抽象
AudioFlinger::AudioFlinger()
: BnAudioFlinger(),
......
{
......
mDevicesFactoryHal = DevicesFactoryHalInterface::create(); //硬件抽象
mEffectsFactoryHal = EffectsFactoryHalInterface::create();
}
DevicesFactoryHalHybrid类将持有DevicesFactoryHalInterface的两个实现
class DevicesFactoryHalHybrid : public DevicesFactoryHalInterface
{
public:
// Opens a device with the specified name. To close the device, it is
// necessary to release references to the returned object.
virtual status_t openDevice(const char *name, sp<DeviceHalInterface> *device);
private:
friend class DevicesFactoryHalInterface;
// Can not be constructed directly by clients.
DevicesFactoryHalHybrid();
virtual ~DevicesFactoryHalHybrid();
sp<DevicesFactoryHalInterface> mLocalFactory;
sp<DevicesFactoryHalInterface> mHidlFactory;
};
具体实现如下,通过系统的宏编译控制创建新老版本的硬件抽象层
sp<DevicesFactoryHalInterface> DevicesFactoryHalInterface::create() {
return new DevicesFactoryHalHybrid();
}
DevicesFactoryHalHybrid::DevicesFactoryHalHybrid()
: mLocalFactory(new DevicesFactoryHalLocal()),
mHidlFactory(
#ifdef USE_LEGACY_LOCAL_AUDIO_HAL
nullptr
#else
new DevicesFactoryHalHidl()
#endif
) {
}
DevicesFactoryHalHybrid::~DevicesFactoryHalHybrid() {
}
//AudioFlinger中调用
status_t DevicesFactoryHalHybrid::openDevice(const char *name, sp<DeviceHalInterface> *device) {
if (mHidlFactory != 0 && strcmp(AUDIO_HARDWARE_MODULE_ID_A2DP, name) != 0) {
return mHidlFactory->openDevice(name, device); //Trable架构
}
return mLocalFactory->openDevice(name, device); //hardware架构
}
在AudioPolicyService构造函数中,根据Audio配置文件载入Audio设备模块,具体函数在AudioFlinger中
audio_module_handle_t AudioFlinger::loadHwModule_l(const char *name)
{
int rc = mDevicesFactoryHal->openDevice(name, &dev); //打开具体的Device
mAudioHwDevs.add(handle, new AudioHwDevice(handle, name, dev, flags)); //抽象为AudioHwDevice
return handle;
}
如果调用 mLocalFactory->openDevice(name, device); //hardware架构,将以8.0以前的模式加载音频模块
static status_t load_audio_interface(const char *if_name, audio_hw_device_t **dev)
{
const hw_module_t *mod;
int rc;
rc = hw_get_module_by_class(AUDIO_HARDWARE_MODULE_ID, if_name, &mod);
if (rc) {
ALOGE("%s couldn't load audio hw module %s.%s (%s)", __func__,
AUDIO_HARDWARE_MODULE_ID, if_name, strerror(-rc));
goto out;
}
rc = audio_hw_device_open(mod, dev);
if (rc) {
ALOGE("%s couldn't open audio hw device in %s.%s (%s)", __func__,
AUDIO_HARDWARE_MODULE_ID, if_name, strerror(-rc));
goto out;
}
if ((*dev)->common.version < AUDIO_DEVICE_API_VERSION_MIN) {
ALOGE("%s wrong audio hw device version %04x", __func__, (*dev)->common.version);
rc = BAD_VALUE;
audio_hw_device_close(*dev);
goto out;
}
return OK;
out:
*dev = NULL;
return rc;
}
status_t DevicesFactoryHalLocal::openDevice(const char *name, sp<DeviceHalInterface> *device) {
audio_hw_device_t *dev;
status_t rc = load_audio_interface(name, &dev);
if (rc == OK) {
*device = new DeviceHalLocal(dev); //封装为DeviceHalLocal
}
return rc;
}
如果调用 mHidlFactory->openDevice(name, device); //Trable架构
DevicesFactoryHalHidl::DevicesFactoryHalHidl() {
mDevicesFactory = IDevicesFactory::getService(); //将调用Treble架构下的HW
if (mDevicesFactory != 0) {
// It is assumed that DevicesFactory is owned by AudioFlinger
// and thus have the same lifespan.
mDevicesFactory->linkToDeath(HalDeathHandler::getInstance(), 0 /*cookie*/);
} else {
ALOGE("Failed to obtain IDevicesFactory service, terminating process.");
exit(1);
}
}
DevicesFactoryHalHidl::~DevicesFactoryHalHidl() {
}
// static
status_t DevicesFactoryHalHidl::nameFromHal(const char *name, IDevicesFactory::Device *device) {
if (strcmp(name, AUDIO_HARDWARE_MODULE_ID_PRIMARY) == 0) {
*device = IDevicesFactory::Device::PRIMARY;
return OK;
} else if(strcmp(name, AUDIO_HARDWARE_MODULE_ID_A2DP) == 0) {
*device = IDevicesFactory::Device::A2DP;
return OK;
} else if(strcmp(name, AUDIO_HARDWARE_MODULE_ID_USB) == 0) {
*device = IDevicesFactory::Device::USB;
return OK;
} else if(strcmp(name, AUDIO_HARDWARE_MODULE_ID_REMOTE_SUBMIX) == 0) {
*device = IDevicesFactory::Device::R_SUBMIX;
return OK;
} else if(strcmp(name, AUDIO_HARDWARE_MODULE_ID_STUB) == 0) {
*device = IDevicesFactory::Device::STUB;
return OK;
}
ALOGE("Invalid device name %s", name);
return BAD_VALUE;
}
status_t DevicesFactoryHalHidl::openDevice(const char *name, sp<DeviceHalInterface> *device) {
if (mDevicesFactory == 0) return NO_INIT;
IDevicesFactory::Device hidlDevice;
status_t status = nameFromHal(name, &hidlDevice);
if (status != OK) return status;
Result retval = Result::NOT_INITIALIZED;
Return<void> ret = mDevicesFactory->openDevice( //调用加载具体的Device
hidlDevice,
[&](Result r, const sp<IDevice>& result) {
retval = r;
if (retval == Result::OK) {
*device = new DeviceHalHidl(result); //封装为DeviceHalHidl
}
});
if (ret.isOk()) {
if (retval == Result::OK) return OK;
else if (retval == Result::INVALID_ARGUMENTS) return BAD_VALUE;
else return NO_INIT;
}
return FAILED_TRANSACTION;
}
hardware\interfaces\audio\2.0\default\DevicesFactory.h
struct DevicesFactory : public IDevicesFactory {
// Methods from ::android::hardware::audio::V2_0::IDevicesFactory follow.
Return<void> openDevice(IDevicesFactory::Device device, openDevice_cb _hidl_cb) override;
private:
static const char* deviceToString(IDevicesFactory::Device device);
static int loadAudioInterface(const char *if_name, audio_hw_device_t **dev);
};
extern "C" IDevicesFactory* HIDL_FETCH_IDevicesFactory(const char* name);
hardware\interfaces\audio\2.0\default\DevicesFactory.cpp
// Methods from ::android::hardware::audio::V2_0::IDevicesFactory follow.
Return<void> DevicesFactory::openDevice(IDevicesFactory::Device device, openDevice_cb _hidl_cb) {
audio_hw_device_t *halDevice;
Result retval(Result::INVALID_ARGUMENTS);
sp<IDevice> result;
const char* moduleName = deviceToString(device);
if (moduleName != nullptr) {
int halStatus = loadAudioInterface(moduleName, &halDevice); //加载音频模块设备
if (halStatus == OK) {
if (device == IDevicesFactory::Device::PRIMARY) {
result = new PrimaryDevice(halDevice);
} else {
result = new ::android::hardware::audio::V2_0::implementation::
Device(halDevice);
}
retval = Result::OK;
} else if (halStatus == -EINVAL) {
retval = Result::NOT_INITIALIZED;
}
}
_hidl_cb(retval, result);
return Void();
}
IDevicesFactory* HIDL_FETCH_IDevicesFactory(const char* /* name */) {
return new DevicesFactory();
}
加载具体的音频模块设备
// static
int DevicesFactory::loadAudioInterface(const char *if_name, audio_hw_device_t **dev)
{
const hw_module_t *mod;
int rc;
rc = hw_get_module_by_class(AUDIO_HARDWARE_MODULE_ID, if_name, &mod);
if (rc) {
ALOGE("%s couldn't load audio hw module %s.%s (%s)", __func__,
AUDIO_HARDWARE_MODULE_ID, if_name, strerror(-rc));
goto out;
}
rc = audio_hw_device_open(mod, dev);
if (rc) {
ALOGE("%s couldn't open audio hw device in %s.%s (%s)", __func__,
AUDIO_HARDWARE_MODULE_ID, if_name, strerror(-rc));
goto out;
}
if ((*dev)->common.version < AUDIO_DEVICE_API_VERSION_MIN) {
ALOGE("%s wrong audio hw device version %04x", __func__, (*dev)->common.version);
rc = -EINVAL;
audio_hw_device_close(*dev);
goto out;
}
return OK;
out:
*dev = NULL;
return rc;
}
在service.cpp文件中我们看到Treble架构下的几项注册到hwservicemanager的服务包括 IDevicesFactory,IEffectsFactory, ISoundTriggerHw, IBroadcastRadioFactory几项
hardware\interfaces\audio\2.0\default\service.cpp
int main(int /* argc */, char* /* argv */ []) {
configureRpcThreadpool(16, true /*callerWillJoin*/);
android::status_t status;
status = registerPassthroughServiceImplementation<IDevicesFactory>();
LOG_ALWAYS_FATAL_IF(status != OK, "Error while registering audio service: %d", status);
status = registerPassthroughServiceImplementation<IEffectsFactory>();
LOG_ALWAYS_FATAL_IF(status != OK, "Error while registering audio effects service: %d", status);
// Soundtrigger and FM radio might be not present.
status = registerPassthroughServiceImplementation<ISoundTriggerHw>();
ALOGE_IF(status != OK, "Error while registering soundtrigger service: %d", status);
if (useBroadcastRadioFutureFeatures) {
status = registerPassthroughServiceImplementation<
broadcastradio::V1_1::IBroadcastRadioFactory>();
} else {
status = registerPassthroughServiceImplementation<
broadcastradio::V1_0::IBroadcastRadioFactory>();
}
ALOGE_IF(status != OK, "Error while registering fm radio service: %d", status);
joinRpcThreadpool();
return status;
}
2. Audio系统硬件抽象层
再看 DeviceHalLocal,实现自DeviceHalInterface
DeviceHalLocal::DeviceHalLocal(audio_hw_device_t *dev)
: mDev(dev) {
}
......
status_t DeviceHalLocal::openOutputStream(
audio_io_handle_t handle,
audio_devices_t devices,
audio_output_flags_t flags,
struct audio_config *config,
const char *address,
sp<StreamOutHalInterface> *outStream) {
audio_stream_out_t *halStream;
ALOGV("open_output_stream handle: %d devices: %x flags: %#x"
"srate: %d format %#x channels %x address %s",
handle, devices, flags,
config->sample_rate, config->format, config->channel_mask,
address);
int openResut = mDev->open_output_stream(
mDev, handle, devices, flags, config, &halStream, address);
if (openResut == OK) {
*outStream = new StreamOutHalLocal(halStream, this);
}
ALOGV("open_output_stream status %d stream %p", openResut, halStream);
return openResut;
}
......
调用硬件抽象层的音频流输出函数
static int adev_open_output_stream(struct audio_hw_device *dev,
audio_io_handle_t handle,
audio_devices_t devices,
audio_output_flags_t flags,
struct audio_config *config,
struct audio_stream_out **stream_out,
const char *address __unused)
{
ALOGV("adev_open_output_stream...");
*stream_out = NULL;
struct stub_stream_out *out =
(struct stub_stream_out *)calloc(1, sizeof(struct stub_stream_out));
if (!out)
return -ENOMEM;
out->stream.common.get_sample_rate = out_get_sample_rate;
out->stream.common.set_sample_rate = out_set_sample_rate;
out->stream.common.get_buffer_size = out_get_buffer_size;
out->stream.common.get_channels = out_get_channels;
out->stream.common.get_format = out_get_format;
out->stream.common.set_format = out_set_format;
out->stream.common.standby = out_standby;
out->stream.common.dump = out_dump;
out->stream.common.set_parameters = out_set_parameters;
out->stream.common.get_parameters = out_get_parameters;
out->stream.common.add_audio_effect = out_add_audio_effect;
out->stream.common.remove_audio_effect = out_remove_audio_effect;
out->stream.get_latency = out_get_latency;
out->stream.set_volume = out_set_volume;
out->stream.write = out_write;
out->stream.get_render_position = out_get_render_position;
out->stream.get_next_write_timestamp = out_get_next_write_timestamp;
*stream_out = &out->stream;
return 0;
}
DeviceHalHidl 实现自 DeviceHalInterface
status_t DeviceHalHidl::openOutputStream(
audio_io_handle_t handle,
audio_devices_t devices,
audio_output_flags_t flags,
struct audio_config *config,
const char *address,
sp<StreamOutHalInterface> *outStream) {
if (mDevice == 0) return NO_INIT;
DeviceAddress hidlDevice;
status_t status = deviceAddressFromHal(devices, address, &hidlDevice);
if (status != OK) return status;
AudioConfig hidlConfig;
HidlUtils::audioConfigFromHal(*config, &hidlConfig);
Result retval = Result::NOT_INITIALIZED;
Return<void> ret = mDevice->openOutputStream( //输出Audio流, 调用硬件抽象层的音频流输出函数
handle,
hidlDevice,
hidlConfig,
AudioOutputFlag(flags),
[&](Result r, const sp<IStreamOut>& result, const AudioConfig& suggestedConfig) {
retval = r;
if (retval == Result::OK) {
*outStream = new StreamOutHalHidl(result);
}
HidlUtils::audioConfigToHal(suggestedConfig, config);
});
return processReturn("openOutputStream", ret, retval);
}
至此整个Audio系统的分析到此结束,其实Audio系统还有很大一部分,在整个Android系统中错综复杂,实在难以详述,只能摘其精要,略其枝蔓。下一个专题我们要来啃一啃Media系统,作为Android重要且复杂的系统来分析,可能会有漫长的篇幅。