blob: aa746fd3de9ff8b8c0d70c0530836ad51951baf9 [file] [log] [blame]
AppaRao Puli071f3f22018-05-24 16:45:30 +05301/*
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#include "channel_mgmt.hpp"
18
19#include "apphandler.hpp"
Johnathan Manteyfd61fc32021-04-08 11:05:38 -070020#include "user_layer.hpp"
AppaRao Puli071f3f22018-05-24 16:45:30 +053021
Johnathan Mantey0a2abc82021-02-18 12:39:12 -080022#include <ifaddrs.h>
AppaRao Puli071f3f22018-05-24 16:45:30 +053023#include <sys/stat.h>
Johnathan Mantey0a2abc82021-02-18 12:39:12 -080024#include <sys/types.h>
AppaRao Puli071f3f22018-05-24 16:45:30 +053025#include <unistd.h>
26
27#include <boost/interprocess/sync/scoped_lock.hpp>
28#include <cerrno>
AppaRao Puli9613ed72018-09-01 23:46:44 +053029#include <exception>
AppaRao Puli071f3f22018-05-24 16:45:30 +053030#include <experimental/filesystem>
31#include <fstream>
32#include <phosphor-logging/log.hpp>
AppaRao Puli9613ed72018-09-01 23:46:44 +053033#include <sdbusplus/bus/match.hpp>
34#include <sdbusplus/server/object.hpp>
AppaRao Puli071f3f22018-05-24 16:45:30 +053035#include <unordered_map>
36
37namespace ipmi
38{
39
40using namespace phosphor::logging;
41
42static constexpr const char* channelAccessDefaultFilename =
43 "/usr/share/ipmi-providers/channel_access.json";
44static constexpr const char* channelConfigDefaultFilename =
45 "/usr/share/ipmi-providers/channel_config.json";
46static constexpr const char* channelNvDataFilename =
47 "/var/lib/ipmi/channel_access_nv.json";
48static constexpr const char* channelVolatileDataFilename =
49 "/run/ipmi/channel_access_volatile.json";
50
AppaRao Puli9613ed72018-09-01 23:46:44 +053051// TODO: Get the service name dynamically..
52static constexpr const char* networkIntfServiceName =
53 "xyz.openbmc_project.Network";
54static constexpr const char* networkIntfObjectBasePath =
55 "/xyz/openbmc_project/network";
56static constexpr const char* networkChConfigIntfName =
57 "xyz.openbmc_project.Channel.ChannelAccess";
58static constexpr const char* privilegePropertyString = "MaxPrivilege";
59static constexpr const char* dBusPropertiesInterface =
60 "org.freedesktop.DBus.Properties";
61static constexpr const char* propertiesChangedSignal = "PropertiesChanged";
Willy Tuac05aa12021-11-16 21:15:58 -080062static constexpr const char* interfaceAddedSignal = "InterfacesAdded";
63static constexpr const char* interfaceRemovedSignal = "InterfacesRemoved";
AppaRao Puli9613ed72018-09-01 23:46:44 +053064
AppaRao Puli071f3f22018-05-24 16:45:30 +053065// STRING DEFINES: Should sync with key's in JSON
66static constexpr const char* nameString = "name";
67static constexpr const char* isValidString = "is_valid";
68static constexpr const char* activeSessionsString = "active_sessions";
Vernon Mauery58317122018-11-28 11:02:43 -080069static constexpr const char* maxTransferSizeString = "max_transfer_size";
AppaRao Puli071f3f22018-05-24 16:45:30 +053070static constexpr const char* channelInfoString = "channel_info";
71static constexpr const char* mediumTypeString = "medium_type";
72static constexpr const char* protocolTypeString = "protocol_type";
73static constexpr const char* sessionSupportedString = "session_supported";
74static constexpr const char* isIpmiString = "is_ipmi";
Johnathan Manteyfd61fc32021-04-08 11:05:38 -070075static constexpr const char* isManagementNIC = "is_management_nic";
AppaRao Puli071f3f22018-05-24 16:45:30 +053076static constexpr const char* authTypeSupportedString = "auth_type_supported";
77static constexpr const char* accessModeString = "access_mode";
78static constexpr const char* userAuthDisabledString = "user_auth_disabled";
79static constexpr const char* perMsgAuthDisabledString = "per_msg_auth_disabled";
80static constexpr const char* alertingDisabledString = "alerting_disabled";
81static constexpr const char* privLimitString = "priv_limit";
82static constexpr const char* authTypeEnabledString = "auth_type_enabled";
83
84// Default values
85static constexpr const char* defaultChannelName = "RESERVED";
86static constexpr const uint8_t defaultMediumType =
87 static_cast<uint8_t>(EChannelMediumType::reserved);
88static constexpr const uint8_t defaultProtocolType =
89 static_cast<uint8_t>(EChannelProtocolType::reserved);
90static constexpr const uint8_t defaultSessionSupported =
91 static_cast<uint8_t>(EChannelSessSupported::none);
92static constexpr const uint8_t defaultAuthType =
93 static_cast<uint8_t>(EAuthType::none);
94static constexpr const bool defaultIsIpmiState = false;
Vernon Mauery58317122018-11-28 11:02:43 -080095static constexpr size_t smallChannelSize = 64;
AppaRao Puli071f3f22018-05-24 16:45:30 +053096
Lei YU4b0ddb62019-01-25 16:43:50 +080097std::unique_ptr<sdbusplus::bus::match_t> chPropertiesSignal
98 __attribute__((init_priority(101)));
AppaRao Puli9613ed72018-09-01 23:46:44 +053099
Willy Tuac05aa12021-11-16 21:15:58 -0800100std::unique_ptr<sdbusplus::bus::match_t> chInterfaceAddedSignal
101 __attribute__((init_priority(101)));
102
103std::unique_ptr<sdbusplus::bus::match_t> chInterfaceRemovedSignal
104 __attribute__((init_priority(101)));
105
AppaRao Puli071f3f22018-05-24 16:45:30 +0530106// String mappings use in JSON config file
107static std::unordered_map<std::string, EChannelMediumType> mediumTypeMap = {
108 {"reserved", EChannelMediumType::reserved},
109 {"ipmb", EChannelMediumType::ipmb},
110 {"icmb-v1.0", EChannelMediumType::icmbV10},
111 {"icmb-v0.9", EChannelMediumType::icmbV09},
112 {"lan-802.3", EChannelMediumType::lan8032},
113 {"serial", EChannelMediumType::serial},
114 {"other-lan", EChannelMediumType::otherLan},
115 {"pci-smbus", EChannelMediumType::pciSmbus},
116 {"smbus-v1.0", EChannelMediumType::smbusV11},
117 {"smbus-v2.0", EChannelMediumType::smbusV20},
118 {"usb-1x", EChannelMediumType::usbV1x},
119 {"usb-2x", EChannelMediumType::usbV2x},
120 {"system-interface", EChannelMediumType::systemInterface},
121 {"oem", EChannelMediumType::oem},
122 {"unknown", EChannelMediumType::unknown}};
123
ssekarf4b2b092018-07-25 18:49:08 +0530124static std::unordered_map<EInterfaceIndex, std::string> interfaceMap = {
Richard Marian Thomaiyar43cb1282018-12-08 17:22:53 +0530125 {interfaceKCS, "SMS"},
Richard Marian Thomaiyar73906b92019-01-04 23:48:02 +0530126 {interfaceLAN1, "eth0"},
ssekarf4b2b092018-07-25 18:49:08 +0530127 {interfaceUnknown, "unknown"}};
128
AppaRao Puli071f3f22018-05-24 16:45:30 +0530129static std::unordered_map<std::string, EChannelProtocolType> protocolTypeMap = {
130 {"na", EChannelProtocolType::na},
131 {"ipmb-1.0", EChannelProtocolType::ipmbV10},
132 {"icmb-2.0", EChannelProtocolType::icmbV11},
133 {"reserved", EChannelProtocolType::reserved},
134 {"ipmi-smbus", EChannelProtocolType::ipmiSmbus},
135 {"kcs", EChannelProtocolType::kcs},
136 {"smic", EChannelProtocolType::smic},
137 {"bt-10", EChannelProtocolType::bt10},
138 {"bt-15", EChannelProtocolType::bt15},
139 {"tmode", EChannelProtocolType::tMode},
140 {"oem", EChannelProtocolType::oem}};
141
142static std::array<std::string, 4> accessModeList = {
143 "disabled", "pre-boot", "always_available", "shared"};
144
145static std::array<std::string, 4> sessionSupportList = {
146 "session-less", "single-session", "multi-session", "session-based"};
147
Sumanth Bhate4e633e2019-05-14 12:13:57 +0000148const std::array<std::string, PRIVILEGE_OEM + 1> privList = {
AppaRao Puli071f3f22018-05-24 16:45:30 +0530149 "priv-reserved", "priv-callback", "priv-user",
150 "priv-operator", "priv-admin", "priv-oem"};
151
Richard Marian Thomaiyar55768e32019-03-02 22:54:37 +0530152std::string ChannelConfig::getChannelName(const uint8_t chNum)
Johnathan Mantey74a21022018-12-13 13:17:56 -0800153{
154 if (!isValidChannel(chNum))
155 {
156 log<level::ERR>("Invalid channel number.",
Richard Marian Thomaiyar619ed5f2020-01-17 12:17:47 +0530157 entry("CHANNEL_ID=%d", chNum));
Johnathan Mantey74a21022018-12-13 13:17:56 -0800158 throw std::invalid_argument("Invalid channel number");
159 }
160
161 return channelData[chNum].chName;
162}
163
164int ChannelConfig::convertToChannelNumberFromChannelName(
165 const std::string& chName)
166{
167 for (const auto& it : channelData)
168 {
169 if (it.chName == chName)
170 {
171 return it.chID;
172 }
173 }
174 log<level::ERR>("Invalid channel name.",
Richard Marian Thomaiyar619ed5f2020-01-17 12:17:47 +0530175 entry("CHANNEL=%s", chName.c_str()));
Johnathan Mantey74a21022018-12-13 13:17:56 -0800176 throw std::invalid_argument("Invalid channel name");
177
178 return -1;
179}
180
181std::string ChannelConfig::getChannelNameFromPath(const std::string& path)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530182{
Richard Marian Thomaiyarbbbc3952020-01-17 12:13:28 +0530183
184 constexpr size_t length = strlen(networkIntfObjectBasePath);
185 if (((length + 1) >= path.size()) ||
186 path.compare(0, length, networkIntfObjectBasePath))
AppaRao Puli9613ed72018-09-01 23:46:44 +0530187 {
Richard Marian Thomaiyarbbbc3952020-01-17 12:13:28 +0530188 log<level::ERR>("Invalid object path.", entry("PATH=%s", path.c_str()));
189 throw std::invalid_argument("Invalid object path");
AppaRao Puli9613ed72018-09-01 23:46:44 +0530190 }
Richard Marian Thomaiyarbbbc3952020-01-17 12:13:28 +0530191 std::string chName(path, length + 1);
Johnathan Mantey74a21022018-12-13 13:17:56 -0800192 return chName;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530193}
194
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800195void ChannelConfig::processChAccessPropChange(
196 const std::string& path, const DbusChObjProperties& chProperties)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530197{
198 // Get interface name from path. ex: '/xyz/openbmc_project/network/eth0'
Johnathan Mantey74a21022018-12-13 13:17:56 -0800199 std::string chName;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530200 try
201 {
Johnathan Mantey74a21022018-12-13 13:17:56 -0800202 chName = getChannelNameFromPath(path);
AppaRao Puli9613ed72018-09-01 23:46:44 +0530203 }
204 catch (const std::invalid_argument& e)
205 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530206 log<level::ERR>("Exception: ", entry("MSG=%s", e.what()));
AppaRao Puli9613ed72018-09-01 23:46:44 +0530207 return;
208 }
209
210 // Get the MaxPrivilege property value from the signal
211 std::string intfPrivStr;
212 std::string propName;
213 for (const auto& prop : chProperties)
214 {
215 if (prop.first == privilegePropertyString)
216 {
217 propName = privilegePropertyString;
Vernon Maueryf442e112019-04-09 11:44:36 -0700218 intfPrivStr = std::get<std::string>(prop.second);
AppaRao Puli9613ed72018-09-01 23:46:44 +0530219 break;
220 }
221 }
222
223 if (propName != privilegePropertyString)
224 {
225 log<level::ERR>("Unknown signal caught.");
226 return;
227 }
228
229 if (intfPrivStr.empty())
230 {
231 log<level::ERR>("Invalid privilege string.",
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530232 entry("INTF=%s", chName.c_str()));
AppaRao Puli9613ed72018-09-01 23:46:44 +0530233 return;
234 }
235
236 uint8_t intfPriv = 0;
Johnathan Mantey74a21022018-12-13 13:17:56 -0800237 int chNum;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530238 try
239 {
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800240 intfPriv = static_cast<uint8_t>(convertToPrivLimitIndex(intfPrivStr));
Johnathan Mantey74a21022018-12-13 13:17:56 -0800241 chNum = convertToChannelNumberFromChannelName(chName);
AppaRao Puli9613ed72018-09-01 23:46:44 +0530242 }
243 catch (const std::invalid_argument& e)
244 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530245 log<level::ERR>("Exception: ", entry("MSG=%s", e.what()));
AppaRao Puli9613ed72018-09-01 23:46:44 +0530246 return;
247 }
248
249 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800250 channelLock{*channelMutex};
AppaRao Puli9613ed72018-09-01 23:46:44 +0530251 // skip updating the values, if this property change originated from IPMI.
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800252 if (signalFlag & (1 << chNum))
AppaRao Puli9613ed72018-09-01 23:46:44 +0530253 {
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800254 signalFlag &= ~(1 << chNum);
AppaRao Puli9613ed72018-09-01 23:46:44 +0530255 log<level::DEBUG>("Request originated from IPMI so ignoring signal");
256 return;
257 }
258
259 // Update both volatile & Non-volatile, if there is mismatch.
260 // as property change other than IPMI, has to update both volatile &
261 // non-volatile data.
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800262 checkAndReloadVolatileData();
263 checkAndReloadNVData();
264 if (channelData[chNum].chAccess.chNonVolatileData.privLimit != intfPriv)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530265 {
266 // Update NV data
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800267 channelData[chNum].chAccess.chNonVolatileData.privLimit = intfPriv;
268 if (writeChannelPersistData() != 0)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530269 {
270 log<level::ERR>("Failed to update the persist data file");
271 return;
272 }
273
274 // Update Volatile data
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800275 if (channelData[chNum].chAccess.chVolatileData.privLimit != intfPriv)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530276 {
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800277 channelData[chNum].chAccess.chVolatileData.privLimit = intfPriv;
278 if (writeChannelVolatileData() != 0)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530279 {
280 log<level::ERR>("Failed to update the volatile data file");
281 return;
282 }
283 }
284 }
285
286 return;
287}
288
AppaRao Puli071f3f22018-05-24 16:45:30 +0530289ChannelConfig& getChannelConfigObject()
290{
291 static ChannelConfig channelConfig;
292 return channelConfig;
293}
294
AppaRao Puli9613ed72018-09-01 23:46:44 +0530295ChannelConfig::~ChannelConfig()
296{
297 if (signalHndlrObjectState)
298 {
299 chPropertiesSignal.reset();
Willy Tuac05aa12021-11-16 21:15:58 -0800300 chInterfaceAddedSignal.reset();
301 chInterfaceRemovedSignal.reset();
AppaRao Puli9613ed72018-09-01 23:46:44 +0530302 sigHndlrLock.unlock();
303 }
304}
305
AppaRao Puli071f3f22018-05-24 16:45:30 +0530306ChannelConfig::ChannelConfig() : bus(ipmid_get_sd_bus_connection())
307{
308 std::ofstream mutexCleanUpFile;
309 mutexCleanUpFile.open(ipmiChMutexCleanupLockFile,
310 std::ofstream::out | std::ofstream::app);
311 if (!mutexCleanUpFile.good())
312 {
313 log<level::DEBUG>("Unable to open mutex cleanup file");
314 return;
315 }
316 mutexCleanUpFile.close();
317 mutexCleanupLock =
318 boost::interprocess::file_lock(ipmiChMutexCleanupLockFile);
319 if (mutexCleanupLock.try_lock())
320 {
321 boost::interprocess::named_recursive_mutex::remove(ipmiChannelMutex);
322 channelMutex =
323 std::make_unique<boost::interprocess::named_recursive_mutex>(
324 boost::interprocess::open_or_create, ipmiChannelMutex);
325 mutexCleanupLock.lock_sharable();
326 }
327 else
328 {
329 mutexCleanupLock.lock_sharable();
330 channelMutex =
331 std::make_unique<boost::interprocess::named_recursive_mutex>(
332 boost::interprocess::open_or_create, ipmiChannelMutex);
333 }
334
335 initChannelPersistData();
AppaRao Puli9613ed72018-09-01 23:46:44 +0530336
337 sigHndlrLock = boost::interprocess::file_lock(channelNvDataFilename);
338 // Register it for single object and single process either netipimd /
339 // host-ipmid
340 if (chPropertiesSignal == nullptr && sigHndlrLock.try_lock())
341 {
342 log<level::DEBUG>("Registering channel signal handler.");
343 chPropertiesSignal = std::make_unique<sdbusplus::bus::match_t>(
344 bus,
345 sdbusplus::bus::match::rules::path_namespace(
346 networkIntfObjectBasePath) +
347 sdbusplus::bus::match::rules::type::signal() +
348 sdbusplus::bus::match::rules::member(propertiesChangedSignal) +
349 sdbusplus::bus::match::rules::interface(
350 dBusPropertiesInterface) +
351 sdbusplus::bus::match::rules::argN(0, networkChConfigIntfName),
352 [&](sdbusplus::message::message& msg) {
353 DbusChObjProperties props;
354 std::string iface;
355 std::string path = msg.get_path();
356 msg.read(iface, props);
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800357 processChAccessPropChange(path, props);
AppaRao Puli9613ed72018-09-01 23:46:44 +0530358 });
359 signalHndlrObjectState = true;
Willy Tuac05aa12021-11-16 21:15:58 -0800360
361 chInterfaceAddedSignal = std::make_unique<sdbusplus::bus::match_t>(
362 bus,
363 sdbusplus::bus::match::rules::type::signal() +
364 sdbusplus::bus::match::rules::member(interfaceAddedSignal) +
365 sdbusplus::bus::match::rules::argNpath(
366 0, std::string(networkIntfObjectBasePath) + "/"),
Arun P. Mohanane39ba992021-12-14 14:15:07 +0530367 [&](sdbusplus::message::message& msg) {
368 initChannelPersistData();
369 });
Willy Tuac05aa12021-11-16 21:15:58 -0800370
371 chInterfaceRemovedSignal = std::make_unique<sdbusplus::bus::match_t>(
372 bus,
373 sdbusplus::bus::match::rules::type::signal() +
374 sdbusplus::bus::match::rules::member(interfaceRemovedSignal) +
375 sdbusplus::bus::match::rules::argNpath(
376 0, std::string(networkIntfObjectBasePath) + "/"),
Arun P. Mohanane39ba992021-12-14 14:15:07 +0530377 [&](sdbusplus::message::message& msg) {
378 initChannelPersistData();
379 });
AppaRao Puli9613ed72018-09-01 23:46:44 +0530380 }
381}
382
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530383bool ChannelConfig::isValidChannel(const uint8_t chNum)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530384{
Meera-Kattac1789482021-05-18 09:53:26 +0000385 if (chNum >= maxIpmiChannels)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530386 {
387 log<level::DEBUG>("Invalid channel ID - Out of range");
388 return false;
389 }
390
391 if (channelData[chNum].isChValid == false)
392 {
393 log<level::DEBUG>("Channel is not valid");
AppaRao Puli071f3f22018-05-24 16:45:30 +0530394 }
395
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800396 return channelData[chNum].isChValid;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530397}
398
399EChannelSessSupported
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530400 ChannelConfig::getChannelSessionSupport(const uint8_t chNum)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530401{
402 EChannelSessSupported chSessSupport =
403 (EChannelSessSupported)channelData[chNum].chInfo.sessionSupported;
404 return chSessSupport;
405}
406
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530407bool ChannelConfig::isValidAuthType(const uint8_t chNum,
AppaRao Puli071f3f22018-05-24 16:45:30 +0530408 const EAuthType& authType)
409{
410 if ((authType < EAuthType::md2) || (authType > EAuthType::oem))
411 {
412 log<level::DEBUG>("Invalid authentication type");
413 return false;
414 }
415
416 uint8_t authTypeSupported = channelData[chNum].chInfo.authTypeSupported;
417 if (!(authTypeSupported & (1 << static_cast<uint8_t>(authType))))
418 {
419 log<level::DEBUG>("Authentication type is not supported.");
420 return false;
421 }
422
423 return true;
424}
425
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530426int ChannelConfig::getChannelActiveSessions(const uint8_t chNum)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530427{
428 // TODO: TEMPORARY FIX
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800429 // Channels active session count is managed separately
AppaRao Puli071f3f22018-05-24 16:45:30 +0530430 // by monitoring channel session which includes LAN and
431 // RAKP layer changes. This will be updated, once the
432 // authentication part is implemented.
433 return channelData[chNum].activeSessCount;
434}
435
Vernon Mauery58317122018-11-28 11:02:43 -0800436size_t ChannelConfig::getChannelMaxTransferSize(uint8_t chNum)
437{
438 return channelData[chNum].maxTransferSize;
439}
440
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000441Cc ChannelConfig::getChannelInfo(const uint8_t chNum, ChannelInfo& chInfo)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530442{
443 if (!isValidChannel(chNum))
444 {
445 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000446 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530447 }
448
449 std::copy_n(reinterpret_cast<uint8_t*>(&channelData[chNum].chInfo),
450 sizeof(channelData[chNum].chInfo),
451 reinterpret_cast<uint8_t*>(&chInfo));
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000452 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530453}
454
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000455Cc ChannelConfig::getChannelAccessData(const uint8_t chNum,
456 ChannelAccess& chAccessData)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530457{
458 if (!isValidChannel(chNum))
459 {
460 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000461 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530462 }
463
464 if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
465 {
466 log<level::DEBUG>("Session-less channel doesn't have access data.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000467 return ccActionNotSupportedForChannel;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530468 }
469
470 if (checkAndReloadVolatileData() != 0)
471 {
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000472 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530473 }
474
475 std::copy_n(
476 reinterpret_cast<uint8_t*>(&channelData[chNum].chAccess.chVolatileData),
477 sizeof(channelData[chNum].chAccess.chVolatileData),
478 reinterpret_cast<uint8_t*>(&chAccessData));
479
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000480 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530481}
482
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000483Cc ChannelConfig::setChannelAccessData(const uint8_t chNum,
484 const ChannelAccess& chAccessData,
485 const uint8_t setFlag)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530486{
487 if (!isValidChannel(chNum))
488 {
489 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000490 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530491 }
492
493 if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
494 {
495 log<level::DEBUG>("Session-less channel doesn't have access data.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000496 return ccActionNotSupportedForChannel;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530497 }
498
jayaprakash Mutyala0e2dbee2019-12-26 13:03:04 +0000499 if ((setFlag & setAccessMode) &&
500 (!isValidAccessMode(chAccessData.accessMode)))
AppaRao Puli071f3f22018-05-24 16:45:30 +0530501 {
jayaprakash Mutyala0e2dbee2019-12-26 13:03:04 +0000502 log<level::DEBUG>("Invalid access mode specified");
503 return ccAccessModeNotSupportedForChannel;
504 }
505 if ((setFlag & setPrivLimit) && (!isValidPrivLimit(chAccessData.privLimit)))
506 {
507 log<level::DEBUG>("Invalid privilege limit specified");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000508 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530509 }
510
511 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
512 channelLock{*channelMutex};
513
514 if (checkAndReloadVolatileData() != 0)
515 {
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000516 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530517 }
518
519 if (setFlag & setAccessMode)
520 {
521 channelData[chNum].chAccess.chVolatileData.accessMode =
522 chAccessData.accessMode;
523 }
524 if (setFlag & setUserAuthEnabled)
525 {
526 channelData[chNum].chAccess.chVolatileData.userAuthDisabled =
527 chAccessData.userAuthDisabled;
528 }
529 if (setFlag & setMsgAuthEnabled)
530 {
531 channelData[chNum].chAccess.chVolatileData.perMsgAuthDisabled =
532 chAccessData.perMsgAuthDisabled;
533 }
534 if (setFlag & setAlertingEnabled)
535 {
536 channelData[chNum].chAccess.chVolatileData.alertingDisabled =
537 chAccessData.alertingDisabled;
538 }
539 if (setFlag & setPrivLimit)
540 {
541 channelData[chNum].chAccess.chVolatileData.privLimit =
542 chAccessData.privLimit;
543 }
544
545 // Write Volatile data to file
546 if (writeChannelVolatileData() != 0)
547 {
548 log<level::DEBUG>("Failed to update the channel volatile data");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000549 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530550 }
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000551 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530552}
553
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000554Cc ChannelConfig::getChannelAccessPersistData(const uint8_t chNum,
555 ChannelAccess& chAccessData)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530556{
557 if (!isValidChannel(chNum))
558 {
559 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000560 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530561 }
562
563 if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
564 {
565 log<level::DEBUG>("Session-less channel doesn't have access data.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000566 return ccActionNotSupportedForChannel;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530567 }
568
569 if (checkAndReloadNVData() != 0)
570 {
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000571 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530572 }
573
574 std::copy_n(reinterpret_cast<uint8_t*>(
575 &channelData[chNum].chAccess.chNonVolatileData),
576 sizeof(channelData[chNum].chAccess.chNonVolatileData),
577 reinterpret_cast<uint8_t*>(&chAccessData));
578
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000579 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530580}
581
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000582Cc ChannelConfig::setChannelAccessPersistData(const uint8_t chNum,
583 const ChannelAccess& chAccessData,
584 const uint8_t setFlag)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530585{
586 if (!isValidChannel(chNum))
587 {
588 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000589 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530590 }
591
592 if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
593 {
594 log<level::DEBUG>("Session-less channel doesn't have access data.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000595 return ccActionNotSupportedForChannel;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530596 }
597
jayaprakash Mutyala0e2dbee2019-12-26 13:03:04 +0000598 if ((setFlag & setAccessMode) &&
599 (!isValidAccessMode(chAccessData.accessMode)))
AppaRao Puli071f3f22018-05-24 16:45:30 +0530600 {
jayaprakash Mutyala0e2dbee2019-12-26 13:03:04 +0000601 log<level::DEBUG>("Invalid access mode specified");
602 return ccAccessModeNotSupportedForChannel;
603 }
604 if ((setFlag & setPrivLimit) && (!isValidPrivLimit(chAccessData.privLimit)))
605 {
606 log<level::DEBUG>("Invalid privilege limit specified");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000607 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530608 }
609
610 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
611 channelLock{*channelMutex};
612
613 if (checkAndReloadNVData() != 0)
614 {
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000615 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530616 }
617
618 if (setFlag & setAccessMode)
619 {
620 channelData[chNum].chAccess.chNonVolatileData.accessMode =
621 chAccessData.accessMode;
622 }
623 if (setFlag & setUserAuthEnabled)
624 {
625 channelData[chNum].chAccess.chNonVolatileData.userAuthDisabled =
626 chAccessData.userAuthDisabled;
627 }
628 if (setFlag & setMsgAuthEnabled)
629 {
630 channelData[chNum].chAccess.chNonVolatileData.perMsgAuthDisabled =
631 chAccessData.perMsgAuthDisabled;
632 }
633 if (setFlag & setAlertingEnabled)
634 {
635 channelData[chNum].chAccess.chNonVolatileData.alertingDisabled =
636 chAccessData.alertingDisabled;
637 }
638 if (setFlag & setPrivLimit)
639 {
AppaRao Puli9613ed72018-09-01 23:46:44 +0530640 // Send Update to network channel config interfaces over dbus
AppaRao Puli9613ed72018-09-01 23:46:44 +0530641 std::string privStr = convertToPrivLimitString(chAccessData.privLimit);
Richard Marian Thomaiyar73906b92019-01-04 23:48:02 +0530642 std::string networkIntfObj = std::string(networkIntfObjectBasePath) +
643 "/" + channelData[chNum].chName;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530644 try
645 {
Johnathan Manteyf92261d2018-12-10 15:49:34 -0800646 if (0 != setDbusProperty(networkIntfServiceName, networkIntfObj,
647 networkChConfigIntfName,
AppaRao Puli9613ed72018-09-01 23:46:44 +0530648 privilegePropertyString, privStr))
649 {
Richard Marian Thomaiyar73906b92019-01-04 23:48:02 +0530650 log<level::DEBUG>(
651 "Network interface does not exist",
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530652 entry("INTERFACE=%s", channelData[chNum].chName.c_str()));
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000653 return ccUnspecifiedError;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530654 }
655 }
Patrick Williamsef1259b2021-09-02 09:12:33 -0500656 catch (const sdbusplus::exception::exception& e)
AppaRao Puli9613ed72018-09-01 23:46:44 +0530657 {
658 log<level::ERR>("Exception: Network interface does not exist");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000659 return ccInvalidFieldRequest;
AppaRao Puli9613ed72018-09-01 23:46:44 +0530660 }
661 signalFlag |= (1 << chNum);
AppaRao Puli071f3f22018-05-24 16:45:30 +0530662 channelData[chNum].chAccess.chNonVolatileData.privLimit =
663 chAccessData.privLimit;
664 }
665
666 // Write persistent data to file
667 if (writeChannelPersistData() != 0)
668 {
669 log<level::DEBUG>("Failed to update the presist data file");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000670 return ccUnspecifiedError;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530671 }
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000672 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530673}
674
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000675Cc ChannelConfig::getChannelAuthTypeSupported(const uint8_t chNum,
676 uint8_t& authTypeSupported)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530677{
678 if (!isValidChannel(chNum))
679 {
680 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000681 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530682 }
683
684 authTypeSupported = channelData[chNum].chInfo.authTypeSupported;
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000685 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530686}
687
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000688Cc ChannelConfig::getChannelEnabledAuthType(const uint8_t chNum,
689 const uint8_t priv,
690 EAuthType& authType)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530691{
692 if (!isValidChannel(chNum))
693 {
694 log<level::DEBUG>("Invalid channel");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000695 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530696 }
697
698 if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
699 {
700 log<level::DEBUG>("Sessionless channel doesn't have access data.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000701 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530702 }
703
704 if (!isValidPrivLimit(priv))
705 {
706 log<level::DEBUG>("Invalid privilege specified.");
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000707 return ccInvalidFieldRequest;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530708 }
709
710 // TODO: Hardcoded for now. Need to implement.
711 authType = EAuthType::none;
712
NITIN SHARMAb541a5a2019-07-18 12:46:59 +0000713 return ccSuccess;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530714}
715
716std::time_t ChannelConfig::getUpdatedFileTime(const std::string& fileName)
717{
718 struct stat fileStat;
719 if (stat(fileName.c_str(), &fileStat) != 0)
720 {
721 log<level::DEBUG>("Error in getting last updated time stamp");
722 return -EIO;
723 }
724 return fileStat.st_mtime;
725}
726
727EChannelAccessMode
728 ChannelConfig::convertToAccessModeIndex(const std::string& mode)
729{
730 auto iter = std::find(accessModeList.begin(), accessModeList.end(), mode);
731 if (iter == accessModeList.end())
732 {
733 log<level::ERR>("Invalid access mode.",
734 entry("MODE_STR=%s", mode.c_str()));
735 throw std::invalid_argument("Invalid access mode.");
736 }
737
738 return static_cast<EChannelAccessMode>(
739 std::distance(accessModeList.begin(), iter));
740}
741
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530742std::string ChannelConfig::convertToAccessModeString(const uint8_t value)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530743{
744 if (accessModeList.size() <= value)
745 {
746 log<level::ERR>("Invalid access mode.", entry("MODE_IDX=%d", value));
747 throw std::invalid_argument("Invalid access mode.");
748 }
749
750 return accessModeList.at(value);
751}
752
753CommandPrivilege
754 ChannelConfig::convertToPrivLimitIndex(const std::string& value)
755{
756 auto iter = std::find(privList.begin(), privList.end(), value);
757 if (iter == privList.end())
758 {
759 log<level::ERR>("Invalid privilege.",
760 entry("PRIV_STR=%s", value.c_str()));
761 throw std::invalid_argument("Invalid privilege.");
762 }
763
764 return static_cast<CommandPrivilege>(std::distance(privList.begin(), iter));
765}
766
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530767std::string ChannelConfig::convertToPrivLimitString(const uint8_t value)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530768{
769 if (privList.size() <= value)
770 {
771 log<level::ERR>("Invalid privilege.", entry("PRIV_IDX=%d", value));
772 throw std::invalid_argument("Invalid privilege.");
773 }
774
775 return privList.at(value);
776}
777
778EChannelSessSupported
779 ChannelConfig::convertToSessionSupportIndex(const std::string& value)
780{
781 auto iter =
782 std::find(sessionSupportList.begin(), sessionSupportList.end(), value);
783 if (iter == sessionSupportList.end())
784 {
785 log<level::ERR>("Invalid session supported.",
786 entry("SESS_STR=%s", value.c_str()));
787 throw std::invalid_argument("Invalid session supported.");
788 }
789
790 return static_cast<EChannelSessSupported>(
791 std::distance(sessionSupportList.begin(), iter));
792}
793
794EChannelMediumType
795 ChannelConfig::convertToMediumTypeIndex(const std::string& value)
796{
797 std::unordered_map<std::string, EChannelMediumType>::iterator it =
798 mediumTypeMap.find(value);
799 if (it == mediumTypeMap.end())
800 {
801 log<level::ERR>("Invalid medium type.",
802 entry("MEDIUM_STR=%s", value.c_str()));
803 throw std::invalid_argument("Invalid medium type.");
804 }
805
806 return static_cast<EChannelMediumType>(it->second);
807}
808
809EChannelProtocolType
810 ChannelConfig::convertToProtocolTypeIndex(const std::string& value)
811{
812 std::unordered_map<std::string, EChannelProtocolType>::iterator it =
813 protocolTypeMap.find(value);
814 if (it == protocolTypeMap.end())
815 {
816 log<level::ERR>("Invalid protocol type.",
817 entry("PROTO_STR=%s", value.c_str()));
818 throw std::invalid_argument("Invalid protocol type.");
819 }
820
821 return static_cast<EChannelProtocolType>(it->second);
822}
823
824Json ChannelConfig::readJsonFile(const std::string& configFile)
825{
826 std::ifstream jsonFile(configFile);
827 if (!jsonFile.good())
828 {
Richard Marian Thomaiyarc4196802019-06-03 19:27:48 +0530829 log<level::INFO>("JSON file not found",
830 entry("FILE_NAME=%s", configFile.c_str()));
AppaRao Puli071f3f22018-05-24 16:45:30 +0530831 return nullptr;
832 }
833
834 Json data = nullptr;
835 try
836 {
837 data = Json::parse(jsonFile, nullptr, false);
838 }
Patrick Williamsa2ad2da2021-10-06 12:21:46 -0500839 catch (const Json::parse_error& e)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530840 {
841 log<level::DEBUG>("Corrupted channel config.",
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530842 entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +0530843 throw std::runtime_error("Corrupted channel config file");
844 }
845
846 return data;
847}
848
849int ChannelConfig::writeJsonFile(const std::string& configFile,
850 const Json& jsonData)
851{
Richard Marian Thomaiyar687df402019-05-09 00:16:53 +0530852 const std::string tmpFile = configFile + "_tmp";
853 int fd = open(tmpFile.c_str(), O_CREAT | O_WRONLY | O_TRUNC | O_SYNC,
854 S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
855 if (fd < 0)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530856 {
Richard Marian Thomaiyar687df402019-05-09 00:16:53 +0530857 log<level::ERR>("Error in creating json file",
858 entry("FILE_NAME = %s", tmpFile.c_str()));
859 return -EIO;
860 }
861 const auto& writeData = jsonData.dump();
862 if (write(fd, writeData.c_str(), writeData.size()) !=
863 static_cast<ssize_t>(writeData.size()))
864 {
865 close(fd);
866 log<level::ERR>("Error in writing configuration file",
867 entry("FILE_NAME = %s", tmpFile.c_str()));
868 return -EIO;
869 }
870 close(fd);
871
872 if (std::rename(tmpFile.c_str(), configFile.c_str()) != 0)
873 {
874 log<level::ERR>("Error in renaming temporary data file",
875 entry("FILE_NAME = %s", tmpFile.c_str()));
AppaRao Puli071f3f22018-05-24 16:45:30 +0530876 return -EIO;
877 }
878
AppaRao Puli071f3f22018-05-24 16:45:30 +0530879 return 0;
880}
881
Richard Marian Thomaiyara45cb342018-12-03 15:08:59 +0530882void ChannelConfig::setDefaultChannelConfig(const uint8_t chNum,
AppaRao Puli071f3f22018-05-24 16:45:30 +0530883 const std::string& chName)
884{
885 channelData[chNum].chName = chName;
886 channelData[chNum].chID = chNum;
887 channelData[chNum].isChValid = false;
888 channelData[chNum].activeSessCount = 0;
Johnathan Manteyfd61fc32021-04-08 11:05:38 -0700889 channelData[chNum].isManagementNIC = false;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530890
891 channelData[chNum].chInfo.mediumType = defaultMediumType;
892 channelData[chNum].chInfo.protocolType = defaultProtocolType;
893 channelData[chNum].chInfo.sessionSupported = defaultSessionSupported;
894 channelData[chNum].chInfo.isIpmi = defaultIsIpmiState;
895 channelData[chNum].chInfo.authTypeSupported = defaultAuthType;
896}
897
Johnathan Manteyfd61fc32021-04-08 11:05:38 -0700898uint8_t ChannelConfig::getManagementNICID()
899{
900 static bool idFound = false;
901 static uint8_t id = 0;
902
903 if (idFound)
904 {
905 return id;
906 }
907
908 for (uint8_t chIdx = 0; chIdx < maxIpmiChannels; chIdx++)
909 {
910 if (channelData[chIdx].isManagementNIC)
911 {
912 id = chIdx;
913 idFound = true;
914 break;
915 }
916 }
917
918 if (!idFound)
919 {
920 id = static_cast<uint8_t>(EChannelID::chanLan1);
921 idFound = true;
922 }
923 return id;
924}
925
AppaRao Puli071f3f22018-05-24 16:45:30 +0530926int ChannelConfig::loadChannelConfig()
927{
928 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
929 channelLock{*channelMutex};
930
931 Json data = readJsonFile(channelConfigDefaultFilename);
Johnathan Manteye5c4f1d2018-12-10 16:24:26 -0800932 if (data.empty())
AppaRao Puli071f3f22018-05-24 16:45:30 +0530933 {
934 log<level::DEBUG>("Error in opening IPMI Channel data file");
935 return -EIO;
936 }
937
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800938 channelData.fill(ChannelProperties{});
939
Johnathan Mantey0a2abc82021-02-18 12:39:12 -0800940 // Collect the list of NIC interfaces connected to the BMC. Use this
941 // information to only add IPMI channels that have active NIC interfaces.
Snehalatha Venkatesh55f5d532021-07-13 11:06:36 +0000942 struct ifaddrs *ifaddr = nullptr, *ifa = nullptr;
Johnathan Mantey0a2abc82021-02-18 12:39:12 -0800943 if (int err = getifaddrs(&ifaddr); err < 0)
944 {
945 log<level::DEBUG>("Unable to acquire network interfaces");
946 return -EIO;
947 }
948
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800949 for (int chNum = 0; chNum < maxIpmiChannels; chNum++)
AppaRao Puli071f3f22018-05-24 16:45:30 +0530950 {
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800951 try
AppaRao Puli071f3f22018-05-24 16:45:30 +0530952 {
AppaRao Puli071f3f22018-05-24 16:45:30 +0530953 std::string chKey = std::to_string(chNum);
954 Json jsonChData = data[chKey].get<Json>();
955 if (jsonChData.is_null())
956 {
957 log<level::WARNING>(
958 "Channel not configured so loading default.",
Ayushi Smriti05ad3412019-10-16 16:10:18 +0530959 entry("CHANNEL_NUM=%d", chNum));
AppaRao Puli071f3f22018-05-24 16:45:30 +0530960 // If user didn't want to configure specific channel (say
961 // reserved channel), then load that index with default values.
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800962 setDefaultChannelConfig(chNum, defaultChannelName);
963 continue;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530964 }
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800965 Json jsonChInfo = jsonChData[channelInfoString].get<Json>();
966 if (jsonChInfo.is_null())
AppaRao Puli071f3f22018-05-24 16:45:30 +0530967 {
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800968 log<level::ERR>("Invalid/corrupted channel config file");
Johnathan Mantey0a2abc82021-02-18 12:39:12 -0800969 freeifaddrs(ifaddr);
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800970 return -EBADMSG;
AppaRao Puli071f3f22018-05-24 16:45:30 +0530971 }
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800972
Johnathan Mantey0a2abc82021-02-18 12:39:12 -0800973 bool channelFound = true;
974 // Confirm the LAN channel is present
975 if (jsonChInfo[mediumTypeString].get<std::string>() == "lan-802.3")
976 {
977 channelFound = false;
978 for (ifa = ifaddr; ifa != NULL; ifa = ifa->ifa_next)
979 {
980 if (jsonChData[nameString].get<std::string>() ==
981 ifa->ifa_name)
982 {
983 channelFound = true;
984 break;
985 }
986 }
987 }
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800988 ChannelProperties& chData = channelData[chNum];
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800989 chData.chID = chNum;
Johnathan Mantey0a2abc82021-02-18 12:39:12 -0800990 chData.chName = jsonChData[nameString].get<std::string>();
991 chData.isChValid =
992 channelFound && jsonChData[isValidString].get<bool>();
Johnathan Mantey4c0435a2018-12-11 13:17:55 -0800993 chData.activeSessCount = jsonChData.value(activeSessionsString, 0);
994 chData.maxTransferSize =
995 jsonChData.value(maxTransferSizeString, smallChannelSize);
Johnathan Manteyfd61fc32021-04-08 11:05:38 -0700996 if (jsonChData.count(isManagementNIC) != 0)
997 {
998 chData.isManagementNIC =
999 jsonChData[isManagementNIC].get<bool>();
1000 }
1001
Johnathan Mantey4c0435a2018-12-11 13:17:55 -08001002 std::string medTypeStr =
1003 jsonChInfo[mediumTypeString].get<std::string>();
1004 chData.chInfo.mediumType =
1005 static_cast<uint8_t>(convertToMediumTypeIndex(medTypeStr));
1006 std::string protoTypeStr =
1007 jsonChInfo[protocolTypeString].get<std::string>();
1008 chData.chInfo.protocolType =
1009 static_cast<uint8_t>(convertToProtocolTypeIndex(protoTypeStr));
1010 std::string sessStr =
1011 jsonChInfo[sessionSupportedString].get<std::string>();
1012 chData.chInfo.sessionSupported =
1013 static_cast<uint8_t>(convertToSessionSupportIndex(sessStr));
1014 chData.chInfo.isIpmi = jsonChInfo[isIpmiString].get<bool>();
1015 chData.chInfo.authTypeSupported = defaultAuthType;
AppaRao Puli071f3f22018-05-24 16:45:30 +05301016 }
Johnathan Mantey4c0435a2018-12-11 13:17:55 -08001017 catch (const Json::exception& e)
1018 {
1019 log<level::DEBUG>("Json Exception caught.",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301020 entry("MSG=%s", e.what()));
Johnathan Mantey0a2abc82021-02-18 12:39:12 -08001021 freeifaddrs(ifaddr);
1022
Johnathan Mantey4c0435a2018-12-11 13:17:55 -08001023 return -EBADMSG;
1024 }
1025 catch (const std::invalid_argument& e)
1026 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301027 log<level::ERR>("Corrupted config.", entry("MSG=%s", e.what()));
Johnathan Mantey0a2abc82021-02-18 12:39:12 -08001028 freeifaddrs(ifaddr);
Johnathan Mantey4c0435a2018-12-11 13:17:55 -08001029 return -EBADMSG;
1030 }
AppaRao Puli071f3f22018-05-24 16:45:30 +05301031 }
Johnathan Mantey0a2abc82021-02-18 12:39:12 -08001032 freeifaddrs(ifaddr);
AppaRao Puli071f3f22018-05-24 16:45:30 +05301033
1034 return 0;
1035}
1036
1037int ChannelConfig::readChannelVolatileData()
1038{
1039 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1040 channelLock{*channelMutex};
1041
1042 Json data = readJsonFile(channelVolatileDataFilename);
1043 if (data == nullptr)
1044 {
1045 log<level::DEBUG>("Error in opening IPMI Channel data file");
1046 return -EIO;
1047 }
AppaRao Puli071f3f22018-05-24 16:45:30 +05301048 try
1049 {
1050 // Fill in global structure
1051 for (auto it = data.begin(); it != data.end(); ++it)
1052 {
1053 std::string chKey = it.key();
1054 uint8_t chNum = std::stoi(chKey, nullptr, 10);
Meera-Kattac1789482021-05-18 09:53:26 +00001055 if (chNum >= maxIpmiChannels)
AppaRao Puli071f3f22018-05-24 16:45:30 +05301056 {
1057 log<level::DEBUG>(
1058 "Invalid channel access entry in config file");
1059 throw std::out_of_range("Out of range - channel number");
1060 }
1061 Json jsonChData = it.value();
1062 if (!jsonChData.is_null())
1063 {
1064 std::string accModeStr =
1065 jsonChData[accessModeString].get<std::string>();
1066 channelData[chNum].chAccess.chVolatileData.accessMode =
1067 static_cast<uint8_t>(convertToAccessModeIndex(accModeStr));
1068 channelData[chNum].chAccess.chVolatileData.userAuthDisabled =
1069 jsonChData[userAuthDisabledString].get<bool>();
1070 channelData[chNum].chAccess.chVolatileData.perMsgAuthDisabled =
1071 jsonChData[perMsgAuthDisabledString].get<bool>();
1072 channelData[chNum].chAccess.chVolatileData.alertingDisabled =
1073 jsonChData[alertingDisabledString].get<bool>();
1074 std::string privStr =
1075 jsonChData[privLimitString].get<std::string>();
1076 channelData[chNum].chAccess.chVolatileData.privLimit =
1077 static_cast<uint8_t>(convertToPrivLimitIndex(privStr));
1078 }
1079 else
1080 {
1081 log<level::ERR>(
1082 "Invalid/corrupted volatile channel access file",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301083 entry("FILE=%s", channelVolatileDataFilename));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301084 throw std::runtime_error(
1085 "Corrupted volatile channel access file");
1086 }
1087 }
1088 }
1089 catch (const Json::exception& e)
1090 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301091 log<level::DEBUG>("Json Exception caught.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301092 throw std::runtime_error("Corrupted volatile channel access file");
1093 }
1094 catch (const std::invalid_argument& e)
1095 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301096 log<level::ERR>("Corrupted config.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301097 throw std::runtime_error("Corrupted volatile channel access file");
1098 }
1099
1100 // Update the timestamp
1101 voltFileLastUpdatedTime = getUpdatedFileTime(channelVolatileDataFilename);
1102 return 0;
1103}
1104
1105int ChannelConfig::readChannelPersistData()
1106{
1107 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1108 channelLock{*channelMutex};
1109
1110 Json data = readJsonFile(channelNvDataFilename);
1111 if (data == nullptr)
1112 {
1113 log<level::DEBUG>("Error in opening IPMI Channel data file");
1114 return -EIO;
1115 }
AppaRao Puli071f3f22018-05-24 16:45:30 +05301116 try
1117 {
1118 // Fill in global structure
1119 for (auto it = data.begin(); it != data.end(); ++it)
1120 {
1121 std::string chKey = it.key();
1122 uint8_t chNum = std::stoi(chKey, nullptr, 10);
Meera-Kattac1789482021-05-18 09:53:26 +00001123 if (chNum >= maxIpmiChannels)
AppaRao Puli071f3f22018-05-24 16:45:30 +05301124 {
1125 log<level::DEBUG>(
1126 "Invalid channel access entry in config file");
1127 throw std::out_of_range("Out of range - channel number");
1128 }
1129 Json jsonChData = it.value();
1130 if (!jsonChData.is_null())
1131 {
1132 std::string accModeStr =
1133 jsonChData[accessModeString].get<std::string>();
1134 channelData[chNum].chAccess.chNonVolatileData.accessMode =
1135 static_cast<uint8_t>(convertToAccessModeIndex(accModeStr));
1136 channelData[chNum].chAccess.chNonVolatileData.userAuthDisabled =
1137 jsonChData[userAuthDisabledString].get<bool>();
1138 channelData[chNum]
1139 .chAccess.chNonVolatileData.perMsgAuthDisabled =
1140 jsonChData[perMsgAuthDisabledString].get<bool>();
1141 channelData[chNum].chAccess.chNonVolatileData.alertingDisabled =
1142 jsonChData[alertingDisabledString].get<bool>();
1143 std::string privStr =
1144 jsonChData[privLimitString].get<std::string>();
1145 channelData[chNum].chAccess.chNonVolatileData.privLimit =
1146 static_cast<uint8_t>(convertToPrivLimitIndex(privStr));
1147 }
1148 else
1149 {
1150 log<level::ERR>("Invalid/corrupted nv channel access file",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301151 entry("FILE=%s", channelNvDataFilename));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301152 throw std::runtime_error("Corrupted nv channel access file");
1153 }
1154 }
1155 }
1156 catch (const Json::exception& e)
1157 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301158 log<level::DEBUG>("Json Exception caught.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301159 throw std::runtime_error("Corrupted nv channel access file");
1160 }
1161 catch (const std::invalid_argument& e)
1162 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301163 log<level::ERR>("Corrupted config.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301164 throw std::runtime_error("Corrupted nv channel access file");
1165 }
1166
1167 // Update the timestamp
1168 nvFileLastUpdatedTime = getUpdatedFileTime(channelNvDataFilename);
1169 return 0;
1170}
1171
1172int ChannelConfig::writeChannelVolatileData()
1173{
1174 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1175 channelLock{*channelMutex};
1176 Json outData;
1177
1178 try
1179 {
1180 for (uint8_t chNum = 0; chNum < maxIpmiChannels; chNum++)
1181 {
1182 if (getChannelSessionSupport(chNum) != EChannelSessSupported::none)
1183 {
1184 Json jsonObj;
1185 std::string chKey = std::to_string(chNum);
1186 std::string accModeStr = convertToAccessModeString(
1187 channelData[chNum].chAccess.chVolatileData.accessMode);
1188 jsonObj[accessModeString] = accModeStr;
1189 jsonObj[userAuthDisabledString] =
1190 channelData[chNum].chAccess.chVolatileData.userAuthDisabled;
1191 jsonObj[perMsgAuthDisabledString] =
1192 channelData[chNum]
1193 .chAccess.chVolatileData.perMsgAuthDisabled;
1194 jsonObj[alertingDisabledString] =
1195 channelData[chNum].chAccess.chVolatileData.alertingDisabled;
1196 std::string privStr = convertToPrivLimitString(
1197 channelData[chNum].chAccess.chVolatileData.privLimit);
1198 jsonObj[privLimitString] = privStr;
1199
1200 outData[chKey] = jsonObj;
1201 }
1202 }
1203 }
1204 catch (const std::invalid_argument& e)
1205 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301206 log<level::ERR>("Corrupted config.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301207 return -EINVAL;
1208 }
1209
1210 if (writeJsonFile(channelVolatileDataFilename, outData) != 0)
1211 {
1212 log<level::DEBUG>("Error in write JSON data to file");
1213 return -EIO;
1214 }
1215
1216 // Update the timestamp
1217 voltFileLastUpdatedTime = getUpdatedFileTime(channelVolatileDataFilename);
1218 return 0;
1219}
1220
1221int ChannelConfig::writeChannelPersistData()
1222{
1223 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1224 channelLock{*channelMutex};
1225 Json outData;
1226
1227 try
1228 {
1229 for (uint8_t chNum = 0; chNum < maxIpmiChannels; chNum++)
1230 {
1231 if (getChannelSessionSupport(chNum) != EChannelSessSupported::none)
1232 {
1233 Json jsonObj;
1234 std::string chKey = std::to_string(chNum);
1235 std::string accModeStr = convertToAccessModeString(
1236 channelData[chNum].chAccess.chNonVolatileData.accessMode);
1237 jsonObj[accessModeString] = accModeStr;
1238 jsonObj[userAuthDisabledString] =
1239 channelData[chNum]
1240 .chAccess.chNonVolatileData.userAuthDisabled;
1241 jsonObj[perMsgAuthDisabledString] =
1242 channelData[chNum]
1243 .chAccess.chNonVolatileData.perMsgAuthDisabled;
1244 jsonObj[alertingDisabledString] =
1245 channelData[chNum]
1246 .chAccess.chNonVolatileData.alertingDisabled;
1247 std::string privStr = convertToPrivLimitString(
1248 channelData[chNum].chAccess.chNonVolatileData.privLimit);
1249 jsonObj[privLimitString] = privStr;
1250
1251 outData[chKey] = jsonObj;
1252 }
1253 }
1254 }
1255 catch (const std::invalid_argument& e)
1256 {
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301257 log<level::ERR>("Corrupted config.", entry("MSG=%s", e.what()));
AppaRao Puli071f3f22018-05-24 16:45:30 +05301258 return -EINVAL;
1259 }
1260
1261 if (writeJsonFile(channelNvDataFilename, outData) != 0)
1262 {
1263 log<level::DEBUG>("Error in write JSON data to file");
1264 return -EIO;
1265 }
1266
1267 // Update the timestamp
1268 nvFileLastUpdatedTime = getUpdatedFileTime(channelNvDataFilename);
1269 return 0;
1270}
1271
1272int ChannelConfig::checkAndReloadNVData()
1273{
1274 std::time_t updateTime = getUpdatedFileTime(channelNvDataFilename);
1275 int ret = 0;
1276 if (updateTime != nvFileLastUpdatedTime || updateTime == -EIO)
1277 {
1278 try
1279 {
1280 ret = readChannelPersistData();
1281 }
1282 catch (const std::exception& e)
1283 {
1284 log<level::ERR>("Exception caught in readChannelPersistData.",
1285 entry("MSG=%s", e.what()));
1286 ret = -EIO;
1287 }
1288 }
1289 return ret;
1290}
1291
1292int ChannelConfig::checkAndReloadVolatileData()
1293{
1294 std::time_t updateTime = getUpdatedFileTime(channelVolatileDataFilename);
1295 int ret = 0;
1296 if (updateTime != voltFileLastUpdatedTime || updateTime == -EIO)
1297 {
1298 try
1299 {
1300 ret = readChannelVolatileData();
1301 }
1302 catch (const std::exception& e)
1303 {
1304 log<level::ERR>("Exception caught in readChannelVolatileData.",
1305 entry("MSG=%s", e.what()));
1306 ret = -EIO;
1307 }
1308 }
1309 return ret;
1310}
1311
Johnathan Manteyf92261d2018-12-10 15:49:34 -08001312int ChannelConfig::setDbusProperty(const std::string& service,
AppaRao Puli9613ed72018-09-01 23:46:44 +05301313 const std::string& objPath,
1314 const std::string& interface,
1315 const std::string& property,
1316 const DbusVariant& value)
1317{
1318 try
1319 {
1320 auto method =
1321 bus.new_method_call(service.c_str(), objPath.c_str(),
1322 "org.freedesktop.DBus.Properties", "Set");
1323
1324 method.append(interface, property, value);
1325
1326 auto reply = bus.call(method);
1327 }
Patrick Williamsef1259b2021-09-02 09:12:33 -05001328 catch (const sdbusplus::exception::exception& e)
AppaRao Puli9613ed72018-09-01 23:46:44 +05301329 {
1330 log<level::DEBUG>("set-property failed",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301331 entry("SERVICE=%s", service.c_str()),
1332 entry("OBJPATH=%s", objPath.c_str()),
1333 entry("INTERFACE=%s", interface.c_str()),
1334 entry("PROP=%s", property.c_str()));
AppaRao Puli9613ed72018-09-01 23:46:44 +05301335 return -EIO;
1336 }
1337
1338 return 0;
1339}
1340
Johnathan Manteyf92261d2018-12-10 15:49:34 -08001341int ChannelConfig::getDbusProperty(const std::string& service,
AppaRao Puli9613ed72018-09-01 23:46:44 +05301342 const std::string& objPath,
1343 const std::string& interface,
1344 const std::string& property,
1345 DbusVariant& value)
1346{
1347 try
1348 {
1349 auto method =
1350 bus.new_method_call(service.c_str(), objPath.c_str(),
1351 "org.freedesktop.DBus.Properties", "Get");
1352
1353 method.append(interface, property);
1354
1355 auto reply = bus.call(method);
1356 reply.read(value);
1357 }
Patrick Williamsef1259b2021-09-02 09:12:33 -05001358 catch (const sdbusplus::exception::exception& e)
AppaRao Puli9613ed72018-09-01 23:46:44 +05301359 {
1360 log<level::DEBUG>("get-property failed",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301361 entry("SERVICE=%s", service.c_str()),
1362 entry("OBJPATH=%s", objPath.c_str()),
1363 entry("INTERFACE=%s", interface.c_str()),
1364 entry("PROP=%s", property.c_str()));
AppaRao Puli9613ed72018-09-01 23:46:44 +05301365 return -EIO;
1366 }
1367 return 0;
1368}
1369
1370int ChannelConfig::syncNetworkChannelConfig()
1371{
1372 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1373 channelLock{*channelMutex};
1374 bool isUpdated = false;
1375 for (uint8_t chNum = 0; chNum < maxIpmiChannels; chNum++)
1376 {
1377 if (getChannelSessionSupport(chNum) != EChannelSessSupported::none)
1378 {
1379 std::string intfPrivStr;
1380 try
1381 {
AppaRao Puli9613ed72018-09-01 23:46:44 +05301382 std::string networkIntfObj =
Richard Marian Thomaiyar73906b92019-01-04 23:48:02 +05301383 std::string(networkIntfObjectBasePath) + "/" +
1384 channelData[chNum].chName;
AppaRao Puli9613ed72018-09-01 23:46:44 +05301385 DbusVariant variant;
Johnathan Manteyf92261d2018-12-10 15:49:34 -08001386 if (0 != getDbusProperty(networkIntfServiceName, networkIntfObj,
AppaRao Puli9613ed72018-09-01 23:46:44 +05301387 networkChConfigIntfName,
1388 privilegePropertyString, variant))
1389 {
1390 log<level::DEBUG>("Network interface does not exist",
Ayushi Smriti05ad3412019-10-16 16:10:18 +05301391 entry("INTERFACE=%s",
Richard Marian Thomaiyar73906b92019-01-04 23:48:02 +05301392 channelData[chNum].chName.c_str()));
AppaRao Puli9613ed72018-09-01 23:46:44 +05301393 continue;
1394 }
Vernon Maueryf442e112019-04-09 11:44:36 -07001395 intfPrivStr = std::get<std::string>(variant);
AppaRao Puli9613ed72018-09-01 23:46:44 +05301396 }
Vernon Maueryf442e112019-04-09 11:44:36 -07001397 catch (const std::bad_variant_access& e)
AppaRao Puli9613ed72018-09-01 23:46:44 +05301398 {
1399 log<level::DEBUG>(
1400 "exception: Network interface does not exist");
1401 continue;
1402 }
Patrick Williamsef1259b2021-09-02 09:12:33 -05001403 catch (const sdbusplus::exception::exception& e)
AppaRao Puli9613ed72018-09-01 23:46:44 +05301404 {
1405 log<level::DEBUG>(
1406 "exception: Network interface does not exist");
1407 continue;
1408 }
1409
1410 uint8_t intfPriv =
1411 static_cast<uint8_t>(convertToPrivLimitIndex(intfPrivStr));
1412 if (channelData[chNum].chAccess.chNonVolatileData.privLimit !=
1413 intfPriv)
1414 {
1415 isUpdated = true;
1416 channelData[chNum].chAccess.chNonVolatileData.privLimit =
1417 intfPriv;
1418 channelData[chNum].chAccess.chVolatileData.privLimit = intfPriv;
1419 }
1420 }
1421 }
1422
1423 if (isUpdated)
1424 {
1425 // Write persistent data to file
1426 if (writeChannelPersistData() != 0)
1427 {
1428 log<level::DEBUG>("Failed to update the persistent data file");
1429 return -EIO;
1430 }
1431 // Write Volatile data to file
1432 if (writeChannelVolatileData() != 0)
1433 {
1434 log<level::DEBUG>("Failed to update the channel volatile data");
1435 return -EIO;
1436 }
1437 }
1438
1439 return 0;
1440}
1441
AppaRao Puli071f3f22018-05-24 16:45:30 +05301442void ChannelConfig::initChannelPersistData()
1443{
Richard Marian Thomaiyare91474c2019-09-01 23:02:47 +05301444 boost::interprocess::scoped_lock<boost::interprocess::named_recursive_mutex>
1445 channelLock{*channelMutex};
1446
AppaRao Puli071f3f22018-05-24 16:45:30 +05301447 /* Always read the channel config */
1448 if (loadChannelConfig() != 0)
1449 {
1450 log<level::ERR>("Failed to read channel config file");
1451 throw std::ios_base::failure("Failed to load channel configuration");
1452 }
1453
1454 /* Populate the channel persist data */
1455 if (readChannelPersistData() != 0)
1456 {
1457 // Copy default NV data to RW location
1458 std::experimental::filesystem::copy_file(channelAccessDefaultFilename,
1459 channelNvDataFilename);
1460
1461 // Load the channel access NV data
1462 if (readChannelPersistData() != 0)
1463 {
1464 log<level::ERR>("Failed to read channel access NV data");
1465 throw std::ios_base::failure(
1466 "Failed to read channel access NV configuration");
1467 }
1468 }
1469
1470 // First check the volatile data file
1471 // If not present, load the default values
1472 if (readChannelVolatileData() != 0)
1473 {
1474 // Copy default volatile data to temporary location
1475 // NV file(channelNvDataFilename) must have created by now.
1476 std::experimental::filesystem::copy_file(channelNvDataFilename,
1477 channelVolatileDataFilename);
1478
1479 // Load the channel access volatile data
1480 if (readChannelVolatileData() != 0)
1481 {
1482 log<level::ERR>("Failed to read channel access volatile data");
1483 throw std::ios_base::failure(
1484 "Failed to read channel access volatile configuration");
1485 }
1486 }
AppaRao Puli9613ed72018-09-01 23:46:44 +05301487
1488 // Synchronize the channel config(priv) with network channel
1489 // configuration(priv) over dbus
1490 if (syncNetworkChannelConfig() != 0)
1491 {
1492 log<level::ERR>(
1493 "Failed to synchronize data with network channel config over dbus");
1494 throw std::ios_base::failure(
1495 "Failed to synchronize data with network channel config over dbus");
1496 }
1497
1498 log<level::DEBUG>("Successfully completed channel data initialization.");
AppaRao Puli071f3f22018-05-24 16:45:30 +05301499 return;
1500}
1501
1502} // namespace ipmi