|
|
|
@ -22,6 +22,11 @@
|
|
|
|
|
|
|
|
|
|
#include "ConversionHelperHidl.h"
|
|
|
|
|
|
|
|
|
|
using ::android::hardware::audio::V4_0::AudioMicrophoneChannelMapping;
|
|
|
|
|
using ::android::hardware::audio::V4_0::AudioMicrophoneDirectionality;
|
|
|
|
|
using ::android::hardware::audio::V4_0::AudioMicrophoneLocation;
|
|
|
|
|
using ::android::hardware::audio::V4_0::DeviceAddress;
|
|
|
|
|
using ::android::hardware::audio::V4_0::MicrophoneInfo;
|
|
|
|
|
using ::android::hardware::audio::V4_0::Result;
|
|
|
|
|
|
|
|
|
|
namespace android {
|
|
|
|
@ -101,5 +106,132 @@ void ConversionHelperHidl::emitError(const char* funcName, const char* descripti
|
|
|
|
|
ALOGE("%s %p %s: %s (from rpc)", mClassName, this, funcName, description);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// TODO: Use the same implementation in the hal when it moves to a util library.
|
|
|
|
|
std::string deviceAddressToHal(const DeviceAddress& address) {
|
|
|
|
|
// HAL assumes that the address is NUL-terminated.
|
|
|
|
|
char halAddress[AUDIO_DEVICE_MAX_ADDRESS_LEN];
|
|
|
|
|
memset(halAddress, 0, sizeof(halAddress));
|
|
|
|
|
audio_devices_t halDevice = static_cast<audio_devices_t>(address.device);
|
|
|
|
|
const bool isInput = (halDevice & AUDIO_DEVICE_BIT_IN) != 0;
|
|
|
|
|
if (isInput) halDevice &= ~AUDIO_DEVICE_BIT_IN;
|
|
|
|
|
if ((!isInput && (halDevice & AUDIO_DEVICE_OUT_ALL_A2DP) != 0) ||
|
|
|
|
|
(isInput && (halDevice & AUDIO_DEVICE_IN_BLUETOOTH_A2DP) != 0)) {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "%02X:%02X:%02X:%02X:%02X:%02X",
|
|
|
|
|
address.address.mac[0], address.address.mac[1], address.address.mac[2],
|
|
|
|
|
address.address.mac[3], address.address.mac[4], address.address.mac[5]);
|
|
|
|
|
} else if ((!isInput && (halDevice & AUDIO_DEVICE_OUT_IP) != 0) ||
|
|
|
|
|
(isInput && (halDevice & AUDIO_DEVICE_IN_IP) != 0)) {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "%d.%d.%d.%d", address.address.ipv4[0],
|
|
|
|
|
address.address.ipv4[1], address.address.ipv4[2], address.address.ipv4[3]);
|
|
|
|
|
} else if ((!isInput && (halDevice & AUDIO_DEVICE_OUT_ALL_USB) != 0) ||
|
|
|
|
|
(isInput && (halDevice & AUDIO_DEVICE_IN_ALL_USB) != 0)) {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "card=%d;device=%d", address.address.alsa.card,
|
|
|
|
|
address.address.alsa.device);
|
|
|
|
|
} else if ((!isInput && (halDevice & AUDIO_DEVICE_OUT_BUS) != 0) ||
|
|
|
|
|
(isInput && (halDevice & AUDIO_DEVICE_IN_BUS) != 0)) {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "%s", address.busAddress.c_str());
|
|
|
|
|
} else if ((!isInput && (halDevice & AUDIO_DEVICE_OUT_REMOTE_SUBMIX)) != 0 ||
|
|
|
|
|
(isInput && (halDevice & AUDIO_DEVICE_IN_REMOTE_SUBMIX) != 0)) {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "%s", address.rSubmixAddress.c_str());
|
|
|
|
|
} else {
|
|
|
|
|
snprintf(halAddress, sizeof(halAddress), "%s", address.busAddress.c_str());
|
|
|
|
|
}
|
|
|
|
|
return halAddress;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//local conversion helpers
|
|
|
|
|
|
|
|
|
|
audio_microphone_channel_mapping_t channelMappingToHal(AudioMicrophoneChannelMapping mapping) {
|
|
|
|
|
switch (mapping) {
|
|
|
|
|
case AudioMicrophoneChannelMapping::UNUSED:
|
|
|
|
|
return AUDIO_MICROPHONE_CHANNEL_MAPPING_UNUSED;
|
|
|
|
|
case AudioMicrophoneChannelMapping::DIRECT:
|
|
|
|
|
return AUDIO_MICROPHONE_CHANNEL_MAPPING_DIRECT;
|
|
|
|
|
case AudioMicrophoneChannelMapping::PROCESSED:
|
|
|
|
|
return AUDIO_MICROPHONE_CHANNEL_MAPPING_PROCESSED;
|
|
|
|
|
default:
|
|
|
|
|
LOG_ALWAYS_FATAL("Unknown channelMappingToHal conversion %d", mapping);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
audio_microphone_location_t locationToHal(AudioMicrophoneLocation location) {
|
|
|
|
|
switch (location) {
|
|
|
|
|
case AudioMicrophoneLocation::UNKNOWN:
|
|
|
|
|
return AUDIO_MICROPHONE_LOCATION_UNKNOWN;
|
|
|
|
|
case AudioMicrophoneLocation::MAINBODY:
|
|
|
|
|
return AUDIO_MICROPHONE_LOCATION_MAINBODY;
|
|
|
|
|
case AudioMicrophoneLocation::MAINBODY_MOVABLE:
|
|
|
|
|
return AUDIO_MICROPHONE_LOCATION_MAINBODY_MOVABLE;
|
|
|
|
|
case AudioMicrophoneLocation::PERIPHERAL:
|
|
|
|
|
return AUDIO_MICROPHONE_LOCATION_PERIPHERAL;
|
|
|
|
|
default:
|
|
|
|
|
LOG_ALWAYS_FATAL("Unknown locationToHal conversion %d", location);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
audio_microphone_directionality_t directionalityToHal(AudioMicrophoneDirectionality dir) {
|
|
|
|
|
switch (dir) {
|
|
|
|
|
case AudioMicrophoneDirectionality::UNKNOWN:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_UNKNOWN;
|
|
|
|
|
case AudioMicrophoneDirectionality::OMNI:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_OMNI;
|
|
|
|
|
case AudioMicrophoneDirectionality::BI_DIRECTIONAL:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_BI_DIRECTIONAL;
|
|
|
|
|
case AudioMicrophoneDirectionality::CARDIOID:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_CARDIOID;
|
|
|
|
|
case AudioMicrophoneDirectionality::HYPER_CARDIOID:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_HYPER_CARDIOID;
|
|
|
|
|
case AudioMicrophoneDirectionality::SUPER_CARDIOID:
|
|
|
|
|
return AUDIO_MICROPHONE_DIRECTIONALITY_SUPER_CARDIOID;
|
|
|
|
|
default:
|
|
|
|
|
LOG_ALWAYS_FATAL("Unknown directionalityToHal conversion %d", dir);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// static
|
|
|
|
|
void ConversionHelperHidl::microphoneInfoToHal(const MicrophoneInfo& src,
|
|
|
|
|
audio_microphone_characteristic_t *pDst) {
|
|
|
|
|
if (pDst != NULL) {
|
|
|
|
|
snprintf(pDst->device_id, sizeof(pDst->device_id),
|
|
|
|
|
"%s", src.deviceId.c_str());
|
|
|
|
|
pDst->device = static_cast<audio_devices_t>(src.deviceAddress.device);
|
|
|
|
|
snprintf(pDst->address, sizeof(pDst->address),
|
|
|
|
|
"%s", deviceAddressToHal(src.deviceAddress).c_str());
|
|
|
|
|
if (src.channelMapping.size() > AUDIO_CHANNEL_COUNT_MAX) {
|
|
|
|
|
ALOGW("microphoneInfoToStruct found %zu channelMapping elements. Max expected is %d",
|
|
|
|
|
src.channelMapping.size(), AUDIO_CHANNEL_COUNT_MAX);
|
|
|
|
|
}
|
|
|
|
|
size_t ch;
|
|
|
|
|
for (ch = 0; ch < src.channelMapping.size() && ch < AUDIO_CHANNEL_COUNT_MAX; ch++) {
|
|
|
|
|
pDst->channel_mapping[ch] = channelMappingToHal(src.channelMapping[ch]);
|
|
|
|
|
}
|
|
|
|
|
for (; ch < AUDIO_CHANNEL_COUNT_MAX; ch++) {
|
|
|
|
|
pDst->channel_mapping[ch] = AUDIO_MICROPHONE_CHANNEL_MAPPING_UNUSED;
|
|
|
|
|
}
|
|
|
|
|
pDst->location = locationToHal(src.location);
|
|
|
|
|
pDst->group = (audio_microphone_group_t)src.group;
|
|
|
|
|
pDst->index_in_the_group = (unsigned int)src.indexInTheGroup;
|
|
|
|
|
pDst->sensitivity = src.sensitivity;
|
|
|
|
|
pDst->max_spl = src.maxSpl;
|
|
|
|
|
pDst->min_spl = src.minSpl;
|
|
|
|
|
pDst->directionality = directionalityToHal(src.directionality);
|
|
|
|
|
pDst->num_frequency_responses = (unsigned int)src.frequencyResponse.size();
|
|
|
|
|
if (pDst->num_frequency_responses > AUDIO_MICROPHONE_MAX_FREQUENCY_RESPONSES) {
|
|
|
|
|
ALOGW("microphoneInfoToStruct found %d frequency responses. Max expected is %d",
|
|
|
|
|
pDst->num_frequency_responses, AUDIO_MICROPHONE_MAX_FREQUENCY_RESPONSES);
|
|
|
|
|
pDst->num_frequency_responses = AUDIO_MICROPHONE_MAX_FREQUENCY_RESPONSES;
|
|
|
|
|
}
|
|
|
|
|
for (size_t k = 0; k < pDst->num_frequency_responses; k++) {
|
|
|
|
|
pDst->frequency_responses[0][k] = src.frequencyResponse[k].frequency;
|
|
|
|
|
pDst->frequency_responses[1][k] = src.frequencyResponse[k].level;
|
|
|
|
|
}
|
|
|
|
|
pDst->geometric_location.x = src.position.x;
|
|
|
|
|
pDst->geometric_location.y = src.position.y;
|
|
|
|
|
pDst->geometric_location.z = src.position.z;
|
|
|
|
|
pDst->orientation.x = src.orientation.x;
|
|
|
|
|
pDst->orientation.y = src.orientation.y;
|
|
|
|
|
pDst->orientation.z = src.orientation.z;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
} // namespace V4_0
|
|
|
|
|
} // namespace android
|
|
|
|
|