network/netdev: do not try to update if not supported
authorYu Watanabe <watanabe.yu+github@gmail.com>
Sun, 10 Nov 2024 00:51:32 +0000 (09:51 +0900)
committerYu Watanabe <watanabe.yu+github@gmail.com>
Thu, 14 Nov 2024 01:17:19 +0000 (10:17 +0900)
Some netdevs cannot update there properties after created.
Let's skip requests in that case.

src/network/netdev/bareudp.c
src/network/netdev/ipvlan.c
src/network/netdev/macvlan.c
src/network/netdev/netdev.c
src/network/netdev/netdev.h
src/network/netdev/veth.c
src/network/netdev/vrf.c
src/network/netdev/vxcan.c
src/network/netdev/wireguard.c

index b2a161ee7a3a53acad0b356e247668c17bc8d2a9..e122abd97fcc166e88cf5464664493edff1108ed 100644 (file)
@@ -72,4 +72,5 @@ const NetDevVTable bare_udp_vtable = {
         .fill_message_create = netdev_bare_udp_fill_message_create,
         .create_type = NETDEV_CREATE_INDEPENDENT,
         .iftype = ARPHRD_NONE,
+        .keep_existing = true,
 };
index 5cfae1eb6432a51b2f11617dcadeba06a9c3c66d..6e50f72aaa7b68e0b4289fff8aea5d1bd357267d 100644 (file)
@@ -60,6 +60,7 @@ const NetDevVTable ipvlan_vtable = {
         .can_set_mac = ipvlan_can_set_mac,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
 
 const NetDevVTable ipvtap_vtable = {
@@ -71,6 +72,7 @@ const NetDevVTable ipvtap_vtable = {
         .can_set_mac = ipvlan_can_set_mac,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
 
 IPVlanMode link_get_ipvlan_mode(Link *link) {
index 1537d868b5f15a13bee3f3abc3dbe414e4848e7c..fd112b58e17033799ba53b0e28f90f648b96861f 100644 (file)
@@ -178,6 +178,7 @@ const NetDevVTable macvtap_vtable = {
         .create_type = NETDEV_CREATE_STACKED,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
 
 const NetDevVTable macvlan_vtable = {
@@ -189,4 +190,5 @@ const NetDevVTable macvlan_vtable = {
         .create_type = NETDEV_CREATE_STACKED,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
index 6cce3838d1fe35618ff44964938605bd84046c9c..d3c2a8e4424cdeea7640cf5d3f7d2f32f1fac32b 100644 (file)
@@ -400,7 +400,7 @@ int netdev_enter_ready(NetDev *netdev) {
         assert(netdev);
         assert(netdev->ifname);
 
-        if (netdev->state != NETDEV_STATE_CREATING)
+        if (!IN_SET(netdev->state, NETDEV_STATE_LOADING, NETDEV_STATE_CREATING))
                 return 0;
 
         netdev->state = NETDEV_STATE_READY;
@@ -856,6 +856,15 @@ static int stacked_netdev_process_request(Request *req, Link *link, void *userda
         if (!netdev_is_managed(netdev))
                 goto cancelled; /* Already detached, due to e.g. reloading .netdev files, cancelling the request. */
 
+        if (NETDEV_VTABLE(netdev)->keep_existing && netdev->ifindex > 0) {
+                /* Already exists, and the netdev does not support updating, entering the ready state. */
+                r = netdev_enter_ready(netdev);
+                if (r < 0)
+                        return r;
+
+                goto cancelled;
+        }
+
         r = netdev_is_ready_to_create(netdev, link);
         if (r <= 0)
                 return r;
@@ -948,6 +957,15 @@ static int independent_netdev_process_request(Request *req, Link *link, void *us
         if (!netdev_is_managed(netdev))
                 return 1; /* Already detached, due to e.g. reloading .netdev files, cancelling the request. */
 
+        if (NETDEV_VTABLE(netdev)->keep_existing && netdev->ifindex > 0) {
+                /* Already exists, and the netdev does not support updating, entering the ready state. */
+                r = netdev_enter_ready(netdev);
+                if (r < 0)
+                        return r;
+
+                return 1; /* Skip this request. */
+        }
+
         r = netdev_is_ready_to_create(netdev, NULL);
         if (r <= 0)
                 return r;
index 765496d04471f831c84ddafac60704b9c2693f48..b330aa394d7ce6d7fa9b4e4fb738100a378907a4 100644 (file)
@@ -199,6 +199,10 @@ typedef struct NetDevVTable {
 
         /* When assigning ifindex to the netdev, skip to check if the netdev kind matches. */
         bool skip_netdev_kind_check;
+
+        /* Provides if the netdev can be updated, that is, whether RTM_NEWLINK with existing ifindex is supported or not.
+         * If this is true, the netdev does not support updating. */
+        bool keep_existing;
 } NetDevVTable;
 
 extern const NetDevVTable * const netdev_vtable[_NETDEV_KIND_MAX];
index edebcf0a747c6a2bbbd9f5ac868310f7b8893b22..54d3b59734963740dc3354b8548418cf1f4bd37e 100644 (file)
@@ -150,4 +150,5 @@ const NetDevVTable veth_vtable = {
         .get_ifindex = netdev_veth_get_ifindex,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
index 9e20bd22b28ba2eafecac7170ce01da97df7dfdf..c35419f859f90d8396ad0edd1c168fa53461d25c 100644 (file)
@@ -33,4 +33,5 @@ const NetDevVTable vrf_vtable = {
         .can_set_mac = vrf_can_set_mac,
         .iftype = ARPHRD_ETHER,
         .generate_mac = true,
+        .keep_existing = true,
 };
index 929d70f61af5f8a47518e09b6df3a272f60b17f8..2de89b8e24425a8f0ce7cbfe79a4e6627e4da681 100644 (file)
@@ -124,4 +124,5 @@ const NetDevVTable vxcan_vtable = {
         .set_ifindex = netdev_vxcan_set_ifindex,
         .get_ifindex = netdev_vxcan_get_ifindex,
         .iftype = ARPHRD_CAN,
+        .keep_existing = true,
 };
index 9e8dfb259a95157b3379005804e0c62e2f92dccc..8d1dddf8288f644f7a51f35fdd75552d88b8d4f9 100644 (file)
@@ -1265,4 +1265,5 @@ const NetDevVTable wireguard_vtable = {
         .create_type = NETDEV_CREATE_INDEPENDENT,
         .config_verify = wireguard_verify,
         .iftype = ARPHRD_NONE,
+        .keep_existing = true,
 };