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

Commit e4145fce authored by Ray Essick's avatar Ray Essick Committed by Android (Google) Code Review
Browse files

Merge "add MediaCodec XML minsdk=# attribute"

parents c8395369 9c362b60
Loading
Loading
Loading
Loading
+70 −3
Original line number Diff line number Diff line
@@ -19,6 +19,8 @@

#include <media/stagefright/xmlparser/MediaCodecsXmlParser.h>

#include <android/api-level.h>

#include <android-base/logging.h>
#include <android-base/macros.h>
#include <android-base/properties.h>
@@ -30,6 +32,7 @@

#include <expat.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>

@@ -360,7 +363,7 @@ struct MediaCodecsXmlParser::Impl {

        status_t updateMediaCodec(
                const char *rank, const StringSet &domain, const StringSet &variants,
                const char *enabled);
                const char *enabled, const char *minsdk);
    };

    status_t parseXmlFilesInSearchDirs(
@@ -493,6 +496,9 @@ void MediaCodecsXmlParser::Impl::Parser::logAnyErrors(const Result &status) cons
    }
}

// current SDK for this device; filled in when initializing the parser.
static int mysdk = 0;

MediaCodecsXmlParser::Impl::Parser::Parser(State *state, std::string path)
    : mState(state),
      mPath(path),
@@ -502,6 +508,20 @@ MediaCodecsXmlParser::Impl::Parser::Parser(State *state, std::string path)
    if (end != std::string::npos) {
        mHrefBase = path.substr(0, end + 1);
    }

#if defined(__ANDROID_API_U__)
    // this is sdk calculation is intended only for devices >= U
    static std::once_flag sCheckOnce;

    std::call_once(sCheckOnce, [&](){
        mysdk = android_get_device_api_level();

        // work around main development branch being on same SDK as the last dessert release.
        if (__ANDROID_API__ == __ANDROID_API_FUTURE__) {
            mysdk++;
        }
    });
#endif  // __ANDROID_API_U__
}

