/*
// Copyright (c) 2019 Intel Corporation
//
// 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 "pfr_mgr.hpp"

#include "file.hpp"

namespace pfr
{

inline void printVersion(const std::string& path, const std::string& version)
{
    lg2::info("VERSION INFO - {TYPE} - {VER}", "TYPE", path, "VER", version);
}
static constexpr uint8_t activeImage = 0;
static constexpr uint8_t recoveryImage = 1;

std::shared_ptr<sdbusplus::asio::dbus_interface> associationIface;
std::set<std::tuple<std::string, std::string, std::string>> associations;

using GetSubTreeType = std::vector<
    std::pair<std::string,
              std::vector<std::pair<std::string, std::vector<std::string>>>>>;

PfrVersion::PfrVersion(sdbusplus::asio::object_server& srv_,
                       std::shared_ptr<sdbusplus::asio::connection>& conn_,
                       const std::string& path_, const ImageType& imgType_,
                       const std::string& purpose_) :
    server(srv_),
    conn(conn_), path(path_), imgType(imgType_), purpose(purpose_)
{
    version = getFirmwareVersion(imgType);

    if (!(version == "0.0" || version.empty()))
    {
        printVersion(path, version);
    }

    std::string objPath = "/xyz/openbmc_project/software/" + path;
    versionIface = server.add_interface(objPath,
                                        "xyz.openbmc_project.Software.Version");

    if (versionIface != nullptr)
    {
        versionIface->register_property("Purpose", purpose);
        versionIface->register_property(
            versionStr, version,
            // Override set
            [this](const std::string& req, std::string& propertyValue) {
            if (internalSet)
            {
                if (req != propertyValue)
                {
                    version = req;
                    propertyValue = req;
                    return 1;
                }
            }
            return 0;
        });

        versionIface->initialize();
    }

    std::string activation =
        "xyz.openbmc_project.Software.Activation.Activations.StandbySpare";

    if ((imgType == ImageType::bmcActive) ||
        (imgType == ImageType::biosActive) ||
        (imgType == ImageType::cpldActive) || (imgType == ImageType::afmActive))
    {
        // Running images so set Activations to "Active"
        activation =
            "xyz.openbmc_project.Software.Activation.Activations.Active";

        // For all Active images, functional endpoints must be added. This is
        // used in bmcweb & ipmi for fetching active component versions.

        // TODO: We have redundant active firmware version objects for BMC
        // and BIOS active images. BMC version is read from /etc/os-release
        // BIOS version is read from SMBIOS. Since it provides more
        // version information, Lets expose those as functional.
        // Down the line, Redundant inventory objects need to be addressed.
        if ((imgType == ImageType::cpldActive) ||
            (imgType == ImageType::afmActive))
        {
            associations.emplace("functional", "software_version", objPath);
        }
    }

    std::string reqActNone =
        "xyz.openbmc_project.Software.Activation.RequestedActivations.None";
    auto activationIface = server.add_interface(
        objPath, "xyz.openbmc_project.Software.Activation");

    if (activationIface != nullptr)
    {
        activationIface->register_property("Activation", activation);
        activationIface->register_property("RequestedActivation", reqActNone);

        activationIface->initialize();
    }

    // All the components exposed under PFR.Manager are updateable.
    // Lets add objPath endpoints to 'updatable' association
    associations.emplace("updateable", "software_version", objPath);
    associationIface->set_property("Associations", associations);
}

void PfrVersion::updateVersion()
{
    if (versionIface && versionIface->is_initialized())
    {
        std::string ver = getFirmwareVersion(imgType);
        printVersion(path, ver);
        internalSet = true;
        versionIface->set_property(versionStr, ver);
        internalSet = false;
    }
    return;
}

PfrConfig::PfrConfig(sdbusplus::asio::object_server& srv_,
                     std::shared_ptr<sdbusplus::asio::connection>& conn_) :
    server(srv_),
    conn(conn_)
{
    pfrCfgIface = server.add_interface("/xyz/openbmc_project/pfr",
                                       "xyz.openbmc_project.PFR.Attributes");

    ufmLocked = false;
    ufmProvisioned = false;
    ufmSupport = false;
    getProvisioningStatus(ufmLocked, ufmProvisioned, ufmSupport);

    pfrCfgIface->register_property(ufmProvisionedStr, ufmProvisioned,
                                   // Override set
                                   [this](const bool req, bool propertyValue) {
        if (internalSet)
        {
            if (req != propertyValue)
            {
                ufmProvisioned = req;
                propertyValue = req;
                return 1;
            }
        }
        return 0;
    });

    pfrCfgIface->register_property(ufmLockedStr, ufmLocked,
                                   // Override set
                                   [this](const bool req, bool propertyValue) {
        if (internalSet)
        {
            if (req != propertyValue)
            {
                ufmLocked = req;
                propertyValue = req;
                return 1;
            }
        }
        return 0;
    });

    pfrCfgIface->register_property(ufmSupportStr, ufmSupport,
                                   // Override set
                                   [this](const bool req, bool propertyValue) {
        if (internalSet)
        {
            if (req != propertyValue)
            {
                ufmSupport = req;
                propertyValue = req;
                return 1;
            }
        }
        return 0;
    });

    pfrCfgIface->initialize();

    /*BMCBusy period MailBox handling */
    pfrMBIface = server.add_interface("/xyz/openbmc_project/pfr",
                                      "xyz.openbmc_project.PFR.Mailbox");

    pfrMBIface->register_method("InitiateBMCBusyPeriod", [](bool setReset) {
        if (setBMCBusy(setReset) < 0)
        {
            return false;
        }
        return true;
    });

    pfrMBIface->register_method("ReadMBRegister", [](uint32_t regAddr) {
        uint8_t mailBoxReply = 0;
        try
        {
            getMBRegister(regAddr, mailBoxReply);
        }
        catch (const std::exception& e)
        {
            throw;
        }
        return mailBoxReply;
    });
    pfrMBIface->initialize();

    associationIface =
        server.add_interface("/xyz/openbmc_project/software",
                             "xyz.openbmc_project.Association.Definitions");
    associationIface->register_property("Associations", associations);
    associationIface->initialize();
}

