/*
 * Copyright 2017, 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.
 */

//#define LOG_NDEBUG 0
#define LOG_TAG "MediaCodecsXmlParser"
#include <utils/Log.h>

#include <media/vndk/xmlparser/1.0/MediaCodecsXmlParser.h>

#include <media/MediaCodecInfo.h>

#include <media/stagefright/foundation/ADebug.h>
#include <media/stagefright/foundation/AMessage.h>
#include <media/stagefright/foundation/AUtils.h>
#include <media/stagefright/MediaErrors.h>

#include <sys/stat.h>

#include <expat.h>
#include <string>

#define MEDIA_CODECS_CONFIG_FILE_PATH_MAX_LENGTH 256

namespace android {

namespace { // Local variables and functions

const char *kProfilingResults =
        "/data/misc/media/media_codecs_profiling_results.xml";

// Treblized media codec list will be located in /odm/etc or /vendor/etc.
const char *kConfigLocationList[] =
        {"/odm/etc", "/vendor/etc", "/etc"};
constexpr int kConfigLocationListSize =
        (sizeof(kConfigLocationList) / sizeof(kConfigLocationList[0]));

bool findMediaCodecListFileFullPath(
        const char *file_name, std::string *out_path) {
    for (int i = 0; i < kConfigLocationListSize; i++) {
        *out_path = std::string(kConfigLocationList[i]) + "/" + file_name;
        struct stat file_stat;
        if (stat(out_path->c_str(), &file_stat) == 0 &&
                S_ISREG(file_stat.st_mode)) {
            return true;
        }
    }
    return false;
}

// Find TypeInfo by name.
std::vector<TypeInfo>::iterator findTypeInfo(
        CodecInfo &codecInfo, const AString &typeName) {
    return std::find_if(
            codecInfo.mTypes.begin(), codecInfo.mTypes.end(),
            [typeName](const auto &typeInfo) {
                return typeInfo.mName == typeName;
            });
}

// Convert a string into a boolean value.
bool ParseBoolean(const char *s) {
    if (!strcasecmp(s, "true") || !strcasecmp(s, "yes") || !strcasecmp(s, "y")) {
        return true;
    }
    char *end;
    unsigned long res = strtoul(s, &end, 10);
    return *s != '\0' && *end == '\0' && res > 0;
}

} // unnamed namespace

MediaCodecsXmlParser::MediaCodecsXmlParser() :
    mInitCheck(NO_INIT),
    mUpdate(false) {
    std::string config_file_path;
    if (findMediaCodecListFileFullPath(
            "media_codecs.xml", &config_file_path)) {
        parseTopLevelXMLFile(config_file_path.c_str(), false);
    } else {
        mInitCheck = NAME_NOT_FOUND;
    }
    if (findMediaCodecListFileFullPath(
            "media_codecs_performance.xml", &config_file_path)) {
        parseTopLevelXMLFile(config_file_path.c_str(), true);
    }
    parseTopLevelXMLFile(kProfilingResults, true);
}

void MediaCodecsXmlParser::parseTopLevelXMLFile(
        const char *codecs_xml, bool ignore_errors) {
    // get href_base
    const char *href_base_end = strrchr(codecs_xml, '/');
    if (href_base_end != NULL) {
        mHrefBase = AString(codecs_xml, href_base_end - codecs_xml + 1);
    }

    mInitCheck = OK; // keeping this here for safety
    mCurrentSection = SECTION_TOPLEVEL;
    mDepth = 0;

    parseXMLFile(codecs_xml);

    if (mInitCheck != OK) {
        if (ignore_errors) {
            mInitCheck = OK;
            return;
        }
        mCodecInfos.clear();
        return;
    }
}

MediaCodecsXmlParser::~MediaCodecsXmlParser() {
}

status_t MediaCodecsXmlParser::initCheck() const {
    return mInitCheck;
}

void MediaCodecsXmlParser::parseXMLFile(const char *path) {
    FILE *file = fopen(path, "r");

    if (file == NULL) {
        ALOGW("unable to open media codecs configuration xml file: %s", path);
        mInitCheck = NAME_NOT_FOUND;
        return;
    }

    ALOGV("Start parsing %s", path);
    XML_Parser parser = ::XML_ParserCreate(NULL);
    CHECK(parser != NULL);

    ::XML_SetUserData(parser, this);
    ::XML_SetElementHandler(
            parser, StartElementHandlerWrapper, EndElementHandlerWrapper);

    const int BUFF_SIZE = 512;
    while (mInitCheck == OK) {
        void *buff = ::XML_GetBuffer(parser, BUFF_SIZE);
        if (buff == NULL) {
            ALOGE("failed in call to XML_GetBuffer()");
            mInitCheck = UNKNOWN_ERROR;
            break;
        }

        int bytes_read = ::fread(buff, 1, BUFF_SIZE, file);
        if (bytes_read < 0) {
            ALOGE("failed in call to read");
            mInitCheck = ERROR_IO;
            break;
        }

        XML_Status status = ::XML_ParseBuffer(parser, bytes_read, bytes_read == 0);
        if (status != XML_STATUS_OK) {
            ALOGE("malformed (%s)", ::XML_ErrorString(::XML_GetErrorCode(parser)));
            mInitCheck = ERROR_MALFORMED;
            break;
        }

        if (bytes_read == 0) {
            break;
        }
    }

    ::XML_ParserFree(parser);

    fclose(file);
    file = NULL;
}

// static
void MediaCodecsXmlParser::StartElementHandlerWrapper(
        void *me, const char *name, const char **attrs) {
    static_cast<MediaCodecsXmlParser *>(me)->startElementHandler(name, attrs);
}

// static
void MediaCodecsXmlParser::EndElementHandlerWrapper(void *me, const char *name) {
    static_cast<MediaCodecsXmlParser *>(me)->endElementHandler(name);
}

status_t MediaCodecsXmlParser::includeXMLFile(const char **attrs) {
    const char *href = NULL;
    size_t i = 0;
    while (attrs[i] != NULL) {
        if (!strcmp(attrs[i], "href")) {
            if (attrs[i + 1] == NULL) {
                return -EINVAL;
            }
            href = attrs[i + 1];
            ++i;
        } else {
            ALOGE("includeXMLFile: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }
        ++i;
    }

    // For security reasons and for simplicity, file names can only contain
    // [a-zA-Z0-9_.] and must start with  media_codecs_ and end with .xml
    for (i = 0; href[i] != '\0'; i++) {
        if (href[i] == '.' || href[i] == '_' ||
                (href[i] >= '0' && href[i] <= '9') ||
                (href[i] >= 'A' && href[i] <= 'Z') ||
                (href[i] >= 'a' && href[i] <= 'z')) {
            continue;
        }
        ALOGE("invalid include file name: %s", href);
        return -EINVAL;
    }

    AString filename = href;
    if (!filename.startsWith("media_codecs_") ||
        !filename.endsWith(".xml")) {
        ALOGE("invalid include file name: %s", href);
        return -EINVAL;
    }
    filename.insert(mHrefBase, 0);

    parseXMLFile(filename.c_str());
    return mInitCheck;
}

void MediaCodecsXmlParser::startElementHandler(
        const char *name, const char **attrs) {
    if (mInitCheck != OK) {
        return;
    }

    bool inType = true;

    if (!strcmp(name, "Include")) {
        mInitCheck = includeXMLFile(attrs);
        if (mInitCheck == OK) {
            mPastSections.push(mCurrentSection);
            mCurrentSection = SECTION_INCLUDE;
        }
        ++mDepth;
        return;
    }

    switch (mCurrentSection) {
        case SECTION_TOPLEVEL:
        {
            if (!strcmp(name, "Decoders")) {
                mCurrentSection = SECTION_DECODERS;
            } else if (!strcmp(name, "Encoders")) {
                mCurrentSection = SECTION_ENCODERS;
            } else if (!strcmp(name, "Settings")) {
                mCurrentSection = SECTION_SETTINGS;
            }
            break;
        }

        case SECTION_SETTINGS:
        {
            if (!strcmp(name, "Setting")) {
                mInitCheck = addSettingFromAttributes(attrs);
            }
            break;
        }

        case SECTION_DECODERS:
        {
            if (!strcmp(name, "MediaCodec")) {
                mInitCheck =
                    addMediaCodecFromAttributes(false /* encoder */, attrs);

                mCurrentSection = SECTION_DECODER;
            }
            break;
        }

        case SECTION_ENCODERS:
        {
            if (!strcmp(name, "MediaCodec")) {
                mInitCheck =
                    addMediaCodecFromAttributes(true /* encoder */, attrs);

                mCurrentSection = SECTION_ENCODER;
            }
            break;
        }

        case SECTION_DECODER:
        case SECTION_ENCODER:
        {
            if (!strcmp(name, "Quirk")) {
                mInitCheck = addQuirk(attrs);
            } else if (!strcmp(name, "Type")) {
                mInitCheck = addTypeFromAttributes(attrs, (mCurrentSection == SECTION_ENCODER));
                mCurrentSection =
                    (mCurrentSection == SECTION_DECODER
                            ? SECTION_DECODER_TYPE : SECTION_ENCODER_TYPE);
            }
        }
        inType = false;
        // fall through

        case SECTION_DECODER_TYPE:
        case SECTION_ENCODER_TYPE:
        {
            // ignore limits and features specified outside of type
            bool outside = !inType && mCurrentType == mCodecInfos[mCurrentName].mTypes.end();
            if (outside && (!strcmp(name, "Limit") || !strcmp(name, "Feature"))) {
                ALOGW("ignoring %s specified outside of a Type", name);
            } else if (!strcmp(name, "Limit")) {
                mInitCheck = addLimit(attrs);
            } else if (!strcmp(name, "Feature")) {
                mInitCheck = addFeature(attrs);
            }
            break;
        }

        default:
            break;
    }

    ++mDepth;
}

void MediaCodecsXmlParser::endElementHandler(const char *name) {
    if (mInitCheck != OK) {
        return;
    }

    switch (mCurrentSection) {
        case SECTION_SETTINGS:
        {
            if (!strcmp(name, "Settings")) {
                mCurrentSection = SECTION_TOPLEVEL;
            }
            break;
        }

        case SECTION_DECODERS:
        {
            if (!strcmp(name, "Decoders")) {
                mCurrentSection = SECTION_TOPLEVEL;
            }
            break;
        }

        case SECTION_ENCODERS:
        {
            if (!strcmp(name, "Encoders")) {
                mCurrentSection = SECTION_TOPLEVEL;
            }
            break;
        }

        case SECTION_DECODER_TYPE:
        case SECTION_ENCODER_TYPE:
        {
            if (!strcmp(name, "Type")) {
                mCurrentSection =
                    (mCurrentSection == SECTION_DECODER_TYPE
                            ? SECTION_DECODER : SECTION_ENCODER);

                mCurrentType = mCodecInfos[mCurrentName].mTypes.end();
            }
            break;
        }

        case SECTION_DECODER:
        {
            if (!strcmp(name, "MediaCodec")) {
                mCurrentSection = SECTION_DECODERS;
                mCurrentName.clear();
            }
            break;
        }

        case SECTION_ENCODER:
        {
            if (!strcmp(name, "MediaCodec")) {
                mCurrentSection = SECTION_ENCODERS;
                mCurrentName.clear();
            }
            break;
        }

        case SECTION_INCLUDE:
        {
            if (!strcmp(name, "Include") && mPastSections.size() > 0) {
                mCurrentSection = mPastSections.top();
                mPastSections.pop();
            }
            break;
        }

        default:
            break;
    }

    --mDepth;
}

status_t MediaCodecsXmlParser::addSettingFromAttributes(const char **attrs) {
    const char *name = NULL;
    const char *value = NULL;
    const char *update = NULL;

    size_t i = 0;
    while (attrs[i] != NULL) {
        if (!strcmp(attrs[i], "name")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addSettingFromAttributes: name is null");
                return -EINVAL;
            }
            name = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "value")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addSettingFromAttributes: value is null");
                return -EINVAL;
            }
            value = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "update")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addSettingFromAttributes: update is null");
                return -EINVAL;
            }
            update = attrs[i + 1];
            ++i;
        } else {
            ALOGE("addSettingFromAttributes: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }

        ++i;
    }

    if (name == NULL || value == NULL) {
        ALOGE("addSettingFromAttributes: name or value unspecified");
        return -EINVAL;
    }

    mUpdate = (update != NULL) && ParseBoolean(update);
    if (mUpdate != (mGlobalSettings.count(name) > 0)) {
        ALOGE("addSettingFromAttributes: updating non-existing setting");
        return -EINVAL;
    }
    mGlobalSettings[name] = value;

    return OK;
}