void MediaCodecsXmlParser::Impl::Parser::parseXmlFile() {
@@ -930,6 +950,7 @@ status_t MediaCodecsXmlParser::Impl::Parser::enterMediaCodec(
    const char *a_domain = nullptr;
    const char *a_variant = nullptr;
    const char *a_enabled = nullptr;
    const char *a_minsdk = nullptr;

    size_t i = 0;
    while (attrs[i] != nullptr) {
@@ -953,6 +974,8 @@ status_t MediaCodecsXmlParser::Impl::Parser::enterMediaCodec(
            a_variant = attrs[++i];
        } else if (strEq(attrs[i], "enabled")) {
            a_enabled = attrs[++i];
        } else if (strEq(attrs[i], "minsdk")) {
            a_minsdk = attrs[++i];
        } else {
            PLOGD("MediaCodec: ignoring unrecognized attribute '%s'", attrs[i]);
            ++i;
@@ -981,7 +1004,7 @@ status_t MediaCodecsXmlParser::Impl::Parser::enterMediaCodec(

    return updateMediaCodec(
            a_rank, parseCommaSeparatedStringSet(a_domain),
            parseCommaSeparatedStringSet(a_variant), a_enabled);
            parseCommaSeparatedStringSet(a_variant), a_enabled, a_minsdk);
}

MediaCodecsXmlParser::Impl::Result
@@ -1035,7 +1058,7 @@ MediaCodecsXmlParser::Impl::State::enterMediaCodec(

status_t MediaCodecsXmlParser::Impl::Parser::updateMediaCodec(
        const char *rank, const StringSet &domains, const StringSet &variants,
        const char *enabled) {
        const char *enabled, const char *minsdk) {
    CHECK(mState->inCodec());
    CodecProperties &codec = mState->codec();

@@ -1048,6 +1071,7 @@ status_t MediaCodecsXmlParser::Impl::Parser::updateMediaCodec(

    codec.variantSet = variants;

    // we allow sets of domains...
    for (const std::string &domain : domains) {
        if (domain.size() && domain.at(0) == '!') {
            codec.domainSet.erase(domain.substr(1));
@@ -1065,6 +1089,49 @@ status_t MediaCodecsXmlParser::Impl::Parser::updateMediaCodec(
            ALOGD("disabling %s", mState->codecName().c_str());
        }
    }

    // evaluate against passed minsdk, with lots of logging to explain the logic
    //
    // if current sdk >= minsdk, we want to enable the codec
    // this OVERRIDES any enabled="true|false" setting on the codec.
    // (enabled=true minsdk=35 on a sdk 34 device results in a disabled codec)
    //
    // Although minsdk is not parsed before Android U, we can carry media_codecs.xml
    // using this to devices earlier (e.g. as part of mainline). An example is appropriate.
    //
    // we have a codec that we want enabled in Android V (sdk=35), so we use:
    //     <MediaCodec ..... enabled="false" minsdk="35" >
    //
    // on Q/R/S/T: it sees enabled=false, but ignores the unrecognized minsdk
    //     so the codec will be disabled
    // on U: it sees enabled=false, and sees minsdk=35, but U==34 and 34 < 35
    //     so the codec will be disabled
    // on V: it sees enabled=false, and sees minsdk=35, V==35 and 35 >= 35
    //     so the codec will be enabled
    //
    // if we know the XML files will be used only on devices >= U, we can skip the enabled=false
    // piece.  Android mainline's support horizons say we will be using the enabled=false for
    // another 4-5 years after U.
    //
    if (minsdk != nullptr) {
        char *p = nullptr;
        int sdk = strtol(minsdk, &p, 0);
        if (p == minsdk || sdk < 0) {
            ALOGE("minsdk parsing '%s' yielded %d, mapping to 0", minsdk, sdk);
            sdk = 0;
        }
        // minsdk="#" means: "enable if sdk is >= #, disable otherwise"
        if (mysdk < sdk) {
            ALOGI("codec %s disabled, device sdk %d < required %d",
                mState->codecName().c_str(), mysdk, sdk);
            codec.quirkSet.emplace("attribute::disabled");
        } else {
            ALOGI("codec %s enabled, device sdk %d >= required %d",
                mState->codecName().c_str(), mysdk, sdk);
            codec.quirkSet.erase("attribute::disabled");
        }
    }

    return OK;
}

+2 −0
Original line number Diff line number Diff line
@@ -84,6 +84,7 @@ package media.codecs {
    method public java.util.List<media.codecs.Feature> getFeature_optional();
    method public java.util.List<media.codecs.Limit> getLimit_optional();
    method public java.util.List<media.codecs.Mapping> getMapping_optional();
    method public String getMinsdk();
    method public String getName();
    method public java.util.List<media.codecs.Quirk> getQuirk_optional();
    method public String getRank();
@@ -95,6 +96,7 @@ package media.codecs {
    method public java.util.List<media.codecs.Variant> getVariant_optional();
    method public void setDomain(String);
    method public void setEnabled(String);
    method public void setMinsdk(String);
    method public void setName(String);
    method public void setRank(String);
    method public void setType(String);
+1 −0
Original line number Diff line number Diff line
@@ -74,6 +74,7 @@
        <xs:attribute name="domain" type="xs:string"/>
        <xs:attribute name="variant" type="xs:string"/>
        <xs:attribute name="enabled" type="xs:string"/>
        <xs:attribute name="minsdk" type="xs:string"/>
    </xs:complexType>
    <xs:complexType name="Quirk">
        <xs:attribute name="name" type="xs:string"/>
+43 −0
Original line number Diff line number Diff line
@@ -145,6 +145,33 @@ void XMLParseTest::setUpDatabase() {
           },
           {}, "");

    // minsdk
    setCodecProperties("test12.encoder", true, 12, {"attribute::disabled"}, {}, {}, "video/t12",
           {
                   pair<string, string>("tuning-enable-goal", "no"),
           },
           {}, "");
    setCodecProperties("test13.encoder", true, 13, {"attribute::disabled"}, {}, {}, "video/t13",
           {
                   pair<string, string>("tuning-enable-goal", "no"),
           },
           {}, "");
    setCodecProperties("test14.encoder", true, 14, {"attribute::disabled"}, {}, {}, "video/t14",
           {
                   pair<string, string>("tuning-enable-goal", "no"),
           },
           {}, "");
    setCodecProperties("test15.encoder", true, 15, {}, {}, {}, "video/t15",
           {
                   pair<string, string>("tuning-enable-goal", "yes"),
           },
           {}, "");
    setCodecProperties("test16.encoder", true, 16, {}, {}, {}, "video/t16",
           {
                   pair<string, string>("tuning-enable-goal", "yes"),
           },
           {}, "");

    setRoleProperties("audio_decoder.mp3", false, 1, "audio/mpeg", "test1.decoder",
                      {pair<string, string>("attribute::disabled", "present"),
                       pair<string, string>("rank", "4")});
@@ -191,6 +218,22 @@ void XMLParseTest::setUpDatabase() {
                        pair<string, string>("tuning-pi", "3.1415")
                       });

    // minsdk
    setRoleProperties("video_encoder.t12", true, 12, "video/t12", "test12.encoder",
                       {pair<string, string>("tuning-enable-goal", "no"),
                        pair<string, string>("attribute::disabled", "present") });
    setRoleProperties("video_encoder.t13", true, 13, "video/t13", "test13.encoder",
                       {pair<string, string>("tuning-enable-goal", "no"),
                        pair<string, string>("attribute::disabled", "present") });
    setRoleProperties("video_encoder.t14", true, 14, "video/t14", "test14.encoder",
                       {pair<string, string>("tuning-enable-goal", "no"),
                        pair<string, string>("attribute::disabled", "present") });
    setRoleProperties("video_encoder.t15", true, 15, "video/t15", "test15.encoder",
                       {pair<string, string>("tuning-enable-goal", "yes")});
    setRoleProperties("video_encoder.t16", true, 16, "video/t16", "test16.encoder",
                       {pair<string, string>("tuning-enable-goal", "yes")});


    setServiceAttribute(
            {pair<string, string>("domain-telephony", "0"), pair<string, string>("domain-tv", "0"),
             pair<string, string>("setting2", "0"), pair<string, string>("variant-variant1", "0")});
+16 −0
Original line number Diff line number Diff line
@@ -88,5 +88,21 @@
            <Tuning name="hungry" value="yes"/>
            <Tuning name="pi" value="3.1415"/>
        </MediaCodec>
        <!-- test minsdk -->
        <MediaCodec name="test12.encoder" type="video/t12" minsdk="100">
            <Tuning name="enable-goal" value="no"/>
        </MediaCodec>
        <MediaCodec name="test13.encoder" type="video/t13" enabled="false" minsdk="100">
            <Tuning name="enable-goal" value="no"/>
        </MediaCodec>
        <MediaCodec name="test14.encoder" type="video/t14" enabled="true" minsdk="100">
            <Tuning name="enable-goal" value="no"/>
        </MediaCodec>
        <MediaCodec name="test15.encoder" type="video/t15" minsdk="34">
            <Tuning name="enable-goal" value="yes"/>
        </MediaCodec>
        <MediaCodec name="test16.encoder" type="video/t16" enabled="false" minsdk="34">
            <Tuning name="enable-goal" value="yes"/>
        </MediaCodec>
    </Encoders>
</Included>