]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
network/netdev: enter ready state only when it is created by us
authorYu Watanabe <watanabe.yu+github@gmail.com>
Fri, 8 Nov 2024 15:58:29 +0000 (00:58 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Thu, 14 Nov 2024 01:17:19 +0000 (10:17 +0900)
Follow-up for PR #34909.

This fixes an issue that network interfaces cannot join a master netdev,
like bond or bridge, when the corresponding .netdev is reloaded.

With PR #34909, networkd supports reloading .netdev files. However,
When a .netdev file is modified and reloaded, ifindex is copied from
the old NetDev object to the new one. Thus, even if the interface is
successfully updated, netdev_set_ifindex_impl() will return 0 and
netdev_enter_ready() will never called. If the netdev is a kind of
master netdev, then port interfaces cannot join the master netdev,
as REQUEST_TYPE_SET_LINK_MASTER requires that the master netdev is
in the ready state.

src/network/netdev/netdev.c

index 805ec095715a4ac5ca8bfb43c6a54c86de96c9d0..67a98576fd678f0b6095bab923e5f7fd59f4b9c3 100644 (file)
@@ -432,18 +432,17 @@ static int netdev_create_handler(sd_netlink *rtnl, sd_netlink_message *m, NetDev
         assert(netdev->state != _NETDEV_STATE_INVALID);
 
         r = sd_netlink_message_get_errno(m);
-        if (r == -EEXIST)
-                log_netdev_info(netdev, "netdev exists, using existing without changing its parameters");
-        else if (r < 0) {
-                log_netdev_warning_errno(netdev, r, "netdev could not be created: %m");
+        if (r >= 0)
+                log_netdev_debug(netdev, "Created.");
+        else if (r == -EEXIST && netdev->ifindex > 0)
+                log_netdev_debug(netdev, "Already exists.");
+        else {
+                log_netdev_warning_errno(netdev, r, "Failed to create netdev: %m");
                 netdev_enter_failed(netdev);
-
-                return 1;
+                return 0;
         }
 
-        log_netdev_debug(netdev, "Created");
-
-        return 1;
+        return netdev_enter_ready(netdev);
 }
 
 int netdev_set_ifindex_internal(NetDev *netdev, int ifindex) {
@@ -464,8 +463,6 @@ int netdev_set_ifindex_internal(NetDev *netdev, int ifindex) {
 }
 
 static int netdev_set_ifindex_impl(NetDev *netdev, const char *name, int ifindex) {
-        int r;
-
         assert(netdev);
         assert(name);
         assert(ifindex > 0);
@@ -478,11 +475,7 @@ static int netdev_set_ifindex_impl(NetDev *netdev, const char *name, int ifindex
                                                 "Received netlink message with unexpected interface name %s (ifindex=%i).",
                                                 name, ifindex);
 
-        r = netdev_set_ifindex_internal(netdev, ifindex);
-        if (r <= 0)
-                return r;
-
-        return netdev_enter_ready(netdev);
+        return netdev_set_ifindex_internal(netdev, ifindex);
 }
 
 int netdev_set_ifindex(NetDev *netdev, sd_netlink_message *message) {
@@ -875,18 +868,26 @@ static int stacked_netdev_process_request(Request *req, Link *link, void *userda
 }
 
 static int create_stacked_netdev_handler(sd_netlink *rtnl, sd_netlink_message *m, Request *req, Link *link, void *userdata) {
+        NetDev *netdev = ASSERT_PTR(userdata);
         int r;
 
         assert(m);
         assert(link);
 
         r = sd_netlink_message_get_errno(m);
-        if (r < 0 && r != -EEXIST) {
-                log_link_message_warning_errno(link, m, r, "Could not create stacked netdev");
+        if (r >= 0)
+                log_netdev_debug(netdev, "Created.");
+        else if (r == -EEXIST && netdev->ifindex > 0)
+                log_netdev_debug(netdev, "Already exists.");
+        else {
+                log_netdev_warning_errno(netdev, r, "Failed to create netdev: %m");
+                netdev_enter_failed(netdev);
                 link_enter_failed(link);
                 return 0;
         }
 
+        (void) netdev_enter_ready(netdev);
+
         if (link->create_stacked_netdev_messages == 0) {
                 link->stacked_netdevs_created = true;
                 log_link_debug(link, "Stacked netdevs created.");