status_t MediaCodecsXmlParser::addMediaCodecFromAttributes(
        bool encoder, const char **attrs) {
    const char *name = NULL;
    const char *type = NULL;
    const char *update = NULL;

    size_t i = 0;
    while (attrs[i] != NULL) {
        if (!strcmp(attrs[i], "name")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addMediaCodecFromAttributes: name is null");
                return -EINVAL;
            }
            name = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "type")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addMediaCodecFromAttributes: type is null");
                return -EINVAL;
            }
            type = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "update")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addMediaCodecFromAttributes: update is null");
                return -EINVAL;
            }
            update = attrs[i + 1];
            ++i;
        } else {
            ALOGE("addMediaCodecFromAttributes: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }

        ++i;
    }

    if (name == NULL) {
        ALOGE("addMediaCodecFromAttributes: name not found");
        return -EINVAL;
    }

    mUpdate = (update != NULL) && ParseBoolean(update);
    if (mUpdate != (mCodecInfos.count(name) > 0)) {
        ALOGE("addMediaCodecFromAttributes: updating non-existing codec or vice versa");
        return -EINVAL;
    }

    CodecInfo *info = &mCodecInfos[name];
    if (mUpdate) {
        // existing codec
        mCurrentName = name;
        mCurrentType = info->mTypes.begin();
        if (type != NULL) {
            // existing type
            mCurrentType = findTypeInfo(*info, type);
            if (mCurrentType == info->mTypes.end()) {
                ALOGE("addMediaCodecFromAttributes: updating non-existing type");
                return -EINVAL;
            }
        }
    } else {
        // new codec
        mCurrentName = name;
        mQuirks[name].clear();
        info->mTypes.clear();
        info->mTypes.emplace_back();
        mCurrentType = --info->mTypes.end();
        mCurrentType->mName = type;
        info->mIsEncoder = encoder;
    }

    return OK;
}

