// Copyright 2022 Google LLC
//
// 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 <flasher/file.hpp>
#include <flasher/mod.hpp>
#include <flasher/ops.hpp>
#include <flashupdate/args.hpp>
#include <flashupdate/info.hpp>
#include <flashupdate/logging.hpp>
#include <flashupdate/ops.hpp>
#include <flashupdate/validator.hpp>

#include <format>
#include <string>

namespace flashupdate
{
namespace ops
{

using flasher::ModArgs;

std::string fetchVersion(const Args& args)
{
    if (args.validatorHelper == nullptr)
    {
        throw std::runtime_error("invalid Validator Helper");
    }

    Config verifyArgs = args.config;
    if (!args.primary)
    {
        if (args.stagingIndex >= verifyArgs.flash.secondary.size())
        {
            throw std::runtime_error(std::format(
                "invalid staged_index for secondary partition: got {}, want < "
                "{}",
                args.stagingIndex, verifyArgs.flash.secondary.size()));
        }
        verifyArgs.flash.stagingIndex = args.stagingIndex;
        LOG(LogLevel::Info, "Verify secondary partition in index {}\n",
            verifyArgs.flash.stagingIndex);
    }

    auto& flashHelper = args.flashHelper;
    flashHelper->setup(verifyArgs, args.keepMux);
    auto flash = flashHelper->getFlash(args.primary);
    if (!flash)
    {
        // Failed to find the flash partition. The partition is corrupted or
        // missing
        throw std::runtime_error("failed to find flash partition");
    }
    auto updateInfo = fetchInfo(args);
    auto metadataDescriptor = updateInfo.stageDescriptor;
    std::string flashDev(flash->first);
    auto devMod = ModArgs(flashDev);

    std::string version = args.validatorHelper->fetchVersion(
        devMod, metadataDescriptor.offset, metadataDescriptor.size);
    stdplus::print(stdout, "{}", version);
    return version;
}

} // namespace ops
} // namespace flashupdate
