]> git.ipfire.org Git - thirdparty/systemd.git/blobdiff - src/network/networkd-dhcp4.c
network: honor MTUBytes= setting
[thirdparty/systemd.git] / src / network / networkd-dhcp4.c
index 01f4e955c85e9b899cf4e4b1c0e45866de9ec3b7..7907988a9bb9937c41f9c4411bee2f4df6c52987 100644 (file)
@@ -1,6 +1,6 @@
 /* SPDX-License-Identifier: LGPL-2.1+ */
 
-#include <netinet/ether.h>
+#include <netinet/in.h>
 #include <linux/if.h>
 
 #include "alloc-util.h"
@@ -261,7 +261,7 @@ static int dhcp_lease_lost(Link *link) {
 
                 r = sd_dhcp_lease_get_mtu(link->dhcp_lease, &mtu);
                 if (r >= 0 && link->original_mtu != mtu) {
-                        r = link_set_mtu(link, link->original_mtu, true);
+                        r = link_set_mtu(link, link->original_mtu);
                         if (r < 0) {
                                 log_link_warning(link,
                                                  "DHCP error: could not reset MTU");
@@ -454,7 +454,7 @@ static int dhcp_lease_acquired(sd_dhcp_client *client, Link *link) {
 
                 r = sd_dhcp_lease_get_mtu(lease, &mtu);
                 if (r >= 0) {
-                        r = link_set_mtu(link, mtu, true);
+                        r = link_set_mtu(link, mtu);
                         if (r < 0)
                                 log_link_error_errno(link, r, "Failed to set MTU to %" PRIu16 ": %m", mtu);
                 }
@@ -512,16 +512,44 @@ static int dhcp_lease_acquired(sd_dhcp_client *client, Link *link) {
         return 0;
 }
 
-static void dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
+static int dhcp_server_is_black_listed(Link *link, sd_dhcp_client *client) {
+        sd_dhcp_lease *lease;
+        struct in_addr addr;
+        int r;
+
+        assert(link);
+        assert(link->network);
+        assert(client);
+
+        r = sd_dhcp_client_get_lease(client, &lease);
+        if (r < 0)
+                return log_link_error_errno(link, r, "Failed to get DHCP lease: %m");
+
+        r = sd_dhcp_lease_get_server_identifier(lease, &addr);
+        if (r < 0)
+                return log_link_debug_errno(link, r, "Failed to get DHCP server ip address: %m");
+
+        if (set_contains(link->network->dhcp_black_listed_ip, UINT32_TO_PTR(addr.s_addr))) {
+                log_struct(LOG_DEBUG,
+                           LOG_LINK_INTERFACE(link),
+                           LOG_LINK_MESSAGE(link, "DHCPv4 ip '%u.%u.%u.%u' found in black listed ip addresses, ignoring offer",
+                                            ADDRESS_FMT_VAL(addr)));
+                return true;
+        }
+
+        return false;
+}
+
+static int dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
         Link *link = userdata;
-        int r = 0;
+        int r;
 
         assert(link);
         assert(link->network);
         assert(link->manager);
 
         if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
-                return;
+                return 0;
 
         switch (event) {
                 case SD_DHCP_CLIENT_EVENT_STOP:
@@ -532,26 +560,27 @@ static void dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
                                 log_link_debug(link, "DHCP client is stopped. Acquiring IPv4 link-local address");
 
                                 r = sd_ipv4ll_start(link->ipv4ll);
-                                if (r < 0) {
-                                        log_link_warning_errno(link, r, "Could not acquire IPv4 link-local address: %m");
-                                        return;
-                                }
+                                if (r < 0)
+                                        return log_link_warning_errno(link, r, "Could not acquire IPv4 link-local address: %m");
                         }
 
+                        if (link->network->dhcp_send_release)
+                                (void) sd_dhcp_client_send_release(client);
+
                         _fallthrough_;
                 case SD_DHCP_CLIENT_EVENT_EXPIRED:
                 case SD_DHCP_CLIENT_EVENT_IP_CHANGE:
 
                         if (link->network->dhcp_critical) {
                                 log_link_error(link, "DHCPv4 connection considered system critical, ignoring request to reconfigure it.");
-                                return;
+                                return 0;
                         }
 
                         if (link->dhcp_lease) {
                                 r = dhcp_lease_lost(link);
                                 if (r < 0) {
                                         link_enter_failed(link);
-                                        return;
+                                        return r;
                                 }
                         }
 
@@ -559,7 +588,7 @@ static void dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
                                 r = dhcp_lease_acquired(client, link);
                                 if (r < 0) {
                                         link_enter_failed(link);
-                                        return;
+                                        return r;
                                 }
                         }
 
@@ -568,16 +597,23 @@ static void dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
                         r = dhcp_lease_renew(client, link);
                         if (r < 0) {
                                 link_enter_failed(link);
-                                return;
+                                return r;
                         }
                         break;
                 case SD_DHCP_CLIENT_EVENT_IP_ACQUIRE:
                         r = dhcp_lease_acquired(client, link);
                         if (r < 0) {
                                 link_enter_failed(link);
-                                return;
+                                return r;
                         }
                         break;
+                case SD_DHCP_CLIENT_EVENT_SELECTING:
+                        r = dhcp_server_is_black_listed(link, client);
+                        if (r < 0)
+                                return r;
+                        if (r != 0)
+                                return -ENOMSG;
+                        break;
                 default:
                         if (event < 0)
                                 log_link_warning_errno(link, event, "DHCP error: Client failed: %m");
@@ -586,7 +622,7 @@ static void dhcp4_handler(sd_dhcp_client *client, int event, void *userdata) {
                         break;
         }
 
-        return;
+        return 0;
 }
 
 static int dhcp4_set_hostname(Link *link) {