summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBeniamino Galvani <bgalvani@redhat.com>2020-07-09 14:29:41 +0200
committerBeniamino Galvani <bgalvani@redhat.com>2020-07-29 18:26:15 +0200
commit18c76745f6bdc310bb6139ef8425bc6ed7109908 (patch)
tree43c873f1018ec1d8cb7f856b74069b1e68ceb468
parentdcb48bc9d9745b7d3915270a7aabac44372dbe72 (diff)
downloadNetworkManager-18c76745f6bdc310bb6139ef8425bc6ed7109908.tar.gz
dhcp6: don't require a hardware address
The systemd DHCPv6 client requires a hardware address only to determine the IAID; NM always overrides the IAID with its own and therefore the hwaddr is not used. Removing such requirement allows DHCPv6 to run over PPP, which is useful with DHCPv6-PD to get a prefix from the ISP. To test this, I set up a server with pppoe-server, radvd and the Wide DHCPv6 server providing an address and a prefix. On the client, NM was able to obtain a prefix using both dhcp=dhclient and dhcp=systemd. Note that if there is no hardware address and you specify ipv6.dhcp-duid=ll or ipv6.dhcp-iaid=mac, a warning will be emitted and NM will use a random DUID/IAID. https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/478 (cherry picked from commit 76a6a30577e7748a67d5ee0c3f5c252b751db81c) (cherry picked from commit 905d4eb36e82499bbae4136253223ca04c4bcd77)
-rw-r--r--src/devices/nm-device.c9
-rw-r--r--src/dhcp/nm-dhcp-manager.c42
-rw-r--r--src/dhcp/nm-dhcp-manager.h2
-rw-r--r--src/dhcp/nm-dhcp-systemd.c20
4 files changed, 24 insertions, 49 deletions
diff --git a/src/devices/nm-device.c b/src/devices/nm-device.c
index e6b3624c73..8dee90fbe1 100644
--- a/src/devices/nm-device.c
+++ b/src/devices/nm-device.c
@@ -9266,7 +9266,6 @@ dhcp6_start_with_link_ready (NMDevice *self, NMConnection *connection)
NMDevicePrivate *priv = NM_DEVICE_GET_PRIVATE (self);
NMSettingIPConfig *s_ip6;
gs_unref_bytes GBytes *hwaddr = NULL;
- gs_unref_bytes GBytes *bcast_hwaddr = NULL;
gs_unref_bytes GBytes *duid = NULL;
gboolean enforce_duid = FALSE;
const NMPlatformLink *pllink;
@@ -9292,20 +9291,16 @@ dhcp6_start_with_link_ready (NMDevice *self, NMConnection *connection)
}
pllink = nm_platform_link_get (nm_device_get_platform (self), nm_device_get_ip_ifindex (self));
- if (pllink) {
+ if (pllink)
hwaddr = nmp_link_address_get_as_bytes (&pllink->l_address);
- bcast_hwaddr = nmp_link_address_get_as_bytes (&pllink->l_broadcast);
- }
iaid = dhcp_get_iaid (self, AF_INET6, connection, &iaid_explicit);
-
duid = dhcp6_get_duid (self, connection, hwaddr, &enforce_duid);
+
priv->dhcp_data_6.client = nm_dhcp_manager_start_ip6 (nm_dhcp_manager_get (),
nm_device_get_multi_index (self),
nm_device_get_ip_iface (self),
nm_device_get_ip_ifindex (self),
- hwaddr,
- bcast_hwaddr,
&ll_addr->address,
nm_connection_get_uuid (connection),
nm_device_get_route_table (self, AF_INET6),
diff --git a/src/dhcp/nm-dhcp-manager.c b/src/dhcp/nm-dhcp-manager.c
index 333744dd31..2d6323b8c0 100644
--- a/src/dhcp/nm-dhcp-manager.c
+++ b/src/dhcp/nm-dhcp-manager.c
@@ -239,21 +239,27 @@ client_start (NMDhcpManager *self,
g_return_val_if_fail (!dhcp_client_id || g_bytes_get_size (dhcp_client_id) >= 2, NULL);
g_return_val_if_fail (!error || !*error, NULL);
- if (!hwaddr || !bcast_hwaddr) {
- nm_utils_error_set (error,
- NM_UTILS_ERROR_UNKNOWN,
- "missing %s address",
- hwaddr ? "broadcast" : "MAC");
- return NULL;
- }
+ if (addr_family == AF_INET) {
+ if (!hwaddr || !bcast_hwaddr) {
+ nm_utils_error_set (error,
+ NM_UTILS_ERROR_UNKNOWN,
+ "missing %s address",
+ hwaddr ? "broadcast" : "MAC");
+ return NULL;
+ }
- hwaddr_len = g_bytes_get_size (hwaddr);
- if ( hwaddr_len == 0
- || hwaddr_len > NM_UTILS_HWADDR_LEN_MAX) {
- nm_utils_error_set (error,
- NM_UTILS_ERROR_UNKNOWN,
- "invalid MAC address");
- g_return_val_if_reached (NULL) ;
+ hwaddr_len = g_bytes_get_size (hwaddr);
+ if ( hwaddr_len == 0
+ || hwaddr_len > NM_UTILS_HWADDR_LEN_MAX) {
+ nm_utils_error_set (error,
+ NM_UTILS_ERROR_UNKNOWN,
+ "invalid MAC address");
+ g_return_val_if_reached (NULL) ;
+ }
+ nm_assert (g_bytes_get_size (hwaddr) == g_bytes_get_size (bcast_hwaddr));
+ } else {
+ hwaddr = NULL;
+ bcast_hwaddr = NULL;
}
if (hostname) {
@@ -267,8 +273,6 @@ client_start (NMDhcpManager *self,
}
}
- nm_assert (g_bytes_get_size (hwaddr) == g_bytes_get_size (bcast_hwaddr));
-
priv = NM_DHCP_MANAGER_GET_PRIVATE (self);
/* Kill any old client instance */
@@ -453,8 +457,6 @@ nm_dhcp_manager_start_ip6 (NMDhcpManager *self,
NMDedupMultiIndex *multi_idx,
const char *iface,
int ifindex,
- GBytes *hwaddr,
- GBytes *bcast_hwaddr,
const struct in6_addr *ll_addr,
const char *uuid,
guint32 route_table,
@@ -488,8 +490,8 @@ nm_dhcp_manager_start_ip6 (NMDhcpManager *self,
multi_idx,
iface,
ifindex,
- hwaddr,
- bcast_hwaddr,
+ NULL,
+ NULL,
uuid,
route_table,
route_metric,
diff --git a/src/dhcp/nm-dhcp-manager.h b/src/dhcp/nm-dhcp-manager.h
index 1b793c22f8..265cf01853 100644
--- a/src/dhcp/nm-dhcp-manager.h
+++ b/src/dhcp/nm-dhcp-manager.h
@@ -53,8 +53,6 @@ NMDhcpClient * nm_dhcp_manager_start_ip6 (NMDhcpManager *manager,
struct _NMDedupMultiIndex *multi_idx,
const char *iface,
int ifindex,
- GBytes *hwaddr,
- GBytes *bcast_hwaddr,
const struct in6_addr *ll_addr,
const char *uuid,
guint32 route_table,
diff --git a/src/dhcp/nm-dhcp-systemd.c b/src/dhcp/nm-dhcp-systemd.c
index 23862e9e9b..c0b7a28c78 100644
--- a/src/dhcp/nm-dhcp-systemd.c
+++ b/src/dhcp/nm-dhcp-systemd.c
@@ -892,15 +892,11 @@ ip6_start (NMDhcpClient *client,
NMDhcpSystemd *self = NM_DHCP_SYSTEMD (client);
NMDhcpSystemdPrivate *priv = NM_DHCP_SYSTEMD_GET_PRIVATE (self);
nm_auto (sd_dhcp6_client_unrefp) sd_dhcp6_client *sd_client = NULL;
- GBytes *hwaddr;
const char *hostname;
int r, i;
const guint8 *duid_arr;
gsize duid_len;
GBytes *duid;
- const uint8_t *hwaddr_arr;
- gsize hwaddr_len;
- int arp_type;
g_return_val_if_fail (!priv->client4, FALSE);
g_return_val_if_fail (!priv->client6, FALSE);
@@ -945,22 +941,6 @@ ip6_start (NMDhcpClient *client,
return FALSE;
}
- hwaddr = nm_dhcp_client_get_hw_addr (client);
- if ( !hwaddr
- || !(hwaddr_arr = g_bytes_get_data (hwaddr, &hwaddr_len))
- || (arp_type = nm_utils_arp_type_detect_from_hwaddrlen (hwaddr_len)) < 0) {
- nm_utils_error_set_literal (error, NM_UTILS_ERROR_UNKNOWN, "invalid MAC address");
- return FALSE;
- }
- r = sd_dhcp6_client_set_mac (sd_client,
- hwaddr_arr,
- hwaddr_len,
- (guint16) arp_type);
- if (r < 0) {
- nm_utils_error_set_errno (error, r, "failed to set MAC address: %s");
- return FALSE;
- }
-
r = sd_dhcp6_client_set_ifindex (sd_client,
nm_dhcp_client_get_ifindex (client));
if (r < 0) {