Implement create interface for ipaddress
Change-Id: Ia4598c27c11667dafb70a8af58871661b7042d0f
Signed-off-by: Ratan Gupta <ratagupt@in.ibm.com>
diff --git a/Makefile.am b/Makefile.am
index 247ea9b..75c49e6 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -13,7 +13,8 @@
noinst_HEADERS = \
ethernet_interface.hpp \
network_manager.hpp \
- ipaddress.hpp
+ ipaddress.hpp \
+ types.hpp
phosphor_network_manager_SOURCES = \
ethernet_interface.cpp \
@@ -40,7 +41,8 @@
phosphor_network_manager_LDFLAGS = \
$(SYSTEMD_LIBS) \
$(SDBUSPLUS_LIBS) \
- $(PHOSPHOR_DBUS_INTERFACES_LIBS)
+ $(PHOSPHOR_DBUS_INTERFACES_LIBS) \
+ -lstdc++fs
phosphor_network_manager_CXXFLAGS = \
$(SYSTEMD_CFLAGS) \
diff --git a/ethernet_interface.cpp b/ethernet_interface.cpp
index f4adf28..20b3e31 100644
--- a/ethernet_interface.cpp
+++ b/ethernet_interface.cpp
@@ -1,7 +1,10 @@
+#include "config.h"
+#include "ipaddress.hpp"
#include "ethernet_interface.hpp"
#include <phosphor-logging/log.hpp>
+#include <arpa/inet.h>
#include <linux/ethtool.h>
#include <net/if.h>
#include <linux/sockios.h>
@@ -10,6 +13,10 @@
#include <sys/socket.h>
#include <unistd.h>
+#include <string>
+#include <algorithm>
+#include <experimental/filesystem>
+
namespace phosphor
{
namespace network
@@ -22,23 +29,72 @@
EthernetInterface::EthernetInterface(sdbusplus::bus::bus& bus,
const std::string& objPath,
- bool dhcpEnabled) :
- details::EthernetIface(bus, objPath.c_str(), true)
+ bool dhcpEnabled,
+ const AddrList& addrs) :
+ Ifaces(bus, objPath.c_str(), true),
+ bus(bus)
{
auto intfName = objPath.substr(objPath.rfind("/") + 1);
interfaceName(intfName);
dHCPEnabled(dhcpEnabled);
mACAddress(getMACAddress());
+ std::string gateway;
+
+ IP::Protocol addressType = IP::Protocol::IPv4;
+
+ for (auto addr : addrs)
+ {
+ if (addr.addrType == AF_INET6)
+ {
+ addressType = IP::Protocol::IPv6;
+ }
+
+ std::string ipAddressObjectPath = getAddressObjectPath(addressType);
+ this->addrs.emplace(
+ std::make_pair(
+ addr.ipaddress,
+ std::make_unique<phosphor::network::IPAddress>(
+ bus,
+ ipAddressObjectPath.c_str(),
+ *this,
+ addressType,
+ addr.ipaddress,
+ addr.prefix,
+ gateway)));
+ }
// Emit deferred signal.
this->emit_object_added();
}
+void EthernetInterface::iP(IP::Protocol protType,
+ std::string ipaddress,
+ uint8_t prefixLength,
+ std::string gateway)
+{
+
+ IP::Protocol protocolType = protType;
+ std::string objectPath = getAddressObjectPath(protocolType);
+
+ this->addrs.emplace(
+ std::make_pair(ipaddress,
+ std::make_unique<phosphor::network::IPAddress>(
+ bus,
+ objectPath.c_str(),
+ *this,
+ protocolType,
+ ipaddress,
+ prefixLength,
+ gateway)));
+}
+
+
/*
Note: We don't have support for ethtool now
will enable this code once we bring the ethtool
in the image.
TODO: https://github.com/openbmc/openbmc/issues/1484
*/
+
InterfaceInfo EthernetInterface::getInterfaceInfo() const
{
int sock{-1};
@@ -138,9 +194,42 @@
return macAddress;
}
+size_t EthernetInterface::getAddressCount(IP::Protocol addressType) const
+{
+ size_t count = 0;
+
+ std::for_each(addrs.cbegin(), addrs.cend(),
+ [&count,addressType](const auto & addr)
+ {
+ if (addr.second->type() == addressType)
+ {
+ count += 1;
+ }
+ });
+
+ return count;
+}
+
void EthernetInterface::deleteObject(const std::string& ipaddress)
{
- //NOTE:- will be implemented in next commit.
+ this->addrs.erase(addrs.find(ipaddress));
+}
+
+std::string EthernetInterface::getAddressObjectPath(IP::Protocol
+ addressType) const
+{
+
+ std::string type = convertForMessage(addressType);
+ type = type.substr(type.rfind('.')+1);
+ std::transform(type.begin(), type.end(), type.begin(), ::tolower);
+
+ std::experimental::filesystem::path objectPath;
+ objectPath /= std::string(OBJ_NETWORK);
+ objectPath /= interfaceName();
+ objectPath /= type;
+ objectPath /= std::to_string(getAddressCount(addressType));
+ return objectPath.string();
+
}
}//namespace network
diff --git a/ethernet_interface.hpp b/ethernet_interface.hpp
index 71a3003..ab69a78 100644
--- a/ethernet_interface.hpp
+++ b/ethernet_interface.hpp
@@ -1,6 +1,10 @@
#pragma once
+#include "ipaddress.hpp"
+#include "types.hpp"
+
#include "xyz/openbmc_project/Network/EthernetInterface/server.hpp"
+#include "xyz/openbmc_project/Network/IP/Create/server.hpp"
#include <sdbusplus/bus.hpp>
#include <sdbusplus/server/object.hpp>
@@ -11,17 +15,14 @@
{
namespace network
{
-namespace details
-{
-template <typename T>
-using ServerObject = typename sdbusplus::server::object::object<T>;
+using Ifaces =
+ sdbusplus::server::object::object<
+ sdbusplus::xyz::openbmc_project::Network::server::EthernetInterface,
+ sdbusplus::xyz::openbmc_project::Network::IP::server::Create>;
-using EthernetIface =
- sdbusplus::server::object::object <
- sdbusplus::xyz::openbmc_project::Network::server::EthernetInterface >;
+using IP = sdbusplus::xyz::openbmc_project::Network::server::IP;
-} // namespace details
using LinkSpeed = uint16_t;
using DuplexMode = uint8_t;
@@ -34,7 +35,7 @@
* @details A concrete implementation for the
* xyz.openbmc_project.Network.EthernetInterface DBus API.
*/
-class EthernetInterface : public details::EthernetIface
+class EthernetInterface : public Ifaces
{
public:
EthernetInterface() = delete;
@@ -52,7 +53,20 @@
*/
EthernetInterface(sdbusplus::bus::bus& bus,
const std::string& objPath,
- bool dhcpEnabled);
+ bool dhcpEnabled,
+ const AddrList& addrs);
+
+ /** @brief Function to create ipaddress dbus object.
+ * @param[in] addressType - Type of ip address.
+ * @param[in] ipaddress- IP adress.
+ * @param[in] prefixLength - Length of prefix.
+ * @param[in] gateway - Gateway ip address.
+ */
+
+ void iP(IP::Protocol addressType,
+ std::string ipaddress,
+ uint8_t prefixLength,
+ std::string gateway) override;
/** @brief delete the dbus object of the given ipaddress.
*/
@@ -74,6 +88,28 @@
std::string getMACAddress() const;
+ /** @brief construct the ip address dbus object path.
+ * @param[in] addressType - Type of ip address.
+ * @return path of the address object.
+ */
+
+ std::string getAddressObjectPath(IP::Protocol addressType) const;
+
+ /** @brief get the ipadress count for a specific type on this interface.
+ * @param[in] addressType - Type of ip address.
+ * @return count of ipaddreses for the incoming type.
+ */
+
+ size_t getAddressCount(IP::Protocol addressType) const;
+
+
+ /** @brief Persistent sdbusplus DBus bus connection. */
+ sdbusplus::bus::bus& bus;
+
+ /** @brief Persistent map of IPAddress dbus objects and their names */
+ std::map<std::string, std::unique_ptr<IPAddress>> addrs;
+
+
};
} // namespace network
diff --git a/network_manager.cpp b/network_manager.cpp
index 479e8a4..7362943 100644
--- a/network_manager.cpp
+++ b/network_manager.cpp
@@ -4,7 +4,7 @@
#include <phosphor-logging/log.hpp>
#include <algorithm>
-
+#include <experimental/filesystem>
#include <arpa/inet.h>
#include <dirent.h>
#include <net/if.h>
@@ -14,34 +14,38 @@
{
namespace network
{
+
using namespace phosphor::logging;
+namespace fs = std::experimental::filesystem;
Manager::Manager(sdbusplus::bus::bus& bus, const char* objPath):
details::VLANCreateIface(bus, objPath, true)
{
- auto interfaceInfoList = getInterfaceAndaddrs();
+ auto interfaceInfoList = getInterfaceAddrs();
for( const auto& intfInfo : interfaceInfoList )
{
- std::string objectPath = std::string(OBJ_NETWORK) + "/" + intfInfo.first;
+
+ fs::path objectPath = std::string(OBJ_NETWORK);
+ objectPath /= intfInfo.first;
this->interfaces.emplace(std::make_pair(
intfInfo.first,
std::make_unique<
phosphor::network::EthernetInterface >
(bus, objectPath.c_str(),
- false)));
+ false,intfInfo.second)));
}
}
-void Manager::vLAN(details::IntfName interfaceName, uint16_t id)
+void Manager::vLAN(IntfName interfaceName, uint16_t id)
{
}
-details::IntfAddrMap Manager::getInterfaceAndaddrs() const
+IntfAddrMap Manager::getInterfaceAddrs() const
{
- details::IntfAddrMap intfMap;
- details::AddrList addrList;
+ IntfAddrMap intfMap;
+ AddrList addrList;
struct ifaddrs* ifaddr;
// attempt to fill struct with ifaddrs
if (getifaddrs(&ifaddr) == -1)
@@ -86,28 +90,28 @@
addrList.clear();
}
intfName = ifa->ifa_name;
- details::AddrInfo info;
- char tmp[INET6_ADDRSTRLEN] = { 0 };
+ AddrInfo info;
+ char ip[INET6_ADDRSTRLEN] = { 0 };
if (ifa->ifa_addr->sa_family == AF_INET)
{
inet_ntop(ifa->ifa_addr->sa_family,
&(((struct sockaddr_in*)(ifa->ifa_addr))->sin_addr),
- tmp,
- sizeof(tmp));
+ ip,
+ sizeof(ip));
}
else
{
inet_ntop(ifa->ifa_addr->sa_family,
&(((struct sockaddr_in6*)(ifa->ifa_addr))->sin6_addr),
- tmp,
- sizeof(tmp));
+ ip,
+ sizeof(ip));
}
info.addrType = ifa->ifa_addr->sa_family;
- info.ipaddress = tmp;
+ info.ipaddress = ip;
addrList.emplace_back(info);
}
}
diff --git a/network_manager.hpp b/network_manager.hpp
index 2e90b23..3d745ce 100644
--- a/network_manager.hpp
+++ b/network_manager.hpp
@@ -1,6 +1,7 @@
#pragma once
#include "ethernet_interface.hpp"
+#include "types.hpp"
#include "xyz/openbmc_project/Network/VLAN/Create/server.hpp"
#include <sdbusplus/bus.hpp>
@@ -69,16 +70,16 @@
*/
Manager(sdbusplus::bus::bus& bus, const char* objPath);
- void vLAN(details::IntfName interfaceName, uint16_t id) override;
+ void vLAN(IntfName interfaceName, uint16_t id) override;
private:
/** @brief Get all the interfaces from the system.
* @returns list of interface names.
*/
- details::IntfAddrMap getInterfaceAndaddrs() const;
+ IntfAddrMap getInterfaceAddrs() const;
/** @brief Persistent map of EthernetInterface dbus objects and their names */
- std::map<details::IntfName, std::unique_ptr<EthernetInterface>> interfaces;
+ std::map<IntfName, std::unique_ptr<EthernetInterface>> interfaces;
};
diff --git a/types.hpp b/types.hpp
new file mode 100644
index 0000000..28b34d9
--- /dev/null
+++ b/types.hpp
@@ -0,0 +1,26 @@
+#pragma once
+
+#include <list>
+#include <string>
+#include <vector>
+#include <map>
+
+namespace phosphor
+{
+namespace network
+{
+
+using IntfName = std::string;
+
+struct AddrInfo {
+ uint8_t addrType;
+ std::string ipaddress;
+ uint16_t prefix;
+};
+
+using AddrList = std::list<AddrInfo>;
+using IntfAddrMap = std::map<IntfName, AddrList>;
+
+
+}//namespace network
+}//namespace phosphor