#include "blob_handler.hpp"

#include <boot_time.pb.h>
#include <fmt/printf.h>

#include <sdbusplus/bus.hpp>

#include <cstdint>
#include <string>
#include <string_view>
#include <variant>
#include <vector>

namespace blobs
{

using CheckpointType = std::vector<std::tuple<std::string, int64_t, int64_t>>;
using DurationType = std::vector<std::tuple<std::string, int64_t>>;

constexpr static std::string_view kHostBlobPath = "/btm/host/0";
constexpr static std::string_view kBMCBlobPath = "/btm/bmc";

namespace BootTimeMonitor
{
constexpr std::string_view kService = "com.google.gbmc.boot_time_monitor";
constexpr std::string_view kHostPath = "/xyz/openbmc_project/time/boot/host0";
constexpr std::string_view kBMCPath = "/xyz/openbmc_project/time/boot/bmc";
} // namespace BootTimeMonitor

namespace Checkpoint
{
constexpr std::string_view kIface = "xyz.openbmc_project.Time.Boot.Checkpoint";
constexpr std::string_view kMethod = "GetCheckpointList";
} // namespace Checkpoint

namespace Duration
{
constexpr std::string_view kIface = "xyz.openbmc_project.Time.Boot.Duration";
constexpr std::string_view kMethod = "GetAdditionalDurations";
} // namespace Duration

namespace Statistic
{
constexpr std::string_view kIface = "org.freedesktop.DBus.Properties";
constexpr std::string_view kMethod = "Get";
constexpr std::string_view kParam1 = "xyz.openbmc_project.Time.Boot.Statistic";
constexpr std::string_view kParam2 = "IsRebooting";
} // namespace Statistic

bool BlobHandler::canHandleBlob(const std::string& path)
{
    return (path == kHostBlobPath) || (path == kBMCBlobPath);
}

// A blob handler may have multiple Blobs.
std::vector<std::string> BlobHandler::getBlobIds()
{
    return {kHostBlobPath.data(), kBMCBlobPath.data()};
}

// BmcBlobDelete (7) is not supported.
bool BlobHandler::deleteBlob([[maybe_unused]] const std::string& path)
{
    return false;
}

// BmcBlobStat (8) (global stat) is not supported.
bool BlobHandler::stat([[maybe_unused]] const std::string& path,
                       [[maybe_unused]] BlobMeta* meta)
{
    return false;
}

// BmcBlobOpen(2) handler.
bool BlobHandler::open(uint16_t session, uint16_t flags,
                       const std::string& path)
{
    if (!isReadOnlyOpenFlags(flags))
    {
        fmt::print(stderr, "[{}] Flag is not read-only. flag={}\n",
                   __FUNCTION__, flags);
        return false;
    }
    if (!canHandleBlob(path))
    {
        fmt::print(stderr, "[{}] Can't handle path={}\n", __FUNCTION__, path);
        return false;
    }

    sdbusplus::bus_t bus = sdbusplus::bus::new_default();
    boottimeproto::BootTime btProto;
    std::string btmPath;
    if (path == kBMCBlobPath)
    {
        btmPath = BootTimeMonitor::kBMCPath;
    }
    else
    {
        btmPath = BootTimeMonitor::kHostPath;
    }

    // Get checkpoints
    try
    {
        auto method = bus.new_method_call(
            BootTimeMonitor::kService.data(), btmPath.c_str(),
            Checkpoint::kIface.data(), Checkpoint::kMethod.data());
        CheckpointType checkpoints;
        bus.call(method).read(checkpoints);
        for (auto checkpoint : checkpoints)
        {
            auto cpProto = btProto.add_checkpoints();
            cpProto->set_name(std::get<0>(checkpoint));
            cpProto->set_wall_time_ms(std::get<1>(checkpoint));
            cpProto->set_mono_time_ms(std::get<2>(checkpoint));
        }
    }
    catch (const sdbusplus::exception::SdBusError& e)
    {
        fmt::print(
            stderr,
            "[{}] Failed in method call. service={}, path={}, Iface={}, method={}, error={}\n",
            __FUNCTION__, BootTimeMonitor::kService.data(), btmPath.c_str(),
            Checkpoint::kIface.data(), Checkpoint::kMethod.data(), e.what());
        return false;
    }

    // Get durations
    try
    {
        auto method = bus.new_method_call(
            BootTimeMonitor::kService.data(), btmPath.c_str(),
            Duration::kIface.data(), Duration::kMethod.data());
        DurationType durations;
        bus.call(method).read(durations);
        for (auto duration : durations)
        {
            auto durProto = btProto.add_durations();
            durProto->set_name(std::get<0>(duration));
            durProto->set_duration_ms(std::get<1>(duration));
        }
    }
    catch (const sdbusplus::exception::SdBusError& e)
    {
        fmt::print(
            stderr,
            "[{}] Failed in method call. service={}, path={}, Iface={}, method={}, error={}\n",
            __FUNCTION__, BootTimeMonitor::kService.data(), btmPath.c_str(),
            Duration::kIface.data(), Duration::kMethod.data(), e.what());
        return false;
    }

    // Get `IsRebooting`
    try
    {
        auto method = bus.new_method_call(
            BootTimeMonitor::kService.data(), btmPath.c_str(),
            Statistic::kIface.data(), Statistic::kMethod.data());
        method.append(Statistic::kParam1.data(), Statistic::kParam2.data());

        std::variant<bool> isRebooting;
        bus.call(method).read(isRebooting);
        btProto.set_is_rebooting(std::get<bool>(isRebooting));
    }
    catch (const sdbusplus::exception::SdBusError& e)
    {
        fmt::print(
            stderr,
            "[{}] Failed in method call. service={}, path={}, Iface={}, method={}, param1={}, param2={}, error={}\n",
            __FUNCTION__, BootTimeMonitor::kService.data(), btmPath.c_str(),
            Statistic::kIface.data(), Statistic::kMethod.data(),
            Statistic::kParam1.data(), Statistic::kParam2.data(), e.what());
        return false;
    }

    std::vector<char> vec(btProto.ByteSizeLong());
    if (!btProto.SerializeToArray(vec.data(), vec.size()))
    {
        fmt::print(stderr, "[{}]: Could not serialize protobuf to array\n",
                   __FUNCTION__);
        return false;
    }

    sessions[session] = std::move(vec);
    return true;
}

// BmcBlobRead(3) handler.
std::vector<uint8_t> BlobHandler::read(uint16_t session, uint32_t offset,
                                       uint32_t requestedSize)
{
    auto it = sessions.find(session);
    if (it == sessions.end())
    {
        return {};
    }

    if (offset + requestedSize > it->second.size())
    {
        return std::vector<uint8_t>(it->second.data() + offset,
                                    it->second.data() + it->second.size());
    }
    return std::vector<uint8_t>(it->second.data() + offset,
                                it->second.data() + offset + requestedSize);
}

// BmcBlobWrite(4) is not supported.
bool BlobHandler::write([[maybe_unused]] uint16_t session,
                        [[maybe_unused]] uint32_t offset,
                        [[maybe_unused]] const std::vector<uint8_t>& data)
{
    return false;
}

// BmcBlobWriteMeta(10) is not supported.
bool BlobHandler::writeMeta([[maybe_unused]] uint16_t session,
                            [[maybe_unused]] uint32_t offset,
                            [[maybe_unused]] const std::vector<uint8_t>& data)
{
    return false;
}

// BmcBlobCommit(5) is not supported.
bool BlobHandler::commit([[maybe_unused]] uint16_t session,
                         [[maybe_unused]] const std::vector<uint8_t>& data)
{
    return false;
}

// BmcBlobClose(6) handler.
bool BlobHandler::close(uint16_t session)
{
    auto itr = sessions.find(session);
    if (itr == sessions.end())
    {
        return false;
    }
    sessions.erase(itr);
    return true;
}

bool BlobHandler::stat(uint16_t session, BlobMeta* meta)
{
    auto it = sessions.find(session);
    if (it == sessions.end())
    {
        return false;
    }

    meta->size = it->second.size();
    meta->blobState = blobs::StateFlags::open_read;
    return true;
}

bool BlobHandler::expire(uint16_t session)
{
    return close(session);
}

// Checks for a read-only flag.
bool BlobHandler::isReadOnlyOpenFlags(const uint16_t flags)
{
    if (((flags & blobs::OpenFlags::read) == blobs::OpenFlags::read) &&
        ((flags & blobs::OpenFlags::write) == 0))
    {
        return true;
    }
    return false;
}

} // namespace blobs
