Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 45137cc7 authored by Treehugger Robot's avatar Treehugger Robot Committed by Gerrit Code Review
Browse files

Merge changes from topic "fix-b-281850726-remove-audio-attributes-int"

* changes:
  Remove AudioAttributesInternal and media.AudioFlag
  [BUG] audio: misalignement of native/java AudioAttributes
parents af7c0387 2a1cf618
Loading
Loading
Loading
Loading
+7 −30
Original line number Original line Diff line number Diff line
@@ -19,7 +19,6 @@
#include <algorithm>
#include <algorithm>
#include <map>
#include <map>
#include <sstream>
#include <sstream>
#include <regex>
#include <utility>
#include <utility>
#include <vector>
#include <vector>


@@ -101,12 +100,6 @@ using media::audio::common::PcmType;


namespace {
namespace {


bool isVendorExtension(const std::string& s) {
    // Must be the same as defined in AudioAttributes.aidl and {Playback|Record}TrackMetadata.aidl
    static const std::regex vendorExtension("VX_[A-Z0-9]{3,}_[_A-Z0-9]+");
    return std::regex_match(s.begin(), s.end(), vendorExtension);
}

std::vector<std::string> splitString(const std::string& s, char separator) {
std::vector<std::string> splitString(const std::string& s, char separator) {
    std::istringstream iss(s);
    std::istringstream iss(s);
    std::string t;
    std::string t;
@@ -1820,11 +1813,6 @@ legacy2aidl_audio_usage_t_AudioUsage(audio_usage_t legacy) {
    return unexpected(BAD_VALUE);
    return unexpected(BAD_VALUE);
}
}


namespace {

// TODO(b/281850726): Expose publicly once android.media.AudioFlag is removed.
// Until that, `legacy2aidl_audio_flags_mask_t_AudioFlag` function is ambiguous.

ConversionResult<audio_flags_mask_t>
ConversionResult<audio_flags_mask_t>
aidl2legacy_AudioFlag_audio_flags_mask_t(AudioFlag aidl) {
aidl2legacy_AudioFlag_audio_flags_mask_t(AudioFlag aidl) {
    switch (aidl) {
    switch (aidl) {
@@ -1926,8 +1914,6 @@ legacy2aidl_audio_flags_mask_t_int32_t_mask(audio_flags_mask_t legacy) {
            enumToMask_bitmask<int32_t, AudioFlag>);
            enumToMask_bitmask<int32_t, AudioFlag>);
}
}


}  // namespace

ConversionResult<std::string>
ConversionResult<std::string>
aidl2legacy_AudioTags_string(const std::vector<std::string>& aidl) {
aidl2legacy_AudioTags_string(const std::vector<std::string>& aidl) {
    std::ostringstream tagsBuffer;
    std::ostringstream tagsBuffer;
@@ -1936,29 +1922,20 @@ aidl2legacy_AudioTags_string(const std::vector<std::string>& aidl) {
        if (hasValue) {
        if (hasValue) {
            tagsBuffer << AUDIO_ATTRIBUTES_TAGS_SEPARATOR;
            tagsBuffer << AUDIO_ATTRIBUTES_TAGS_SEPARATOR;
        }
        }
        if (isVendorExtension(tag)) {
            // Note: with the current regex for vendor tags: VX_[A-Z0-9]{3,}_[_A-Z0-9]+
            // it's impossible to create a vendor tag that would contain the separator, but in case
            // the criteria changes, we double check it here.
        if (strchr(tag.c_str(), AUDIO_ATTRIBUTES_TAGS_SEPARATOR) == nullptr) {
        if (strchr(tag.c_str(), AUDIO_ATTRIBUTES_TAGS_SEPARATOR) == nullptr) {
            tagsBuffer << tag;
            tagsBuffer << tag;
            hasValue = true;
            hasValue = true;
        } else {
        } else {
                ALOGE("Vendor extension tag is ill-formed: \"%s\"", tag.c_str());
            ALOGE("Tag is ill-formed: \"%s\"", tag.c_str());
            return unexpected(BAD_VALUE);
            return unexpected(BAD_VALUE);
        }
        }
    }
    }
    }
    return tagsBuffer.str();
    return tagsBuffer.str();
}
}


ConversionResult<std::vector<std::string>>
ConversionResult<std::vector<std::string>>
legacy2aidl_string_AudioTags(const std::string& legacy) {
legacy2aidl_string_AudioTags(const std::string& legacy) {
    auto allTags = splitString(legacy, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    return splitString(legacy, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    std::vector<std::string> result;
    std::copy_if(std::make_move_iterator(allTags.begin()), std::make_move_iterator(allTags.end()),
                    std::back_inserter(result), isVendorExtension);
    return result;
}
}


ConversionResult<audio_attributes_t>
ConversionResult<audio_attributes_t>
+62 −4
Original line number Original line Diff line number Diff line
@@ -15,6 +15,7 @@
 */
 */


#include <algorithm>
#include <algorithm>
#include <regex>
#include <type_traits>
#include <type_traits>


#define LOG_TAG "AidlConversionNdkCpp"
#define LOG_TAG "AidlConversionNdkCpp"
@@ -34,6 +35,24 @@ namespace android {


namespace {
namespace {


bool isVendorExtension(const std::string& s) {
    // Per definition in AudioAttributes.aidl and {Playback|Record}TrackMetadata.aidl
    static const std::regex vendorExtension("VX_[A-Z0-9]{3,}_[_A-Z0-9]+");
    return std::regex_match(s.begin(), s.end(), vendorExtension);
}

inline bool isNotVendorExtension(const std::string& s) { return !isVendorExtension(s); }

void filterOutNonVendorTagsInPlace(std::vector<std::string>& tags) {
    if (std::find_if(tags.begin(), tags.end(), isNotVendorExtension) == tags.end()) {
        return;
    }
    std::vector<std::string> temp;
    temp.reserve(tags.size());
    std::copy_if(tags.begin(), tags.end(), std::back_inserter(temp), isVendorExtension);
    tags = std::move(temp);
}

// cpp2ndk and ndk2cpp are universal converters which work for any type,
// cpp2ndk and ndk2cpp are universal converters which work for any type,
// however they are not the most efficient way to convert due to extra
// however they are not the most efficient way to convert due to extra
// marshaling / unmarshaling step.
// marshaling / unmarshaling step.
@@ -100,11 +119,14 @@ template<typename CppEnum, typename NdkEnum>
}  // namespace
}  // namespace


#define GENERATE_CONVERTERS(packageName, className) \
#define GENERATE_CONVERTERS(packageName, className) \
    ConversionResult<::aidl::packageName::className> cpp2ndk_##className( \
    GENERATE_CONVERTERS_IMPL(packageName, _, className)

#define GENERATE_CONVERTERS_IMPL(packageName, prefix, className)        \
    ConversionResult<::aidl::packageName::className> cpp2ndk##prefix##className( \
            const ::packageName::className& cpp) {                      \
            const ::packageName::className& cpp) {                      \
        return cpp2ndk<::aidl::packageName::className>(cpp);            \
        return cpp2ndk<::aidl::packageName::className>(cpp);            \
    }                                                                   \
    }                                                                   \
    ConversionResult<::packageName::className> ndk2cpp_##className(     \
    ConversionResult<::packageName::className> ndk2cpp##prefix##className( \
            const ::aidl::packageName::className& ndk) {                \
            const ::aidl::packageName::className& ndk) {                \
        return ndk2cpp<::packageName::className>(ndk);                  \
        return ndk2cpp<::packageName::className>(ndk);                  \
    }
    }
@@ -120,10 +142,46 @@ template<typename CppEnum, typename NdkEnum>
}
}


