118c42b0fSMatt Spinler #pragma once 218c42b0fSMatt Spinler 318c42b0fSMatt Spinler #include <filesystem> 418c42b0fSMatt Spinler #include <nlohmann/json.hpp> 518c42b0fSMatt Spinler #include <string> 618c42b0fSMatt Spinler #include <tuple> 718c42b0fSMatt Spinler #include <vector> 818c42b0fSMatt Spinler 918c42b0fSMatt Spinler /** 1018c42b0fSMatt Spinler * @file device_callouts.hpp 1118c42b0fSMatt Spinler * 1218c42b0fSMatt Spinler * @brief Looks up FRU callouts, which are D-Bus inventory paths, 1318c42b0fSMatt Spinler * in JSON for device sysfs paths. 1418c42b0fSMatt Spinler * 1518c42b0fSMatt Spinler * The code will extract the search keys from the sysfs path to 1618c42b0fSMatt Spinler * use to look up the callout list in the JSON. The callouts will 1718c42b0fSMatt Spinler * be sorted by priority as defined in th PEL spec. 1818c42b0fSMatt Spinler * 1918c42b0fSMatt Spinler * The JSON is normally generated from the MRW, and contains 2018c42b0fSMatt Spinler * sections for the following types of callouts: 2118c42b0fSMatt Spinler * * I2C (also based on bus/addr as well as the path) 2218c42b0fSMatt Spinler * * FSI 2318c42b0fSMatt Spinler * * FSI-I2C 2418c42b0fSMatt Spinler * * FSI-SPI 2518c42b0fSMatt Spinler * 2618c42b0fSMatt Spinler * The JSON looks like: 2718c42b0fSMatt Spinler * 2818c42b0fSMatt Spinler * "I2C": 2918c42b0fSMatt Spinler * "<bus>": 3018c42b0fSMatt Spinler * "<address>": 3118c42b0fSMatt Spinler * "Callouts": [ 3218c42b0fSMatt Spinler * { 3318c42b0fSMatt Spinler * "LocationCode": "<location code>", 3418c42b0fSMatt Spinler * "Name": "<inventory path>", 3518c42b0fSMatt Spinler * "Priority": "<priority=H/M/L>", 3618c42b0fSMatt Spinler * "MRU": "<optional MRU name>" 3718c42b0fSMatt Spinler * }, 3818c42b0fSMatt Spinler * ... 3918c42b0fSMatt Spinler * ], 4018c42b0fSMatt Spinler * "Dest": "<destination MRW target>" 4118c42b0fSMatt Spinler * 4218c42b0fSMatt Spinler * "FSI": 4318c42b0fSMatt Spinler * "<fsi link>": 4418c42b0fSMatt Spinler * "Callouts": [ 4518c42b0fSMatt Spinler * ... 4618c42b0fSMatt Spinler * ], 4718c42b0fSMatt Spinler * "Dest": "<destination MRW target>" 4818c42b0fSMatt Spinler * 4918c42b0fSMatt Spinler * "FSI-I2C": 5018c42b0fSMatt Spinler * "<fsi link>": 5118c42b0fSMatt Spinler * "<bus>": 5218c42b0fSMatt Spinler * "<address>": 5318c42b0fSMatt Spinler * "Callouts": [ 5418c42b0fSMatt Spinler * ... 5518c42b0fSMatt Spinler * ], 5618c42b0fSMatt Spinler * "Dest": "<destination MRW target>" 5718c42b0fSMatt Spinler * 5818c42b0fSMatt Spinler * "FSI-SPI": 5918c42b0fSMatt Spinler * "<fsi link>": 6018c42b0fSMatt Spinler * "<bus>": 6118c42b0fSMatt Spinler * "Callouts": [ 6218c42b0fSMatt Spinler * ... 6318c42b0fSMatt Spinler * ], 6418c42b0fSMatt Spinler * "Dest": "<destination MRW target>" 6518c42b0fSMatt Spinler * 6618c42b0fSMatt Spinler */ 6718c42b0fSMatt Spinler 6818c42b0fSMatt Spinler namespace openpower::pels::device_callouts 6918c42b0fSMatt Spinler { 7018c42b0fSMatt Spinler 7118c42b0fSMatt Spinler /** 7218c42b0fSMatt Spinler * @brief Represents a callout in the device JSON. 7318c42b0fSMatt Spinler * 7418c42b0fSMatt Spinler * The debug field will only be filled in for the first 7518c42b0fSMatt Spinler * callout in the list of them and contains additional 7618c42b0fSMatt Spinler * information about what happened when looking up the 7718c42b0fSMatt Spinler * callouts that is meant to aid in debug. 7818c42b0fSMatt Spinler */ 7918c42b0fSMatt Spinler struct Callout 8018c42b0fSMatt Spinler { 8118c42b0fSMatt Spinler std::string priority; 8218c42b0fSMatt Spinler std::string locationCode; 8318c42b0fSMatt Spinler std::string name; 8418c42b0fSMatt Spinler std::string mru; 8518c42b0fSMatt Spinler std::string debug; 8618c42b0fSMatt Spinler }; 8718c42b0fSMatt Spinler 8818c42b0fSMatt Spinler /** 8918c42b0fSMatt Spinler * @brief Looks up the callouts in a JSON File to add to a PEL 9018c42b0fSMatt Spinler * for when the path between the BMC and the device specified 9118c42b0fSMatt Spinler * by the passed in device path needs to be called out. 9218c42b0fSMatt Spinler * 9318c42b0fSMatt Spinler * The path is the path used to access the device in sysfs. It 9418c42b0fSMatt Spinler * can be either a directory path or a file path. 9518c42b0fSMatt Spinler * 9618c42b0fSMatt Spinler * @param[in] devPath - The device path 9718c42b0fSMatt Spinler * @param[in] compatibleList - The list of compatible names for this 9818c42b0fSMatt Spinler * system. 9918c42b0fSMatt Spinler * @return std::vector<Callout> - The list of callouts 10018c42b0fSMatt Spinler */ 10118c42b0fSMatt Spinler std::vector<Callout> 10218c42b0fSMatt Spinler getCallouts(const std::string& devPath, 10318c42b0fSMatt Spinler const std::vector<std::string>& compatibleList); 10418c42b0fSMatt Spinler 10518c42b0fSMatt Spinler /** 10618c42b0fSMatt Spinler * @brief Looks up the callouts to add to a PEL for when the path 10718c42b0fSMatt Spinler * between the BMC and the device specified by the passed in 10818c42b0fSMatt Spinler * I2C bus and address needs to be called out. 10918c42b0fSMatt Spinler * 11018c42b0fSMatt Spinler * @param[in] i2cBus - The I2C bus 11118c42b0fSMatt Spinler * @param[in] i2cAddress - The I2C address 11218c42b0fSMatt Spinler * @param[in] compatibleList - The list of compatible names for this 11318c42b0fSMatt Spinler * system. 11418c42b0fSMatt Spinler * @return std::vector<Callout> - The list of callouts 11518c42b0fSMatt Spinler */ 11618c42b0fSMatt Spinler std::vector<Callout> 11718c42b0fSMatt Spinler getI2CCallouts(size_t i2cBus, uint8_t i2cAddress, 11818c42b0fSMatt Spinler const std::vector<std::string>& compatibleList); 11918c42b0fSMatt Spinler 12018c42b0fSMatt Spinler namespace util 12118c42b0fSMatt Spinler { 12218c42b0fSMatt Spinler 12318c42b0fSMatt Spinler /** 124a307089cSMatt Spinler * @brief The different callout path types 125a307089cSMatt Spinler */ 126a307089cSMatt Spinler enum class CalloutType 127a307089cSMatt Spinler { 128a307089cSMatt Spinler i2c, 129a307089cSMatt Spinler fsi, 130a307089cSMatt Spinler fsii2c, 131a307089cSMatt Spinler fsispi, 132a307089cSMatt Spinler unknown 133a307089cSMatt Spinler }; 134a307089cSMatt Spinler 135a307089cSMatt Spinler /** 13618c42b0fSMatt Spinler * @brief Returns the path to the JSON file to look up callouts in. 13718c42b0fSMatt Spinler * 13818c42b0fSMatt Spinler * @param[in] compatibleList - The list of compatible names for this 13918c42b0fSMatt Spinler * system. 14018c42b0fSMatt Spinler * 14118c42b0fSMatt Spinler * @return path - The path to the file. 14218c42b0fSMatt Spinler */ 14318c42b0fSMatt Spinler std::filesystem::path 14418c42b0fSMatt Spinler getJSONFilename(const std::vector<std::string>& compatibleList); 14518c42b0fSMatt Spinler 14618c42b0fSMatt Spinler /** 14718c42b0fSMatt Spinler * @brief Looks up the callouts in the JSON using the I2C keys. 14818c42b0fSMatt Spinler * 14918c42b0fSMatt Spinler * @param[in] i2cBus - The I2C bus 15018c42b0fSMatt Spinler * @param[in] i2cAddress - The I2C address 15118c42b0fSMatt Spinler * @param[in] calloutJSON - The JSON containing the callouts 15218c42b0fSMatt Spinler * 15318c42b0fSMatt Spinler * @return std::vector<Callout> - The callouts 15418c42b0fSMatt Spinler */ 15518c42b0fSMatt Spinler std::vector<device_callouts::Callout> 15618c42b0fSMatt Spinler calloutI2C(size_t i2CBus, uint8_t i2cAddress, 15718c42b0fSMatt Spinler const nlohmann::json& calloutJSON); 158a307089cSMatt Spinler 159a307089cSMatt Spinler /** 160a307089cSMatt Spinler * @brief Determines the type of the path (FSI, I2C, etc) based 161a307089cSMatt Spinler * on tokens in the device path. 162a307089cSMatt Spinler * 163a307089cSMatt Spinler * @param[in] devPath - The device path 164a307089cSMatt Spinler * 165a307089cSMatt Spinler * @return CalloutType - The callout type 166a307089cSMatt Spinler */ 167a307089cSMatt Spinler CalloutType getCalloutType(const std::string& devPath); 168a307089cSMatt Spinler 169*44c0a643SMatt Spinler /** 170*44c0a643SMatt Spinler * @brief Pulls the fields out of the I2C device path to use as search keys 171*44c0a643SMatt Spinler * in the JSON. 172*44c0a643SMatt Spinler * 173*44c0a643SMatt Spinler * The keys are the I2C bus and address. 174*44c0a643SMatt Spinler * 175*44c0a643SMatt Spinler * @param[in] devPath - The device path 176*44c0a643SMatt Spinler * 177*44c0a643SMatt Spinler * @return std::tuple<size_t, uint8_t> - The I2C bus and address keys 178*44c0a643SMatt Spinler */ 179*44c0a643SMatt Spinler std::tuple<size_t, uint8_t> getI2CSearchKeys(const std::string& devPath); 180*44c0a643SMatt Spinler 181*44c0a643SMatt Spinler /** 182*44c0a643SMatt Spinler * @brief Pulls the fields out of the FSI device path to use as search keys 183*44c0a643SMatt Spinler * in the JSON. 184*44c0a643SMatt Spinler * 185*44c0a643SMatt Spinler * The key is the FSI link. For multi-hop paths, the links are 186*44c0a643SMatt Spinler * separated by '-'s, like "0-1-2". 187*44c0a643SMatt Spinler * 188*44c0a643SMatt Spinler * @param[in] devPath - The device path 189*44c0a643SMatt Spinler * 190*44c0a643SMatt Spinler * @return std::string - The FSI links key 191*44c0a643SMatt Spinler */ 192*44c0a643SMatt Spinler std::string getFSISearchKeys(const std::string& devPath); 193*44c0a643SMatt Spinler 194*44c0a643SMatt Spinler /** 195*44c0a643SMatt Spinler * @brief Pulls the fields out of the FSI-I2C device path to use as 196*44c0a643SMatt Spinler * search keys in the JSON. 197*44c0a643SMatt Spinler * 198*44c0a643SMatt Spinler * The keys are the FSI link string and the I2C bus and address. 199*44c0a643SMatt Spinler * 200*44c0a643SMatt Spinler * @param[in] devPath - The device path 201*44c0a643SMatt Spinler * 202*44c0a643SMatt Spinler * @return std::tuple<std::string, std::tuple<size_t, uint8_t>> 203*44c0a643SMatt Spinler * - The FSI links key along with the I2C bus/address. 204*44c0a643SMatt Spinler */ 205*44c0a643SMatt Spinler std::tuple<std::string, std::tuple<size_t, uint8_t>> 206*44c0a643SMatt Spinler getFSII2CSearchKeys(const std::string& devPath); 207*44c0a643SMatt Spinler 208*44c0a643SMatt Spinler /** 209*44c0a643SMatt Spinler * @brief Pulls the fields out of the SPI device path to use as search keys 210*44c0a643SMatt Spinler * in the JSON. 211*44c0a643SMatt Spinler * 212*44c0a643SMatt Spinler * The key is the SPI bus number. 213*44c0a643SMatt Spinler * 214*44c0a643SMatt Spinler * @param[in] devPath - The device path 215*44c0a643SMatt Spinler * 216*44c0a643SMatt Spinler * @return size_t - The SPI bus key 217*44c0a643SMatt Spinler */ 218*44c0a643SMatt Spinler size_t getSPISearchKeys(const std::string& devPath); 219*44c0a643SMatt Spinler 220*44c0a643SMatt Spinler /** 221*44c0a643SMatt Spinler * @brief Pulls the fields out of the FSI-SPI device path to use as 222*44c0a643SMatt Spinler * search keys in the JSON. 223*44c0a643SMatt Spinler * 224*44c0a643SMatt Spinler * The keys are the FSI link string and the SPI bus number. 225*44c0a643SMatt Spinler * 226*44c0a643SMatt Spinler * @param[in] devPath - The device path 227*44c0a643SMatt Spinler * 228*44c0a643SMatt Spinler * @return std::tuple<std::string, size_t> 229*44c0a643SMatt Spinler * - The FSI links key along with the SPI bus number. 230*44c0a643SMatt Spinler */ 231*44c0a643SMatt Spinler std::tuple<std::string, size_t> getFSISPISearchKeys(const std::string& devPath); 232*44c0a643SMatt Spinler 23318c42b0fSMatt Spinler } // namespace util 23418c42b0fSMatt Spinler } // namespace openpower::pels::device_callouts 235