From 1046bf9b1a484a086f61f646c0cacc84b571b4e1 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Sat, 6 Oct 2018 13:55:19 +0900 Subject: [PATCH] network: add destroy callbacks for asynchronous netlink calls --- src/network/netdev/bridge.c | 5 +- src/network/netdev/geneve.c | 7 +- src/network/netdev/netdev.c | 45 ++++++------- src/network/netdev/netdev.h | 2 +- src/network/networkd-address-label.c | 3 +- src/network/networkd-address.c | 6 +- src/network/networkd-brvlan.c | 5 +- src/network/networkd-dhcp4.c | 4 +- src/network/networkd-dhcp6.c | 20 +++--- src/network/networkd-fdb.c | 5 +- src/network/networkd-ipv4ll.c | 4 +- src/network/networkd-ipv6-proxy-ndp.c | 5 +- src/network/networkd-link.c | 78 +++++++++++++--------- src/network/networkd-link.h | 4 +- src/network/networkd-manager.c | 25 +++---- src/network/networkd-ndisc.c | 2 +- src/network/networkd-route.c | 6 +- src/network/networkd-routing-policy-rule.c | 10 +-- 18 files changed, 131 insertions(+), 105 deletions(-) diff --git a/src/network/netdev/bridge.c b/src/network/netdev/bridge.c index 3ff7189ca7..ce9f75e27b 100644 --- a/src/network/netdev/bridge.c +++ b/src/network/netdev/bridge.c @@ -10,7 +10,7 @@ /* callback for brige netdev's parameter set */ static int netdev_bridge_set_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(netdev_unrefp) NetDev *netdev = userdata; + NetDev *netdev = userdata; int r; assert(netdev); @@ -129,7 +129,8 @@ static int netdev_bridge_post_create(NetDev *netdev, Link *link, sd_netlink_mess if (r < 0) return log_netdev_error_errno(netdev, r, "Could not append IFLA_INFO_DATA attribute: %m"); - r = sd_netlink_call_async(netdev->manager->rtnl, req, netdev_bridge_set_handler, NULL, netdev, 0, NULL); + r = sd_netlink_call_async(netdev->manager->rtnl, req, netdev_bridge_set_handler, + netdev_netlink_destroy_callback, netdev, 0, NULL); if (r < 0) return log_netdev_error_errno(netdev, r, "Could not send rtnetlink message: %m"); diff --git a/src/network/netdev/geneve.c b/src/network/netdev/geneve.c index ff43f94bd2..9350f0257a 100644 --- a/src/network/netdev/geneve.c +++ b/src/network/netdev/geneve.c @@ -18,9 +18,10 @@ /* callback for geneve netdev's created without a backing Link */ static int geneve_netdev_create_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(netdev_unrefp) NetDev *netdev = userdata; + NetDev *netdev = userdata; int r; + assert(netdev); assert(netdev->state != _NETDEV_STATE_INVALID); r = sd_netlink_message_get_errno(m); @@ -135,12 +136,12 @@ static int netdev_geneve_create(NetDev *netdev) { if (r < 0) return log_netdev_error_errno(netdev, r, "Could not append IFLA_LINKINFO attribute: %m"); - r = sd_netlink_call_async(netdev->manager->rtnl, m, geneve_netdev_create_handler, NULL, netdev, 0, NULL); + r = sd_netlink_call_async(netdev->manager->rtnl, m, geneve_netdev_create_handler, + netdev_netlink_destroy_callback, netdev, 0, NULL); if (r < 0) return log_netdev_error_errno(netdev, r, "Could not send rtnetlink message: %m"); netdev_ref(netdev); - netdev->state = NETDEV_STATE_CREATING; log_netdev_debug(netdev, "Creating"); diff --git a/src/network/netdev/netdev.c b/src/network/netdev/netdev.c index 77cbdd0e86..55f24d0fbc 100644 --- a/src/network/netdev/netdev.c +++ b/src/network/netdev/netdev.c @@ -99,25 +99,13 @@ static const char* const netdev_kind_table[_NETDEV_KIND_MAX] = { DEFINE_STRING_TABLE_LOOKUP(netdev_kind, NetDevKind); DEFINE_CONFIG_PARSE_ENUM(config_parse_netdev_kind, netdev_kind, NetDevKind, "Failed to parse netdev kind"); -static void netdev_cancel_callbacks(NetDev *netdev) { - _cleanup_(sd_netlink_message_unrefp) sd_netlink_message *m = NULL; +static void netdev_callbacks_clear(NetDev *netdev) { netdev_join_callback *callback; - if (!netdev || !netdev->manager) + if (!netdev) return; - rtnl_message_new_synthetic_error(netdev->manager->rtnl, -ENODEV, 0, &m); - while ((callback = netdev->callbacks)) { - if (m) { - assert(callback->link); - assert(callback->callback); - assert(netdev->manager); - assert(netdev->manager->rtnl); - - callback->callback(netdev->manager->rtnl, m, callback->link); - } - LIST_REMOVE(callbacks, netdev->callbacks, callback); link_unref(callback->link); free(callback); @@ -127,7 +115,7 @@ static void netdev_cancel_callbacks(NetDev *netdev) { static NetDev *netdev_free(NetDev *netdev) { assert(netdev); - netdev_cancel_callbacks(netdev); + netdev_callbacks_clear(netdev); if (netdev->ifname && netdev->manager) hashmap_remove(netdev->manager->netdevs, netdev->ifname); @@ -161,6 +149,14 @@ static NetDev *netdev_free(NetDev *netdev) { DEFINE_TRIVIAL_REF_UNREF_FUNC(NetDev, netdev, netdev_free); +void netdev_netlink_destroy_callback(void *userdata) { + NetDev *netdev = userdata; + + assert(userdata); + + netdev_unref(netdev); +} + void netdev_drop(NetDev *netdev) { if (!netdev || netdev->state == NETDEV_STATE_LINGER) return; @@ -169,7 +165,7 @@ void netdev_drop(NetDev *netdev) { log_netdev_debug(netdev, "netdev removed"); - netdev_cancel_callbacks(netdev); + netdev_callbacks_clear(netdev); netdev_unref(netdev); @@ -197,7 +193,7 @@ int netdev_get(Manager *manager, const char *name, NetDev **ret) { static int netdev_enter_failed(NetDev *netdev) { netdev->state = NETDEV_STATE_FAILED; - netdev_cancel_callbacks(netdev); + netdev_callbacks_clear(netdev); return 0; } @@ -229,7 +225,8 @@ static int netdev_enslave_ready(NetDev *netdev, Link* link, sd_netlink_message_h if (r < 0) return log_netdev_error_errno(netdev, r, "Could not append IFLA_MASTER attribute: %m"); - r = sd_netlink_call_async(netdev->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(netdev->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_netdev_error_errno(netdev, r, "Could not send rtnetlink message: %m"); @@ -274,9 +271,10 @@ static int netdev_enter_ready(NetDev *netdev) { /* callback for netdev's created without a backing Link */ static int netdev_create_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(netdev_unrefp) NetDev *netdev = userdata; + NetDev *netdev = userdata; int r; + assert(netdev); assert(netdev->state != _NETDEV_STATE_INVALID); r = sd_netlink_message_get_errno(m); @@ -321,8 +319,7 @@ int netdev_enslave(NetDev *netdev, Link *link, sd_netlink_message_handler_t call return log_oom(); cb->callback = callback; - cb->link = link; - link_ref(link); + cb->link = link_ref(link); LIST_PREPEND(callbacks, netdev->callbacks, cb); @@ -537,13 +534,15 @@ static int netdev_create(NetDev *netdev, Link *link, return log_netdev_error_errno(netdev, r, "Could not append IFLA_LINKINFO attribute: %m"); if (link) { - r = sd_netlink_call_async(netdev->manager->rtnl, m, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(netdev->manager->rtnl, m, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_netdev_error_errno(netdev, r, "Could not send rtnetlink message: %m"); link_ref(link); } else { - r = sd_netlink_call_async(netdev->manager->rtnl, m, netdev_create_handler, NULL, netdev, 0, NULL); + r = sd_netlink_call_async(netdev->manager->rtnl, m, netdev_create_handler, + netdev_netlink_destroy_callback, netdev, 0, NULL); if (r < 0) return log_netdev_error_errno(netdev, r, "Could not send rtnetlink message: %m"); diff --git a/src/network/netdev/netdev.h b/src/network/netdev/netdev.h index 2746de01a0..855eadf9d3 100644 --- a/src/network/netdev/netdev.h +++ b/src/network/netdev/netdev.h @@ -150,7 +150,7 @@ void netdev_drop(NetDev *netdev); NetDev *netdev_unref(NetDev *netdev); NetDev *netdev_ref(NetDev *netdev); - +void netdev_netlink_destroy_callback(void *userdata); DEFINE_TRIVIAL_CLEANUP_FUNC(NetDev*, netdev_unref); int netdev_get(Manager *manager, const char *name, NetDev **ret); diff --git a/src/network/networkd-address-label.c b/src/network/networkd-address-label.c index 92b2c58f6b..a0c4be3ef0 100644 --- a/src/network/networkd-address-label.c +++ b/src/network/networkd-address-label.c @@ -112,7 +112,8 @@ int address_label_configure( if (r < 0) return log_error_errno(r, "Could not append IFA_ADDRESS attribute: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m"); diff --git a/src/network/networkd-address.c b/src/network/networkd-address.c index 45e02c76da..3ffd3fe4ab 100644 --- a/src/network/networkd-address.c +++ b/src/network/networkd-address.c @@ -453,7 +453,8 @@ int address_remove( if (r < 0) return log_error_errno(r, "Could not append IFA_LOCAL attribute: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m"); @@ -631,7 +632,8 @@ int address_configure( if (r < 0) return r; - r = sd_netlink_call_async(link->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) { address_release(address); return log_error_errno(r, "Could not send rtnetlink message: %m"); diff --git a/src/network/networkd-brvlan.c b/src/network/networkd-brvlan.c index fe418b4768..3707347a68 100644 --- a/src/network/networkd-brvlan.c +++ b/src/network/networkd-brvlan.c @@ -195,10 +195,13 @@ int br_vlan_configure(Link *link, uint16_t pvid, uint32_t *br_vid_bitmap, uint32 return log_link_error_errno(link, r, "Could not close IFLA_AF_SPEC container: %m"); /* send message to the kernel */ - r = sd_netlink_call_async(rtnl, req, set_brvlan_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(rtnl, req, set_brvlan_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); + link_ref(link); + return 0; } diff --git a/src/network/networkd-dhcp4.c b/src/network/networkd-dhcp4.c index 18867d9401..45b784d023 100644 --- a/src/network/networkd-dhcp4.c +++ b/src/network/networkd-dhcp4.c @@ -17,7 +17,7 @@ static int dhcp4_route_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); @@ -302,7 +302,7 @@ static int dhcp_lease_lost(Link *link) { static int dhcp4_address_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); diff --git a/src/network/networkd-dhcp6.c b/src/network/networkd-dhcp6.c index 82f49e5ac0..7071adc0bb 100644 --- a/src/network/networkd-dhcp6.c +++ b/src/network/networkd-dhcp6.c @@ -102,14 +102,14 @@ static int dhcp6_pd_prefix_assign(Link *link, struct in6_addr *prefix, static int dhcp6_route_remove_cb(sd_netlink *nl, sd_netlink_message *m, void *userdata) { - Link *l = userdata; + Link *link = userdata; int r; + assert(link); + r = sd_netlink_message_get_errno(m); if (r < 0) - log_link_debug_errno(l, r, "Received error on unreachable route removal for DHCPv6 delegated subnetl: %m"); - - l = link_unref(l); + log_link_debug_errno(link, r, "Received error on unreachable route removal for DHCPv6 delegated subnetl: %m"); return 0; } @@ -163,7 +163,6 @@ int dhcp6_lease_pd_prefix_lost(sd_dhcp6_client *client, Link* link) { continue; } - link = link_ref(link); log_link_debug(link, "Removing unreachable route %s/%u", strnull(buf), pd_prefix_len); @@ -251,14 +250,14 @@ static int dhcp6_pd_prefix_distribute(Link *dhcp6_link, Iterator *i, static int dhcp6_route_add_cb(sd_netlink *nl, sd_netlink_message *m, void *userdata) { - Link *l = userdata; + Link *link = userdata; int r; + assert(link); + r = sd_netlink_message_get_errno(m); if (r < 0 && r != -EEXIST) - log_link_debug_errno(l, r, "Received error when adding unreachable route for DHCPv6 delegated subnet: %m"); - - l = link_unref(l); + log_link_debug_errno(link, r, "Received error when adding unreachable route for DHCPv6 delegated subnet: %m"); return 0; } @@ -322,7 +321,6 @@ static int dhcp6_lease_pd_prefix_acquired(sd_dhcp6_client *client, Link *link) { route_free(route); continue; } - link = link_ref(link); route_free(route); @@ -412,7 +410,7 @@ int dhcp6_request_prefix_delegation(Link *link) { static int dhcp6_address_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); diff --git a/src/network/networkd-fdb.c b/src/network/networkd-fdb.c index 32fcf82bbd..5112d91b90 100644 --- a/src/network/networkd-fdb.c +++ b/src/network/networkd-fdb.c @@ -134,10 +134,13 @@ int fdb_entry_configure(Link *link, FdbEntry *fdb_entry) { } /* send message to the kernel to update its internal static MAC table. */ - r = sd_netlink_call_async(rtnl, req, set_fdb_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(rtnl, req, set_fdb_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); + link_ref(link); + return 0; } diff --git a/src/network/networkd-ipv4ll.c b/src/network/networkd-ipv4ll.c index ce50a67400..0f333175da 100644 --- a/src/network/networkd-ipv4ll.c +++ b/src/network/networkd-ipv4ll.c @@ -52,7 +52,7 @@ static int ipv4ll_address_lost(Link *link) { } static int ipv4ll_route_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); @@ -73,7 +73,7 @@ static int ipv4ll_route_handler(sd_netlink *rtnl, sd_netlink_message *m, void *u } static int ipv4ll_address_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); diff --git a/src/network/networkd-ipv6-proxy-ndp.c b/src/network/networkd-ipv6-proxy-ndp.c index 7e1c7d6d2e..1dcdbad0be 100644 --- a/src/network/networkd-ipv6-proxy-ndp.c +++ b/src/network/networkd-ipv6-proxy-ndp.c @@ -173,10 +173,13 @@ int ipv6_proxy_ndp_address_configure(Link *link, IPv6ProxyNDPAddress *ipv6_proxy if (r < 0) return rtnl_log_create_error(r); - r = sd_netlink_call_async(rtnl, req, set_ipv6_proxy_ndp_address_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(rtnl, req, set_ipv6_proxy_ndp_address_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); + link_ref(link); + return 0; } diff --git a/src/network/networkd-link.c b/src/network/networkd-link.c index f74308b5ec..ba15cac468 100644 --- a/src/network/networkd-link.c +++ b/src/network/networkd-link.c @@ -407,6 +407,8 @@ static int link_update_flags(Link *link, sd_netlink_message *m) { return 0; } +DEFINE_TRIVIAL_CLEANUP_FUNC(Link*, link_unref); + static int link_new(Manager *manager, sd_netlink_message *message, Link **ret) { _cleanup_(link_unrefp) Link *link = NULL; uint16_t type; @@ -549,6 +551,7 @@ static Link *link_free(Link *link) { if (link->manager) { hashmap_remove(link->manager->links, INT_TO_PTR(link->ifindex)); set_remove(link->manager->links_requesting_uuid, link); + link_clean(link); } free(link->ifname); @@ -573,6 +576,14 @@ static Link *link_free(Link *link) { DEFINE_TRIVIAL_REF_UNREF_FUNC(Link, link, link_free); +void link_netlink_destroy_callback(void *userdata) { + Link *link = userdata; + + assert(userdata); + + link_unref(link); +} + int link_get(Manager *m, int ifindex, Link **ret) { Link *link; @@ -796,9 +807,10 @@ static int link_set_routing_policy_rule(Link *link) { } static int route_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; + assert(link); assert(link->route_messages > 0); assert(IN_SET(link->state, LINK_STATE_SETTING_ADDRESSES, LINK_STATE_SETTING_ROUTES, LINK_STATE_FAILED, @@ -855,7 +867,7 @@ static int link_enter_set_routes(Link *link) { } int link_route_remove_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(m); @@ -873,7 +885,7 @@ int link_route_remove_handler(sd_netlink *rtnl, sd_netlink_message *m, void *use } static int address_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(rtnl); @@ -904,7 +916,7 @@ static int address_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userda } static int address_label_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(rtnl); @@ -1204,7 +1216,7 @@ static int link_enter_set_addresses(Link *link) { } int link_address_remove_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(m); @@ -1248,9 +1260,11 @@ static int link_set_proxy_arp(Link *link) { } static int link_set_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; + assert(link); + log_link_debug(link, "Set link"); r = sd_netlink_message_get_errno(m); @@ -1266,7 +1280,7 @@ static int link_set_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userd static int link_configure_after_setting_mtu(Link *link); static int set_mtu_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(m); @@ -1327,19 +1341,19 @@ int link_set_mtu(Link *link, uint32_t mtu) { if (r < 0) return log_link_error_errno(link, r, "Could not append MTU: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, set_mtu_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, set_mtu_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); - link->setting_mtu = true; - link_ref(link); + link->setting_mtu = true; return 0; } static int set_flags_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(m); @@ -1398,7 +1412,8 @@ static int link_set_flags(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not set link flags: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, set_flags_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, set_flags_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1473,7 +1488,8 @@ static int link_set_bridge(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not append IFLA_LINKINFO attribute: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, link_set_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, link_set_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1525,7 +1541,8 @@ static int link_bond_set(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not append IFLA_INFO_DATA attribute: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, set_flags_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, set_flags_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1725,7 +1742,7 @@ bool link_has_carrier(Link *link) { } static int link_up_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); @@ -1818,7 +1835,8 @@ int link_up(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not close IFLA_AF_SPEC container: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, link_up_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, link_up_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1843,7 +1861,8 @@ static int link_up_can(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not set link flags: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, link_up_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, link_up_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1932,7 +1951,8 @@ static int link_set_can(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Failed to close netlink container: %m"); - r = sd_netlink_call_async(link->manager->rtnl, m, link_set_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, m, link_set_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -1952,7 +1972,7 @@ static int link_set_can(Link *link) { } static int link_down_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); @@ -1964,10 +1984,8 @@ static int link_down_handler(sd_netlink *rtnl, sd_netlink_message *m, void *user if (r < 0) log_link_warning_errno(link, r, "Could not bring down interface: %m"); - if (streq_ptr(link->kind, "can")) { - link_ref(link); + if (streq_ptr(link->kind, "can")) link_set_can(link); - } return 1; } @@ -1991,7 +2009,8 @@ int link_down(Link *link) { if (r < 0) return log_link_error_errno(link, r, "Could not set link flags: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, link_down_handler, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, link_down_handler, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_link_error_errno(link, r, "Could not send rtnetlink message: %m"); @@ -2296,7 +2315,7 @@ static int link_joined(Link *link) { } static int netdev_join_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); @@ -3007,7 +3026,7 @@ static int link_configure_duid(Link *link) { static int link_initialized_and_synced(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; Network *network; int r; @@ -3104,7 +3123,7 @@ int link_initialized(Link *link, sd_device *device) { r = sd_netlink_call_async(link->manager->rtnl, req, link_initialized_and_synced, - NULL, link, 0, NULL); + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return r; @@ -3350,9 +3369,6 @@ int link_add(Manager *m, sd_netlink_message *message, Link **ret) { if (r < 0) goto failed; } else { - /* we are calling a callback directly, so must take a ref */ - link_ref(link); - r = link_initialized_and_synced(m->rtnl, NULL, link); if (r < 0) goto failed; @@ -3479,7 +3495,6 @@ int link_update(Link *link, sd_netlink_message *m) { assert(m); if (link->state == LINK_STATE_LINGER) { - link_ref(link); log_link_info(link, "Link readded"); link_set_state(link, LINK_STATE_ENSLAVING); @@ -4004,8 +4019,7 @@ void link_clean(Link *link) { assert(link); assert(link->manager); - set_remove(link->manager->dirty_links, link); - link_unref(link); + link_unref(set_remove(link->manager->dirty_links, link)); } static const char* const link_state_table[_LINK_STATE_MAX] = { diff --git a/src/network/networkd-link.h b/src/network/networkd-link.h index 033cca1576..bd66793cb6 100644 --- a/src/network/networkd-link.h +++ b/src/network/networkd-link.h @@ -130,6 +130,8 @@ int get_product_uuid_handler(sd_bus_message *m, void *userdata, sd_bus_error *re Link *link_unref(Link *link); Link *link_ref(Link *link); +void link_netlink_destroy_callback(void *userdata); + int link_get(Manager *m, int ifindex, Link **ret); int link_add(Manager *manager, sd_netlink_message *message, Link **ret); void link_drop(Link *link); @@ -180,8 +182,6 @@ int link_node_enumerator(sd_bus *bus, const char *path, void *userdata, char *** int link_object_find(sd_bus *bus, const char *path, const char *interface, void *userdata, void **found, sd_bus_error *error); int link_send_changed(Link *link, const char *property, ...) _sentinel_; -DEFINE_TRIVIAL_CLEANUP_FUNC(Link*, link_unref); - /* Macros which append INTERFACE= to the message */ #define log_link_full(link, level, error, ...) \ diff --git a/src/network/networkd-manager.c b/src/network/networkd-manager.c index 819a18e26c..51c9a5d1db 100644 --- a/src/network/networkd-manager.c +++ b/src/network/networkd-manager.c @@ -1241,14 +1241,14 @@ Link *manager_dhcp6_prefix_get(Manager *m, struct in6_addr *addr) { static int dhcp6_route_add_callback(sd_netlink *nl, sd_netlink_message *m, void *userdata) { - Link *l = userdata; + Link *link = userdata; int r; + assert(link); + r = sd_netlink_message_get_errno(m); if (r < 0 && r != -EEXIST) - log_link_debug_errno(l, r, "Received error adding DHCPv6 Prefix Delegation route: %m"); - - l = link_unref(l); + log_link_debug_errno(link, r, "Received error adding DHCPv6 Prefix Delegation route: %m"); return 0; } @@ -1274,21 +1274,19 @@ int manager_dhcp6_prefix_add(Manager *m, struct in6_addr *addr, Link *link) { (void) in_addr_to_string(AF_INET6, (union in_addr_union *) addr, &buf); log_link_debug(link, "Adding prefix route %s/64", strnull(buf)); - link = link_ref(link); - return hashmap_put(m->dhcp6_prefixes, addr, link); } static int dhcp6_route_remove_callback(sd_netlink *nl, sd_netlink_message *m, void *userdata) { - Link *l = userdata; + Link *link = userdata; int r; + assert(link); + r = sd_netlink_message_get_errno(m); if (r < 0) - log_link_debug_errno(l, r, "Received error on DHCPv6 Prefix Delegation route removal: %m"); - - l = link_unref(l); + log_link_debug_errno(link, r, "Received error on DHCPv6 Prefix Delegation route removal: %m"); return 0; } @@ -1320,8 +1318,6 @@ int manager_dhcp6_prefix_remove(Manager *m, struct in6_addr *addr) { (void) in_addr_to_string(AF_INET6, (union in_addr_union *) addr, &buf); log_link_debug(l, "Removing prefix route %s/64", strnull(buf)); - l = link_ref(l); - return 0; } @@ -1440,6 +1436,9 @@ void manager_free(Manager *m) { free(m->state_file); + sd_netlink_unref(m->rtnl); + sd_netlink_unref(m->genl); + while ((network = m->networks)) network_free(network); @@ -1474,8 +1473,6 @@ void manager_free(Manager *m) { set_free_with_destructor(m->rules_foreign, routing_policy_rule_free); set_free_with_destructor(m->rules_saved, routing_policy_rule_free); - sd_netlink_unref(m->rtnl); - sd_netlink_unref(m->genl); sd_event_unref(m->event); sd_resolve_unref(m->resolve); diff --git a/src/network/networkd-ndisc.c b/src/network/networkd-ndisc.c index 4709d9c9c7..1dd949cea2 100644 --- a/src/network/networkd-ndisc.c +++ b/src/network/networkd-ndisc.c @@ -17,7 +17,7 @@ #define NDISC_PREFIX_LFT_MIN 7200U static int ndisc_netlink_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(link); diff --git a/src/network/networkd-route.c b/src/network/networkd-route.c index 9ebbc4355e..16a30b5731 100644 --- a/src/network/networkd-route.c +++ b/src/network/networkd-route.c @@ -439,7 +439,8 @@ int route_remove(Route *route, Link *link, return log_error_errno(r, "Could not append RTA_OIF attribute: %m"); } - r = sd_netlink_call_async(link->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m"); @@ -638,7 +639,8 @@ int route_configure( if (r < 0) return log_error_errno(r, "Could not append RTA_METRICS attribute: %m"); - r = sd_netlink_call_async(link->manager->rtnl, req, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, req, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m"); diff --git a/src/network/networkd-routing-policy-rule.c b/src/network/networkd-routing-policy-rule.c index cd9e913ebb..d7c68c680f 100644 --- a/src/network/networkd-routing-policy-rule.c +++ b/src/network/networkd-routing-policy-rule.c @@ -308,7 +308,7 @@ int routing_policy_rule_add_foreign(Manager *m, } static int routing_policy_rule_remove_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(m); @@ -370,7 +370,8 @@ int routing_policy_rule_remove(RoutingPolicyRule *routing_policy_rule, Link *lin return log_error_errno(r, "Could not set destination prefix length: %m"); } - r = sd_netlink_call_async(link->manager->rtnl, m, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, m, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m"); @@ -419,7 +420,7 @@ static int routing_policy_rule_new_static(Network *network, const char *filename } int link_routing_policy_rule_handler(sd_netlink *rtnl, sd_netlink_message *m, void *userdata) { - _cleanup_(link_unrefp) Link *link = userdata; + Link *link = userdata; int r; assert(rtnl); @@ -538,7 +539,8 @@ int routing_policy_rule_configure(RoutingPolicyRule *rule, Link *link, sd_netlin rule->link = link; - r = sd_netlink_call_async(link->manager->rtnl, m, callback, NULL, link, 0, NULL); + r = sd_netlink_call_async(link->manager->rtnl, m, callback, + link_netlink_destroy_callback, link, 0, NULL); if (r < 0) return log_error_errno(r, "Could not send rtnetlink message: %m");