GENERATE_CONVERTERS(android::media::audio::common, AudioFormatDescription);
GENERATE_CONVERTERS(android::media::audio::common, AudioFormatDescription);
GENERATE_CONVERTERS(android::media::audio::common, AudioHalEngineConfig);
GENERATE_CONVERTERS_IMPL(android::media::audio::common, _Impl_, AudioHalEngineConfig);
GENERATE_CONVERTERS(android::media::audio::common, AudioMMapPolicyInfo);
GENERATE_CONVERTERS(android::media::audio::common, AudioMMapPolicyInfo);
GENERATE_ENUM_CONVERTERS(android::media::audio::common, AudioMMapPolicyType);
GENERATE_ENUM_CONVERTERS(android::media::audio::common, AudioMMapPolicyType);
GENERATE_ENUM_CONVERTERS(android::media::audio::common, AudioMode);
GENERATE_ENUM_CONVERTERS(android::media::audio::common, AudioMode);
GENERATE_CONVERTERS(android::media::audio::common, AudioPort);
GENERATE_CONVERTERS(android::media::audio::common, AudioPort);


namespace {

// Filter out all AudioAttributes tags that do not conform to the vendor extension pattern.
template<typename T>
void filterOutNonVendorTags(T& audioHalEngineConfig) {
    for (auto& strategy : audioHalEngineConfig.productStrategies) {
        for (auto& group : strategy.attributesGroups) {
            for (auto& attr : group.attributes) {
                filterOutNonVendorTagsInPlace(attr.tags);
            }
        }
    }
}

}  // namespace

