aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBen Hutchings <bhutchings@solarflare.com>2010-08-17 05:31:15 -0400
committerDavid S. Miller <davem@davemloft.net>2010-08-17 05:31:15 -0400
commit01414802054c382072b6cb9a1bdc6e243c74b2d5 (patch)
treef09b05eb9fff16a69d83ec28653992d1bae8d74c
parentbb8a10bbd10a45db0eb45bac520489bdbc0917ef (diff)
ethtool: Provide a default implementation of ethtool_ops::get_drvinfo
The driver name and bus address for a net_device can normally be found through the driver model now. Instead of requiring drivers to provide this information redundantly through the ethtool_ops::get_drvinfo operation, use the driver model to do so if the driver does not define the operation. Since ETHTOOL_GDRVINFO no longer requires the driver to implement any operations, do not require net_device::ethtool_ops to be set either. Remove implementations of get_drvinfo and ethtool_ops that provide only this information. Signed-off-by: Ben Hutchings <bhutchings@solarflare.com> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--drivers/firewire/net.c13
-rw-r--r--drivers/ieee1394/eth1394.c16
-rw-r--r--drivers/net/bmac.c7
-rw-r--r--drivers/net/fec_mpc52xx.c6
-rw-r--r--drivers/net/pasemi_mac_ethtool.c16
-rw-r--r--drivers/net/pcmcia/3c574_cs.c13
-rw-r--r--drivers/net/pcmcia/axnet_cs.c13
-rw-r--r--drivers/net/pcmcia/ibmtr_cs.c13
-rw-r--r--drivers/net/pcmcia/pcnet_cs.c16
-rw-r--r--drivers/net/sc92031.c11
-rw-r--r--drivers/net/tulip/xircom_cb.c15
-rw-r--r--drivers/net/usb/hso.c9
-rw-r--r--drivers/net/usb/kaweth.c9
-rw-r--r--drivers/net/virtio_net.c14
-rw-r--r--drivers/net/wireless/ray_cs.c16
-rw-r--r--drivers/net/wireless/wl3501_cs.c11
-rw-r--r--net/core/ethtool.c33
17 files changed, 23 insertions, 208 deletions
diff --git a/drivers/firewire/net.c b/drivers/firewire/net.c
index da17d409a244..51e8a35ebd7e 100644
--- a/drivers/firewire/net.c
+++ b/drivers/firewire/net.c
@@ -8,7 +8,6 @@
8 8
9#include <linux/bug.h> 9#include <linux/bug.h>
10#include <linux/device.h> 10#include <linux/device.h>
11#include <linux/ethtool.h>
12#include <linux/firewire.h> 11#include <linux/firewire.h>
13#include <linux/firewire-constants.h> 12#include <linux/firewire-constants.h>
14#include <linux/highmem.h> 13#include <linux/highmem.h>
@@ -1359,17 +1358,6 @@ static int fwnet_change_mtu(struct net_device *net, int new_mtu)
1359 return 0; 1358 return 0;
1360} 1359}
1361 1360
1362static void fwnet_get_drvinfo(struct net_device *net,
1363 struct ethtool_drvinfo *info)
1364{
1365 strcpy(info->driver, KBUILD_MODNAME);
1366 strcpy(info->bus_info, "ieee1394");
1367}
1368
1369static const struct ethtool_ops fwnet_ethtool_ops = {
1370 .get_drvinfo = fwnet_get_drvinfo,
1371};
1372
1373static const struct net_device_ops fwnet_netdev_ops = { 1361static const struct net_device_ops fwnet_netdev_ops = {
1374 .ndo_open = fwnet_open, 1362 .ndo_open = fwnet_open,
1375 .ndo_stop = fwnet_stop, 1363 .ndo_stop = fwnet_stop,
@@ -1388,7 +1376,6 @@ static void fwnet_init_dev(struct net_device *net)
1388 net->hard_header_len = FWNET_HLEN; 1376 net->hard_header_len = FWNET_HLEN;
1389 net->type = ARPHRD_IEEE1394; 1377 net->type = ARPHRD_IEEE1394;
1390 net->tx_queue_len = 10; 1378 net->tx_queue_len = 10;
1391 SET_ETHTOOL_OPS(net, &fwnet_ethtool_ops);
1392} 1379}
1393 1380
1394/* caller must hold fwnet_device_mutex */ 1381/* caller must hold fwnet_device_mutex */
diff --git a/drivers/ieee1394/eth1394.c b/drivers/ieee1394/eth1394.c
index bc289e367e30..63403822330e 100644
--- a/drivers/ieee1394/eth1394.c
+++ b/drivers/ieee1394/eth1394.c
@@ -58,7 +58,6 @@
58#include <linux/tcp.h> 58#include <linux/tcp.h>
59#include <linux/skbuff.h> 59#include <linux/skbuff.h>
60#include <linux/bitops.h> 60#include <linux/bitops.h>
61#include <linux/ethtool.h>
62#include <asm/uaccess.h> 61#include <asm/uaccess.h>
63#include <asm/delay.h> 62#include <asm/delay.h>
64#include <asm/unaligned.h> 63#include <asm/unaligned.h>
@@ -173,8 +172,6 @@ static netdev_tx_t ether1394_tx(struct sk_buff *skb,
173 struct net_device *dev); 172 struct net_device *dev);
174static void ether1394_iso(struct hpsb_iso *iso); 173static void ether1394_iso(struct hpsb_iso *iso);
175 174
176static const struct ethtool_ops ethtool_ops;
177
178static int ether1394_write(struct hpsb_host *host, int srcid, int destid, 175static int ether1394_write(struct hpsb_host *host, int srcid, int destid,
179 quadlet_t *data, u64 addr, size_t len, u16 flags); 176 quadlet_t *data, u64 addr, size_t len, u16 flags);
180static void ether1394_add_host(struct hpsb_host *host); 177static void ether1394_add_host(struct hpsb_host *host);
@@ -525,8 +522,6 @@ static void ether1394_init_dev(struct net_device *dev)
525 dev->header_ops = &ether1394_header_ops; 522 dev->header_ops = &ether1394_header_ops;
526 dev->netdev_ops = &ether1394_netdev_ops; 523 dev->netdev_ops = &ether1394_netdev_ops;
527 524
528 SET_ETHTOOL_OPS(dev, &ethtool_ops);
529
530 dev->watchdog_timeo = ETHER1394_TIMEOUT; 525 dev->watchdog_timeo = ETHER1394_TIMEOUT;
531 dev->flags = IFF_BROADCAST | IFF_MULTICAST; 526 dev->flags = IFF_BROADCAST | IFF_MULTICAST;
532 dev->features = NETIF_F_HIGHDMA; 527 dev->features = NETIF_F_HIGHDMA;
@@ -1695,17 +1690,6 @@ fail:
1695 return NETDEV_TX_OK; 1690 return NETDEV_TX_OK;
1696} 1691}
1697 1692
1698static void ether1394_get_drvinfo(struct net_device *dev,
1699 struct ethtool_drvinfo *info)
1700{
1701 strcpy(info->driver, driver_name);
1702 strcpy(info->bus_info, "ieee1394"); /* FIXME provide more detail? */
1703}
1704
1705static const struct ethtool_ops ethtool_ops = {
1706 .get_drvinfo = ether1394_get_drvinfo
1707};
1708
1709static int __init ether1394_init_module(void) 1693static int __init ether1394_init_module(void)
1710{ 1694{
1711 int err; 1695 int err;
diff --git a/drivers/net/bmac.c b/drivers/net/bmac.c
index 959add2410bf..9322699bb31c 100644
--- a/drivers/net/bmac.c
+++ b/drivers/net/bmac.c
@@ -1233,15 +1233,8 @@ static void bmac_reset_and_enable(struct net_device *dev)
1233 } 1233 }
1234 spin_unlock_irqrestore(&bp->lock, flags); 1234 spin_unlock_irqrestore(&bp->lock, flags);
1235} 1235}
1236static void bmac_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
1237{
1238 struct bmac_data *bp = netdev_priv(dev);
1239 strcpy(info->driver, "bmac");
1240 strcpy(info->bus_info, dev_name(&bp->mdev->ofdev.dev));
1241}
1242 1236
1243static const struct ethtool_ops bmac_ethtool_ops = { 1237static const struct ethtool_ops bmac_ethtool_ops = {
1244 .get_drvinfo = bmac_get_drvinfo,
1245 .get_link = ethtool_op_get_link, 1238 .get_link = ethtool_op_get_link,
1246}; 1239};
1247 1240
diff --git a/drivers/net/fec_mpc52xx.c b/drivers/net/fec_mpc52xx.c
index e3e10b4add9c..e9f5d030bc26 100644
--- a/drivers/net/fec_mpc52xx.c
+++ b/drivers/net/fec_mpc52xx.c
@@ -771,11 +771,6 @@ static void mpc52xx_fec_reset(struct net_device *dev)
771 771
772 772
773/* ethtool interface */ 773/* ethtool interface */
774static void mpc52xx_fec_get_drvinfo(struct net_device *dev,
775 struct ethtool_drvinfo *info)
776{
777 strcpy(info->driver, DRIVER_NAME);
778}
779 774
780static int mpc52xx_fec_get_settings(struct net_device *dev, struct ethtool_cmd *cmd) 775static int mpc52xx_fec_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)
781{ 776{
@@ -810,7 +805,6 @@ static void mpc52xx_fec_set_msglevel(struct net_device *dev, u32 level)
810} 805}
811 806
812static const struct ethtool_ops mpc52xx_fec_ethtool_ops = { 807static const struct ethtool_ops mpc52xx_fec_ethtool_ops = {
813 .get_drvinfo = mpc52xx_fec_get_drvinfo,
814 .get_settings = mpc52xx_fec_get_settings, 808 .get_settings = mpc52xx_fec_get_settings,
815 .set_settings = mpc52xx_fec_set_settings, 809 .set_settings = mpc52xx_fec_set_settings,
816 .get_link = ethtool_op_get_link, 810 .get_link = ethtool_op_get_link,
diff --git a/drivers/net/pasemi_mac_ethtool.c b/drivers/net/pasemi_mac_ethtool.c
index fefa79e34b95..4825959a0efe 100644
--- a/drivers/net/pasemi_mac_ethtool.c
+++ b/drivers/net/pasemi_mac_ethtool.c
@@ -90,21 +90,6 @@ pasemi_mac_ethtool_set_settings(struct net_device *netdev,
90 return phy_ethtool_sset(phydev, cmd); 90 return phy_ethtool_sset(phydev, cmd);
91} 91}
92 92
93static void
94pasemi_mac_ethtool_get_drvinfo(struct net_device *netdev,
95 struct ethtool_drvinfo *drvinfo)
96{
97 struct pasemi_mac *mac;
98 mac = netdev_priv(netdev);
99
100 /* clear and fill out info */
101 memset(drvinfo, 0, sizeof(struct ethtool_drvinfo));
102 strncpy(drvinfo->driver, "pasemi_mac", 12);
103 strcpy(drvinfo->version, "N/A");
104 strcpy(drvinfo->fw_version, "N/A");
105 strncpy(drvinfo->bus_info, pci_name(mac->pdev), 32);
106}
107
108static u32 93static u32
109pasemi_mac_ethtool_get_msglevel(struct net_device *netdev) 94pasemi_mac_ethtool_get_msglevel(struct net_device *netdev)
110{ 95{
@@ -164,7 +149,6 @@ static void pasemi_mac_get_strings(struct net_device *netdev, u32 stringset,
164const struct ethtool_ops pasemi_mac_ethtool_ops = { 149const struct ethtool_ops pasemi_mac_ethtool_ops = {
165 .get_settings = pasemi_mac_ethtool_get_settings, 150 .get_settings = pasemi_mac_ethtool_get_settings,
166 .set_settings = pasemi_mac_ethtool_set_settings, 151 .set_settings = pasemi_mac_ethtool_set_settings,
167 .get_drvinfo = pasemi_mac_ethtool_get_drvinfo,
168 .get_msglevel = pasemi_mac_ethtool_get_msglevel, 152 .get_msglevel = pasemi_mac_ethtool_get_msglevel,
169 .set_msglevel = pasemi_mac_ethtool_set_msglevel, 153 .set_msglevel = pasemi_mac_ethtool_set_msglevel,
170 .get_link = ethtool_op_get_link, 154 .get_link = ethtool_op_get_link,
diff --git a/drivers/net/pcmcia/3c574_cs.c b/drivers/net/pcmcia/3c574_cs.c
index c683f77c6f42..9a1840b67e78 100644
--- a/drivers/net/pcmcia/3c574_cs.c
+++ b/drivers/net/pcmcia/3c574_cs.c
@@ -83,7 +83,6 @@ earlier 3Com products.
83#include <linux/skbuff.h> 83#include <linux/skbuff.h>
84#include <linux/if_arp.h> 84#include <linux/if_arp.h>
85#include <linux/ioport.h> 85#include <linux/ioport.h>
86#include <linux/ethtool.h>
87#include <linux/bitops.h> 86#include <linux/bitops.h>
88#include <linux/mii.h> 87#include <linux/mii.h>
89 88
@@ -238,7 +237,6 @@ static int el3_rx(struct net_device *dev, int worklimit);
238static int el3_close(struct net_device *dev); 237static int el3_close(struct net_device *dev);
239static void el3_tx_timeout(struct net_device *dev); 238static void el3_tx_timeout(struct net_device *dev);
240static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd); 239static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
241static const struct ethtool_ops netdev_ethtool_ops;
242static void set_rx_mode(struct net_device *dev); 240static void set_rx_mode(struct net_device *dev);
243static void set_multicast_list(struct net_device *dev); 241static void set_multicast_list(struct net_device *dev);
244 242
@@ -285,7 +283,6 @@ static int tc574_probe(struct pcmcia_device *link)
285 link->conf.ConfigIndex = 1; 283 link->conf.ConfigIndex = 1;
286 284
287 dev->netdev_ops = &el3_netdev_ops; 285 dev->netdev_ops = &el3_netdev_ops;
288 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
289 dev->watchdog_timeo = TX_TIMEOUT; 286 dev->watchdog_timeo = TX_TIMEOUT;
290 287
291 return tc574_config(link); 288 return tc574_config(link);
@@ -1065,16 +1062,6 @@ static int el3_rx(struct net_device *dev, int worklimit)
1065 return worklimit; 1062 return worklimit;
1066} 1063}
1067 1064
1068static void netdev_get_drvinfo(struct net_device *dev,
1069 struct ethtool_drvinfo *info)
1070{
1071 strcpy(info->driver, "3c574_cs");
1072}
1073
1074static const struct ethtool_ops netdev_ethtool_ops = {
1075 .get_drvinfo = netdev_get_drvinfo,
1076};
1077
1078/* Provide ioctl() calls to examine the MII xcvr state. */ 1065/* Provide ioctl() calls to examine the MII xcvr state. */
1079static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd) 1066static int el3_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
1080{ 1067{
diff --git a/drivers/net/pcmcia/axnet_cs.c b/drivers/net/pcmcia/axnet_cs.c
index 5f05ffb240cc..a6e37b29e3bf 100644
--- a/drivers/net/pcmcia/axnet_cs.c
+++ b/drivers/net/pcmcia/axnet_cs.c
@@ -32,7 +32,6 @@
32#include <linux/timer.h> 32#include <linux/timer.h>
33#include <linux/delay.h> 33#include <linux/delay.h>
34#include <linux/spinlock.h> 34#include <linux/spinlock.h>
35#include <linux/ethtool.h>
36#include <linux/netdevice.h> 35#include <linux/netdevice.h>
37#include <linux/etherdevice.h> 36#include <linux/etherdevice.h>
38#include <linux/crc32.h> 37#include <linux/crc32.h>
@@ -86,7 +85,6 @@ static netdev_tx_t axnet_start_xmit(struct sk_buff *skb,
86static struct net_device_stats *get_stats(struct net_device *dev); 85static struct net_device_stats *get_stats(struct net_device *dev);
87static void set_multicast_list(struct net_device *dev); 86static void set_multicast_list(struct net_device *dev);
88static void axnet_tx_timeout(struct net_device *dev); 87static void axnet_tx_timeout(struct net_device *dev);
89static const struct ethtool_ops netdev_ethtool_ops;
90static irqreturn_t ei_irq_wrapper(int irq, void *dev_id); 88static irqreturn_t ei_irq_wrapper(int irq, void *dev_id);
91static void ei_watchdog(u_long arg); 89static void ei_watchdog(u_long arg);
92static void axnet_reset_8390(struct net_device *dev); 90static void axnet_reset_8390(struct net_device *dev);
@@ -171,7 +169,6 @@ static int axnet_probe(struct pcmcia_device *link)
171 169
172 dev->netdev_ops = &axnet_netdev_ops; 170 dev->netdev_ops = &axnet_netdev_ops;
173 171
174 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
175 dev->watchdog_timeo = TX_TIMEOUT; 172 dev->watchdog_timeo = TX_TIMEOUT;
176 173
177 return axnet_config(link); 174 return axnet_config(link);
@@ -658,16 +655,6 @@ reschedule:
658 add_timer(&info->watchdog); 655 add_timer(&info->watchdog);
659} 656}
660 657
661static void netdev_get_drvinfo(struct net_device *dev,
662 struct ethtool_drvinfo *info)
663{
664 strcpy(info->driver, "axnet_cs");
665}
666
667static const struct ethtool_ops netdev_ethtool_ops = {
668 .get_drvinfo = netdev_get_drvinfo,
669};
670
671/*====================================================================*/ 658/*====================================================================*/
672 659
673static int axnet_ioctl(struct net_device *dev, struct ifreq *rq, int cmd) 660static int axnet_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
diff --git a/drivers/net/pcmcia/ibmtr_cs.c b/drivers/net/pcmcia/ibmtr_cs.c
index b0d06a3d962f..cbcda123b1bf 100644
--- a/drivers/net/pcmcia/ibmtr_cs.c
+++ b/drivers/net/pcmcia/ibmtr_cs.c
@@ -52,7 +52,6 @@
52#include <linux/string.h> 52#include <linux/string.h>
53#include <linux/timer.h> 53#include <linux/timer.h>
54#include <linux/module.h> 54#include <linux/module.h>
55#include <linux/ethtool.h>
56#include <linux/netdevice.h> 55#include <linux/netdevice.h>
57#include <linux/trdevice.h> 56#include <linux/trdevice.h>
58#include <linux/ibmtr.h> 57#include <linux/ibmtr.h>
@@ -107,16 +106,6 @@ typedef struct ibmtr_dev_t {
107 struct tok_info *ti; 106 struct tok_info *ti;
108} ibmtr_dev_t; 107} ibmtr_dev_t;
109 108
110static void netdev_get_drvinfo(struct net_device *dev,
111 struct ethtool_drvinfo *info)
112{
113 strcpy(info->driver, "ibmtr_cs");
114}
115
116static const struct ethtool_ops netdev_ethtool_ops = {
117 .get_drvinfo = netdev_get_drvinfo,
118};
119
120static irqreturn_t ibmtr_interrupt(int irq, void *dev_id) { 109static irqreturn_t ibmtr_interrupt(int irq, void *dev_id) {
121 ibmtr_dev_t *info = dev_id; 110 ibmtr_dev_t *info = dev_id;
122 struct net_device *dev = info->dev; 111 struct net_device *dev = info->dev;
@@ -159,8 +148,6 @@ static int __devinit ibmtr_attach(struct pcmcia_device *link)
159 148
160 info->dev = dev; 149 info->dev = dev;
161 150
162 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
163
164 return ibmtr_config(link); 151 return ibmtr_config(link);
165} /* ibmtr_attach */ 152} /* ibmtr_attach */
166 153
diff --git a/drivers/net/pcmcia/pcnet_cs.c b/drivers/net/pcmcia/pcnet_cs.c
index c3edfe4c2651..2e1348c0033e 100644
--- a/drivers/net/pcmcia/pcnet_cs.c
+++ b/drivers/net/pcmcia/pcnet_cs.c
@@ -35,7 +35,6 @@
35#include <linux/string.h> 35#include <linux/string.h>
36#include <linux/timer.h> 36#include <linux/timer.h>
37#include <linux/delay.h> 37#include <linux/delay.h>
38#include <linux/ethtool.h>
39#include <linux/netdevice.h> 38#include <linux/netdevice.h>
40#include <linux/log2.h> 39#include <linux/log2.h>
41#include <linux/etherdevice.h> 40#include <linux/etherdevice.h>
@@ -100,7 +99,6 @@ static void pcnet_release(struct pcmcia_device *link);
100static int pcnet_open(struct net_device *dev); 99static int pcnet_open(struct net_device *dev);
101static int pcnet_close(struct net_device *dev); 100static int pcnet_close(struct net_device *dev);
102static int ei_ioctl(struct net_device *dev, struct ifreq *rq, int cmd); 101static int ei_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
103static const struct ethtool_ops netdev_ethtool_ops;
104static irqreturn_t ei_irq_wrapper(int irq, void *dev_id); 102static irqreturn_t ei_irq_wrapper(int irq, void *dev_id);
105static void ei_watchdog(u_long arg); 103static void ei_watchdog(u_long arg);
106static void pcnet_reset_8390(struct net_device *dev); 104static void pcnet_reset_8390(struct net_device *dev);
@@ -628,8 +626,6 @@ static int pcnet_config(struct pcmcia_device *link)
628 ei_status.word16 = 1; 626 ei_status.word16 = 1;
629 ei_status.reset_8390 = &pcnet_reset_8390; 627 ei_status.reset_8390 = &pcnet_reset_8390;
630 628
631 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
632
633 if (info->flags & (IS_DL10019|IS_DL10022)) 629 if (info->flags & (IS_DL10019|IS_DL10022))
634 mii_phy_probe(dev); 630 mii_phy_probe(dev);
635 631
@@ -1143,18 +1139,6 @@ reschedule:
1143 1139
1144/*====================================================================*/ 1140/*====================================================================*/
1145 1141
1146static void netdev_get_drvinfo(struct net_device *dev,
1147 struct ethtool_drvinfo *info)
1148{
1149 strcpy(info->driver, "pcnet_cs");
1150}
1151
1152static const struct ethtool_ops netdev_ethtool_ops = {
1153 .get_drvinfo = netdev_get_drvinfo,
1154};
1155
1156/*====================================================================*/
1157
1158 1142
1159static int ei_ioctl(struct net_device *dev, struct ifreq *rq, int cmd) 1143static int ei_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
1160{ 1144{
diff --git a/drivers/net/sc92031.c b/drivers/net/sc92031.c
index 8c4067af32b0..31b92f5f32cb 100644
--- a/drivers/net/sc92031.c
+++ b/drivers/net/sc92031.c
@@ -1251,16 +1251,6 @@ static int sc92031_ethtool_set_settings(struct net_device *dev,
1251 return 0; 1251 return 0;
1252} 1252}
1253 1253
1254static void sc92031_ethtool_get_drvinfo(struct net_device *dev,
1255 struct ethtool_drvinfo *drvinfo)
1256{
1257 struct sc92031_priv *priv = netdev_priv(dev);
1258 struct pci_dev *pdev = priv->pdev;
1259
1260 strcpy(drvinfo->driver, SC92031_NAME);
1261 strcpy(drvinfo->bus_info, pci_name(pdev));
1262}
1263
1264static void sc92031_ethtool_get_wol(struct net_device *dev, 1254static void sc92031_ethtool_get_wol(struct net_device *dev,
1265 struct ethtool_wolinfo *wolinfo) 1255 struct ethtool_wolinfo *wolinfo)
1266{ 1256{
@@ -1382,7 +1372,6 @@ static void sc92031_ethtool_get_ethtool_stats(struct net_device *dev,
1382static const struct ethtool_ops sc92031_ethtool_ops = { 1372static const struct ethtool_ops sc92031_ethtool_ops = {
1383 .get_settings = sc92031_ethtool_get_settings, 1373 .get_settings = sc92031_ethtool_get_settings,
1384 .set_settings = sc92031_ethtool_set_settings, 1374 .set_settings = sc92031_ethtool_set_settings,
1385 .get_drvinfo = sc92031_ethtool_get_drvinfo,
1386 .get_wol = sc92031_ethtool_get_wol, 1375 .get_wol = sc92031_ethtool_get_wol,
1387 .set_wol = sc92031_ethtool_set_wol, 1376 .set_wol = sc92031_ethtool_set_wol,
1388 .nway_reset = sc92031_ethtool_nway_reset, 1377 .nway_reset = sc92031_ethtool_nway_reset,
diff --git a/drivers/net/tulip/xircom_cb.c b/drivers/net/tulip/xircom_cb.c
index a439e93be22d..5a73752be2ca 100644
--- a/drivers/net/tulip/xircom_cb.c
+++ b/drivers/net/tulip/xircom_cb.c
@@ -29,7 +29,6 @@
29#include <linux/skbuff.h> 29#include <linux/skbuff.h>
30#include <linux/delay.h> 30#include <linux/delay.h>
31#include <linux/init.h> 31#include <linux/init.h>
32#include <linux/ethtool.h>
33#include <linux/bitops.h> 32#include <linux/bitops.h>
34 33
35#include <asm/uaccess.h> 34#include <asm/uaccess.h>
@@ -181,19 +180,6 @@ static void print_binary(unsigned int number)
181} 180}
182#endif 181#endif
183 182
184static void netdev_get_drvinfo(struct net_device *dev,
185 struct ethtool_drvinfo *info)
186{
187 struct xircom_private *private = netdev_priv(dev);
188
189 strcpy(info->driver, "xircom_cb");
190 strcpy(info->bus_info, pci_name(private->pdev));
191}
192
193static const struct ethtool_ops netdev_ethtool_ops = {
194 .get_drvinfo = netdev_get_drvinfo,
195};
196
197static const struct net_device_ops netdev_ops = { 183static const struct net_device_ops netdev_ops = {
198 .ndo_open = xircom_open, 184 .ndo_open = xircom_open,
199 .ndo_stop = xircom_close, 185 .ndo_stop = xircom_close,
@@ -279,7 +265,6 @@ static int __devinit xircom_probe(struct pci_dev *pdev, const struct pci_device_
279 setup_descriptors(private); 265 setup_descriptors(private);
280 266
281 dev->netdev_ops = &netdev_ops; 267 dev->netdev_ops = &netdev_ops;
282 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
283 pci_set_drvdata(pdev, dev); 268 pci_set_drvdata(pdev, dev);
284 269
285 if (register_netdev(dev)) { 270 if (register_netdev(dev)) {
diff --git a/drivers/net/usb/hso.c b/drivers/net/usb/hso.c
index 6efca66b8766..4f123f869bdc 100644
--- a/drivers/net/usb/hso.c
+++ b/drivers/net/usb/hso.c
@@ -843,16 +843,7 @@ static netdev_tx_t hso_net_start_xmit(struct sk_buff *skb,
843 return NETDEV_TX_OK; 843 return NETDEV_TX_OK;
844} 844}
845 845
846static void hso_get_drvinfo(struct net_device *net, struct ethtool_drvinfo *info)
847{
848 struct hso_net *odev = netdev_priv(net);
849
850 strncpy(info->driver, driver_name, ETHTOOL_BUSINFO_LEN);
851 usb_make_path(odev->parent->usb, info->bus_info, sizeof info->bus_info);
852}
853
854static const struct ethtool_ops ops = { 846static const struct ethtool_ops ops = {
855 .get_drvinfo = hso_get_drvinfo,
856 .get_link = ethtool_op_get_link 847 .get_link = ethtool_op_get_link
857}; 848};
858 849
diff --git a/drivers/net/usb/kaweth.c b/drivers/net/usb/kaweth.c
index 2b7b39cad1ce..5e98643a4a21 100644
--- a/drivers/net/usb/kaweth.c
+++ b/drivers/net/usb/kaweth.c
@@ -759,14 +759,6 @@ static int kaweth_close(struct net_device *net)
759 return 0; 759 return 0;
760} 760}
761 761
762static void kaweth_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
763{
764 struct kaweth_device *kaweth = netdev_priv(dev);
765
766 strlcpy(info->driver, driver_name, sizeof(info->driver));
767 usb_make_path(kaweth->dev, info->bus_info, sizeof (info->bus_info));
768}
769
770static u32 kaweth_get_link(struct net_device *dev) 762static u32 kaweth_get_link(struct net_device *dev)
771{ 763{
772 struct kaweth_device *kaweth = netdev_priv(dev); 764 struct kaweth_device *kaweth = netdev_priv(dev);
@@ -775,7 +767,6 @@ static u32 kaweth_get_link(struct net_device *dev)
775} 767}
776 768
777static const struct ethtool_ops ops = { 769static const struct ethtool_ops ops = {
778 .get_drvinfo = kaweth_get_drvinfo,
779 .get_link = kaweth_get_link 770 .get_link = kaweth_get_link
780}; 771};
781 772
diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 4598e9d2608f..bb6b67f6b0cc 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -705,19 +705,6 @@ static int virtnet_close(struct net_device *dev)
705 return 0; 705 return 0;
706} 706}
707 707
708static void virtnet_get_drvinfo(struct net_device *dev,
709 struct ethtool_drvinfo *drvinfo)
710{
711 struct virtnet_info *vi = netdev_priv(dev);
712 struct virtio_device *vdev = vi->vdev;
713
714 strncpy(drvinfo->driver, KBUILD_MODNAME, ARRAY_SIZE(drvinfo->driver));
715 strncpy(drvinfo->version, "N/A", ARRAY_SIZE(drvinfo->version));
716 strncpy(drvinfo->fw_version, "N/A", ARRAY_SIZE(drvinfo->fw_version));
717 strncpy(drvinfo->bus_info, dev_name(&vdev->dev),
718 ARRAY_SIZE(drvinfo->bus_info));
719}
720
721static int virtnet_set_tx_csum(struct net_device *dev, u32 data) 708static int virtnet_set_tx_csum(struct net_device *dev, u32 data)
722{ 709{
723 struct virtnet_info *vi = netdev_priv(dev); 710 struct virtnet_info *vi = netdev_priv(dev);
@@ -830,7 +817,6 @@ static void virtnet_vlan_rx_kill_vid(struct net_device *dev, u16 vid)
830} 817}
831 818
832static const struct ethtool_ops virtnet_ethtool_ops = { 819static const struct ethtool_ops virtnet_ethtool_ops = {
833 .get_drvinfo = virtnet_get_drvinfo,
834 .set_tx_csum = virtnet_set_tx_csum, 820 .set_tx_csum = virtnet_set_tx_csum,
835 .set_sg = ethtool_op_set_sg, 821 .set_sg = ethtool_op_set_sg,
836 .set_tso = ethtool_op_set_tso, 822 .set_tso = ethtool_op_set_tso,
diff --git a/drivers/net/wireless/ray_cs.c b/drivers/net/wireless/ray_cs.c
index 88560d0ae50a..3bd9cf76517d 100644
--- a/drivers/net/wireless/ray_cs.c
+++ b/drivers/net/wireless/ray_cs.c
@@ -43,7 +43,6 @@
43#include <linux/if_arp.h> 43#include <linux/if_arp.h>
44#include <linux/ioport.h> 44#include <linux/ioport.h>
45#include <linux/skbuff.h> 45#include <linux/skbuff.h>
46#include <linux/ethtool.h>
47#include <linux/ieee80211.h> 46#include <linux/ieee80211.h>
48 47
49#include <pcmcia/cs.h> 48#include <pcmcia/cs.h>
@@ -80,8 +79,6 @@ static int ray_dev_config(struct net_device *dev, struct ifmap *map);
80static struct net_device_stats *ray_get_stats(struct net_device *dev); 79static struct net_device_stats *ray_get_stats(struct net_device *dev);
81static int ray_dev_init(struct net_device *dev); 80static int ray_dev_init(struct net_device *dev);
82 81
83static const struct ethtool_ops netdev_ethtool_ops;
84
85static int ray_open(struct net_device *dev); 82static int ray_open(struct net_device *dev);
86static netdev_tx_t ray_dev_start_xmit(struct sk_buff *skb, 83static netdev_tx_t ray_dev_start_xmit(struct sk_buff *skb,
87 struct net_device *dev); 84 struct net_device *dev);
@@ -333,7 +330,6 @@ static int ray_probe(struct pcmcia_device *p_dev)
333 330
334 /* Raylink entries in the device structure */ 331 /* Raylink entries in the device structure */
335 dev->netdev_ops = &ray_netdev_ops; 332 dev->netdev_ops = &ray_netdev_ops;
336 SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
337 dev->wireless_handlers = &ray_handler_def; 333 dev->wireless_handlers = &ray_handler_def;
338#ifdef WIRELESS_SPY 334#ifdef WIRELESS_SPY
339 local->wireless_data.spy_data = &local->spy_data; 335 local->wireless_data.spy_data = &local->spy_data;
@@ -1062,18 +1058,6 @@ AP to AP 1 1 dest AP src AP dest source
1062 } 1058 }
1063} /* end encapsulate_frame */ 1059} /* end encapsulate_frame */
1064 1060
1065/*===========================================================================*/
1066
1067static void netdev_get_drvinfo(struct net_device *dev,
1068 struct ethtool_drvinfo *info)
1069{
1070 strcpy(info->driver, "ray_cs");
1071}
1072
1073static const struct ethtool_ops netdev_ethtool_ops = {
1074 .get_drvinfo = netdev_get_drvinfo,
1075};
1076
1077/*====================================================================*/ 1061/*====================================================================*/
1078 1062
1079/*------------------------------------------------------------------*/ 1063/*------------------------------------------------------------------*/
diff --git a/drivers/net/wireless/wl3501_cs.c b/drivers/net/wireless/wl3501_cs.c
index a1cc2d498a1c..420e9e986a18 100644
--- a/drivers/net/wireless/wl3501_cs.c
+++ b/drivers/net/wireless/wl3501_cs.c
@@ -29,7 +29,6 @@
29 29
30#include <linux/delay.h> 30#include <linux/delay.h>
31#include <linux/types.h> 31#include <linux/types.h>
32#include <linux/ethtool.h>
33#include <linux/init.h> 32#include <linux/init.h>
34#include <linux/interrupt.h> 33#include <linux/interrupt.h>
35#include <linux/in.h> 34#include <linux/in.h>
@@ -1411,15 +1410,6 @@ static struct iw_statistics *wl3501_get_wireless_stats(struct net_device *dev)
1411 return wstats; 1410 return wstats;
1412} 1411}
1413 1412
1414static void wl3501_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
1415{
1416 strlcpy(info->driver, "wl3501_cs", sizeof(info->driver));
1417}
1418
1419static const struct ethtool_ops ops = {
1420 .get_drvinfo = wl3501_get_drvinfo
1421};
1422
1423/** 1413/**
1424 * wl3501_detach - deletes a driver "instance" 1414 * wl3501_detach - deletes a driver "instance"
1425 * @link - FILL_IN 1415 * @link - FILL_IN
@@ -1905,7 +1895,6 @@ static int wl3501_probe(struct pcmcia_device *p_dev)
1905 this->p_dev = p_dev; 1895 this->p_dev = p_dev;
1906 dev->wireless_data = &this->wireless_data; 1896 dev->wireless_data = &this->wireless_data;
1907 dev->wireless_handlers = &wl3501_handler_def; 1897 dev->wireless_handlers = &wl3501_handler_def;
1908 SET_ETHTOOL_OPS(dev, &ops);
1909 netif_stop_queue(dev); 1898 netif_stop_queue(dev);
1910 p_dev->priv = dev; 1899 p_dev->priv = dev;
1911 1900
diff --git a/net/core/ethtool.c b/net/core/ethtool.c
index 7a85367b3c2f..d2c4da5a6a4f 100644
--- a/net/core/ethtool.c
+++ b/net/core/ethtool.c
@@ -205,18 +205,24 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev,
205 struct ethtool_drvinfo info; 205 struct ethtool_drvinfo info;
206 const struct ethtool_ops *ops = dev->ethtool_ops; 206 const struct ethtool_ops *ops = dev->ethtool_ops;
207 207
208 if (!ops->get_drvinfo)
209 return -EOPNOTSUPP;
210
211 memset(&info, 0, sizeof(info)); 208 memset(&info, 0, sizeof(info));
212 info.cmd = ETHTOOL_GDRVINFO; 209 info.cmd = ETHTOOL_GDRVINFO;
213 ops->get_drvinfo(dev, &info); 210 if (ops && ops->get_drvinfo) {
211 ops->get_drvinfo(dev, &info);
212 } else if (dev->dev.parent && dev->dev.parent->driver) {
213 strlcpy(info.bus_info, dev_name(dev->dev.parent),
214 sizeof(info.bus_info));
215 strlcpy(info.driver, dev->dev.parent->driver->name,
216 sizeof(info.driver));
217 } else {
218 return -EOPNOTSUPP;
219 }
214 220
215 /* 221 /*
216 * this method of obtaining string set info is deprecated; 222 * this method of obtaining string set info is deprecated;
217 * Use ETHTOOL_GSSET_INFO instead. 223 * Use ETHTOOL_GSSET_INFO instead.
218 */ 224 */
219 if (ops->get_sset_count) { 225 if (ops && ops->get_sset_count) {
220 int rc; 226 int rc;
221 227
222 rc = ops->get_sset_count(dev, ETH_SS_TEST); 228 rc = ops->get_sset_count(dev, ETH_SS_TEST);
@@ -229,9 +235,9 @@ static noinline_for_stack int ethtool_get_drvinfo(struct net_device *dev,
229 if (rc >= 0) 235 if (rc >= 0)
230 info.n_priv_flags = rc; 236 info.n_priv_flags = rc;
231 } 237 }
232 if (ops->get_regs_len) 238 if (ops && ops->get_regs_len)
233 info.regdump_len = ops->get_regs_len(dev); 239 info.regdump_len = ops->get_regs_len(dev);
234 if (ops->get_eeprom_len) 240 if (ops && ops->get_eeprom_len)
235 info.eedump_len = ops->get_eeprom_len(dev); 241 info.eedump_len = ops->get_eeprom_len(dev);
236 242
237 if (copy_to_user(useraddr, &info, sizeof(info))) 243 if (copy_to_user(useraddr, &info, sizeof(info)))
@@ -1402,12 +1408,19 @@ int dev_ethtool(struct net *net, struct ifreq *ifr)
1402 if (!dev || !netif_device_present(dev)) 1408 if (!dev || !netif_device_present(dev))
1403 return -ENODEV; 1409 return -ENODEV;
1404 1410
1405 if (!dev->ethtool_ops)
1406 return -EOPNOTSUPP;
1407
1408 if (copy_from_user(&ethcmd, useraddr, sizeof(ethcmd))) 1411 if (copy_from_user(&ethcmd, useraddr, sizeof(ethcmd)))
1409 return -EFAULT; 1412 return -EFAULT;
1410 1413
1414 if (!dev->ethtool_ops) {
1415 /* ETHTOOL_GDRVINFO does not require any driver support.
1416 * It is also unprivileged and does not change anything,
1417 * so we can take a shortcut to it. */
1418 if (ethcmd == ETHTOOL_GDRVINFO)
1419 return ethtool_get_drvinfo(dev, useraddr);
1420 else
1421 return -EOPNOTSUPP;
1422 }
1423
1411 /* Allow some commands to be done by anyone */ 1424 /* Allow some commands to be done by anyone */
1412 switch (ethcmd) { 1425 switch (ethcmd) {
1413 case ETHTOOL_GDRVINFO: 1426 case ETHTOOL_GDRVINFO: