xref: /openbmc/openpower-vpd-parser/ibm_vpd_utils.hpp (revision a0b2391a6ea9b152105a346918cd1c74e17857e4)
1 #pragma once
2 
3 #include "const.hpp"
4 #include "store.hpp"
5 #include "types.hpp"
6 
7 #include <iostream>
8 
9 using namespace std;
10 
11 namespace openpower
12 {
13 namespace vpd
14 {
15 
16 /** @brief Return the hex representation of the incoming byte
17  *
18  * @param [in] c - The input byte
19  * @returns The hex representation of the byte as a character.
20  */
21 constexpr auto toHex(size_t c)
22 {
23     constexpr auto map = "0123456789abcdef";
24     return map[c];
25 }
26 
27 namespace inventory
28 {
29 /** @brief API to obtain a dictionary of path -> services
30  * where path is in subtree and services is of the type
31  * returned by the GetObject method.
32  *
33  * @param [in] root - Root path for object subtree
34  * @param [in] depth - Maximum subtree depth required
35  * @param [in] interfaces - Array to interfaces for which
36  * result is required.
37  * @return A dictionary of Path -> services
38  */
39 MapperResponse
40     getObjectSubtreeForInterfaces(const std::string& root, const int32_t depth,
41                                   const std::vector<std::string>& interfaces);
42 
43 } // namespace inventory
44 
45 /**@brief This API reads 2 Bytes of data and swap the read data
46  * @param[in] iterator- Pointer pointing to the data to be read
47  * @return returns 2 Byte data read at the given pointer
48  */
49 openpower::vpd::constants::LE2ByteData
50     readUInt16LE(Binary::const_iterator iterator);
51 
52 /** @brief Encodes a keyword for D-Bus.
53  *  @param[in] kw - kwd data in string format
54  *  @param[in] encoding - required for kwd data
55  */
56 string encodeKeyword(const string& kw, const string& encoding);
57 
58 /** @brief Reads a property from the inventory manager given object path,
59  *         intreface and property.
60  *  @param[in] obj - object path
61  *  @param[in] inf - interface
62  *  @param[in] prop - property whose value is fetched
63  *  @return [out] - value of the property
64  */
65 string readBusProperty(const string& obj, const string& inf,
66                        const string& prop);
67 
68 /**
69  * @brief API to create PEL entry
70  * @param[in] additionalData - Map holding the additional data
71  * @param[in] sev - Severity
72  * @param[in] errIntf - error interface
73  */
74 void createPEL(const std::map<std::string, std::string>& additionalData,
75                const constants::PelSeverity& sev, const std::string& errIntf);
76 
77 /**
78  * @brief getVpdFilePath
79  * Get vpd file path corresponding to the given object path.
80  * @param[in] - json file path
81  * @param[in] - Object path
82  * @return - Vpd file path
83  */
84 inventory::VPDfilepath getVpdFilePath(const string& jsonFile,
85                                       const std::string& ObjPath);
86 
87 /**
88  * @brief isPathInJson
89  * API which checks for the presence of the given eeprom path in the given json.
90  * @param[in] - eepromPath
91  * @return - true if the eeprom is present in the json; false otherwise
92  */
93 bool isPathInJson(const std::string& eepromPath);
94 
95 /**
96  * @brief isRecKwInDbusJson
97  * API which checks whether the given keyword under the given record is to be
98  * published on dbus or not. Checks against the keywords present in
99  * dbus_property.json.
100  * @param[in] - record name
101  * @param[in] - keyword name
102  * @return - true if the record-keyword pair is present in dbus_property.json;
103  * false otherwise.
104  */
105 bool isRecKwInDbusJson(const std::string& record, const std::string& keyword);
106 
107 /**
108  * @brief Check the type of VPD.
109  *
110  * Checks the type of vpd based on the start tag.
111  * @param[in] vector - Vpd data in vector format
112  *
113  * @return enum of type vpdType
114  */
115 constants::vpdType vpdTypeCheck(const Binary& vector);
116 
117 /*
118  * @brief This method does nothing. Just an empty function to return null
119  * at the end of variadic template args
120  */
121 inline string getCommand()
122 {
123     return "";
124 }
125 
126 /**
127  * @brief This function to arrange all arguments to make commandy
128  * @param[in] arguments to create the command
129  * @return cmd - command string
130  */
131 template <typename T, typename... Types>
132 inline string getCommand(T arg1, Types... args)
133 {
134     string cmd = " " + arg1 + getCommand(args...);
135 
136     return cmd;
137 }
138 
139 /**
140  * @brief This API takes arguments, creates a shell command line and executes
141  * them.
142  * @param[in] arguments for command
143  * @returns output of that command
144  */
145 template <typename T, typename... Types>
146 inline vector<string> executeCmd(T&& path, Types... args)
147 {
148     vector<string> stdOutput;
149     array<char, 128> buffer;
150 
151     string cmd = path + getCommand(args...);
152 
153     unique_ptr<FILE, decltype(&pclose)> pipe(popen(cmd.c_str(), "r"), pclose);
154     if (!pipe)
155     {
156         throw runtime_error("popen() failed!");
157     }
158     while (fgets(buffer.data(), buffer.size(), pipe.get()) != nullptr)
159     {
160         stdOutput.emplace_back(buffer.data());
161     }
162 
163     return stdOutput;
164 }
165 
166 /** @brief This API checks for IM and HW keywords, and based
167  *         on these values decides which system json to be used.
168  *  @param[in] vpdMap -  parsed vpd
169  *  @returns System json path
170  */
171 string getSystemsJson(const Parsed& vpdMap);
172 
173 /** @brief Reads HW Keyword from the vpd
174  *  @param[in] vpdMap -  parsed vpd
175  *  @returns value of HW Keyword
176  */
177 const string getHW(const Parsed& vpdMap);
178 
179 /** @brief Reads IM Keyword from the vpd
180  *  @param[in] vpdMap -  parsed vpd
181  *  @returns value of IM Keyword
182  */
183 const string getIM(const Parsed& vpdMap);
184 
185 /** @brief Translate udev event generated path to a generic /sys/bus eeprom path
186  *  @param[io] file - path generated from udev event.
187  */
188 void udevToGenericPath(string& file);
189 
190 /**
191  * @brief API to generate a vpd name in some pattern.
192  * This vpd-name denotes name of the bad vpd file.
193  * For i2c eeproms - the pattern of the vpd-name will be
194  * i2c-<bus-number>-<eeprom-address>. For spi eeproms - the pattern of the
195  * vpd-name will be spi-<spi-number>.
196  *
197  * @param[in] file - file path of the vpd
198  * @return the vpd-name.
199  */
200 string getBadVpdName(const string& file);
201 
202 /**
203  * @brief API which dumps the broken/bad vpd in a directory
204  * When the vpd is bad, this api places  the bad vpd file inside
205  * "/tmp/bad-vpd" in BMC, in order to collect bad VPD data as a part of user
206  * initiated BMC dump.
207  *
208  * @param[in] file - bad vpd file path
209  * @param[in] vpdVector - bad vpd vector
210  */
211 void dumpBadVpd(const std::string& file, const Binary& vpdVector);
212 
213 /*
214  * @brief This function fetches the value for given keyword in the given record
215  *        from vpd data and returns this value.
216  *
217  * @param[in] vpdMap - vpd to find out the data
218  * @param[in] rec - Record under which desired keyword exists
219  * @param[in] kwd - keyword to read the data from
220  *
221  * @returns keyword value if record/keyword combination found
222  *          empty string if record or keyword is not found.
223  */
224 const string getKwVal(const Parsed& vpdMap, const string& rec,
225                       const string& kwd);
226 
227 /** @brief This creates a complete command using all it's input parameters,
228  *         to bind or unbind the driver.
229  *  @param[in] devNameAddr - device address on that bus
230  *  @param[in] busType - i2c, spi
231  *  @param[in] driverType - type of driver like at24
232  *  @param[in] bindOrUnbind - either bind or unbind
233  *  @returns  Command to bind or unbind the driver.
234  */
235 inline string createBindUnbindDriverCmnd(const string& devNameAddr,
236                                          const string& busType,
237                                          const string& driverType,
238                                          const string& bindOrUnbind)
239 {
240     return ("echo " + devNameAddr + " > /sys/bus/" + busType + "/drivers/" +
241             driverType + "/" + bindOrUnbind);
242 }
243 
244 /**
245  * @brief Get Printable Value
246  *
247  * Checks if the vector value has non printable characters.
248  * Returns hex value if non printable char is found else
249  * returns ascii value.
250  *
251  * @param[in] vector - Reference of the Binary vector
252  * @return printable value - either in hex or in ascii.
253  */
254 string getPrintableValue(const Binary& vec);
255 
256 /**
257  * @brief Convert byte array to hex string.
258  * @param[in] vec - byte array
259  * @return hexadecimal string of bytes.
260  */
261 string byteArrayToHexString(const Binary& vec);
262 
263 } // namespace vpd
264 } // namespace openpower