ConversionResult<::aidl::android::media::audio::common::AudioHalEngineConfig>
cpp2ndk_AudioHalEngineConfig(const ::android::media::audio::common::AudioHalEngineConfig& cpp) {
    auto conv = cpp2ndk_Impl_AudioHalEngineConfig(cpp);
    if (conv.ok()) {
        filterOutNonVendorTags(conv.value());
    }
    return conv;
}

ConversionResult<::android::media::audio::common::AudioHalEngineConfig>
ndk2cpp_AudioHalEngineConfig(
        const ::aidl::android::media::audio::common::AudioHalEngineConfig& ndk) {
    auto conv = ndk2cpp_Impl_AudioHalEngineConfig(ndk);
    if (conv.ok()) {
        filterOutNonVendorTags(conv.value());
    }
    return conv;
}


}  // namespace android
}  // namespace android
+10 −0
Original line number Original line Diff line number Diff line
@@ -357,6 +357,16 @@ ConversionResult<audio_usage_t> aidl2legacy_AudioUsage_audio_usage_t(
ConversionResult<media::audio::common::AudioUsage> legacy2aidl_audio_usage_t_AudioUsage(
ConversionResult<media::audio::common::AudioUsage> legacy2aidl_audio_usage_t_AudioUsage(
        audio_usage_t legacy);
        audio_usage_t legacy);


ConversionResult<audio_flags_mask_t>
aidl2legacy_AudioFlag_audio_flags_mask_t(media::audio::common::AudioFlag aidl);
ConversionResult<media::audio::common::AudioFlag>
legacy2aidl_audio_flags_mask_t_AudioFlag(audio_flags_mask_t legacy);

ConversionResult<audio_flags_mask_t>
aidl2legacy_int32_t_audio_flags_mask_t_mask(int32_t aidl);
ConversionResult<int32_t>
legacy2aidl_audio_flags_mask_t_int32_t_mask(audio_flags_mask_t legacy);

ConversionResult<std::string>
ConversionResult<std::string>
aidl2legacy_AudioTags_string(const std::vector<std::string>& aidl);
aidl2legacy_AudioTags_string(const std::vector<std::string>& aidl);
ConversionResult<std::vector<std::string>>
ConversionResult<std::vector<std::string>>
+19 −13
Original line number Original line Diff line number Diff line
@@ -107,25 +107,31 @@ INSTANTIATE_TEST_SUITE_P(AudioTagsRoundTrip, AudioTagsRoundTripTest,
                std::vector<std::string>{"VX_GOOGLE_41"},
                std::vector<std::string>{"VX_GOOGLE_41"},
                std::vector<std::string>{"VX_GOOGLE_41", "VX_GOOGLE_42"}));
                std::vector<std::string>{"VX_GOOGLE_41", "VX_GOOGLE_42"}));


