mirror of
https://github.com/systemd/systemd-stable.git
synced 2025-02-03 13:47:04 +03:00
Merge pull request #16968 from yuwata/remove-old-device-on-move-event
core, udev: remove old device on move event
This commit is contained in:
commit
fc8bc57f6b
@ -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"
|
||||
|
||||
|
@ -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"
|
||||
|
@ -894,6 +894,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;
|
||||
@ -918,6 +941,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 */
|
||||
|
@ -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
|
||||
};
|
||||
|
@ -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_;
|
||||
|
@ -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"
|
||||
@ -241,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;
|
||||
@ -267,40 +269,91 @@ 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;
|
||||
}
|
||||
}
|
||||
|
||||
*ret = NULL;
|
||||
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 +410,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;
|
||||
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(rtnl);
|
||||
assert(config);
|
||||
assert(device);
|
||||
|
||||
r = sd_device_get_ifindex(device, &ifindex);
|
||||
if (r < 0)
|
||||
return log_device_error_errno(device, r, "Could not find ifindex: %m");
|
||||
|
||||
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 = rtnl_set_link_properties(rtnl, ifindex, config->alias, mac, config->mtu);
|
||||
if (r < 0)
|
||||
log_device_warning_errno(device, r, "Could not set Alias=, MACAddress= or MTU=, ignoring: %m");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
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;
|
||||
const char *old_name;
|
||||
unsigned speed, name_type = NET_NAME_UNKNOWN;
|
||||
NamePolicy policy;
|
||||
int r, ifindex;
|
||||
int r;
|
||||
|
||||
assert(ctx);
|
||||
assert(config);
|
||||
assert(device);
|
||||
assert(name);
|
||||
|
||||
r = sd_device_get_sysname(device, &old_name);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
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));
|
||||
|
||||
r = ethtool_set_features(&ctx->ethtool_fd, old_name, config->features);
|
||||
if (r < 0)
|
||||
log_warning_errno(r, "Could not set offload features of %s: %m", old_name);
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
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);
|
||||
}
|
||||
|
||||
r = sd_device_get_ifindex(device, &ifindex);
|
||||
if (r < 0)
|
||||
return log_device_warning_errno(device, r, "Could not find ifindex: %m");
|
||||
assert(ret_name);
|
||||
|
||||
(void) link_unsigned_attribute(device, "name_assign_type", &name_type);
|
||||
|
||||
@ -482,24 +496,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 +572,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 +584,63 @@ 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");
|
||||
|
||||
*name = new_name;
|
||||
return 0;
|
||||
}
|
||||
|
||||
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);
|
||||
assert(config);
|
||||
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;
|
||||
|
||||
r = link_config_apply_rtnl_settings(&ctx->rtnl, config, device);
|
||||
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)
|
||||
return r;
|
||||
|
||||
*ret_name = new_name;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -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_;
|
||||
|
@ -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;
|
||||
}
|
||||
|
@ -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
|
||||
|
@ -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
|
||||
|
Loading…
x
Reference in New Issue
Block a user