1 #pragma once 2 3 #include "config.h" 4 5 #include "ethernet_interface.hpp" 6 #include "types.hpp" 7 8 #include <netinet/ether.h> 9 #include <unistd.h> 10 11 #include <cstring> 12 #include <optional> 13 #include <sdbusplus/bus.hpp> 14 #include <string> 15 #include <string_view> 16 #include <xyz/openbmc_project/Network/EthernetInterface/server.hpp> 17 18 namespace phosphor 19 { 20 namespace network 21 { 22 23 using EthernetInterfaceIntf = 24 sdbusplus::xyz::openbmc_project::Network::server::EthernetInterface; 25 26 constexpr auto IPV4_MIN_PREFIX_LENGTH = 1; 27 constexpr auto IPV4_MAX_PREFIX_LENGTH = 32; 28 constexpr auto IPV6_MAX_PREFIX_LENGTH = 128; 29 constexpr auto IPV4_PREFIX = "169.254"; 30 constexpr auto IPV6_PREFIX = "fe80"; 31 32 namespace mac_address 33 { 34 35 /** @brief gets the MAC address from the Inventory. 36 * @param[in] bus - DBUS Bus Object. 37 * @param[in] intfName - Interface name 38 */ 39 ether_addr getfromInventory(sdbusplus::bus::bus& bus, 40 const std::string& intfName); 41 42 /** @brief Converts the given mac address into byte form 43 * @param[in] str - The mac address in human readable form 44 * @returns A mac address in network byte order 45 * @throws std::runtime_error for bad mac 46 */ 47 ether_addr fromString(const char* str); 48 inline ether_addr fromString(const std::string& str) 49 { 50 return fromString(str.c_str()); 51 } 52 53 /** @brief Converts the given mac address bytes into a string 54 * @param[in] mac - The mac address 55 * @returns A valid mac address string 56 */ 57 std::string toString(const ether_addr& mac); 58 59 /** @brief Determines if the mac address is empty 60 * @param[in] mac - The mac address 61 * @return True if 00:00:00:00:00:00 62 */ 63 bool isEmpty(const ether_addr& mac); 64 65 /** @brief Determines if the mac address is a multicast address 66 * @param[in] mac - The mac address 67 * @return True if multicast bit is set 68 */ 69 bool isMulticast(const ether_addr& mac); 70 71 /** @brief Determines if the mac address is a unicast address 72 * @param[in] mac - The mac address 73 * @return True if not multicast or empty 74 */ 75 bool isUnicast(const ether_addr& mac); 76 77 } // namespace mac_address 78 79 constexpr auto networkdService = "systemd-networkd.service"; 80 constexpr auto timeSynchdService = "systemd-timesyncd.service"; 81 82 /* @brief converts the given subnet into prefix notation. 83 * @param[in] addressFamily - IP address family(AF_INET/AF_INET6). 84 * @param[in] mask - Subnet Mask. 85 * @returns prefix. 86 */ 87 uint8_t toCidr(int addressFamily, const std::string& mask); 88 89 /* @brief converts a sockaddr for the specified address family into 90 * a type_safe InAddrAny. 91 * @param[in] addressFamily - The address family of the buf 92 * @param[in] buf - The network byte order address 93 */ 94 InAddrAny addrFromBuf(int addressFamily, std::string_view buf); 95 96 /* @brief converts the ip bytes into a string representation 97 * @param[in] addr - input ip address to convert. 98 * @returns String representation of the ip. 99 */ 100 std::string toString(const InAddrAny& addr); 101 std::string toString(const struct in_addr& addr); 102 std::string toString(const struct in6_addr& addr); 103 104 /* @brief converts the prefix into subnetmask. 105 * @param[in] addressFamily - IP address family(AF_INET/AF_INET6). 106 * @param[in] prefix - prefix length. 107 * @returns subnet mask. 108 */ 109 std::string toMask(int addressFamily, uint8_t prefix); 110 111 /* @brief checks that the given ip address is link local or not. 112 * @param[in] address - IP address. 113 * @returns true if it is linklocal otherwise false. 114 */ 115 bool isLinkLocalIP(const std::string& address); 116 117 /* @brief checks that the given ip address valid or not. 118 * @param[in] addressFamily - IP address family(AF_INET/AF_INET6). 119 * @param[in] address - IP address. 120 * @returns true if it is valid otherwise false. 121 */ 122 bool isValidIP(int addressFamily, const std::string& address); 123 124 /* @brief checks that the given prefix is valid or not. 125 * @param[in] addressFamily - IP address family(AF_INET/AF_INET6). 126 * @param[in] prefix - prefix length. 127 * @returns true if it is valid otherwise false. 128 */ 129 bool isValidPrefix(int addressFamily, uint8_t prefixLength); 130 131 /** @brief Gets the map of interface and the associated 132 * address. 133 * @returns map of interface and the address. 134 */ 135 IntfAddrMap getInterfaceAddrs(); 136 137 /** @brief Get all the interfaces from the system. 138 * @returns list of interface names. 139 */ 140 InterfaceList getInterfaces(); 141 142 /** @brief Delete the given interface. 143 * @param[in] intf - interface name. 144 */ 145 void deleteInterface(const std::string& intf); 146 147 /** @brief Converts the interface name into a u-boot environment 148 * variable that would hold its ethernet address. 149 * 150 * @param[in] intf - interface name 151 * @return The name of th environment key 152 */ 153 std::optional<std::string> interfaceToUbootEthAddr(const char* intf); 154 155 /** @brief read the DHCP value from the configuration file 156 * @param[in] confDir - Network configuration directory. 157 * @param[in] intf - Interface name. 158 */ 159 EthernetInterfaceIntf::DHCPConf getDHCPValue(const std::string& confDir, 160 const std::string& intf); 161 162 namespace internal 163 { 164 165 /* @brief runs the given command in child process. 166 * @param[in] path - path of the binary file which needs to be execeuted. 167 * @param[in] args - arguments of the command. 168 */ 169 void executeCommandinChildProcess(const char* path, char** args); 170 171 /** @brief Get ignored interfaces from environment */ 172 std::string_view getIgnoredInterfacesEnv(); 173 174 /** @brief Parse the comma separated interface names */ 175 std::set<std::string_view> parseInterfaces(std::string_view interfaces); 176 177 /** @brief Get the ignored interfaces */ 178 const std::set<std::string_view>& getIgnoredInterfaces(); 179 180 } // namespace internal 181 182 /* @brief runs the given command in child process. 183 * @param[in] path -path of the binary file which needs to be execeuted. 184 * @param[in] tArgs - arguments of the command. 185 */ 186 template <typename... ArgTypes> 187 void execute(const char* path, ArgTypes&&... tArgs) 188 { 189 using expandType = char*[]; 190 191 expandType args = {const_cast<char*>(tArgs)..., nullptr}; 192 193 internal::executeCommandinChildProcess(path, args); 194 } 195 196 } // namespace network 197 198 class Descriptor 199 { 200 private: 201 /** default value */ 202 int fd = -1; 203 204 public: 205 Descriptor() = default; 206 Descriptor(const Descriptor&) = delete; 207 Descriptor& operator=(const Descriptor&) = delete; 208 Descriptor(Descriptor&&) = delete; 209 Descriptor& operator=(Descriptor&&) = delete; 210 211 explicit Descriptor(int fd) : fd(fd) 212 { 213 } 214 215 /* @brief sets the internal file descriptor with the given descriptor 216 * and closes the old descriptor. 217 * @param[in] descriptor - File/Socket descriptor. 218 */ 219 void set(int descriptor) 220 { 221 // same descriptor given 222 if (fd == descriptor) 223 { 224 return; 225 } 226 227 // close the old descriptor 228 if (fd >= 0) 229 { 230 close(fd); 231 } 232 233 fd = descriptor; 234 } 235 236 ~Descriptor() 237 { 238 if (fd >= 0) 239 { 240 close(fd); 241 } 242 } 243 244 int operator()() const 245 { 246 return fd; 247 } 248 }; 249 250 } // namespace phosphor 251