TEST(AudioTags, NonVendorTags) {
TEST(AudioTags, NonVendorTagsAllowed) {
    const std::string separator(1, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    const std::string separator(1, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    const std::vector<std::string> initial{
    const std::vector<std::string> initial{"random_string", "VX_GOOGLE_42"};
        "random_string", "random" + separator + "string", "VX_GOOGLE_42"};
    auto conv = aidl2legacy_AudioTags_string(initial);
    auto conv = aidl2legacy_AudioTags_string(initial);
    ASSERT_TRUE(conv.ok());
    ASSERT_TRUE(conv.ok());
    EXPECT_EQ("VX_GOOGLE_42", conv.value());
    EXPECT_EQ("random_string" + separator + "VX_GOOGLE_42", conv.value());
}
}


TEST(AudioTags, IllFormedAidlTag) {
TEST(AudioTags, IllFormedAidlTag) {
    const std::string separator(1, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    const std::string separator(1, AUDIO_ATTRIBUTES_TAGS_SEPARATOR);
    {
        const std::vector<std::string> initial{"VX_GOOGLE" + separator + "42", "VX_GOOGLE_42"};
        const std::vector<std::string> initial{"VX_GOOGLE" + separator + "42", "VX_GOOGLE_42"};
        auto conv = aidl2legacy_AudioTags_string(initial);
        auto conv = aidl2legacy_AudioTags_string(initial);
    // Note: with the current regex for vendor tags: VX_[A-Z0-9]{3,}_[_A-Z0-9]+
    // it's impossible to create a vendor tag that would contain the separator, but in case
    // the criteria changes, we ensure that either such tags get filtered out or an error happens.
        if (conv.ok()) {
        if (conv.ok()) {
            EXPECT_EQ("VX_GOOGLE_42", conv.value());
            EXPECT_EQ("VX_GOOGLE_42", conv.value());
    } else {
        }
        EXPECT_FALSE(conv.ok()) << conv.value();
        // Failing this conversion is also OK. The result depends on whether the conversion
        // only passes through vendor tags.
    }
    {
        const std::vector<std::string> initial{
            "random_string", "random" + separator + "string", "VX_GOOGLE_42"};
        auto conv = aidl2legacy_AudioTags_string(initial);
        if (conv.ok()) {
            EXPECT_EQ("VX_GOOGLE_42", conv.value());
        }
    }
    }
}
}
+0 −123
Original line number Original line Diff line number Diff line
@@ -480,129 +480,6 @@ ConversionResult<media::AudioClient> legacy2aidl_AudioClient_AudioClient(
    return aidl;
    return aidl;
}
}


ConversionResult<audio_flags_mask_t>
aidl2legacy_AudioFlag_audio_flags_mask_t(media::AudioFlag aidl) {
    switch (aidl) {
        case media::AudioFlag::AUDIBILITY_ENFORCED:
            return AUDIO_FLAG_AUDIBILITY_ENFORCED;
        case media::AudioFlag::SECURE:
            return AUDIO_FLAG_SECURE;
        case media::AudioFlag::SCO:
            return AUDIO_FLAG_SCO;
        case media::AudioFlag::BEACON:
            return AUDIO_FLAG_BEACON;
        case media::AudioFlag::HW_AV_SYNC:
            return AUDIO_FLAG_HW_AV_SYNC;
        case media::AudioFlag::HW_HOTWORD:
            return AUDIO_FLAG_HW_HOTWORD;
        case media::AudioFlag::BYPASS_INTERRUPTION_POLICY:
            return AUDIO_FLAG_BYPASS_INTERRUPTION_POLICY;
        case media::AudioFlag::BYPASS_MUTE:
            return AUDIO_FLAG_BYPASS_MUTE;
        case media::AudioFlag::LOW_LATENCY:
            return AUDIO_FLAG_LOW_LATENCY;
        case media::AudioFlag::DEEP_BUFFER:
            return AUDIO_FLAG_DEEP_BUFFER;
        case media::AudioFlag::NO_MEDIA_PROJECTION:
            return AUDIO_FLAG_NO_MEDIA_PROJECTION;
        case media::AudioFlag::MUTE_HAPTIC:
            return AUDIO_FLAG_MUTE_HAPTIC;
        case media::AudioFlag::NO_SYSTEM_CAPTURE:
            return AUDIO_FLAG_NO_SYSTEM_CAPTURE;
        case media::AudioFlag::CAPTURE_PRIVATE:
            return AUDIO_FLAG_CAPTURE_PRIVATE;
        case media::AudioFlag::CONTENT_SPATIALIZED:
            return AUDIO_FLAG_CONTENT_SPATIALIZED;
        case media::AudioFlag::NEVER_SPATIALIZE:
            return AUDIO_FLAG_NEVER_SPATIALIZE;
        case media::AudioFlag::CALL_REDIRECTION:
            return AUDIO_FLAG_CALL_REDIRECTION;
    }
    return unexpected(BAD_VALUE);
}

ConversionResult<media::AudioFlag>
legacy2aidl_audio_flags_mask_t_AudioFlag(audio_flags_mask_t legacy) {
    switch (legacy) {
        case AUDIO_FLAG_NONE:
            return unexpected(BAD_VALUE);
        case AUDIO_FLAG_AUDIBILITY_ENFORCED:
            return media::AudioFlag::AUDIBILITY_ENFORCED;
        case AUDIO_FLAG_SECURE:
            return media::AudioFlag::SECURE;
        case AUDIO_FLAG_SCO:
            return media::AudioFlag::SCO;
        case AUDIO_FLAG_BEACON:
            return media::AudioFlag::BEACON;
        case AUDIO_FLAG_HW_AV_SYNC:
            return media::AudioFlag::HW_AV_SYNC;
        case AUDIO_FLAG_HW_HOTWORD:
            return media::AudioFlag::HW_HOTWORD;
        case AUDIO_FLAG_BYPASS_INTERRUPTION_POLICY:
            return media::AudioFlag::BYPASS_INTERRUPTION_POLICY;
        case AUDIO_FLAG_BYPASS_MUTE:
            return media::AudioFlag::BYPASS_MUTE;
        case AUDIO_FLAG_LOW_LATENCY:
            return media::AudioFlag::LOW_LATENCY;
        case AUDIO_FLAG_DEEP_BUFFER:
            return media::AudioFlag::DEEP_BUFFER;
        case AUDIO_FLAG_NO_MEDIA_PROJECTION:
            return media::AudioFlag::NO_MEDIA_PROJECTION;
        case AUDIO_FLAG_MUTE_HAPTIC:
            return media::AudioFlag::MUTE_HAPTIC;
        case AUDIO_FLAG_NO_SYSTEM_CAPTURE:
            return media::AudioFlag::NO_SYSTEM_CAPTURE;
        case AUDIO_FLAG_CAPTURE_PRIVATE:
            return media::AudioFlag::CAPTURE_PRIVATE;
        case AUDIO_FLAG_CONTENT_SPATIALIZED:
            return media::AudioFlag::CONTENT_SPATIALIZED;
        case AUDIO_FLAG_NEVER_SPATIALIZE:
            return media::AudioFlag::NEVER_SPATIALIZE;
        case AUDIO_FLAG_CALL_REDIRECTION:
            return media::AudioFlag::CALL_REDIRECTION;
    }
    return unexpected(BAD_VALUE);
}

ConversionResult<audio_flags_mask_t>
aidl2legacy_int32_t_audio_flags_mask_t_mask(int32_t aidl) {
    return convertBitmask<audio_flags_mask_t, int32_t, audio_flags_mask_t, media::AudioFlag>(
            aidl, aidl2legacy_AudioFlag_audio_flags_mask_t, indexToEnum_index<media::AudioFlag>,
            enumToMask_bitmask<audio_flags_mask_t, audio_flags_mask_t>);
}

ConversionResult<int32_t>
legacy2aidl_audio_flags_mask_t_int32_t_mask(audio_flags_mask_t legacy) {
    return convertBitmask<int32_t, audio_flags_mask_t, media::AudioFlag, audio_flags_mask_t>(
            legacy, legacy2aidl_audio_flags_mask_t_AudioFlag,
            indexToEnum_bitmask<audio_flags_mask_t>,
            enumToMask_index<int32_t, media::AudioFlag>);
}

ConversionResult<audio_attributes_t>
aidl2legacy_AudioAttributesInternal_audio_attributes_t(const media::AudioAttributesInternal& aidl) {
    audio_attributes_t legacy;
    legacy.content_type = VALUE_OR_RETURN(
            aidl2legacy_AudioContentType_audio_content_type_t(aidl.contentType));
    legacy.usage = VALUE_OR_RETURN(aidl2legacy_AudioUsage_audio_usage_t(aidl.usage));
    legacy.source = VALUE_OR_RETURN(aidl2legacy_AudioSource_audio_source_t(aidl.source));
    legacy.flags = VALUE_OR_RETURN(aidl2legacy_int32_t_audio_flags_mask_t_mask(aidl.flags));
    RETURN_IF_ERROR(aidl2legacy_string(aidl.tags, legacy.tags, sizeof(legacy.tags)));
    return legacy;
}

ConversionResult<media::AudioAttributesInternal>
legacy2aidl_audio_attributes_t_AudioAttributesInternal(const audio_attributes_t& legacy) {
    media::AudioAttributesInternal aidl;
    aidl.contentType = VALUE_OR_RETURN(
            legacy2aidl_audio_content_type_t_AudioContentType(legacy.content_type));
    aidl.usage = VALUE_OR_RETURN(legacy2aidl_audio_usage_t_AudioUsage(legacy.usage));
    aidl.source = VALUE_OR_RETURN(legacy2aidl_audio_source_t_AudioSource(legacy.source));
    aidl.flags = VALUE_OR_RETURN(legacy2aidl_audio_flags_mask_t_int32_t_mask(legacy.flags));
    aidl.tags = VALUE_OR_RETURN(legacy2aidl_string(legacy.tags, sizeof(legacy.tags)));
    return aidl;
}

ConversionResult<sp<IMemory>>
ConversionResult<sp<IMemory>>
aidl2legacy_SharedFileRegion_IMemory(const media::SharedFileRegion& aidl) {
aidl2legacy_SharedFileRegion_IMemory(const media::SharedFileRegion& aidl) {
    sp<IMemory> legacy;
    sp<IMemory> legacy;
Loading