From 87bc687a8cbadbc9eb3c77fba41a6caf3219cf7c Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 7 Sep 2020 13:43:56 +0900 Subject: core/device: remove .device unit corresponding to DEVPATH_OLD Partially fixes #16967. --- src/core/device.c | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/src/core/device.c b/src/core/device.c index 31aa3341c2..d242d15e36 100644 --- a/src/core/device.c +++ b/src/core/device.c @@ -897,6 +897,29 @@ static void device_propagate_reload_by_sysfs(Manager *m, const char *sysfs) { } } +static int device_remove_old(Manager *m, sd_device *dev) { + _cleanup_free_ char *syspath_old = NULL, *e = NULL; + const char *devpath_old; + int r; + + r = sd_device_get_property_value(dev, "DEVPATH_OLD", &devpath_old); + if (r < 0) { + log_device_debug_errno(dev, r, "Failed to get DEVPATH_OLD= property on 'move' uevent, ignoring: %m"); + return 0; + } + + syspath_old = path_join("/sys", devpath_old); + if (!syspath_old) + return log_oom(); + + r = unit_name_from_path(syspath_old, ".device", &e); + if (r < 0) + return log_device_error_errno(dev, r, "Failed to generate unit name from old device path: %m"); + + device_update_found_by_sysfs(m, syspath_old, 0, DEVICE_FOUND_UDEV|DEVICE_FOUND_MOUNT|DEVICE_FOUND_SWAP); + return 0; +} + static int device_dispatch_io(sd_device_monitor *monitor, sd_device *dev, void *userdata) { Manager *m = userdata; DeviceAction action; @@ -921,6 +944,9 @@ static int device_dispatch_io(sd_device_monitor *monitor, sd_device *dev, void * if (!IN_SET(action, DEVICE_ACTION_ADD, DEVICE_ACTION_REMOVE, DEVICE_ACTION_MOVE)) device_propagate_reload_by_sysfs(m, sysfs); + if (action == DEVICE_ACTION_MOVE) + (void) device_remove_old(m, dev); + /* A change event can signal that a device is becoming ready, in particular if the device is using * the SYSTEMD_READY logic in udev so we need to reach the else block of the following if, even for * change events */ -- cgit v1.2.3 From cadc7ed2e2720f39725647fd6f26be15afecc718 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Tue, 15 Sep 2020 10:40:54 +0900 Subject: ethtool: constify arguments for ethtool_set_xxx() --- src/shared/ethtool-util.c | 8 ++++---- src/shared/ethtool-util.h | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/shared/ethtool-util.c b/src/shared/ethtool-util.c index 9326d2856e..adbf8d1db3 100644 --- a/src/shared/ethtool-util.c +++ b/src/shared/ethtool-util.c @@ -414,7 +414,7 @@ int ethtool_set_wol(int *ethtool_fd, const char *ifname, WakeOnLan wol) { return 0; } -int ethtool_set_nic_buffer_size(int *ethtool_fd, const char *ifname, netdev_ring_param *ring) { +int ethtool_set_nic_buffer_size(int *ethtool_fd, const char *ifname, const netdev_ring_param *ring) { struct ethtool_ringparam ecmd = { .cmd = ETHTOOL_GRINGPARAM }; @@ -543,7 +543,7 @@ static int set_features_bit( return found ? 0 : -ENODATA; } -int ethtool_set_features(int *ethtool_fd, const char *ifname, int *features) { +int ethtool_set_features(int *ethtool_fd, const char *ifname, const int *features) { _cleanup_free_ struct ethtool_gstrings *strings = NULL; struct ethtool_sfeatures *sfeatures; struct ifreq ifr = {}; @@ -754,7 +754,7 @@ int ethtool_set_glinksettings( int *fd, const char *ifname, int autonegotiation, - uint32_t advertise[static N_ADVERTISE], + const uint32_t advertise[static N_ADVERTISE], uint64_t speed, Duplex duplex, NetDevPort port) { @@ -813,7 +813,7 @@ int ethtool_set_glinksettings( return r; } -int ethtool_set_channels(int *fd, const char *ifname, netdev_channels *channels) { +int ethtool_set_channels(int *fd, const char *ifname, const netdev_channels *channels) { struct ethtool_channels ecmd = { .cmd = ETHTOOL_GCHANNELS }; diff --git a/src/shared/ethtool-util.h b/src/shared/ethtool-util.h index 4730241708..9e3f1ed51a 100644 --- a/src/shared/ethtool-util.h +++ b/src/shared/ethtool-util.h @@ -101,12 +101,12 @@ int ethtool_get_link_info(int *ethtool_fd, const char *ifname, int ethtool_get_permanent_macaddr(int *ethtool_fd, const char *ifname, struct ether_addr *ret); int ethtool_set_speed(int *ethtool_fd, const char *ifname, unsigned speed, Duplex duplex); int ethtool_set_wol(int *ethtool_fd, const char *ifname, WakeOnLan wol); -int ethtool_set_nic_buffer_size(int *ethtool_fd, const char *ifname, netdev_ring_param *ring); -int ethtool_set_features(int *ethtool_fd, const char *ifname, int *features); +int ethtool_set_nic_buffer_size(int *ethtool_fd, const char *ifname, const netdev_ring_param *ring); +int ethtool_set_features(int *ethtool_fd, const char *ifname, const int *features); int ethtool_set_glinksettings(int *ethtool_fd, const char *ifname, - int autonegotiation, uint32_t advertise[static N_ADVERTISE], + int autonegotiation, const uint32_t advertise[static N_ADVERTISE], uint64_t speed, Duplex duplex, NetDevPort port); -int ethtool_set_channels(int *ethtool_fd, const char *ifname, netdev_channels *channels); +int ethtool_set_channels(int *ethtool_fd, const char *ifname, const netdev_channels *channels); int ethtool_set_flow_control(int *fd, const char *ifname, int rx, int tx, int autoneg); const char *duplex_to_string(Duplex d) _const_; -- cgit v1.2.3 From 2e17fed5f3000175f3ea67ece47fb7fd6ca41efa Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Tue, 15 Sep 2020 10:41:38 +0900 Subject: udev: split link_config_apply() into small pieces --- src/udev/net/link-config.c | 242 +++++++++++++++++++++++++++++---------------- src/udev/net/link-config.h | 4 +- 2 files changed, 158 insertions(+), 88 deletions(-) diff --git a/src/udev/net/link-config.c b/src/udev/net/link-config.c index 03fd429b27..77edbb674d 100644 --- a/src/udev/net/link-config.c +++ b/src/udev/net/link-config.c @@ -301,6 +301,70 @@ int link_config_get(link_config_ctx *ctx, sd_device *device, link_config **ret) return -ENOENT; } +static int link_config_apply_ethtool_settings(int *ethtool_fd, const link_config *config, sd_device *device) { + const char *name; + int r; + + assert(ethtool_fd); + assert(config); + assert(device); + + r = sd_device_get_sysname(device, &name); + if (r < 0) + return log_device_error_errno(device, r, "Failed to get sysname: %m"); + + r = ethtool_set_glinksettings(ethtool_fd, name, + config->autonegotiation, config->advertise, + config->speed, config->duplex, config->port); + if (r < 0) { + if (config->port != _NET_DEV_PORT_INVALID) + log_device_warning_errno(device, r, "Could not set port '%s', ignoring: %m", port_to_string(config->port)); + + if (!eqzero(config->advertise)) + log_device_warning_errno(device, r, "Could not set advertise mode, ignoring: %m"); /* TODO: include modes in the log message. */ + + if (config->speed) { + unsigned speed = DIV_ROUND_UP(config->speed, 1000000); + if (r == -EOPNOTSUPP) { + r = ethtool_set_speed(ethtool_fd, name, speed, config->duplex); + if (r < 0) + log_device_warning_errno(device, r, "Could not set speed to %uMbps, ignoring: %m", speed); + } + } + + if (config->duplex != _DUP_INVALID) + log_device_warning_errno(device, r, "Could not set duplex to %s, ignoring: %m", duplex_to_string(config->duplex)); + } + + r = ethtool_set_wol(ethtool_fd, name, config->wol); + if (r < 0) + log_device_warning_errno(device, r, "Could not set WakeOnLan to %s, ignoring: %m", wol_to_string(config->wol)); + + r = ethtool_set_features(ethtool_fd, name, config->features); + if (r < 0) + log_device_warning_errno(device, r, "Could not set offload features, ignoring: %m"); + + if (config->channels.rx_count_set || config->channels.tx_count_set || config->channels.other_count_set || config->channels.combined_count_set) { + r = ethtool_set_channels(ethtool_fd, name, &config->channels); + if (r < 0) + log_device_warning_errno(device, r, "Could not set channels, ignoring: %m"); + } + + if (config->ring.rx_pending_set || config->ring.rx_mini_pending_set || config->ring.rx_jumbo_pending_set || config->ring.tx_pending_set) { + r = ethtool_set_nic_buffer_size(ethtool_fd, name, &config->ring); + if (r < 0) + log_device_warning_errno(device, r, "Could not set ring buffer, ignoring: %m"); + } + + if (config->rx_flow_control >= 0 || config->tx_flow_control >= 0 || config->autoneg_flow_control >= 0) { + r = ethtool_set_flow_control(ethtool_fd, name, config->rx_flow_control, config->tx_flow_control, config->autoneg_flow_control); + if (r < 0) + log_device_warning_errno(device, r, "Could not set flow control, ignoring: %m"); + } + + return 0; +} + static int get_mac(sd_device *device, MACAddressPolicy policy, struct ether_addr *mac) { unsigned addr_type; bool want_random = policy == MAC_ADDRESS_POLICY_RANDOM; @@ -357,80 +421,41 @@ static int get_mac(sd_device *device, MACAddressPolicy policy, struct ether_addr return 1; } -int link_config_apply(link_config_ctx *ctx, link_config *config, - sd_device *device, const char **name) { - _cleanup_strv_free_ char **altnames = NULL, **current_altnames = NULL; - struct ether_addr generated_mac; - struct ether_addr *mac = NULL; - const char *new_name = NULL; - const char *old_name; - unsigned speed, name_type = NET_NAME_UNKNOWN; - NamePolicy policy; - int r, ifindex; +static int link_config_apply_rtnl_settings(sd_netlink **rtnl, const link_config *config, sd_device *device) { + struct ether_addr generated_mac, *mac = NULL; + int ifindex, r; - assert(ctx); + assert(rtnl); assert(config); assert(device); - assert(name); - r = sd_device_get_sysname(device, &old_name); + r = sd_device_get_ifindex(device, &ifindex); if (r < 0) - return r; + return log_device_error_errno(device, r, "Could not find ifindex: %m"); - r = ethtool_set_glinksettings(&ctx->ethtool_fd, old_name, - config->autonegotiation, config->advertise, - config->speed, config->duplex, config->port); - if (r < 0) { - - if (config->port != _NET_DEV_PORT_INVALID) - log_warning_errno(r, "Could not set port (%s) of %s: %m", port_to_string(config->port), old_name); - - if (!eqzero(config->advertise)) - log_warning_errno(r, "Could not set advertise mode: %m"); /* TODO: include modes in the log message. */ - - if (config->speed) { - speed = DIV_ROUND_UP(config->speed, 1000000); - if (r == -EOPNOTSUPP) { - r = ethtool_set_speed(&ctx->ethtool_fd, old_name, speed, config->duplex); - if (r < 0) - log_warning_errno(r, "Could not set speed of %s to %u Mbps: %m", old_name, speed); - } - } - - if (config->duplex != _DUP_INVALID) - log_warning_errno(r, "Could not set duplex of %s to %s: %m", old_name, duplex_to_string(config->duplex)); - } - - r = ethtool_set_wol(&ctx->ethtool_fd, old_name, config->wol); - if (r < 0) - log_warning_errno(r, "Could not set WakeOnLan of %s to %s: %m", - old_name, wol_to_string(config->wol)); + if (IN_SET(config->mac_address_policy, MAC_ADDRESS_POLICY_PERSISTENT, MAC_ADDRESS_POLICY_RANDOM)) { + if (get_mac(device, config->mac_address_policy, &generated_mac) > 0) + mac = &generated_mac; + } else + mac = config->mac; - r = ethtool_set_features(&ctx->ethtool_fd, old_name, config->features); + r = rtnl_set_link_properties(rtnl, ifindex, config->alias, mac, config->mtu); if (r < 0) - log_warning_errno(r, "Could not set offload features of %s: %m", old_name); + log_device_warning_errno(device, r, "Could not set Alias=, MACAddress= or MTU=, ignoring: %m"); - if (config->channels.rx_count_set || config->channels.tx_count_set || config->channels.other_count_set || config->channels.combined_count_set) { - r = ethtool_set_channels(&ctx->ethtool_fd, old_name, &config->channels); - if (r < 0) - log_warning_errno(r, "Could not set channels of %s: %m", old_name); - } - - if (config->ring.rx_pending_set || config->ring.rx_mini_pending_set || config->ring.rx_jumbo_pending_set || config->ring.tx_pending_set) { - r = ethtool_set_nic_buffer_size(&ctx->ethtool_fd, old_name, &config->ring); - if (r < 0) - log_warning_errno(r, "Could not set ring buffer of %s: %m", old_name); - } + return 0; +} - if (config->rx_flow_control >= 0 || config->tx_flow_control >= 0 || config->autoneg_flow_control >= 0) { - r = ethtool_set_flow_control(&ctx->ethtool_fd, old_name, config->rx_flow_control, config->tx_flow_control, config->autoneg_flow_control); - if (r < 0) - log_warning_errno(r, "Could not set flow control of %s: %m", old_name); - } +static int link_config_generate_new_name(const link_config_ctx *ctx, const link_config *config, sd_device *device, const char **ret_name) { + unsigned name_type = NET_NAME_UNKNOWN; + const char *new_name = NULL; + NamePolicy policy; + int r; - r = sd_device_get_ifindex(device, &ifindex); - if (r < 0) - return log_device_warning_errno(device, r, "Could not find ifindex: %m"); + assert(ctx); + assert(config); + assert(device); + assert(ret_name); (void) link_unsigned_attribute(device, "name_assign_type", &name_type); @@ -482,24 +507,43 @@ int link_config_apply(link_config_ctx *ctx, link_config *config, break; } - if (new_name) + if (new_name) { log_device_debug(device, "Policy *%s* yields \"%s\".", name_policy_to_string(policy), new_name); - else if (config->name) { - new_name = config->name; - log_device_debug(device, "Policies didn't yield a name, using specified Name=%s.", new_name); - } else - log_device_debug(device, "Policies didn't yield a name and Name= is not given, not renaming."); - no_rename: + *ret_name = new_name; + return 0; + } - if (IN_SET(config->mac_address_policy, MAC_ADDRESS_POLICY_PERSISTENT, MAC_ADDRESS_POLICY_RANDOM)) { - if (get_mac(device, config->mac_address_policy, &generated_mac) > 0) - mac = &generated_mac; - } else - mac = config->mac; + if (config->name) { + log_device_debug(device, "Policies didn't yield a name, using specified Name=%s.", config->name); + *ret_name = config->name; + return 0; + } - r = rtnl_set_link_properties(&ctx->rtnl, ifindex, config->alias, mac, config->mtu); + log_device_debug(device, "Policies didn't yield a name and Name= is not given, not renaming."); +no_rename: + r = sd_device_get_sysname(device, ret_name); if (r < 0) - return log_warning_errno(r, "Could not set Alias=, MACAddress= or MTU= on %s: %m", old_name); + return log_device_error_errno(device, r, "Failed to get sysname: %m"); + + return 0; +} + +static int link_config_apply_alternative_names(sd_netlink **rtnl, const link_config *config, sd_device *device, const char *new_name) { + _cleanup_strv_free_ char **altnames = NULL, **current_altnames = NULL; + const char *current_name; + int ifindex, r; + + assert(rtnl); + assert(config); + assert(device); + + r = sd_device_get_sysname(device, ¤t_name); + if (r < 0) + return log_device_error_errno(device, r, "Failed to get sysname: %m"); + + r = sd_device_get_ifindex(device, &ifindex); + if (r < 0) + return log_device_error_errno(device, r, "Could not find ifindex: %m"); if (config->alternative_names) { altnames = strv_copy(config->alternative_names); @@ -539,11 +583,11 @@ int link_config_apply(link_config_ctx *ctx, link_config *config, if (new_name) strv_remove(altnames, new_name); - strv_remove(altnames, old_name); + strv_remove(altnames, current_name); - r = rtnl_get_link_alternative_names(&ctx->rtnl, ifindex, ¤t_altnames); + r = rtnl_get_link_alternative_names(rtnl, ifindex, ¤t_altnames); if (r < 0) - log_debug_errno(r, "Failed to get alternative names on %s, ignoring: %m", old_name); + log_device_debug_errno(device, r, "Failed to get alternative names, ignoring: %m"); char **p; STRV_FOREACH(p, current_altnames) @@ -551,14 +595,40 @@ int link_config_apply(link_config_ctx *ctx, link_config *config, strv_uniq(altnames); strv_sort(altnames); - r = rtnl_set_link_alternative_names(&ctx->rtnl, ifindex, altnames); - if (r == -EOPNOTSUPP) - log_debug_errno(r, "Could not set AlternativeName= or apply AlternativeNamesPolicy= on %s, ignoring: %m", old_name); - else if (r < 0) - return log_warning_errno(r, "Could not set AlternativeName= or apply AlternativeNamesPolicy= on %s: %m", old_name); + r = rtnl_set_link_alternative_names(rtnl, ifindex, altnames); + if (r < 0) + log_device_full_errno(device, r == -EOPNOTSUPP ? LOG_DEBUG : LOG_WARNING, r, + "Could not set AlternativeName= or apply AlternativeNamesPolicy=, ignoring: %m"); + + return 0; +} - *name = new_name; +int link_config_apply(link_config_ctx *ctx, const link_config *config, sd_device *device, const char **ret_name) { + const char *new_name; + int r; + + assert(ctx); + assert(config); + assert(device); + assert(ret_name); + + r = link_config_apply_ethtool_settings(&ctx->ethtool_fd, config, device); + if (r < 0) + return r; + + r = link_config_apply_rtnl_settings(&ctx->rtnl, config, device); + if (r < 0) + return r; + + r = link_config_generate_new_name(ctx, config, device, &new_name); + if (r < 0) + return r; + + r = link_config_apply_alternative_names(&ctx->rtnl, config, device, new_name); + if (r < 0) + return r; + *ret_name = new_name; return 0; } diff --git a/src/udev/net/link-config.h b/src/udev/net/link-config.h index 827ebf436c..8b5801c003 100644 --- a/src/udev/net/link-config.h +++ b/src/udev/net/link-config.h @@ -77,8 +77,8 @@ int link_load_one(link_config_ctx *ctx, const char *filename); int link_config_load(link_config_ctx *ctx); bool link_config_should_reload(link_config_ctx *ctx); -int link_config_get(link_config_ctx *ctx, sd_device *device, struct link_config **ret); -int link_config_apply(link_config_ctx *ctx, struct link_config *config, sd_device *device, const char **name); +int link_config_get(link_config_ctx *ctx, sd_device *device, link_config **ret); +int link_config_apply(link_config_ctx *ctx, const link_config *config, sd_device *device, const char **ret_name); int link_get_driver(link_config_ctx *ctx, sd_device *device, char **ret); const char *name_policy_to_string(NamePolicy p) _const_; -- cgit v1.2.3 From 51d9aec0ff333ff554079da4babf6dbfa9837096 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 14 Sep 2020 15:20:04 +0900 Subject: Revert "udev: import the full db on MOVE events for devices without dev_t" This reverts commit b081b27e1433cdc7ac72b25ae8b4db887d79187f. If a network interface get a 'move' event, then previously SYSTEMD_ALIAS= property still contains an old alias, and the old alias .device unit will not be removed. This makes all properties cleared on 'move' event, and then old alias .device unit will be removed by pid1. Fixes #16967. --- src/udev/udev-event.c | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/src/udev/udev-event.c b/src/udev/udev-event.c index 7c78b4c680..ede8e3aef7 100644 --- a/src/udev/udev-event.c +++ b/src/udev/udev-event.c @@ -940,16 +940,9 @@ static void event_execute_rules_on_remove( (void) udev_node_remove(dev); } -static int udev_event_on_move(UdevEvent *event) { - sd_device *dev = event->dev; +static int udev_event_on_move(sd_device *dev) { int r; - if (sd_device_get_devnum(dev, NULL) < 0) { - r = device_copy_properties(dev, event->dev_db_clone); - if (r < 0) - log_device_debug_errno(dev, r, "Failed to copy properties from cloned sd_device object, ignoring: %m"); - } - /* Drop previously added property */ r = device_add_property(dev, "ID_RENAMING", NULL); if (r < 0) @@ -1017,7 +1010,7 @@ int udev_event_execute_rules(UdevEvent *event, (void) udev_watch_end(event->dev_db_clone); if (action == DEVICE_ACTION_MOVE) { - r = udev_event_on_move(event); + r = udev_event_on_move(event->dev); if (r < 0) return r; } -- cgit v1.2.3 From e0e789c1e97e2cdf1cafe0c6b7d7e43fa054f151 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 14 Sep 2020 15:21:04 +0900 Subject: udev: re-assign ID_NET_DRIVER=, ID_NET_LINK_FILE=, ID_NET_NAME= properties on non-'add' uevent Previous commit makes drop ID_NET_DRIVER=, ID_NET_LINK_FILE=, and ID_NET_NAME= properties for network interfaces on 'move' uevent. ID_NET_DRIVER= and ID_NET_LINK_FILE= properties are used by networkctl. ID_NET_NAME= may be used by end-user rules or programs. So, let's re-assign them on 'move' uevent. (Note that strictly speaking, this makes them re-assigned on all but 'remove' uevent.) --- rules.d/80-net-setup-link.rules | 2 +- src/udev/net/link-config.c | 30 +++++++++++++++++++++++++++--- 2 files changed, 28 insertions(+), 4 deletions(-) diff --git a/rules.d/80-net-setup-link.rules b/rules.d/80-net-setup-link.rules index 6e411a91f0..bafc3fbc84 100644 --- a/rules.d/80-net-setup-link.rules +++ b/rules.d/80-net-setup-link.rules @@ -4,7 +4,7 @@ SUBSYSTEM!="net", GOTO="net_setup_link_end" IMPORT{builtin}="path_id" -ACTION!="add", GOTO="net_setup_link_end" +ACTION=="remove", GOTO="net_setup_link_end" IMPORT{builtin}="net_setup_link" diff --git a/src/udev/net/link-config.c b/src/udev/net/link-config.c index 77edbb674d..5c871b6717 100644 --- a/src/udev/net/link-config.c +++ b/src/udev/net/link-config.c @@ -11,6 +11,7 @@ #include "conf-files.h" #include "conf-parser.h" #include "def.h" +#include "device-private.h" #include "device-util.h" #include "ethtool-util.h" #include "fd-util.h" @@ -605,6 +606,7 @@ static int link_config_apply_alternative_names(sd_netlink **rtnl, const link_con int link_config_apply(link_config_ctx *ctx, const link_config *config, sd_device *device, const char **ret_name) { const char *new_name; + DeviceAction a; int r; assert(ctx); @@ -612,6 +614,20 @@ int link_config_apply(link_config_ctx *ctx, const link_config *config, sd_device assert(device); assert(ret_name); + r = device_get_action(device, &a); + if (r < 0) + return log_device_error_errno(device, r, "Failed to get ACTION= property: %m"); + + if (!IN_SET(a, DEVICE_ACTION_ADD, DEVICE_ACTION_BIND, DEVICE_ACTION_MOVE)) { + log_device_debug(device, "Skipping to apply .link settings on '%s' uevent.", device_action_to_string(a)); + + r = sd_device_get_sysname(device, ret_name); + if (r < 0) + return log_device_error_errno(device, r, "Failed to get sysname: %m"); + + return 0; + } + r = link_config_apply_ethtool_settings(&ctx->ethtool_fd, config, device); if (r < 0) return r; @@ -620,9 +636,17 @@ int link_config_apply(link_config_ctx *ctx, const link_config *config, sd_device if (r < 0) return r; - r = link_config_generate_new_name(ctx, config, device, &new_name); - if (r < 0) - return r; + if (a == DEVICE_ACTION_MOVE) { + log_device_debug(device, "Skipping to apply Name= and NamePolicy= on '%s' uevent.", device_action_to_string(a)); + + r = sd_device_get_sysname(device, &new_name); + if (r < 0) + return log_device_error_errno(device, r, "Failed to get sysname: %m"); + } else { + r = link_config_generate_new_name(ctx, config, device, &new_name); + if (r < 0) + return r; + } r = link_config_apply_alternative_names(&ctx->rtnl, config, device, new_name); if (r < 0) -- cgit v1.2.3 From f57673025680fdca0c200e7ca7a37fed943d2b49 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 14 Sep 2020 18:28:29 +0900 Subject: udev: allow to match OriginalName= with renamed interface name --- src/udev/net/link-config.c | 27 ++++++++------------------- 1 file changed, 8 insertions(+), 19 deletions(-) diff --git a/src/udev/net/link-config.c b/src/udev/net/link-config.c index 5c871b6717..cb1db3b52b 100644 --- a/src/udev/net/link-config.c +++ b/src/udev/net/link-config.c @@ -242,6 +242,7 @@ bool link_config_should_reload(link_config_ctx *ctx) { } int link_config_get(link_config_ctx *ctx, sd_device *device, link_config **ret) { + unsigned name_assign_type = NET_NAME_UNKNOWN; struct ether_addr permanent_mac = {}; unsigned short iftype = 0; link_config *link; @@ -268,30 +269,18 @@ int link_config_get(link_config_ctx *ctx, sd_device *device, link_config **ret) if (r < 0) log_device_debug_errno(device, r, "Failed to get permanent MAC address, ignoring: %m"); + (void) link_unsigned_attribute(device, "name_assign_type", &name_assign_type); + LIST_FOREACH(links, link, ctx->links) { if (net_match_config(link->match_mac, link->match_permanent_mac, link->match_path, link->match_driver, link->match_type, link->match_name, link->match_property, NULL, NULL, NULL, device, NULL, &permanent_mac, NULL, iftype, NULL, NULL, 0, NULL, NULL)) { - if (link->match_name && !strv_contains(link->match_name, "*")) { - unsigned name_assign_type = NET_NAME_UNKNOWN; - - (void) link_unsigned_attribute(device, "name_assign_type", &name_assign_type); - - if (name_assign_type == NET_NAME_ENUM) { - log_device_warning(device, "Config file %s applies to device based on potentially unpredictable interface name", - link->filename); - *ret = link; - - return 0; - } else if (name_assign_type == NET_NAME_RENAMED) { - log_device_warning(device, "Config file %s matches device based on renamed interface name, ignoring", - link->filename); - - continue; - } - } - log_device_debug(device, "Config file %s is applied", link->filename); + if (link->match_name && !strv_contains(link->match_name, "*") && name_assign_type == NET_NAME_ENUM) + log_device_warning(device, "Config file %s is applied to device based on potentially unpredictable interface name.", + link->filename); + else + log_device_debug(device, "Config file %s is applied", link->filename); *ret = link; return 0; -- cgit v1.2.3 From 7f67b01e3f81029a64c2bb46e2fb57fae6c9d505 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 14 Sep 2020 18:30:58 +0900 Subject: udev: do not update return value on failure --- src/udev/net/link-config.c | 1 - 1 file changed, 1 deletion(-) diff --git a/src/udev/net/link-config.c b/src/udev/net/link-config.c index cb1db3b52b..c23c2bdd20 100644 --- a/src/udev/net/link-config.c +++ b/src/udev/net/link-config.c @@ -287,7 +287,6 @@ int link_config_get(link_config_ctx *ctx, sd_device *device, link_config **ret) } } - *ret = NULL; return -ENOENT; } -- cgit v1.2.3 From 6d4bcea4ca39a5a6e294e8d76a6227bb1d8d330d Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 7 Sep 2020 15:06:00 +0900 Subject: udev: merge rules for bluetooth device --- rules.d/99-systemd.rules.in | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/rules.d/99-systemd.rules.in b/rules.d/99-systemd.rules.in index 1c60eec587..9e2772388d 100644 --- a/rules.d/99-systemd.rules.in +++ b/rules.d/99-systemd.rules.in @@ -46,9 +46,9 @@ SUBSYSTEM=="block", KERNEL=="nbd*", ENV{DEVTYPE}=="disk", TEST!="pid", ENV{SYSTE # http://cgit.freedesktop.org/systemd/systemd/tree/src/libudev/libudev-enumerate.c#n955 SUBSYSTEM=="net", KERNEL!="lo", TAG+="systemd", ENV{SYSTEMD_ALIAS}+="/sys/subsystem/net/devices/$name" -SUBSYSTEM=="bluetooth", TAG+="systemd", ENV{SYSTEMD_ALIAS}+="/sys/subsystem/bluetooth/devices/%k" +SUBSYSTEM=="bluetooth", TAG+="systemd", ENV{SYSTEMD_ALIAS}+="/sys/subsystem/bluetooth/devices/%k", \ + ENV{SYSTEMD_WANTS}+="bluetooth.target", ENV{SYSTEMD_USER_WANTS}+="bluetooth.target" -SUBSYSTEM=="bluetooth", TAG+="systemd", ENV{SYSTEMD_WANTS}+="bluetooth.target", ENV{SYSTEMD_USER_WANTS}+="bluetooth.target" SUBSYSTEM=="usb", ENV{DEVTYPE}=="usb_device", ENV{ID_USB_INTERFACES}=="*:0b????:*", ENV{ID_SMARTCARD_READER}="1" ENV{ID_SMARTCARD_READER}=="?*", TAG+="systemd", ENV{SYSTEMD_WANTS}+="smartcard.target", ENV{SYSTEMD_USER_WANTS}+="smartcard.target" SUBSYSTEM=="sound", KERNEL=="card*", TAG+="systemd", ENV{SYSTEMD_WANTS}+="sound.target", ENV{SYSTEMD_USER_WANTS}+="sound.target" -- cgit v1.2.3 From efdaeb88f02aeb406068d45ae7687abf1bd4a8a3 Mon Sep 17 00:00:00 2001 From: Yu Watanabe Date: Mon, 14 Sep 2020 15:44:30 +0900 Subject: test: add test for device renaming issue #16967 --- test/TEST-29-UDEV-ID_RENAMING/test.sh | 15 +++++++++++++++ test/units/testsuite-29.sh | 16 ++++++++++++++++ 2 files changed, 31 insertions(+) diff --git a/test/TEST-29-UDEV-ID_RENAMING/test.sh b/test/TEST-29-UDEV-ID_RENAMING/test.sh index 4feafc04d7..ddf6db9735 100755 --- a/test/TEST-29-UDEV-ID_RENAMING/test.sh +++ b/test/TEST-29-UDEV-ID_RENAMING/test.sh @@ -1,9 +1,24 @@ #!/usr/bin/env bash set -e TEST_DESCRIPTION="UDEV ID_RENAMING property" +IMAGE_NAME="udev-id-renaming" TEST_NO_NSPAWN=1 . $TEST_BASE_DIR/test-functions QEMU_TIMEOUT=300 +test_create_image() { + create_empty_image_rootdir + + # Create what will eventually be our root filesystem onto an overlay + ( + LOG_LEVEL=5 + setup_basic_environment + mask_supporting_services + + instmods dummy + generate_module_dependencies + ) +} + do_test "$@" 29 diff --git a/test/units/testsuite-29.sh b/test/units/testsuite-29.sh index 5abdb53eb3..5c62556895 100755 --- a/test/units/testsuite-29.sh +++ b/test/units/testsuite-29.sh @@ -38,6 +38,22 @@ STATE=$(systemctl show --property=ActiveState --value sys-devices-virtual-net-lo rm -f /run/udev/rules.d/50-testsuite.rules udevadm control --reload --timeout=600 +# test for issue #16967 + +ip link add hoge type dummy +udevadm info --wait-for-initialization=10s /sys/devices/virtual/net/hoge +sleep 1 +if ! systemctl status sys-devices-virtual-net-hoge.device; then exit 1; fi +if ! systemctl status sys-subsystem-net-devices-hoge.device; then exit 1; fi + +ip link set hoge name foobar +udevadm info --wait-for-initialization=10s /sys/devices/virtual/net/foobar +sleep 1 +if systemctl status sys-devices-virtual-net-hoge.device; then exit 1; fi +if systemctl status sys-subsystem-net-devices-hoge.device; then exit 1; fi +if ! systemctl status sys-devices-virtual-net-foobar.device; then exit 1; fi +if ! systemctl status sys-subsystem-net-devices-foobar.device; then exit 1; fi + echo OK > /testok exit 0 -- cgit v1.2.3