From 001f9dd91ef8ea7cd82f75ebecb524b49f391234 Mon Sep 17 00:00:00 2001 From: eportnov Date: Fri, 14 Oct 2022 13:25:35 +0300 Subject: Add caching pcie devices --- .../interfaces/bmcweb/0022-add-caching-pcie.patch | 40 + .../recipes-phosphor/interfaces/bmcweb_%.bbappend | 1 + .../peci-pcie/0002-add-caching-devices.patch | 854 +++++++++++++++++++++ .../peci-pcie/peci-pcie_%.bbappend | 1 + 4 files changed, 896 insertions(+) create mode 100644 meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb/0022-add-caching-pcie.patch create mode 100644 meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie/0002-add-caching-devices.patch diff --git a/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb/0022-add-caching-pcie.patch b/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb/0022-add-caching-pcie.patch new file mode 100644 index 0000000000..85cd43d653 --- /dev/null +++ b/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb/0022-add-caching-pcie.patch @@ -0,0 +1,40 @@ +From b172d7a4a9413a2877681ea1cfc707ad315e39f5 Mon Sep 17 00:00:00 2001 +From: claiff +Date: Fri, 14 Oct 2022 12:46:48 +0300 +Subject: [PATCH] add caching pcie + +--- + redfish-core/lib/pcie.hpp | 9 ++++----- + 1 file changed, 4 insertions(+), 5 deletions(-) + +diff --git a/redfish-core/lib/pcie.hpp b/redfish-core/lib/pcie.hpp +index 30d7d7a6..a58c46bf 100644 +--- a/redfish-core/lib/pcie.hpp ++++ b/redfish-core/lib/pcie.hpp +@@ -306,7 +306,7 @@ inline void requestRoutesSystemPCIeFunctionCollection(App& app) + // Check if this function exists by looking for a + // device ID + std::string devIDProperty = +- "Function" + std::to_string(functionNum) + "DeviceId"; ++ "Function" + std::to_string(functionNum) + "DeviceName"; + + auto find = std::find_if(pcieDevProperties.begin(), pcieDevProperties.end(),[devIDProperty](auto const& propEntry) + { return propEntry.first == devIDProperty; }); +@@ -377,14 +377,13 @@ inline void requestRoutesSystemPCIeFunction(App& app) + // Check if this function exists by looking for a device + // ID + std::string functionName = "Function" + function; +- std::string devIDProperty = functionName + "DeviceId"; + std::string devNameProperty = functionName + "DeviceName"; + +- auto find = std::find_if(pcieDevProperties.begin(), pcieDevProperties.end(),[devIDProperty](auto const& propEntry) +- { return propEntry.first == devIDProperty; }); ++ auto find = std::find_if(pcieDevProperties.begin(), pcieDevProperties.end(),[devNameProperty](auto const& propEntry) ++ { return propEntry.first == devNameProperty; }); + if(find == pcieDevProperties.end()) + { +- BMCWEB_LOG_DEBUG << "property" << devIDProperty << "not found"; ++ BMCWEB_LOG_DEBUG << "property" << devNameProperty << "not found"; + return; + } + auto property_func = std::get_if(&find->second); diff --git a/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb_%.bbappend b/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb_%.bbappend index 466abc6d99..2a87ee4fcf 100644 --- a/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb_%.bbappend +++ b/meta-ibs/meta-cp2-5422/recipes-phosphor/interfaces/bmcweb_%.bbappend @@ -18,6 +18,7 @@ SRC_URI += "\ file://0019-add-smtp-logging.patch \ file://0020-set-smtp-send-post-request.patch \ file://0021-Fix-getting-properties-from-DBUS-for-CPU-and-DIMM.patch \ + file://0022-add-caching-pcie.patch \ " #SRC_URI += "\ diff --git a/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie/0002-add-caching-devices.patch b/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie/0002-add-caching-devices.patch new file mode 100644 index 0000000000..cee5217df0 --- /dev/null +++ b/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie/0002-add-caching-devices.patch @@ -0,0 +1,854 @@ +From 178f1440b841657d9ff68e05fd4abb014b0f6317 Mon Sep 17 00:00:00 2001 +From: claiff +Date: Fri, 14 Oct 2022 12:37:53 +0300 +Subject: [PATCH] add caching devices + +--- + src/peci_pcie.cpp | 91 +++++++++++--- + vendor_storage/CMakeLists.txt | 10 ++ + vendor_storage/cache_devices.cpp | 76 ++++++++++++ + vendor_storage/cache_devices.hpp | 31 +++++ + vendor_storage/cache_file/cache_data.cpp | 98 +++++++++++++++ + vendor_storage/cache_file/cache_data.hpp | 65 ++++++++++ + vendor_storage/cache_file/file.cpp | 71 +++++++++++ + vendor_storage/cache_file/file.hpp | 23 ++++ + vendor_storage/cache_file/parser.cpp | 152 +++++++++++++++++++++++ + vendor_storage/cache_file/parser.hpp | 28 +++++ + vendor_storage/vendor_data_getter.cpp | 1 + + 11 files changed, 628 insertions(+), 18 deletions(-) + create mode 100644 vendor_storage/cache_devices.cpp + create mode 100644 vendor_storage/cache_devices.hpp + create mode 100644 vendor_storage/cache_file/cache_data.cpp + create mode 100644 vendor_storage/cache_file/cache_data.hpp + create mode 100644 vendor_storage/cache_file/file.cpp + create mode 100644 vendor_storage/cache_file/file.hpp + create mode 100644 vendor_storage/cache_file/parser.cpp + create mode 100644 vendor_storage/cache_file/parser.hpp + +diff --git a/src/peci_pcie.cpp b/src/peci_pcie.cpp +index 070c717..8e85d73 100644 +--- a/src/peci_pcie.cpp ++++ b/src/peci_pcie.cpp +@@ -19,6 +19,7 @@ + #include "pciDeviceClass.hpp" + #include "pciVendors.hpp" + #include "vendor_storage/vendor_data_getter.hpp" ++#include "vendor_storage/cache_devices.hpp" + + #include + #include +@@ -85,6 +86,9 @@ struct CPUInfo + }; + + storage::VendorStorage mVendorStorage; ++storage::CacheDevices mCacheDevice; ++std::list> mCacheIface; ++bool mFoundPCIE = false; + + // PECI Client Address Map + static resCode getCPUBusMap(std::vector& cpuInfo) +@@ -461,6 +465,19 @@ static resCode setPCIeFunctionProperties(const int& clientAddr, const int& bus, + resCode error; + std::optional vendor_id; + std::optional device_id; ++ std::string class_name; ++ ++ // Set the function Device Class ++ error = getDeviceClass(clientAddr, bus, dev, func, res); ++ if (error != resCode::resOk) ++ { ++ return error; ++ } ++ setPCIeProperty(clientAddr, bus, dev, ++ "Function" + std::to_string(func) + ++ std::string(peci_pcie::function::deviceClassName), ++ res); ++ class_name = res; + + for (const auto& [name, offset, size] : peci_pcie::pciConfigInfo) + { +@@ -490,7 +507,6 @@ static resCode setPCIeFunctionProperties(const int& clientAddr, const int& bus, + } + if( vendor_id && device_id ) + { +- std::cout << " vendor " << *vendor_id << " device " << *device_id << std::endl; + auto vendor_data = mVendorStorage.ConvertVendorData(*vendor_id, *device_id); + + setPCIeProperty(clientAddr, bus, dev, +@@ -501,7 +517,10 @@ static resCode setPCIeFunctionProperties(const int& clientAddr, const int& bus, + "Function" + std::to_string(func) + + std::string(peci_pcie::function::deviceName), + vendor_data.device_id); ++ auto device = storage::cache_file::DeviceData{clientAddr, bus, dev}; + ++ mCacheDevice.AddDevice(device); ++ mCacheDevice.AddFunctionData(device, func, vendor_data.device_id, class_name); + if(func == 0) + { + setPCIeProperty(clientAddr, bus, dev, "Device", vendor_data.device_id); +@@ -514,18 +533,6 @@ static resCode setPCIeFunctionProperties(const int& clientAddr, const int& bus, + std::string(peci_pcie::function::functionTypeName), + "Physical"); + +- +- +- // Set the function Device Class +- error = getDeviceClass(clientAddr, bus, dev, func, res); +- if (error != resCode::resOk) +- { +- return error; +- } +- setPCIeProperty(clientAddr, bus, dev, +- "Function" + std::to_string(func) + +- std::string(peci_pcie::function::deviceClassName), +- res); + return resCode::resOk; + } + +@@ -540,6 +547,7 @@ static resCode setPCIeDeviceProperties(const int& clientAddr, const int& bus, + return error; + } + setPCIeProperty(clientAddr, bus, dev, "Manufacturer", manuf); ++ mCacheDevice.SetManufacturing({clientAddr, bus, dev}, manuf); + + // Set the device type + constexpr char const* deviceTypeName = "DeviceType"; +@@ -552,10 +560,12 @@ static resCode setPCIeDeviceProperties(const int& clientAddr, const int& bus, + if (multiFunc) + { + setPCIeProperty(clientAddr, bus, dev, deviceTypeName, "MultiFunction"); ++ mCacheDevice.SetDeviceType({clientAddr, bus, dev}, "MultiFunction"); + } + else + { + setPCIeProperty(clientAddr, bus, dev, deviceTypeName, "SingleFunction"); ++ mCacheDevice.SetDeviceType({clientAddr, bus, dev}, "SingleFunction"); + } + + // Set PCIe Generation +@@ -581,11 +591,6 @@ static resCode setPCIeDeviceProperties(const int& clientAddr, const int& bus, + static resCode updatePCIeDevice(const int& clientAddr, const int& bus, + const int& dev) + { +- if (setPCIeDeviceProperties(clientAddr, bus, dev) != resCode::resOk) +- { +- return resCode::resErr; +- } +- + // Walk through and populate the functions for this device + for (int func = 0; func < peci_pcie::maxPCIFunctions; func++) + { +@@ -610,6 +615,10 @@ static resCode updatePCIeDevice(const int& clientAddr, const int& bus, + setDefaultPCIeFunctionProperties(clientAddr, bus, dev, func); + } + } ++ if (setPCIeDeviceProperties(clientAddr, bus, dev) != resCode::resOk) ++ { ++ return resCode::resErr; ++ } + return resCode::resOk; + } + +@@ -655,6 +664,34 @@ static resCode addPCIeDevice(sdbusplus::asio::object_server& objServer, + return resCode::resOk; + } + ++static resCode addPCIeDeviceForce(sdbusplus::asio::object_server& objServer, ++ storage::cache_file::DeviceData const& device_data ) ++{ ++ std::string pathName = std::string(peci_pcie::peciPCIePath) + "/S" + ++ std::to_string(device_data.GetCpu()) + "B" + std::to_string(device_data.GetBus()) + ++ "D" + std::to_string(device_data.GetDev()); ++ auto iface = ++ objServer.add_interface(pathName, peci_pcie::peciPCIeDeviceInterface); ++ iface->register_property("DeviceType", device_data.GetDeviceType()); ++ iface->register_property("Manufacturer", device_data.GetManufacturing()); ++ auto functions = device_data.GetFunctionData(); ++ ++ for( const auto& function : functions ) ++ { ++ auto class_field = "Function" + std::to_string(function.func) + "Class"; ++ auto device_field = "Function" + std::to_string(function.func) + "DeviceName"; ++ iface->register_property(class_field, function.class_name); ++ iface->register_property(device_field, function.device_name); ++ } ++ if(!functions.empty()) ++ { ++ iface->register_property("Device", functions.front().device_name); ++ } ++ iface->initialize(); ++ mCacheIface.push_back(iface); ++ return resCode::resOk; ++} ++ + static bool pcieDeviceInDBusMap(const int& clientAddr, const int& bus, + const int& dev) + { +@@ -689,6 +726,16 @@ static resCode probePCIeDevice(boost::asio::io_service& io, + } + if (res) + { ++ if(!mFoundPCIE) ++ { ++ mCacheDevice.ClearDevices(); ++ for(const auto& iface : mCacheIface) ++ { ++ auto result = objServer.remove_interface(iface); ++ } ++ mCacheIface.clear(); ++ mFoundPCIE = true; ++ } + if (pcieDeviceInDBusMap(addr, bus, dev)) + { + // This device is already in D-Bus, so update it +@@ -988,6 +1035,14 @@ int main(int argc, char* argv[]) + // CPU map + std::vector cpuInfo; + ++ if(!mCacheDevice.IsEmpty()) ++ { ++ for(auto it = mCacheDevice.CBegin(); it != mCacheDevice.CEnd(); ++it) ++ { ++ addPCIeDeviceForce(server, *it); ++ } ++ } ++ + #ifdef WAIT_FOR_OS_STANDBY + boost::asio::steady_timer osStandbyTimer(io); + monitorOSStandby(io, conn, server, osStandbyTimer, cpuInfo); +diff --git a/vendor_storage/CMakeLists.txt b/vendor_storage/CMakeLists.txt +index 0797a06..44a7dad 100644 +--- a/vendor_storage/CMakeLists.txt ++++ b/vendor_storage/CMakeLists.txt +@@ -8,12 +8,15 @@ set(CMAKE_CXX_STANDARD_REQUIRED ON) + set(STORAGE_DIR .) + set(PARSER_DIR ${STORAGE_DIR}/parser) + set(RESULT_DIR ${STORAGE_DIR}/result) ++set(CACHE_FILE_DIR ${STORAGE_DIR}/cache_file) + + include_directories(${STORAGE_DIR}) + + add_library(vendor_storage + ${STORAGE_DIR}/vendor_data_getter.cpp + ${STORAGE_DIR}/vendor_data_getter.hpp ++ ${STORAGE_DIR}/cache_devices.cpp ++ ${STORAGE_DIR}/cache_devices.hpp + + ${PARSER_DIR}/empty.hpp + ${PARSER_DIR}/empty.cpp +@@ -44,4 +47,11 @@ add_library(vendor_storage + ${RESULT_DIR}/device_id.hpp + ${RESULT_DIR}/device_id.cpp + ${RESULT_DIR}/types/iresult.hpp ++ ++ ${CACHE_FILE_DIR}/file.hpp ++ ${CACHE_FILE_DIR}/file.cpp ++ ${CACHE_FILE_DIR}/parser.hpp ++ ${CACHE_FILE_DIR}/parser.cpp ++ ${CACHE_FILE_DIR}/cache_data.hpp ++ ${CACHE_FILE_DIR}/cache_data.cpp + ) +diff --git a/vendor_storage/cache_devices.cpp b/vendor_storage/cache_devices.cpp +new file mode 100644 +index 0000000..8c257ff +--- /dev/null ++++ b/vendor_storage/cache_devices.cpp +@@ -0,0 +1,76 @@ ++#include ++ ++#include "cache_devices.hpp" ++ ++namespace storage ++{ ++ CacheDevices::CacheDevices() ++ { ++ mDevices = mFile.Read(); ++ } ++ ++ void CacheDevices::AddDevice( cache_file::DeviceData const& device ) ++ { ++ auto find = std::find_if(mDevices.begin(), mDevices.end(), [device]( cache_file::DeviceData const& device_in_set ){return device_in_set == device;}); ++ if(find != mDevices.end()) ++ { ++ return; ++ } ++ mDevices.push_back( device ); ++ mFile.Write( mDevices ); ++ } ++ ++ void CacheDevices::ClearDevices() ++ { ++ mDevices.clear(); ++ mFile.Write( mDevices ); ++ } ++ ++ void CacheDevices::AddFunctionData(const cache_file::DeviceData &device, int func, const std::string &device_name, const std::string &class_name) ++ { ++ auto find = std::find_if(mDevices.begin(), mDevices.end(), [device]( cache_file::DeviceData const& device_in_set ){return device_in_set == device;}); ++ if( find == mDevices.end()) ++ { ++ return; ++ } ++ find->AddFunctionData(func, device_name, class_name); ++ mFile.Write( mDevices ); ++ } ++ ++ void CacheDevices::SetDeviceType(const cache_file::DeviceData &device, const std::string &device_type) ++ { ++ auto find = std::find_if(mDevices.begin(), mDevices.end(), [device]( cache_file::DeviceData const& device_in_set ){return device_in_set == device;}); ++ if( find == mDevices.end()) ++ { ++ return; ++ } ++ find->SetDeviceType( device_type); ++ mFile.Write( mDevices ); ++ } ++ ++ void CacheDevices::SetManufacturing(const cache_file::DeviceData &device, const std::string &manufacturing) ++ { ++ auto find = std::find_if(mDevices.begin(), mDevices.end(), [device]( cache_file::DeviceData const& device_in_set ){return device_in_set == device;}); ++ if( find == mDevices.end()) ++ { ++ return; ++ } ++ find->SetManufactoring( manufacturing ); ++ mFile.Write( mDevices ); ++ } ++ ++ bool CacheDevices::IsEmpty() const noexcept ++ { ++ return mDevices.empty(); ++ } ++ ++ std::list::const_iterator CacheDevices::CBegin() const ++ { ++ return mDevices.cbegin(); ++ } ++ ++ std::list::const_iterator CacheDevices::CEnd() const ++ { ++ return mDevices.cend(); ++ } ++} +diff --git a/vendor_storage/cache_devices.hpp b/vendor_storage/cache_devices.hpp +new file mode 100644 +index 0000000..ea1038b +--- /dev/null ++++ b/vendor_storage/cache_devices.hpp +@@ -0,0 +1,31 @@ ++#pragma once ++ ++#include ++ ++#include "cache_file/cache_data.hpp" ++#include "cache_file/file.hpp" ++ ++namespace storage ++{ ++ class CacheDevices ++ { ++ public: ++ CacheDevices(); ++ ~CacheDevices() = default; ++ ++ void AddDevice( cache_file::DeviceData const& device ); ++ void ClearDevices(); ++ void AddFunctionData(cache_file::DeviceData const& device, int func, std::string const& device_name, std::string const& class_name); ++ void SetDeviceType( cache_file::DeviceData const& device, std::string const& device_type ); ++ void SetManufacturing( cache_file::DeviceData const& device, std::string const& manufacturing ); ++ ++ ++ bool IsEmpty() const noexcept; ++ ++ std::list::const_iterator CBegin() const; ++ std::list::const_iterator CEnd() const; ++ private: ++ std::list mDevices; ++ cache_file::File mFile; ++ }; ++} +diff --git a/vendor_storage/cache_file/cache_data.cpp b/vendor_storage/cache_file/cache_data.cpp +new file mode 100644 +index 0000000..84b9a0d +--- /dev/null ++++ b/vendor_storage/cache_file/cache_data.cpp +@@ -0,0 +1,98 @@ ++#include ++ ++#include "cache_data.hpp" ++ ++namespace storage::cache_file ++{ ++ ++ DeviceData::DeviceData(int addr, int bus, int dev) ++ : mAddr( addr ) ++ , mBus( bus ) ++ , mDev( dev ) ++ , mCpu( 0 ) ++ { ++ ++ } ++ ++ size_t DeviceData::GetAddr() const noexcept ++ { ++ return mAddr; ++ } ++ ++ void DeviceData::SetAddr(int addr) ++ { ++ mAddr = addr; ++ } ++ ++ int DeviceData::GetCpu() const noexcept ++ { ++ return mCpu; ++ } ++ ++ void DeviceData::SetCpu(int cpu) ++ { ++ mCpu = cpu; ++ } ++ ++ int DeviceData::GetBus() const noexcept ++ { ++ return mBus; ++ } ++ ++ void DeviceData::SetBus(int bus) ++ { ++ mBus = bus; ++ } ++ ++ int DeviceData::GetDev() const noexcept ++ { ++ return mDev; ++ } ++ ++ void DeviceData::SetDev(int dev) ++ { ++ mDev = dev; ++ } ++ ++ std::string DeviceData::GetManufacturing() const noexcept ++ { ++ return mManufacturing; ++ } ++ ++ void DeviceData::SetManufactoring(const std::string &manufactoring) ++ { ++ mManufacturing = manufactoring; ++ } ++ ++ std::string DeviceData::GetDeviceType() const noexcept ++ { ++ return mDeviceType; ++ } ++ ++ void DeviceData::SetDeviceType(const std::string &device_type) ++ { ++ mDeviceType = device_type; ++ } ++ ++ std::list DeviceData::GetFunctionData() const noexcept ++ { ++ return mFunctionSet; ++ } ++ ++ void DeviceData::AddFunctionData(int func, const std::string &device_name, const std::string &class_name) ++ { ++ mFunctionSet.push_back({class_name, device_name, func}); ++ } ++ ++ void DeviceData::AddFunctionData(const std::list &functions) ++ { ++ for(const auto& function : functions) ++ { ++ auto find = std::find_if(mFunctionSet.begin(), mFunctionSet.end(), [function](FunctionInfo const& functions_from_set){ return functions_from_set == function;}); ++ if(find == mFunctionSet.end()) ++ { ++ mFunctionSet.push_back(function); ++ } ++ } ++ } ++} +diff --git a/vendor_storage/cache_file/cache_data.hpp b/vendor_storage/cache_file/cache_data.hpp +new file mode 100644 +index 0000000..2cc70f4 +--- /dev/null ++++ b/vendor_storage/cache_file/cache_data.hpp +@@ -0,0 +1,65 @@ ++#pragma once ++ ++#include ++#include ++#include ++ ++namespace storage::cache_file ++{ ++ struct FunctionInfo ++ { ++ std::string class_name; ++ std::string device_name; ++ int func; ++ ++ bool operator==(FunctionInfo const& right) const ++ { ++ return class_name == right.class_name && ++ device_name == right.device_name && ++ func == right.func; ++ } ++ }; ++ ++ class DeviceData ++ { ++ public: ++ DeviceData( int addr, int bus, int dev ); ++ ++ size_t GetAddr() const noexcept; ++ void SetAddr( int addr ); ++ ++ int GetCpu() const noexcept; ++ void SetCpu( int cpu ); ++ ++ int GetBus() const noexcept; ++ void SetBus( int bus ); ++ ++ int GetDev() const noexcept; ++ void SetDev( int dev ); ++ ++ std::string GetManufacturing() const noexcept; ++ void SetManufactoring( std::string const& manufactoring ); ++ ++ std::string GetDeviceType( ) const noexcept; ++ void SetDeviceType( std::string const& device_type ); ++ ++ std::list GetFunctionData() const noexcept; ++ void AddFunctionData( int func, std::string const& device_name, std::string const& class_name ); ++ void AddFunctionData( std::list const& functions ); ++ ++ bool operator==(DeviceData const& right) const ++ { ++ return mAddr == right.mAddr && ++ mBus == right.mBus && ++ mDev == right.mDev; ++ } ++ private: ++ int mAddr; ++ int mBus; ++ int mDev; ++ int mCpu; ++ std::string mManufacturing; ++ std::string mDeviceType; ++ std::list mFunctionSet; ++ }; ++} +diff --git a/vendor_storage/cache_file/file.cpp b/vendor_storage/cache_file/file.cpp +new file mode 100644 +index 0000000..d3e580a +--- /dev/null ++++ b/vendor_storage/cache_file/file.cpp +@@ -0,0 +1,71 @@ ++#include ++ ++#include "cache_devices.hpp" ++#include "parser.hpp" ++ ++namespace storage::cache_file ++{ ++ std::list cache_file::File::Read() ++ { ++ std::ifstream file_reader{ GetPath(), std::fstream::in }; ++ if ( !file_reader.is_open() ) ++ { ++ CreateFile(); ++ return {}; ++ } ++ return ReadFile(file_reader); ++ } ++ ++ void File::Write( std::list const& device_data ) ++ { ++ Parser parser; ++ ++ std::ofstream file_writer{ GetPath(), std::fstream::out }; ++ if ( !file_writer.is_open() ) ++ { ++ return; ++ } ++ for(const auto& line : device_data) ++ { ++ auto line_as_string = parser.InvertParse( line ); ++ file_writer << line_as_string << "\n"; ++ } ++ ++ file_writer.close(); ++ } ++ ++ void File::CreateFile() const ++ { ++ std::fstream file_writer; ++ file_writer.open( GetPath(), std::fstream::out ); ++ if( !file_writer.is_open() ) ++ { ++ return; ++ } ++ file_writer.close(); ++ } ++ ++ std::list File::ReadFile( std::ifstream& file_reader ) const ++ { ++ std::string line{}; ++ Parser parser; ++ std::list result; ++ ++ while ( std::getline( file_reader, line ) ) ++ { ++ auto data_parsed = parser.Parse(line); ++ if( data_parsed ) ++ { ++ result.push_back(*data_parsed); ++ } ++ } ++ file_reader.close(); ++ return result; ++ } ++ ++ std::string File::GetPath() const noexcept ++ { ++ static const std::string PATH_CACHE = "/usr/share/misc/cache.txt"; ++ return PATH_CACHE; ++ } ++} +diff --git a/vendor_storage/cache_file/file.hpp b/vendor_storage/cache_file/file.hpp +new file mode 100644 +index 0000000..865fcb7 +--- /dev/null ++++ b/vendor_storage/cache_file/file.hpp +@@ -0,0 +1,23 @@ ++#pragma once ++ ++#include ++#include ++ ++#include "cache_data.hpp" ++ ++namespace storage::cache_file ++{ ++ class File ++ { ++ public: ++ File() = default; ++ ~File() = default; ++ ++ std::list Read(); ++ void Write( std::list const& device_data ); ++ private: ++ void CreateFile() const; ++ std::list ReadFile( std::ifstream& file_reader ) const; ++ std::string GetPath() const noexcept; ++ }; ++} +diff --git a/vendor_storage/cache_file/parser.cpp b/vendor_storage/cache_file/parser.cpp +new file mode 100644 +index 0000000..549ca57 +--- /dev/null ++++ b/vendor_storage/cache_file/parser.cpp +@@ -0,0 +1,152 @@ ++#include ++ ++#include "parser.hpp" ++ ++ ++namespace storage::cache_file ++{ ++ std::optional Parser::Parse( std::string const& line) ++ { ++ static const std::string DELIMITER = "&"; ++ auto params = BuildParams( ParseLine( line, DELIMITER ) ); ++ ++ auto result = GetDataFromParams( params ); ++ return result; ++ } ++ ++ std::string Parser::InvertParse( DeviceData const& device_data) ++ { ++ std::string result; ++ ++ ApplyToString(result, "addr", std::to_string( device_data.GetAddr() )); ++ ApplyToString(result, "cpu", std::to_string(device_data.GetCpu())); ++ ApplyToString(result, "bus", std::to_string(device_data.GetBus())); ++ ApplyToString(result, "dev", std::to_string(device_data.GetDev())); ++ ApplyToString(result, "dev_type", device_data.GetDeviceType()); ++ ApplyToString(result, "manuf", device_data.GetManufacturing()); ++ ++ auto function_set = device_data.GetFunctionData(); ++ for(const auto& function : function_set) ++ { ++ ApplyToString(result, "Function" + std::to_string(function.func) +"Class", function.class_name); ++ ApplyToString(result, "Function" + std::to_string(function.func) +"DeviceName", function.device_name); ++ } ++ ++ return result; ++ } ++ ++ std::list Parser::ParseLine( std::string const& line, std::string const& delimiter ) const ++ { ++ std::list result; ++ ++ auto start = 0U; ++ auto end = line.find(delimiter); ++ while(end != std::string::npos) ++ { ++ auto parsed = line.substr(start, end - start); ++ result.push_back(parsed); ++ start = end + delimiter.length(); ++ end = line.find(delimiter, start); ++ } ++ auto parsed = line.substr(start, end); ++ result.push_back( parsed ); ++ return result; ++ } ++ ++ std::unordered_map Parser::BuildParams(std::list const& parsed_data) const ++ { ++ static const std::string DELIMITER_ON_PARAMETER = "="; ++ ++ std::unordered_map result; ++ for(const auto& not_parsed_param : parsed_data) ++ { ++ auto param_pair = ParseLine( not_parsed_param, DELIMITER_ON_PARAMETER ); ++ result.insert( {param_pair.front(), param_pair.back()} ); ++ } ++ return result; ++ } ++ ++ DeviceData Parser::GetDataFromParams( std::unordered_map const& params ) const ++ { ++ DeviceData result{0,0,0}; ++ ++ auto addr = params.find("addr"); ++ if(addr != params.end()) ++ { ++ result.SetAddr( ConvertToInt( (*addr).second )); ++ } ++ auto cpu = params.find("cpu"); ++ if(cpu != params.end()) ++ { ++ result.SetCpu( ConvertToInt( (*cpu).second )); ++ } ++ auto bus = params.find("bus"); ++ if(bus != params.end()) ++ { ++ result.SetBus( ConvertToInt( (*bus).second )); ++ } ++ auto dev = params.find("dev"); ++ if(dev != params.end()) ++ { ++ result.SetDev( ConvertToInt( (*dev).second )); ++ } ++ auto device_type = params.find("dev_type"); ++ if(device_type != params.end()) ++ { ++ result.SetDeviceType((*device_type).second ); ++ } ++ auto manufactoring = params.find("manuf"); ++ if(manufactoring != params.end()) ++ { ++ result.SetManufactoring((*manufactoring).second); ++ } ++ result.AddFunctionData( GetFunctionSet( params ) ); ++ return result; ++ } ++ ++ int Parser::ConvertToInt( std::string const& number_as_string) const ++ { ++ int result = 0; ++ try ++ { ++ result = std::stoi(number_as_string); ++ } ++ catch (...) ++ { ++ ++ } ++ return result; ++ } ++ ++ void Parser::ApplyToString(std::string &result, std::string const& field, std::string const& value ) const ++ { ++ result += field; ++ result += "="; ++ result += value; ++ result += "&"; ++ } ++ ++ std::list Parser::GetFunctionSet( std::unordered_map const& params ) const ++ { ++ std::list result; ++ int i = 0; ++ auto find_class = params.end(); ++ auto find_name = params.end(); ++ do ++ { ++ find_class = params.find("Function" + std::to_string(i) + "Class"); ++ find_name = params.find("Function" + std::to_string(i) +"DeviceName"); ++ if(find_class != params.end() && find_name != params.end()) ++ { ++ FunctionInfo function; ++ function.class_name = (*find_class).second; ++ function.device_name = (*find_name).second; ++ function.func = i; ++ result.push_back(function); ++ } ++ ++i; ++ } ++ while(find_class != params.end() || find_name != params.end()); ++ return result; ++ } ++} +diff --git a/vendor_storage/cache_file/parser.hpp b/vendor_storage/cache_file/parser.hpp +new file mode 100644 +index 0000000..f84ee6b +--- /dev/null ++++ b/vendor_storage/cache_file/parser.hpp +@@ -0,0 +1,28 @@ ++#pragma once ++ ++#include ++#include ++#include ++#include ++ ++#include "cache_data.hpp" ++ ++namespace storage::cache_file ++{ ++ class Parser ++ { ++ public: ++ Parser() = default; ++ ~Parser() = default; ++ ++ std::optional Parse( std::string const& line ); ++ std::string InvertParse( DeviceData const& device_data ); ++ private: ++ std::list ParseLine( std::string const& line, std::string const& delimiter ) const; ++ std::unordered_map BuildParams( std::list const& parsed_data ) const; ++ DeviceData GetDataFromParams( std::unordered_map const& params ) const; ++ int ConvertToInt( std::string const& number_as_string ) const; ++ void ApplyToString( std::string& result, std::string const& field, std::string const& value) const; ++ std::list GetFunctionSet( std::unordered_map const& params ) const; ++ }; ++} +diff --git a/vendor_storage/vendor_data_getter.cpp b/vendor_storage/vendor_data_getter.cpp +index 44d6e1c..71ce91e 100644 +--- a/vendor_storage/vendor_data_getter.cpp ++++ b/vendor_storage/vendor_data_getter.cpp +@@ -34,6 +34,7 @@ namespace storage + { + ProcessLine( line ); + } ++ idfile.close(); + } + + // diff --git a/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie_%.bbappend b/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie_%.bbappend index e2dc7ef8c7..a6defaa863 100644 --- a/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie_%.bbappend +++ b/meta-ibs/meta-cp2-5422/recipes-phosphor/peci-pcie/peci-pcie_%.bbappend @@ -1,6 +1,7 @@ FILESEXTRAPATHS:append := "${THISDIR}/${PN}:" SRC_URI += "file://storage \ file://0001-Add-device-human-name.patch \ + file://0002-add-caching-devices.patch \ " do_install:append() { install -d ${D}/usr/share/misc -- cgit v1.2.3