// Copyright 2021 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 "metric.hpp"

#include "metricblob.pb.n.h"

#include "util.hpp"

#include <pb_encode.h>
#include <sys/statvfs.h>

#include <phosphor-logging/log.hpp>

#include <cstdint>
#include <filesystem>
#include <sstream>
#include <string>
#include <string_view>

namespace metric_blob
{

using phosphor::logging::entry;
using phosphor::logging::log;
using level = phosphor::logging::level;

BmcHealthSnapshot::BmcHealthSnapshot() :
    done(false), stringId(0), ticksPerSec(0)
{}

template <typename T>
static constexpr auto pbEncodeStr =
    [](pb_ostream_t* stream, const pb_field_iter_t* field,
       void* const* arg) noexcept {
        static_assert(sizeof(*std::declval<T>().data()) == sizeof(pb_byte_t));
        const auto& s = *reinterpret_cast<const T*>(*arg);
        return pb_encode_tag_for_field(stream, field) &&
               pb_encode_string(stream,
                                reinterpret_cast<const pb_byte_t*>(s.data()),
                                s.size());
    };

template <typename T>
static pb_callback_t pbStrEncoder(const T& t) noexcept
{
    return {{.encode = pbEncodeStr<T>}, const_cast<T*>(&t)};
}

template <auto fields, typename T>
static constexpr auto pbEncodeSubs =
    [](pb_ostream_t* stream, const pb_field_iter_t* field,
       void* const* arg) noexcept {
        for (const auto& sub : *reinterpret_cast<const std::vector<T>*>(*arg))
        {
            if (!pb_encode_tag_for_field(stream, field) ||
                !pb_encode_submessage(stream, fields, &sub))
            {
                return false;
            }
        }
        return true;
    };

template <auto fields, typename T>
static pb_callback_t pbSubsEncoder(const std::vector<T>& t)
{
    return {{.encode = pbEncodeSubs<fields, T>},
            const_cast<std::vector<T>*>(&t)};
}

struct ProcStatEntry
{
    std::string cmdline;
    std::string tcomm;
    float utime;
    float stime;

    // Processes with the longest utime + stime are ranked first.
    // Tie breaking is done with cmdline then tcomm.
    bool operator<(const ProcStatEntry& other) const
    {
        const float negTime = -(utime + stime);
        const float negOtherTime = -(other.utime + other.stime);
        return std::tie(negTime, cmdline, tcomm) <
               std::tie(negOtherTime, other.cmdline, other.tcomm);
    }
};

static bmcmetrics_metricproto_BmcProcStatMetric getProcStatMetric(
    BmcHealthSnapshot& obj, long ticksPerSec,
    std::vector<bmcmetrics_metricproto_BmcProcStatMetric_BmcProcStat>& procs,
    bool& use) noexcept
{
    if (ticksPerSec == 0)
    {
        return {};
    }
    constexpr std::string_view procPath = "/proc/";

    std::vector<ProcStatEntry> entries;

    for (const auto& procEntry : std::filesystem::directory_iterator(procPath))
    {
        const std::string& path = procEntry.path();
        int pid = -1;
        if (isNumericPath(path, pid))
        {
            ProcStatEntry entry;

            try
            {
                entry.cmdline = getCmdLine(pid);
                TcommUtimeStime t = getTcommUtimeStime(pid, ticksPerSec);
                entry.tcomm = t.tcomm;
                entry.utime = t.utime;
                entry.stime = t.stime;

                entries.push_back(entry);
            }
            catch (const std::exception& e)
            {
                log<level::ERR>("Could not obtain process stats");
            }
        }
    }

    std::sort(entries.begin(), entries.end());

    bool isOthers = false;
    ProcStatEntry others;
    others.cmdline = "(Others)";
    others.utime = others.stime = 0;

    // Only show this many processes and aggregate all remaining ones into
    // "others" in order to keep the size of the snapshot reasonably small.
    // With 10 process stat entries and 10 FD count entries, the size of the
    // snapshot reaches around 1.5KiB. This is non-trivial, and we have to set
    // the collection interval long enough so as not to over-stress the IPMI
    // interface and the data collection service. The value of 10 is chosen
    // empirically, it might be subject to adjustments when the system is
    // launched later.
    constexpr int topN = 10;

    for (size_t i = 0; i < entries.size(); ++i)
    {
        if (i >= topN)
        {
            isOthers = true;
        }

        const ProcStatEntry& entry = entries[i];

        if (isOthers)
        {
            others.utime += entry.utime;
            others.stime += entry.stime;
        }
        else
        {
            std::string fullCmdline = entry.cmdline;
            if (entry.tcomm.size() > 0)
            {
                fullCmdline += " ";
                fullCmdline += entry.tcomm;
            }
            procs.emplace_back(
                bmcmetrics_metricproto_BmcProcStatMetric_BmcProcStat{
                    .sidx_cmdline = obj.getStringID(fullCmdline),
                    .utime = entry.utime,
                    .stime = entry.stime,
                });
        }
    }

    if (isOthers)
    {
        procs.emplace_back(bmcmetrics_metricproto_BmcProcStatMetric_BmcProcStat{
            .sidx_cmdline = obj.getStringID(others.cmdline),
            .utime = others.utime,
            .stime = others.stime,

        });
    }

    use = true;
    return bmcmetrics_metricproto_BmcProcStatMetric{
        .stats = pbSubsEncoder<
            bmcmetrics_metricproto_BmcProcStatMetric_BmcProcStat_fields>(procs),
    };
}

int getFdCount(int pid)
{
    const std::string& fdPath = "/proc/" + std::to_string(pid) + "/fd";
    return std::distance(std::filesystem::directory_iterator(fdPath),
                         std::filesystem::directory_iterator{});
}

struct FdStatEntry
{
    int fdCount;
    std::string cmdline;
    std::string tcomm;