void PfrConfig::updateProvisioningStatus()
{
    if (pfrCfgIface && pfrCfgIface->is_initialized())
    {
        bool lockVal = false;
        bool provVal = false;
        bool supportVal = false;
        getProvisioningStatus(lockVal, provVal, supportVal);
        internalSet = true;
        pfrCfgIface->set_property(ufmProvisionedStr, provVal);
        pfrCfgIface->set_property(ufmLockedStr, lockVal);
        pfrCfgIface->set_property(ufmSupportStr, supportVal);
        internalSet = false;
    }
    return;
}

static constexpr const char* postcodeStrProp = "PlatformState";
static constexpr const char* postcodeStrDefault = "Unknown";
static constexpr const char* postcodeDataProp = "Data";
static constexpr const char* postcodeIface =
    "xyz.openbmc_project.State.Boot.Platform";

PfrPostcode::PfrPostcode(sdbusplus::asio::object_server& srv_,
                         std::shared_ptr<sdbusplus::asio::connection>& conn_) :
    server(srv_),
    conn(conn_)
{
    if (getPlatformState(postcode) < 0)
    {
        postcode = 0;
    }

    pfrPostcodeIface = server.add_interface("/xyz/openbmc_project/pfr",
                                            postcodeIface);

    if (pfrPostcodeIface != nullptr)
    {
        pfrPostcodeIface->register_property(
            postcodeDataProp, postcode,
            // Override set
            [this](const uint8_t req, uint8_t& propertyValue) {
            if (internalSet)
            {
                if (req != propertyValue)
                {
                    postcode = req;
                    propertyValue = req;
                    return 1;
                }
            }
            return 0;
        },
            [this](uint8_t& propertyValue) {
            updatePostcode();
            propertyValue = postcode;
            return propertyValue;
        });

        pfrPostcodeIface->register_property(postcodeStrProp,
                                            std::string(postcodeStrDefault));

        pfrPostcodeIface->initialize();
        auto it = postcodeMap.find(postcode);
        if (it != postcodeMap.end())
        {
            pfrPostcodeIface->set_property(postcodeStrProp, it->second);
        }
    }
}

void PfrPostcode::updatePostcode()
{
    if (pfrPostcodeIface && pfrPostcodeIface->is_initialized())
    {
        if (getPlatformState(postcode) < 0)
        {
            postcode = 0;
        }

        internalSet = true;
        pfrPostcodeIface->set_property(postcodeDataProp, postcode);
        auto it = postcodeMap.find(postcode);
        if (it == postcodeMap.end())
        {
            pfrPostcodeIface->set_property(postcodeStrProp, postcodeStrDefault);
        }
        else
        {
            pfrPostcodeIface->set_property(postcodeStrProp, it->second);
        }
        internalSet = false;
    }
    return;
}

} // namespace pfr
