return 0;
}
+void link_assign_netdev(Link *link) {
+ _unused_ _cleanup_(netdev_unrefp) NetDev *old = NULL;
+ NetDev *netdev;
+
+ assert(link);
+ assert(link->manager);
+ assert(link->ifname);
+
+ old = TAKE_PTR(link->netdev);
+
+ if (netdev_get(link->manager, link->ifname, &netdev) < 0)
+ return;
+
+ if (netdev->ifindex != link->ifindex)
+ return;
+
+ if (NETDEV_VTABLE(netdev)->iftype != link->iftype)
+ return;
+
+ if (!NETDEV_VTABLE(netdev)->skip_netdev_kind_check) {
+ const char *kind;
+
+ if (netdev->kind == NETDEV_KIND_TAP)
+ kind = "tun"; /* the kernel does not distinguish between tun and tap */
+ else
+ kind = netdev_kind_to_string(netdev->kind);
+
+ if (!streq_ptr(kind, link->kind))
+ return;
+ }
+
+ link->netdev = netdev_ref(netdev);
+
+ if (netdev != old)
+ log_link_debug(link, "Found matching .netdev file: %s", netdev->filename);
+}
+
void netdev_enter_failed(NetDev *netdev) {
netdev->state = NETDEV_STATE_FAILED;
}
bool netdev_is_managed(NetDev *netdev);
int netdev_get(Manager *manager, const char *name, NetDev **ret);
+void link_assign_netdev(Link *link);
int netdev_set_ifindex(NetDev *netdev, sd_netlink_message *newlink);
int netdev_generate_hw_addr(NetDev *netdev, Link *link, const char *name,
const struct hw_addr_data *hw_addr, struct hw_addr_data *ret);
int link_reconfigure_impl(Link *link, bool force) {
Network *network = NULL;
- NetDev *netdev = NULL;
int r;
assert(link);
+ link_assign_netdev(link);
+
if (IN_SET(link->state, LINK_STATE_PENDING, LINK_STATE_LINGER))
return 0;
- r = netdev_get(link->manager, link->ifname, &netdev);
- if (r < 0 && r != -ENOENT)
- return r;
-
r = link_get_network(link, &network);
if (r < 0 && r != -ENOENT)
return r;
link_free_engines(link);
link->network = network_unref(link->network);
- netdev_unref(link->netdev);
- link->netdev = netdev_ref(netdev);
-
if (!network) {
link_set_state(link, LINK_STATE_UNMANAGED);
return 0;