    // Processes with the largest fdCount goes first.
    // Tie-breaking using cmdline then tcomm.
    bool operator<(const FdStatEntry& other) const
    {
        const int negFdCount = -fdCount;
        const int negOtherFdCount = -other.fdCount;
        return std::tie(negFdCount, cmdline, tcomm) <
               std::tie(negOtherFdCount, other.cmdline, other.tcomm);
    }
};

static bmcmetrics_metricproto_BmcFdStatMetric getFdStatMetric(
    BmcHealthSnapshot& obj, long ticksPerSec,
    std::vector<bmcmetrics_metricproto_BmcFdStatMetric_BmcFdStat>& fds,
    bool& use) noexcept
{
    if (ticksPerSec == 0)
    {
        return {};
    }

    // Sort by fd count, no tie-breaking
    std::vector<FdStatEntry> entries;

    const std::string_view procPath = "/proc/";
    for (const auto& procEntry : std::filesystem::directory_iterator(procPath))
    {
        const std::string& path = procEntry.path();
        int pid = 0;
        FdStatEntry entry;
        if (isNumericPath(path, pid))
        {
            try
            {
                entry.fdCount = getFdCount(pid);
                TcommUtimeStime t = getTcommUtimeStime(pid, ticksPerSec);
                entry.cmdline = getCmdLine(pid);
                entry.tcomm = t.tcomm;
                entries.push_back(entry);
            }
            catch (const std::exception& e)
            {
                log<level::ERR>("Could not get file descriptor stats");
            }
        }
    }

    std::sort(entries.begin(), entries.end());

    bool isOthers = false;

    // Only report the detailed fd count and cmdline for the top 10 entries,
    // and collapse all others into "others".
    constexpr int topN = 10;

    FdStatEntry others;
    others.cmdline = "(Others)";
    others.fdCount = 0;

    for (size_t i = 0; i < entries.size(); ++i)
    {
        if (i >= topN)
        {
            isOthers = true;
        }

        const FdStatEntry& entry = entries[i];
        if (isOthers)
        {
            others.fdCount += entry.fdCount;
        }
        else
        {
            std::string fullCmdline = entry.cmdline;
            if (entry.tcomm.size() > 0)
            {
                fullCmdline += " ";
                fullCmdline += entry.tcomm;
            }
            fds.emplace_back(bmcmetrics_metricproto_BmcFdStatMetric_BmcFdStat{
                .sidx_cmdline = obj.getStringID(fullCmdline),
                .fd_count = entry.fdCount,
            });
        }
    }

    if (isOthers)
    {
        fds.emplace_back(bmcmetrics_metricproto_BmcFdStatMetric_BmcFdStat{
            .sidx_cmdline = obj.getStringID(others.cmdline),
            .fd_count = others.fdCount,
        });
    }

    use = true;
    return bmcmetrics_metricproto_BmcFdStatMetric{
        .stats = pbSubsEncoder<
            bmcmetrics_metricproto_BmcFdStatMetric_BmcFdStat_fields>(fds),
    };
}

static bmcmetrics_metricproto_BmcECCMetric getECCMetric(bool& use) noexcept
{
    EccCounts eccCounts;
    use = getECCErrorCounts(eccCounts);
    if (!use)
    {
        return {};
    }
    return bmcmetrics_metricproto_BmcECCMetric{
        .correctable_error_count = eccCounts.correctableErrCount,
        .uncorrectable_error_count = eccCounts.uncorrectableErrCount,
    };
}

static bmcmetrics_metricproto_BmcMemoryMetric getMemMetric() noexcept
{
    bmcmetrics_metricproto_BmcMemoryMetric ret = {};
    auto data = readFileThenGrepIntoString("/proc/meminfo");
    int value;
    if (parseMeminfoValue(data, "MemAvailable:", value))
    {
        ret.mem_available = value;
    }
    if (parseMeminfoValue(data, "Slab:", value))
    {
        ret.slab = value;
    }

    if (parseMeminfoValue(data, "KernelStack:", value))
    {
        ret.kernel_stack = value;
    }
    return ret;
}

static bmcmetrics_metricproto_BmcUptimeMetric getUptimeMetric(
    bool& use) noexcept
{
    bmcmetrics_metricproto_BmcUptimeMetric ret = {};

    double uptime = 0;
    {
        auto data = readFileThenGrepIntoString("/proc/uptime");
        double idleProcessTime = 0;
        if (!parseProcUptime(data, uptime, idleProcessTime))
        {
            log<level::ERR>("Error parsing /proc/uptime");
            return ret;
        }
        ret.uptime = uptime;
        ret.idle_process_time = idleProcessTime;
    }

    BootTimesMonotonic btm;
    if (!getBootTimesMonotonic(btm))
    {
        log<level::ERR>("Could not get boot time");
        return ret;
    }
    if (btm.firmwareTime == 0 && btm.powerOnSecCounterTime != 0)
    {
        ret.firmware_boot_time_sec =
            static_cast<double>(btm.powerOnSecCounterTime) - uptime;
    }
    else
    {
        ret.firmware_boot_time_sec =
            static_cast<double>(btm.firmwareTime - btm.loaderTime) / 1e6;
    }
    ret.loader_boot_time_sec = static_cast<double>(btm.loaderTime) / 1e6;
    if (btm.initrdTime != 0)
    {
        ret.kernel_boot_time_sec = static_cast<double>(btm.initrdTime) / 1e6;
        ret.initrd_boot_time_sec =
            static_cast<double>(btm.userspaceTime - btm.initrdTime) / 1e6;
        ret.userspace_boot_time_sec =
            static_cast<double>(btm.finishTime - btm.userspaceTime) / 1e6;
    }
    else
    {
        ret.kernel_boot_time_sec = static_cast<double>(btm.userspaceTime) / 1e6;
        ret.initrd_boot_time_sec = 0;
        ret.userspace_boot_time_sec =
            static_cast<double>(btm.finishTime - btm.userspaceTime) / 1e6;
    }

    use = true;
    return ret;
}

static bmcmetrics_metricproto_BmcDiskSpaceMetric getStorageMetric(
    bool& use) noexcept
{
    bmcmetrics_metricproto_BmcDiskSpaceMetric ret = {};
    struct statvfs rwFiData, tmpFiData;
    if (statvfs("/", &rwFiData) < 0)
    {
        log<level::ERR>("Could not call statvfs");
    }
    else
    {
        ret.rwfs_kib_available = (rwFiData.f_bsize * rwFiData.f_bfree) / 1024;
        use = true;
    }
    if (statvfs("/tmp", &tmpFiData) < 0)
    {
        log<level::ERR>("Could not call statvfs");
    }
    else
    {
        ret.tmpfs_kib_available =
            (tmpFiData.f_bsize * tmpFiData.f_bfree) / 1024;
        use = true;
    }
    return ret;
}

void BmcHealthSnapshot::doWork()
{
    // The next metrics require a sane ticks_per_sec value, typically 100 on
    // the BMC. In the very rare circumstance when it's 0, exit early and return
    // a partially complete snapshot (no process).
    ticksPerSec = getTicksPerSec();

    static constexpr auto stcb = [](pb_ostream_t* stream,
                                    const pb_field_t* field,
                                    void* const* arg) noexcept {
        auto& self = *reinterpret_cast<BmcHealthSnapshot*>(*arg);
        std::vector<std::string_view> strs(self.stringTable.size());
        for (const auto& [str, i] : self.stringTable)
        {
            strs[i] = str;
        }
        for (auto& str : strs)
        {
            bmcmetrics_metricproto_BmcStringTable_StringEntry msg = {
                .value = pbStrEncoder(str),
            };
            if (!pb_encode_tag_for_field(stream, field) ||
                !pb_encode_submessage(
                    stream,
                    bmcmetrics_metricproto_BmcStringTable_StringEntry_fields,
                    &msg))
            {
                return false;
            }
        }
        return true;
    };
    std::vector<bmcmetrics_metricproto_BmcProcStatMetric_BmcProcStat> procs;
    std::vector<bmcmetrics_metricproto_BmcFdStatMetric_BmcFdStat> fds;
    bmcmetrics_metricproto_BmcMetricSnapshot snapshot = {
        .has_string_table = true,
        .string_table =
            {
                .entries = {{.encode = stcb}, this},
            },
        .has_memory_metric = true,
        .memory_metric = getMemMetric(),
        .has_uptime_metric = false,
        .uptime_metric = getUptimeMetric(snapshot.has_uptime_metric),
        .has_storage_space_metric = false,
        .storage_space_metric =
            getStorageMetric(snapshot.has_storage_space_metric),
        .has_procstat_metric = false,
        .procstat_metric = getProcStatMetric(*this, ticksPerSec, procs,
                                             snapshot.has_procstat_metric),
        .has_fdstat_metric = false,
        .fdstat_metric = getFdStatMetric(*this, ticksPerSec, fds,
                                         snapshot.has_fdstat_metric),
        .has_ecc_metric = false,
        .ecc_metric = getECCMetric(snapshot.has_ecc_metric),
    };
    pb_ostream_t nost = {};
    if (!pb_encode(&nost, bmcmetrics_metricproto_BmcMetricSnapshot_fields,
                   &snapshot))
    {
        auto msg = std::format("Getting pb size: {}", PB_GET_ERROR(&nost));
        log<level::ERR>(msg.c_str());
        return;
    }
    pbDump.resize(nost.bytes_written);
    auto ost = pb_ostream_from_buffer(
        reinterpret_cast<pb_byte_t*>(pbDump.data()), pbDump.size());
    if (!pb_encode(&ost, bmcmetrics_metricproto_BmcMetricSnapshot_fields,
                   &snapshot))
    {
        auto msg = std::format("Writing pb msg: {}", PB_GET_ERROR(&ost));
        log<level::ERR>(msg.c_str());
        return;
    }
    done = true;
}

// BmcBlobSessionStat (9) but passing meta as reference instead of pointer,
// since the metadata must not be null at this point.
bool BmcHealthSnapshot::stat(blobs::BlobMeta& meta)
{
    if (!done)
    {
        // Bits 8~15 are blob-specific state flags.
        // For this blob, bit 8 is set when metric collection is still in
        // progress.
        meta.blobState |= (1 << 8);
    }
    else
    {
        meta.blobState = 0;
        meta.blobState = blobs::StateFlags::open_read;
        meta.size = pbDump.size();
    }
    return true;
}

std::string_view BmcHealthSnapshot::read(uint32_t offset,
                                         uint32_t requestedSize)
{
    uint32_t size = static_cast<uint32_t>(pbDump.size());
    if (offset >= size)
    {
        return {};
    }
    return std::string_view(pbDump.data() + offset,
                            std::min(requestedSize, size - offset));
}

int BmcHealthSnapshot::getStringID(const std::string_view s)
{
    int ret = 0;
    auto itr = stringTable.find(s.data());
    if (itr == stringTable.end())
    {
        stringTable[s.data()] = stringId;
        ret = stringId;
        ++stringId;
    }
    else
    {
        ret = itr->second;
    }
    return ret;
}

} // namespace metric_blob
