blob: bcd71de7d98b662a3bd6103c28775548807f4d04 [file] [edit]
#pragma once
#include <sdbusplus/bus.hpp>
#include <sdbusplus/message/types.hpp>
#include <sdbusplus/server/object.hpp>
#include <xyz/openbmc_project/Association/Definitions/server.hpp>
#include <xyz/openbmc_project/Inventory/Item/NetworkAdapter/server.hpp>
#include <xyz/openbmc_project/Inventory/Item/Port/server.hpp>
#include <format>
#include <memory>
#include <string>
namespace pldm
{
namespace platform_mc
{
using NetworkAdapterInterface = sdbusplus::server::object_t<
sdbusplus::xyz::openbmc_project::Inventory::Item::server::NetworkAdapter>;
using PortInterface = sdbusplus::server::object_t<
sdbusplus::xyz::openbmc_project::Inventory::Item::server::Port>;
using AssociationDefinitionsInterface = sdbusplus::server::object_t<
sdbusplus::xyz::openbmc_project::Association::server::Definitions>;
struct PLDMEntity
{
uint16_t entityType;
uint16_t instNum;
uint16_t containerId;
std::string toString() const
{
return std::format("(Type:{}, Inst:{}, Container:{})", entityType,
instNum, containerId);
}
bool operator==(const PLDMEntity& other) const
{
return (entityType == other.entityType && instNum == other.instNum &&
containerId == other.containerId);
}
bool operator<(const PLDMEntity& other) const
{
if (entityType != other.entityType)
return entityType < other.entityType;
if (instNum != other.instNum)
return instNum < other.instNum;
return containerId < other.containerId;
}
};
struct PLDMEntityHasher
{
std::size_t operator()(const PLDMEntity& k) const
{
std::size_t res = 17;
res = res * 31 + std::hash<uint16_t>()(k.entityType);
res = res * 31 + std::hash<uint16_t>()(k.instNum);
res = res * 31 + std::hash<uint16_t>()(k.containerId);
return res;
}
};
class InventoryBase
{
protected:
PLDMEntity entity;
std::string name;
std::string inventoryPath;
std::string parentInventoryPath;
public:
InventoryBase(const PLDMEntity& entity, const std::string& name,
const std::string& inventoryPath,
const std::string& parentInventoryPath) :
entity(entity), name(name), inventoryPath(inventoryPath),
parentInventoryPath(parentInventoryPath)
{}
const std::string& getInventoryPath() const
{
return inventoryPath;
}
virtual ~InventoryBase() {}
virtual void setHealthState([[maybe_unused]] const std::string& health) {}
inline static const std::string HealthStateOK = "OK";
inline static const std::string HealthStateWarning = "Warning";
inline static const std::string HealthStateCritical = "Critical";
inline static const std::string Unknown = "Unknown";
};
class NicInventory : public InventoryBase
{
public:
NicInventory(sdbusplus::bus::bus& bus, const PLDMEntity& entity,
const std::string& name, const std::string& inventoryPath,
const std::string& parentInventoryPath) :
InventoryBase(entity, name, inventoryPath, parentInventoryPath)
{
nicInterface = std::make_unique<NetworkAdapterInterface>(
bus, inventoryPath.c_str());
nicInterface->statusHealth(Unknown);
association = std::make_unique<AssociationDefinitionsInterface>(
bus, inventoryPath.c_str());
association->associations(
{{"chassis", "network_adapter", parentInventoryPath}});
}
void setHealthState(const std::string& health)
{
if (nicInterface)
{
nicInterface->statusHealth(health);
}
}
private:
std::unique_ptr<NetworkAdapterInterface> nicInterface;
std::unique_ptr<AssociationDefinitionsInterface> association;
};
class PortInventory : public InventoryBase
{
public:
PortInventory(sdbusplus::bus::bus& bus, const PLDMEntity& entity,
const std::string& name, const std::string& inventoryPath,
const std::string& parentInventoryPath) :
InventoryBase(entity, name, inventoryPath, parentInventoryPath)
{
portInterface =
std::make_unique<PortInterface>(bus, inventoryPath.c_str());
portInterface->linkState(LinkStateDisabled);
portInterface->linkStatus(Unknown);
portInterface->currentSpeedGbps(0);
association = std::make_unique<AssociationDefinitionsInterface>(
bus, inventoryPath.c_str());
association->associations(
{{"adapter", "all_ports", parentInventoryPath}});
}
void setSpeedGbps(double gbps)
{
if (portInterface)
{
portInterface->currentSpeedGbps(gbps);
}
}
void setLinkState(const std::string& linkState)
{
if (portInterface)
{
portInterface->linkState(linkState);
}
}
void setLinkStatus(const std::string& linkStatus)
{
if (portInterface)
{
portInterface->linkStatus(linkStatus);
}
}
public:
inline static const std::string LinkStateDisabled = "Disabled";
inline static const std::string LinkStateEnabled = "Enabled";
inline static const std::string LinkStatusLinkDown = "LinkDown";
inline static const std::string LinkStatusLinkUp = "LinkUp";
inline static const std::string LinkStatusNoLink = "NoLink";
private:
std::unique_ptr<PortInterface> portInterface;
std::unique_ptr<AssociationDefinitionsInterface> association;
};
} // namespace platform_mc
} // namespace pldm