1 /* 2 // Copyright (c) 2018 Intel Corporation 3 // 4 // Licensed under the Apache License, Version 2.0 (the "License"); 5 // you may not use this file except in compliance with the License. 6 // You may obtain a copy of the License at 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unless required by applicable law or agreed to in writing, software 11 // distributed under the License is distributed on an "AS IS" BASIS, 12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 // See the License for the specific language governing permissions and 14 // limitations under the License. 15 */ 16 17 #pragma once 18 #include "channel_layer.hpp" 19 #include "ipmid/api-types.hpp" 20 21 #include <boost/interprocess/sync/file_lock.hpp> 22 #include <boost/interprocess/sync/named_recursive_mutex.hpp> 23 #include <cstdint> 24 #include <ctime> 25 #include <nlohmann/json.hpp> 26 #include <sdbusplus/bus.hpp> 27 #include <variant> 28 29 namespace ipmi 30 { 31 32 using Json = nlohmann::json; 33 34 using DbusVariant = std::variant<std::vector<std::string>, std::string, bool>; 35 36 using DbusChObjProperties = std::vector<std::pair<std::string, DbusVariant>>; 37 38 static constexpr const char* ipmiChannelMutex = "ipmi_channel_mutex"; 39 static constexpr const char* ipmiChMutexCleanupLockFile = 40 "/var/lib/ipmi/ipmi_channel_mutex_cleanup"; 41 42 /** @struct ChannelAccessData 43 * 44 * Structure to store both non-volatile and volatile channel access information 45 * as used by IPMI specification (refer spec sec 22.22 to 22.24) 46 */ 47 struct ChannelAccessData 48 { 49 ChannelAccess chNonVolatileData; 50 ChannelAccess chVolatileData; 51 }; 52 53 /** @struct ChannelProperties 54 * 55 * Structure for channel information - base structure to get all information 56 * about the channel.(refer spec sec 22.22 to 22.24) 57 */ 58 struct ChannelProperties 59 { 60 std::string chName; 61 uint8_t chID; 62 bool isChValid; 63 uint8_t activeSessCount; 64 ChannelInfo chInfo; 65 ChannelAccessData chAccess; 66 size_t maxTransferSize; 67 bool isManagementNIC; 68 }; 69 70 class ChannelConfig; 71 72 ChannelConfig& getChannelConfigObject(); 73 74 class ChannelConfig 75 { 76 public: 77 ChannelConfig(const ChannelConfig&) = delete; 78 ChannelConfig& operator=(const ChannelConfig&) = delete; 79 ChannelConfig(ChannelConfig&&) = delete; 80 ChannelConfig& operator=(ChannelConfig&&) = delete; 81 82 ~ChannelConfig(); 83 ChannelConfig(); 84 85 /** @brief determines valid channel 86 * 87 * @param[in] chNum - channel number 88 * 89 * @return true if valid, false otherwise 90 */ 91 bool isValidChannel(const uint8_t chNum); 92 93 /** @brief determines valid authentication type 94 * 95 * @param[in] chNum - channel number 96 * @param[in] authType - authentication type 97 * 98 * @return true if valid, false otherwise 99 */ 100 bool isValidAuthType(const uint8_t chNum, const EAuthType& authType); 101 102 /** @brief function to get channel name from channel number 103 * 104 * @param[in] chNum - channel number index 105 * 106 * @return network channel interface name 107 */ 108 std::string getChannelName(const uint8_t chNum); 109 110 /** @brief function to get channel number from channel name 111 * 112 * @param[in] chName - channel name 113 * 114 * @return network channel interface number 115 */ 116 117 uint8_t getChannelByName(const std::string& chName) 118 { 119 return convertToChannelNumberFromChannelName(chName); 120 } 121 122 /** @brief determines supported session type of a channel 123 * 124 * @param[in] chNum - channel number 125 * 126 * @return EChannelSessSupported - supported session type 127 */ 128 EChannelSessSupported getChannelSessionSupport(const uint8_t chNum); 129 130 /** @brief determines number of active sessions on a channel 131 * 132 * @param[in] chNum - channel number 133 * 134 * @return numer of active sessions 135 */ 136 int getChannelActiveSessions(const uint8_t chNum); 137 138 /** @brief determines maximum transfer size for a channel 139 * 140 * @param[in] chNum - channel number 141 * 142 * @return maximum bytes that can be transferred on this channel 143 */ 144 size_t getChannelMaxTransferSize(uint8_t chNum); 145 146 /** @brief provides channel info details 147 * 148 * @param[in] chNum - channel number 149 * @param[out] chInfo - channel info details 150 * 151 * @return ccSuccess for success, others for failure. 152 */ 153 Cc getChannelInfo(const uint8_t chNum, ChannelInfo& chInfo); 154 155 /** @brief provides channel access data 156 * 157 * @param[in] chNum - channel number 158 * @param[out] chAccessData - channel access data 159 * 160 * @return ccSuccess for success, others for failure. 161 */ 162 Cc getChannelAccessData(const uint8_t chNum, ChannelAccess& chAccessData); 163 164 /** @brief to set channel access data 165 * 166 * @param[in] chNum - channel number 167 * @param[in] chAccessData - channel access data 168 * @param[in] setFlag - flag to indicate updatable fields 169 * 170 * @return ccSuccess for success, others for failure. 171 */ 172 Cc setChannelAccessData(const uint8_t chNum, 173 const ChannelAccess& chAccessData, 174 const uint8_t setFlag); 175 176 /** @brief to get channel access data persistent data 177 * 178 * @param[in] chNum - channel number 179 * @param[out] chAccessData - channel access data 180 * 181 * @return ccSuccess for success, others for failure. 182 */ 183 Cc getChannelAccessPersistData(const uint8_t chNum, 184 ChannelAccess& chAccessData); 185 186 /** @brief to set channel access data persistent data 187 * 188 * @param[in] chNum - channel number 189 * @param[in] chAccessData - channel access data 190 * @param[in] setFlag - flag to indicate updatable fields 191 * 192 * @return ccSuccess for success, others for failure. 193 */ 194 Cc setChannelAccessPersistData(const uint8_t chNum, 195 const ChannelAccess& chAccessData, 196 const uint8_t setFlag); 197 198 /** @brief provides supported authentication type for the channel 199 * 200 * @param[in] chNum - channel number 201 * @param[out] authTypeSupported - supported authentication type 202 * 203 * @return ccSuccess for success, others for failure. 204 */ 205 Cc getChannelAuthTypeSupported(const uint8_t chNum, 206 uint8_t& authTypeSupported); 207 208 /** @brief provides enabled authentication type for the channel 209 * 210 * @param[in] chNum - channel number 211 * @param[in] priv - privilege 212 * @param[out] authType - enabled authentication type 213 * 214 * @return ccSuccess for success, others for failure. 215 */ 216 Cc getChannelEnabledAuthType(const uint8_t chNum, const uint8_t priv, 217 EAuthType& authType); 218 219 /** @brief conver to channel privilege from system privilege 220 * 221 * @param[in] value - privilege value 222 * 223 * @return Channel privilege 224 */ 225 CommandPrivilege convertToPrivLimitIndex(const std::string& value); 226 227 /** @brief function to write persistent channel configuration to config file 228 * 229 * @return 0 for success, -errno for failure. 230 */ 231 int writeChannelPersistData(); 232 233 /** @brief function to write volatile channel configuration to config file 234 * 235 * @return 0 for success, -errno for failure. 236 */ 237 int writeChannelVolatileData(); 238 239 /** @brief Returns the IPMI channel ID authorized to push IPMI privilege 240 * changes to phosphor-user-manager. Any channel access changes made on 241 * any other channel are ignored. 242 * 243 * @return IPMI channel ID as defined in channel_config.json 244 */ 245 uint8_t getManagementNICID(); 246 247 private: 248 uint32_t signalFlag = 0; 249 std::unique_ptr<boost::interprocess::named_recursive_mutex> channelMutex{ 250 nullptr}; 251 std::array<ChannelProperties, maxIpmiChannels> channelData; 252 std::time_t nvFileLastUpdatedTime; 253 std::time_t voltFileLastUpdatedTime; 254 boost::interprocess::file_lock mutexCleanupLock; 255 sdbusplus::bus::bus bus; 256 bool signalHndlrObjectState = false; 257 boost::interprocess::file_lock sigHndlrLock; 258 259 /** @brief function to initialize persistent channel configuration 260 * 261 */ 262 void initChannelPersistData(); 263 264 /** @brief function to set default channel configuration based on channel 265 * number 266 * 267 * @param[in] chNum - channel number 268 * @param[in] chName - channel name 269 */ 270 void setDefaultChannelConfig(const uint8_t chNum, 271 const std::string& chName); 272 273 /** @brief function to load all channel configuration 274 * 275 * @return 0 for success, -errno for failure. 276 */ 277 int loadChannelConfig(); 278 279 /** @brief function to read persistent channel data 280 * 281 * @return 0 for success, -errno for failure. 282 */ 283 int readChannelPersistData(); 284 285 /** @brief function to read volatile channel data 286 * 287 * @return 0 for success, -errno for failure. 288 */ 289 int readChannelVolatileData(); 290 291 /** @brief function to check and reload persistent channel data 292 * 293 * @return 0 for success, -errno for failure. 294 */ 295 int checkAndReloadNVData(); 296 297 /** @brief function to check and reload volatile channel data 298 * 299 * @return 0 for success, -errno for failure. 300 */ 301 int checkAndReloadVolatileData(); 302 303 /** @brief function to sync channel privilege with system network channel 304 * privilege 305 * 306 * @return 0 for success, -errno for failure. 307 */ 308 int syncNetworkChannelConfig(); 309 310 /** @brief function to set D-Bus property value 311 * 312 * @param[in] service - service name 313 * @param[in] objPath - object path 314 * @param[in] interface - interface 315 * @param[in] property - property name 316 * @param[in] value - property value 317 * 318 * @return 0 for success, -errno for failure. 319 */ 320 int setDbusProperty(const std::string& service, const std::string& objPath, 321 const std::string& interface, 322 const std::string& property, const DbusVariant& value); 323 324 /** @brief function to get D-Bus property value 325 * 326 * @param[in] service - service name 327 * @param[in] objPath - object path 328 * @param[in] interface - interface 329 * @param[in] property - property name 330 * @param[out] value - property value 331 * 332 * @return 0 for success, -errno for failure. 333 */ 334 int getDbusProperty(const std::string& service, const std::string& objPath, 335 const std::string& interface, 336 const std::string& property, DbusVariant& value); 337 338 /** @brief function to read json config file 339 * 340 * @param[in] configFile - configuration file name 341 * 342 * @return Json object 343 */ 344 Json readJsonFile(const std::string& configFile); 345 346 /** @brief function to write json config file 347 * 348 * @param[in] configFile - configuration file name 349 * @param[in] jsonData - json object 350 * 351 * @return 0 for success, -errno for failure. 352 */ 353 int writeJsonFile(const std::string& configFile, const Json& jsonData); 354 355 /** @brief function to convert system access mode to Channel access mode 356 * type 357 * 358 * @param[in] mode - access mode in string 359 * 360 * @return Channel access mode. 361 */ 362 EChannelAccessMode convertToAccessModeIndex(const std::string& mode); 363 364 /** @brief function to convert access mode value to string 365 * 366 * @param[in] value - acess mode value 367 * 368 * @return access mode in string 369 */ 370 std::string convertToAccessModeString(const uint8_t value); 371 372 /** @brief function to convert privilege value to string 373 * 374 * @param[in] value - privilege value 375 * 376 * @return privilege in string 377 */ 378 std::string convertToPrivLimitString(const uint8_t value); 379 380 /** @brief function to convert session support string to value type 381 * 382 * @param[in] value - session support type in string 383 * 384 * @return support session type 385 */ 386 EChannelSessSupported 387 convertToSessionSupportIndex(const std::string& value); 388 389 /** @brief function to convert medium type string to value type 390 * 391 * @param[in] value - medium type in string 392 * 393 * @return channel medium type 394 */ 395 EChannelMediumType convertToMediumTypeIndex(const std::string& value); 396 397 /** @brief function to convert protocol type string to value type 398 * 399 * @param[in] value - protocol type in string 400 * 401 * @return channel protocol type 402 */ 403 EChannelProtocolType convertToProtocolTypeIndex(const std::string& value); 404 405 /** @brief function to convert channel name to the IPMI channel number. 406 * 407 * @param[in] chName - the channel name defined in the JSON input file 408 * (i.e. LAN1) 409 * 410 * @return IPMI channel number 411 */ 412 int convertToChannelNumberFromChannelName(const std::string& chName); 413 414 /** @brief function to handle Channel access property update through the 415 * D-Bus handler. 416 * 417 * @param[in] path - D-Bus path to the network element (i.e. eth0) 418 * @param[in] chProperties - D-Bus channel properties 419 */ 420 void processChAccessPropChange(const std::string& path, 421 const DbusChObjProperties& chProperties); 422 423 /** @brief function to retrieve last modification time for the named file 424 * 425 * @param[in] fileName - the name of the file for which to acquire 426 * timestamp data 427 * 428 * @return time the file was last modified 429 */ 430 std::time_t getUpdatedFileTime(const std::string& fileName); 431 432 /** @brief function to convert the DBus path to a network channel name 433 * 434 * @param[in] path - The DBus path to the device 435 * 436 * @return network channel name (i.e. eth0) 437 */ 438 std::string getChannelNameFromPath(const std::string& path); 439 }; 440 441 } // namespace ipmi 442