status_t MediaCodecsXmlParser::addQuirk(const char **attrs) {
    const char *name = NULL;

    size_t i = 0;
    while (attrs[i] != NULL) {
        if (!strcmp(attrs[i], "name")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addQuirk: name is null");
                return -EINVAL;
            }
            name = attrs[i + 1];
            ++i;
        } else {
            ALOGE("addQuirk: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }

        ++i;
    }

    if (name == NULL) {
        ALOGE("addQuirk: name not found");
        return -EINVAL;
    }

    mQuirks[mCurrentName].emplace_back(name);
    return OK;
}

status_t MediaCodecsXmlParser::addTypeFromAttributes(const char **attrs, bool encoder) {
    const char *name = NULL;
    const char *update = NULL;

    size_t i = 0;
    while (attrs[i] != NULL) {
        if (!strcmp(attrs[i], "name")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addTypeFromAttributes: name is null");
                return -EINVAL;
            }
            name = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "update")) {
            if (attrs[i + 1] == NULL) {
                ALOGE("addTypeFromAttributes: update is null");
                return -EINVAL;
            }
            update = attrs[i + 1];
            ++i;
        } else {
            ALOGE("addTypeFromAttributes: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }

        ++i;
    }

    if (name == NULL) {
        return -EINVAL;
    }

    CodecInfo *info = &mCodecInfos[mCurrentName];
    info->mIsEncoder = encoder;
    mCurrentType = findTypeInfo(*info, name);
    if (!mUpdate) {
        if (mCurrentType != info->mTypes.end()) {
            ALOGE("addTypeFromAttributes: re-defining existing type without update");
            return -EINVAL;
        }
        info->mTypes.emplace_back();
        mCurrentType = --info->mTypes.end();
    } else if (mCurrentType == info->mTypes.end()) {
        ALOGE("addTypeFromAttributes: updating non-existing type");
        return -EINVAL;
    }

    return OK;
}

static status_t limitFoundMissingAttr(const AString &name, const char *attr, bool found = true) {
    ALOGE("limit '%s' with %s'%s' attribute", name.c_str(),
            (found ? "" : "no "), attr);
    return -EINVAL;
}

static status_t limitError(const AString &name, const char *msg) {
    ALOGE("limit '%s' %s", name.c_str(), msg);
    return -EINVAL;
}

static status_t limitInvalidAttr(const AString &name, const char *attr, const AString &value) {
    ALOGE("limit '%s' with invalid '%s' attribute (%s)", name.c_str(),
            attr, value.c_str());
    return -EINVAL;
}

status_t MediaCodecsXmlParser::addLimit(const char **attrs) {
    sp<AMessage> msg = new AMessage();

    size_t i = 0;
    while (attrs[i] != NULL) {
        if (attrs[i + 1] == NULL) {
            ALOGE("addLimit: limit is not given");
            return -EINVAL;
        }

        // attributes with values
        if (!strcmp(attrs[i], "name")
                || !strcmp(attrs[i], "default")
                || !strcmp(attrs[i], "in")
                || !strcmp(attrs[i], "max")
                || !strcmp(attrs[i], "min")
                || !strcmp(attrs[i], "range")
                || !strcmp(attrs[i], "ranges")
                || !strcmp(attrs[i], "scale")
                || !strcmp(attrs[i], "value")) {
            msg->setString(attrs[i], attrs[i + 1]);
            ++i;
        } else {
            ALOGE("addLimit: unrecognized limit: %s", attrs[i]);
            return -EINVAL;
        }
        ++i;
    }

    AString name;
    if (!msg->findString("name", &name)) {
        ALOGE("limit with no 'name' attribute");
        return -EINVAL;
    }

    // size, blocks, bitrate, frame-rate, blocks-per-second, aspect-ratio,
    // measured-frame-rate, measured-blocks-per-second: range
    // quality: range + default + [scale]
    // complexity: range + default
    bool found;
    if (mCurrentType == mCodecInfos[mCurrentName].mTypes.end()) {
        ALOGW("ignoring null type");
        return OK;
    }

    if (name == "aspect-ratio" || name == "bitrate" || name == "block-count"
            || name == "blocks-per-second" || name == "complexity"
            || name == "frame-rate" || name == "quality" || name == "size"
            || name == "measured-blocks-per-second" || name.startsWith("measured-frame-rate-")) {
        AString min, max;
        if (msg->findString("min", &min) && msg->findString("max", &max)) {
            min.append("-");
            min.append(max);
            if (msg->contains("range") || msg->contains("value")) {
                return limitError(name, "has 'min' and 'max' as well as 'range' or "
                        "'value' attributes");
            }
            msg->setString("range", min);
        } else if (msg->contains("min") || msg->contains("max")) {
            return limitError(name, "has only 'min' or 'max' attribute");
        } else if (msg->findString("value", &max)) {
            min = max;
            min.append("-");
            min.append(max);
            if (msg->contains("range")) {
                return limitError(name, "has both 'range' and 'value' attributes");
            }
            msg->setString("range", min);
        }

        AString range, scale = "linear", def, in_;
        if (!msg->findString("range", &range)) {
            return limitError(name, "with no 'range', 'value' or 'min'/'max' attributes");
        }

        if ((name == "quality" || name == "complexity") ^
                (found = msg->findString("default", &def))) {
            return limitFoundMissingAttr(name, "default", found);
        }
        if (name != "quality" && msg->findString("scale", &scale)) {
            return limitFoundMissingAttr(name, "scale");
        }
        if ((name == "aspect-ratio") ^ (found = msg->findString("in", &in_))) {
            return limitFoundMissingAttr(name, "in", found);
        }

        if (name == "aspect-ratio") {
            if (!(in_ == "pixels") && !(in_ == "blocks")) {
                return limitInvalidAttr(name, "in", in_);
            }
            in_.erase(5, 1); // (pixel|block)-aspect-ratio
            in_.append("-");
            in_.append(name);
            name = in_;
        }
        if (name == "quality") {
            mCurrentType->mDetails["quality-scale"] = scale;
        }
        if (name == "quality" || name == "complexity") {
            AString tag = name;
            tag.append("-default");
            mCurrentType->mDetails[tag] = def;
        }
        AString tag = name;
        tag.append("-range");
        mCurrentType->mDetails[tag] = range;
    } else {
        AString max, value, ranges;
        if (msg->contains("default")) {
            return limitFoundMissingAttr(name, "default");
        } else if (msg->contains("in")) {
            return limitFoundMissingAttr(name, "in");
        } else if ((name == "channel-count" || name == "concurrent-instances") ^
                (found = msg->findString("max", &max))) {
            return limitFoundMissingAttr(name, "max", found);
        } else if (msg->contains("min")) {
            return limitFoundMissingAttr(name, "min");
        } else if (msg->contains("range")) {
            return limitFoundMissingAttr(name, "range");
        } else if ((name == "sample-rate") ^
                (found = msg->findString("ranges", &ranges))) {
            return limitFoundMissingAttr(name, "ranges", found);
        } else if (msg->contains("scale")) {
            return limitFoundMissingAttr(name, "scale");
        } else if ((name == "alignment" || name == "block-size") ^
                (found = msg->findString("value", &value))) {
            return limitFoundMissingAttr(name, "value", found);
        }

        if (max.size()) {
            AString tag = "max-";
            tag.append(name);
            mCurrentType->mDetails[tag] = max;
        } else if (value.size()) {
            mCurrentType->mDetails[name] = value;
        } else if (ranges.size()) {
            AString tag = name;
            tag.append("-ranges");
            mCurrentType->mDetails[tag] = ranges;
        } else {
            ALOGW("Ignoring unrecognized limit '%s'", name.c_str());
        }
    }

    return OK;
}

status_t MediaCodecsXmlParser::addFeature(const char **attrs) {
    size_t i = 0;
    const char *name = NULL;
    int32_t optional = -1;
    int32_t required = -1;
    const char *value = NULL;

    while (attrs[i] != NULL) {
        if (attrs[i + 1] == NULL) {
            ALOGE("addFeature: feature is not given");
            return -EINVAL;
        }

        // attributes with values
        if (!strcmp(attrs[i], "name")) {
            name = attrs[i + 1];
            ++i;
        } else if (!strcmp(attrs[i], "optional") || !strcmp(attrs[i], "required")) {
            int value = (int)ParseBoolean(attrs[i + 1]);
            if (!strcmp(attrs[i], "optional")) {
                optional = value;
            } else {
                required = value;
            }
            ++i;
        } else if (!strcmp(attrs[i], "value")) {
            value = attrs[i + 1];
            ++i;
        } else {
            ALOGE("addFeature: unrecognized attribute: %s", attrs[i]);
            return -EINVAL;
        }
        ++i;
    }
    if (name == NULL) {
        ALOGE("feature with no 'name' attribute");
        return -EINVAL;
    }

    if (optional == required && optional != -1) {
        ALOGE("feature '%s' is both/neither optional and required", name);
        return -EINVAL;
    }

    if (mCurrentType == mCodecInfos[mCurrentName].mTypes.end()) {
        ALOGW("ignoring null type");
        return OK;
    }
    if (value != NULL) {
        mCurrentType->mStringFeatures[name] = value;
    } else {
        mCurrentType->mBoolFeatures[name] = (required == 1) || (optional == 0);
    }
    return OK;
}

void MediaCodecsXmlParser::getGlobalSettings(
        std::map<AString, AString> *settings) const {
    settings->clear();
    settings->insert(mGlobalSettings.begin(), mGlobalSettings.end());
}

status_t MediaCodecsXmlParser::getCodecInfo(const char *name, CodecInfo *info) const {
    if (mCodecInfos.count(name) == 0) {
        ALOGE("Codec not found with name '%s'", name);
        return NAME_NOT_FOUND;
    }
    *info = mCodecInfos.at(name);
    return OK;
}

status_t MediaCodecsXmlParser::getQuirks(const char *name, std::vector<AString> *quirks) const {
    if (mQuirks.count(name) == 0) {
        ALOGE("Codec not found with name '%s'", name);
        return NAME_NOT_FOUND;
    }
    quirks->clear();
    quirks->insert(quirks->end(), mQuirks.at(name).begin(), mQuirks.at(name).end());
    return OK;
}

}  // namespace android
