From 847a8a5fed4d265dfa659917515c6f9bd1b8d5c4 Mon Sep 17 00:00:00 2001 From: Tom Gundersen Date: Fri, 21 Feb 2014 16:54:00 +0100 Subject: [PATCH] udev - link-setup - expose ID_NET_DRIVER This is the same as shown by 'ethtool -i ', and is sometimes set even though DRIVER is not. --- src/udev/net/ethtool-util.c | 23 +++++++++++++++ src/udev/net/ethtool-util.h | 1 + src/udev/net/link-config.c | 40 ++++++++++++++++++++------ src/udev/net/link-config.h | 2 ++ src/udev/udev-builtin-net_setup_link.c | 5 ++++ 5 files changed, 62 insertions(+), 9 deletions(-) diff --git a/src/udev/net/ethtool-util.c b/src/udev/net/ethtool-util.c index c644f91d0..aaba94c2f 100644 --- a/src/udev/net/ethtool-util.c +++ b/src/udev/net/ethtool-util.c @@ -63,6 +63,29 @@ int ethtool_connect(int *ret) { return 0; } +int ethtool_get_driver(int fd, const char *ifname, char **ret) { + struct ifreq ifr; + struct ethtool_drvinfo ecmd; + int r; + + zero(ecmd); + ecmd.cmd = ETHTOOL_GDRVINFO; + + zero(ifr); + strscpy(ifr.ifr_name, IFNAMSIZ, ifname); + ifr.ifr_data = (void *)&ecmd; + + r = ioctl(fd, SIOCETHTOOL, &ifr); + if (r < 0) + return -errno; + + *ret = strdup(ecmd.driver); + if (!*ret) + return -ENOMEM; + + return 0; +} + int ethtool_set_speed(int fd, const char *ifname, unsigned int speed, Duplex duplex) { struct ifreq ifr; diff --git a/src/udev/net/ethtool-util.h b/src/udev/net/ethtool-util.h index c8638f22e..f44de5076 100644 --- a/src/udev/net/ethtool-util.h +++ b/src/udev/net/ethtool-util.h @@ -42,6 +42,7 @@ typedef enum WakeOnLan { int ethtool_connect(int *ret); +int ethtool_get_driver(int fd, const char *ifname, char **ret); int ethtool_set_speed(int fd, const char *ifname, unsigned int speed, Duplex duplex); int ethtool_set_wol(int fd, const char *ifname, WakeOnLan wol); diff --git a/src/udev/net/link-config.c b/src/udev/net/link-config.c index e8389c9be..40b1d7f7b 100644 --- a/src/udev/net/link-config.c +++ b/src/udev/net/link-config.c @@ -90,16 +90,17 @@ int link_config_ctx_new(link_config_ctx **ret) { static int link_config_ctx_connect(link_config_ctx *ctx) { int r; - if (ctx->ethtool_fd >= 0 && ctx->rtnl) - return 0; - - r = ethtool_connect(&ctx->ethtool_fd); - if (r < 0) - return r; + if (ctx->ethtool_fd == -1) { + r = ethtool_connect(&ctx->ethtool_fd); + if (r < 0) + return r; + } - r = sd_rtnl_open(&ctx->rtnl, 0); - if (r < 0) - return r; + if (!ctx->rtnl) { + r = sd_rtnl_open(&ctx->rtnl, 0); + if (r < 0) + return r; + } return 0; } @@ -442,6 +443,27 @@ int link_config_apply(link_config_ctx *ctx, link_config *config, struct udev_dev return 0; } +int link_get_driver(link_config_ctx *ctx, struct udev_device *device, char **ret) { + const char *name; + char *driver; + int r; + + r = link_config_ctx_connect(ctx); + if (r < 0) + return r; + + name = udev_device_get_sysname(device); + if (!name) + return -EINVAL; + + r = ethtool_get_driver(ctx->ethtool_fd, name, &driver); + if (r < 0) + return r; + + *ret = driver; + return 0; +} + static const char* const mac_policy_table[] = { [MACPOLICY_PERSISTENT] = "persistent", [MACPOLICY_RANDOM] = "random" diff --git a/src/udev/net/link-config.h b/src/udev/net/link-config.h index 9d2eaff37..24fdb87e4 100644 --- a/src/udev/net/link-config.h +++ b/src/udev/net/link-config.h @@ -83,6 +83,8 @@ bool link_config_should_reload(link_config_ctx *ctx); int link_config_get(link_config_ctx *ctx, struct udev_device *device, struct link_config **ret); int link_config_apply(link_config_ctx *ctx, struct link_config *config, struct udev_device *device, const char **name); +int link_get_driver(link_config_ctx *ctx, struct udev_device *device, char **ret); + const char *name_policy_to_string(NamePolicy p) _const_; NamePolicy name_policy_from_string(const char *p) _pure_; diff --git a/src/udev/udev-builtin-net_setup_link.c b/src/udev/udev-builtin-net_setup_link.c index b7ba8c906..3cd384e94 100644 --- a/src/udev/udev-builtin-net_setup_link.c +++ b/src/udev/udev-builtin-net_setup_link.c @@ -26,6 +26,7 @@ static link_config_ctx *ctx = NULL; static int builtin_net_setup_link(struct udev_device *dev, int argc, char **argv, bool test) { + _cleanup_free_ char *driver = NULL; const char *name; link_config *link; int r; @@ -35,6 +36,10 @@ static int builtin_net_setup_link(struct udev_device *dev, int argc, char **argv return EXIT_FAILURE; } + r = link_get_driver(ctx, dev, &driver); + if (r >= 0) + udev_builtin_add_property(dev, test, "ID_NET_DRIVER", driver); + r = link_config_get(ctx, dev, &link); if (r < 0) { if (r == -ENOENT) { -- 2.30.2