blob: 4990ee00d0b4aee14a516229dec79170e08d4db9 [file] [log] [blame]
Ratan Gupta6811f822017-04-14 16:34:56 +05301#include "config.h"
Ratan Gupta3681a502017-06-17 19:20:04 +05302#include "util.hpp"
Ratan Gupta6811f822017-04-14 16:34:56 +05303#include "network_manager.hpp"
Michael Tritz29f2fd62017-05-22 15:27:26 -05004#include "network_config.hpp"
Ratan Gupta5978dd12017-07-25 13:47:13 +05305#include "ipaddress.hpp"
Ratan Guptae05083a2017-09-16 07:12:11 +05306#include "timer.hpp"
Ratan Gupta44ae86e2017-05-15 21:52:14 +05307#include "xyz/openbmc_project/Common/error.hpp"
Ratan Gupta6811f822017-04-14 16:34:56 +05308
9#include <phosphor-logging/log.hpp>
Ratan Gupta44ae86e2017-05-15 21:52:14 +053010#include <phosphor-logging/elog-errors.hpp>
Ratan Gupta6811f822017-04-14 16:34:56 +053011
12#include <algorithm>
Ratan Gupta738a67f2017-04-21 10:38:05 +053013#include <bitset>
Ratan Gupta738a67f2017-04-21 10:38:05 +053014#include <map>
Ratan Gupta4f1c18b2017-05-25 12:59:35 +053015#include <fstream>
Ratan Gupta738a67f2017-04-21 10:38:05 +053016
Ratan Gupta6811f822017-04-14 16:34:56 +053017#include <arpa/inet.h>
18#include <dirent.h>
19#include <net/if.h>
20
Michael Tritz29f2fd62017-05-22 15:27:26 -050021#include <string>
Ratan Gupta6811f822017-04-14 16:34:56 +053022
23namespace phosphor
24{
25namespace network
26{
Ratan Gupta82549cc2017-04-21 08:45:23 +053027
Ratan Gupta16f12882017-09-22 18:26:11 +053028extern std::unique_ptr<phosphor::network::Timer> refreshObjectTimer;
29extern std::unique_ptr<phosphor::network::Timer> restartTimer;
Ratan Gupta6811f822017-04-14 16:34:56 +053030using namespace phosphor::logging;
Ratan Guptaef85eb92017-06-15 08:57:54 +053031using namespace sdbusplus::xyz::openbmc_project::Common::Error;
Ratan Gupta6811f822017-04-14 16:34:56 +053032
Ratan Gupta255d5142017-08-10 09:02:08 +053033Manager::Manager(sdbusplus::bus::bus& bus, const char* objPath,
34 const std::string& path):
Ratan Gupta29b0e432017-05-25 12:51:40 +053035 details::VLANCreateIface(bus, objPath, true),
36 bus(bus),
37 objectPath(objPath)
Ratan Gupta6811f822017-04-14 16:34:56 +053038{
Ratan Gupta255d5142017-08-10 09:02:08 +053039 fs::path confDir(path);
40 setConfDir(confDir);
Ratan Guptaef85eb92017-06-15 08:57:54 +053041}
42
Ratan Guptab610caf2017-09-19 09:33:51 +053043bool Manager::createDefaultNetworkFiles(bool force)
44{
45 auto isCreated = false;
46 try
47 {
48 // Directory would have created before with
49 // setConfDir function.
50 if (force)
51 {
52 // Factory Reset case
53 // we need to forcefully write the files
54 // so delete the existing ones.
55 if (fs::is_directory(confDir))
56 {
57 for (const auto& file : fs::directory_iterator(confDir))
58 {
59 fs::remove(file.path());
60 }
61 }
62 }
63
64 auto interfaceStrList = getInterfaces();
65 for (const auto& interface : interfaceStrList)
66 {
Michael Tritz08c34f42017-10-16 14:59:09 -050067 // if the interface has '.' in the name, it means that this is a
68 // VLAN - don't create the network file.
69 if (interface.find(".") != std::string::npos)
70 {
71 continue;
72 }
73
Ratan Guptab610caf2017-09-19 09:33:51 +053074 auto fileName = systemd::config::networkFilePrefix + interface +
75 systemd::config::networkFileSuffix;
76
77 fs::path filePath = confDir;
78 filePath /= fileName;
79
80 // create the interface specific network file
81 // if not exist or we forcefully wants to write
82 // the network file.
83
84 if (force || !fs::is_regular_file(filePath.string()))
85 {
86 bmc::writeDHCPDefault(filePath.string(), interface);
87 log<level::INFO>("Created the default network file.",
88 entry("INTERFACE=%s", interface.c_str()));
89 isCreated = true;
90 }
91 }
92 }
93 catch (std::exception& e)
94 {
95 log<level::ERR>("Unable to create the default network file");
96 }
97 return isCreated;
98}
99
Ratan Guptaef85eb92017-06-15 08:57:54 +0530100void Manager::setConfDir(const fs::path& dir)
101{
102 confDir = dir;
Ratan Gupta255d5142017-08-10 09:02:08 +0530103
104 if (!fs::exists(confDir))
105 {
106 if (!fs::create_directories(confDir))
107 {
108 log<level::ERR>("Unable to create the network conf dir",
109 entry("DIR=%s", confDir.c_str()));
110 elog<InternalFailure>();
111 }
112 }
113
Ratan Gupta29b0e432017-05-25 12:51:40 +0530114}
115
116void Manager::createInterfaces()
117{
Ratan Guptaef85eb92017-06-15 08:57:54 +0530118 //clear all the interfaces first
119 interfaces.clear();
Ratan Gupta29b0e432017-05-25 12:51:40 +0530120
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530121 auto interfaceStrList = getInterfaces();
Ratan Gupta6811f822017-04-14 16:34:56 +0530122
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530123 for (auto& interface : interfaceStrList)
Ratan Gupta6811f822017-04-14 16:34:56 +0530124 {
Ratan Gupta29b0e432017-05-25 12:51:40 +0530125 fs::path objPath = objectPath;
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530126 auto index = interface.find(".");
Ratan Gupta92bc2fe2017-07-26 22:40:21 +0530127
128 // interface can be of vlan type or normal ethernet interface.
129 // vlan interface looks like "interface.vlanid",so here by looking
130 // at the interface name we decide that we need
131 // to create the vlaninterface or normal physical interface.
132 if (index != std::string::npos)
133 {
134 //it is vlan interface
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530135 auto interfaceName = interface.substr(0, index);
136 auto vlanid = interface.substr(index + 1);
Ratan Gupta92bc2fe2017-07-26 22:40:21 +0530137 uint32_t vlanInt = std::stoul(vlanid);
138
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530139 interfaces[interfaceName]->loadVLAN(vlanInt);
Ratan Gupta6e8df632017-08-13 09:41:58 +0530140 continue;
Ratan Gupta92bc2fe2017-07-26 22:40:21 +0530141 }
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530142 // normal ethernet interface
143 objPath /= interface;
Ratan Gupta6811f822017-04-14 16:34:56 +0530144
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530145 auto dhcp = getDHCPValue(confDir, interface);
Ratan Gupta34f96d62017-06-15 09:16:22 +0530146
Ratan Gupta92bc2fe2017-07-26 22:40:21 +0530147 auto intf = std::make_shared<phosphor::network::EthernetInterface>(
148 bus,
149 objPath.string(),
150 dhcp,
151 *this);
152
153
154 intf->createIPAddressObjects();
155
Ratan Gupta6811f822017-04-14 16:34:56 +0530156 this->interfaces.emplace(std::make_pair(
Ratan Guptafd4b0f02017-09-16 06:01:24 +0530157 std::move(interface), std::move(intf)));
Ratan Gupta29b0e432017-05-25 12:51:40 +0530158
Ratan Gupta6811f822017-04-14 16:34:56 +0530159 }
Ratan Gupta87c13982017-06-15 09:27:27 +0530160
Ratan Gupta6811f822017-04-14 16:34:56 +0530161}
162
Ratan Guptaef85eb92017-06-15 08:57:54 +0530163void Manager::createChildObjects()
164{
165 // creates the ethernet interface dbus object.
166 createInterfaces();
Ratan Guptae05083a2017-09-16 07:12:11 +0530167
168 systemConf.reset(nullptr);
169 dhcpConf.reset(nullptr);
170
Ratan Guptaef85eb92017-06-15 08:57:54 +0530171 fs::path objPath = objectPath;
172 objPath /= "config";
Ratan Guptae05083a2017-09-16 07:12:11 +0530173
174 // create the system conf object.
Ratan Guptaef85eb92017-06-15 08:57:54 +0530175 systemConf = std::make_unique<phosphor::network::SystemConfiguration>(
176 bus, objPath.string(), *this);
Ratan Guptad16f88c2017-07-11 17:47:57 +0530177 // create the dhcp conf object.
178 objPath /= "dhcp";
179 dhcpConf = std::make_unique<phosphor::network::dhcp::Configuration>(
180 bus, objPath.string(), *this);
Ratan Guptaef85eb92017-06-15 08:57:54 +0530181
182}
183
Ratan Gupta584df832017-07-31 16:21:54 +0530184void Manager::vLAN(IntfName interfaceName, uint32_t id)
Ratan Gupta6811f822017-04-14 16:34:56 +0530185{
Ratan Gupta2b106532017-07-25 16:05:02 +0530186 interfaces[interfaceName]->createVLAN(id);
Ratan Gupta6811f822017-04-14 16:34:56 +0530187}
188
Michael Tritz29f2fd62017-05-22 15:27:26 -0500189void Manager::reset()
190{
Ratan Guptab610caf2017-09-19 09:33:51 +0530191 if(!createDefaultNetworkFiles(true))
Michael Tritz29f2fd62017-05-22 15:27:26 -0500192 {
Ratan Guptab610caf2017-09-19 09:33:51 +0530193 log<level::ERR>("Network Factory Reset failed.");
194 return;
195 // TODO: openbmc/openbmc#1721 - Log ResetFailed error here.
Michael Tritz29f2fd62017-05-22 15:27:26 -0500196 }
197
Ratan Guptab610caf2017-09-19 09:33:51 +0530198 log<level::INFO>("Network Factory Reset done.");
Michael Tritz29f2fd62017-05-22 15:27:26 -0500199}
200
Ratan Gupta4f1c18b2017-05-25 12:59:35 +0530201// Need to merge the below function with the code which writes the
202// config file during factory reset.
203//TODO openbmc/openbmc#1751
204void Manager::writeToConfigurationFile()
205{
206 // write all the static ip address in the systemd-network conf file
Ratan Gupta4f1c18b2017-05-25 12:59:35 +0530207 for (const auto& intf : interfaces)
208 {
Ratan Gupta2b106532017-07-25 16:05:02 +0530209 intf.second->writeConfigurationFile();
Ratan Gupta4f1c18b2017-05-25 12:59:35 +0530210
Ratan Gupta4f1c18b2017-05-25 12:59:35 +0530211 }
Ratan Gupta16f12882017-09-22 18:26:11 +0530212 restartTimers();
Ratan Guptae05083a2017-09-16 07:12:11 +0530213}
214
Ratan Gupta16f12882017-09-22 18:26:11 +0530215void Manager::restartTimers()
Ratan Guptae05083a2017-09-16 07:12:11 +0530216{
217 using namespace std::chrono;
Ratan Gupta16f12882017-09-22 18:26:11 +0530218 if (refreshObjectTimer && restartTimer)
Ratan Guptae05083a2017-09-16 07:12:11 +0530219 {
Ratan Gupta16f12882017-09-22 18:26:11 +0530220 // start the restart timer.
221 auto restartTime = duration_cast<microseconds>(
222 phosphor::network::restartTimeout);
223 restartTimer->startTimer(restartTime);
224
225 // start the refresh timer.
226 auto refreshTime = duration_cast<microseconds>(
227 phosphor::network::refreshTimeout);
228 refreshObjectTimer->startTimer(refreshTime);
Ratan Guptae05083a2017-09-16 07:12:11 +0530229 }
Ratan Gupta70c7e5b2017-07-12 11:41:55 +0530230}
231
Ratan Gupta6811f822017-04-14 16:34:56 +0530232}//namespace network
233}//namespace phosphor