/**
 * Copyright (C) 2018 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.
 */

#include <stdlib.h>
#include <string.h>

#include <android-base/logging.h>
#include <gtest/gtest.h>

#include "installd_constants.h"
#include "otapreopt_parameters.h"

namespace android {
namespace installd {

static bool ParseBool(const char* in) {
    if (strcmp(in, "true") == 0) {
        return true;
    }
    return false;
}

static const char* ParseNull(const char* arg) {
    return (strcmp(arg, "!") == 0) ? nullptr : arg;
}

class OTAPreoptTest : public testing::Test {
protected:
    virtual void SetUp() {
        setenv("ANDROID_LOG_TAGS", "*:f", 1);
        android::base::InitLogging(nullptr, android::base::StderrLogger);
    }

    void verifyPackageParameters(const OTAPreoptParameters& params,
                                 uint32_t version,
                                 bool versioned,
                                 const char** args) {
        //  otapreopt target-slot [version] dexopt {DEXOPT_PARAMETERS}
        int i = 0;
        if (version > 2 || (version == 2 && versioned)) {
            i += 4;
        } else {
            i += 3;
        }
        ASSERT_STREQ(params.target_slot.c_str(), args[1]);
        ASSERT_STREQ(params.apk_path, args[i++]);
        ASSERT_EQ(params.uid, static_cast<uid_t>(atoi(args[i++])));
        ASSERT_STREQ(params.pkgName, args[i++]);
        ASSERT_STREQ(params.instruction_set, args[i++]);
        ASSERT_EQ(params.dexopt_needed, atoi(args[i++]));
        ASSERT_STREQ(params.oat_dir, args[i++]);
        const int dexopt_flags = atoi(args[i++]);
        ASSERT_STREQ(params.compiler_filter, args[i++]);
        ASSERT_STREQ(params.volume_uuid, ParseNull(args[i++]));
        ASSERT_STREQ(params.shared_libraries, ParseNull(args[i++]));
        if (version > 1) {
            ASSERT_STREQ(params.se_info, ParseNull(args[i++]));
        } else {
            ASSERT_EQ(params.se_info, nullptr);
        }
        if (version > 2) {
            ASSERT_EQ(params.downgrade, ParseBool(args[i++]));
        } else {
            ASSERT_FALSE(params.downgrade);
        }
        if (version > 3) {
            ASSERT_EQ(params.target_sdk_version, atoi(args[i++]));
        } else {
            ASSERT_EQ(params.target_sdk_version, 0);
        }
        if (version > 4) {
            ASSERT_STREQ(params.profile_name, ParseNull(args[i++]));
        } else {
            ASSERT_STREQ(params.profile_name, "primary.prof");
        }
        if (version > 5) {
            ASSERT_STREQ(params.dex_metadata_path, ParseNull(args[i++]));
        } else {
            ASSERT_EQ(params.dex_metadata_path, nullptr);
        }
        if (version > 6) {
            ASSERT_STREQ(params.compilation_reason, ParseNull(args[i++]));
        } else {
            ASSERT_STREQ(params.compilation_reason, "ab-ota");
        }
        if (version > 7) {
            ASSERT_EQ(params.dexopt_flags, dexopt_flags);
        } else {
            ASSERT_EQ(params.dexopt_flags, dexopt_flags | DEXOPT_GENERATE_COMPACT_DEX);
        }
    }

    const char* getVersionCStr(uint32_t version) {
        switch (version) {
            case 1: return "1";
            case 2: return "2";
            case 3: return "3";
            case 4: return "4";
            case 5: return "5";
            case 6: return "6";
            case 7: return "7";
            case 8: return "8";
        }
        return nullptr;
    }

    std::vector<const char*> getArgs(uint32_t version, bool versioned) {
        std::vector<const char*> args;
        args.push_back("otapreopt");  // "otapreopt"
        args.push_back("a");  // slot
        if (versioned) {
            args.push_back(getVersionCStr(version));
        }
        args.push_back("dexopt");  // "dexopt"
        args.push_back("foo.apk");  // apk_path
        args.push_back("123");  // uid
        args.push_back("pkgname");  // pkg
        args.push_back("arm");  // isa
        args.push_back("1");  // dexopt_needed (DEX2OAT_FROM_SCRATCH)
        args.push_back("oat_dir");  // oat_dir
        args.push_back("0");  // dexopt_flags
        args.push_back("speed");  // filter
        args.push_back("!");  // volume
        args.push_back("shared.lib");  // libs

        if (version > 1) {
            args.push_back("!");  // seinfo
        }
        if (version > 2) {
            args.push_back("true");  // downgrade
        }
        if (version > 3) {
            args.push_back("28");  // sdk_version
        }
        if (version > 4) {
            args.push_back("split_a.prof");  // profile_name
        }
        if (version > 5) {
            args.push_back("dex_metadata.dm");  // dex_metadata_path
        }
        if (version > 6) {
            args.push_back("ab-ota-test");  // compilation_reason
        }
        args.push_back(nullptr);  // we have to end with null.
        return args;
    }

    void VerifyReadArguments(uint32_t version, bool versioned) {
        OTAPreoptParameters params;
        std::vector<const char*> args = getArgs(version, versioned);
        ASSERT_TRUE(params.ReadArguments(args.size() - 1, args.data()));
        verifyPackageParameters(params, version, versioned, args.data());
    }
};

TEST_F(OTAPreoptTest, ReadArgumentsV1) {
    VerifyReadArguments(1, false);
}

TEST_F(OTAPreoptTest, ReadArgumentsV2Unversioned) {
    VerifyReadArguments(2, false);
}

TEST_F(OTAPreoptTest, ReadArgumentsV2) {
    VerifyReadArguments(2, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsV3) {
    VerifyReadArguments(3, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsV4) {
    VerifyReadArguments(4, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsV5) {
    VerifyReadArguments(5, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsV6) {
    VerifyReadArguments(6, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsV7) {
    VerifyReadArguments(7, true);
}

TEST_F(OTAPreoptTest, ReadArgumentsFailToManyArgs) {
    OTAPreoptParameters params;
    std::vector<const char*> args = getArgs(5, true);
    args[2] = "3";  // pretend it's version 3. It should fail since there are too many args.
    ASSERT_FALSE(params.ReadArguments(args.size() - 1, args.data()));
}

TEST_F(OTAPreoptTest, ReadArgumentsFailInsufficientArgs) {
    OTAPreoptParameters params;
    std::vector<const char*> args = getArgs(4, true);
    args[2] = "5";  // pretend it's version 5. It should fail since there are insufficient args.
    ASSERT_FALSE(params.ReadArguments(args.size() - 1, args.data()));
}

TEST_F(OTAPreoptTest, ReadArgumentsFailInvalidDexopt) {
    OTAPreoptParameters params;
    std::vector<const char*> args = getArgs(4, true);
    args[3] = "dexopt-invalid";
    ASSERT_FALSE(params.ReadArguments(args.size() - 1, args.data()));
}

TEST_F(OTAPreoptTest, ReadArgumentsFailInvalidSlot) {
    OTAPreoptParameters params;
    std::vector<const char*> args = getArgs(3, true);
    args[1] = "invalid-slot???";
    ASSERT_FALSE(params.ReadArguments(args.size() - 1, args.data()));
}

}  // namespace installd
}  // namespace android
