diff options
author | Jeff Garzik <jeff@garzik.org> | 2007-08-15 19:01:08 -0400 |
---|---|---|
committer | David S. Miller <davem@sunset.davemloft.net> | 2007-10-10 19:48:08 -0400 |
commit | ff03d49f0ca1959246068b315d26e009da692ff2 (patch) | |
tree | 210cf86efa9fd4430d0011c81956bef92c3d71a3 /net | |
parent | 3ae7c0b2e3747b50c3a6c63ebb67469e0a6b3203 (diff) |
[ETHTOOL]: Introduce get_sset_count. Obsolete get_stats_count, self_test_count
Signed-off-by: Jeff Garzik <jeff@garzik.org>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net')
-rw-r--r-- | net/core/ethtool.c | 95 |
1 files changed, 70 insertions, 25 deletions
diff --git a/net/core/ethtool.c b/net/core/ethtool.c index 6f8b78bcfd84..1edae460d616 100644 --- a/net/core/ethtool.c +++ b/net/core/ethtool.c | |||
@@ -179,10 +179,23 @@ static int ethtool_get_drvinfo(struct net_device *dev, void __user *useraddr) | |||
179 | info.cmd = ETHTOOL_GDRVINFO; | 179 | info.cmd = ETHTOOL_GDRVINFO; |
180 | ops->get_drvinfo(dev, &info); | 180 | ops->get_drvinfo(dev, &info); |
181 | 181 | ||
182 | if (ops->self_test_count) | 182 | if (ops->get_sset_count) { |
183 | info.testinfo_len = ops->self_test_count(dev); | 183 | int rc; |
184 | if (ops->get_stats_count) | 184 | |
185 | info.n_stats = ops->get_stats_count(dev); | 185 | rc = ops->get_sset_count(dev, ETH_SS_TEST); |
186 | if (rc >= 0) | ||
187 | info.testinfo_len = rc; | ||
188 | rc = ops->get_sset_count(dev, ETH_SS_STATS); | ||
189 | if (rc >= 0) | ||
190 | info.n_stats = rc; | ||
191 | } else { | ||
192 | /* code path for obsolete hooks */ | ||
193 | |||
194 | if (ops->self_test_count) | ||
195 | info.testinfo_len = ops->self_test_count(dev); | ||
196 | if (ops->get_stats_count) | ||
197 | info.n_stats = ops->get_stats_count(dev); | ||
198 | } | ||
186 | if (ops->get_regs_len) | 199 | if (ops->get_regs_len) |
187 | info.regdump_len = ops->get_regs_len(dev); | 200 | info.regdump_len = ops->get_regs_len(dev); |
188 | if (ops->get_eeprom_len) | 201 | if (ops->get_eeprom_len) |
@@ -669,16 +682,27 @@ static int ethtool_self_test(struct net_device *dev, char __user *useraddr) | |||
669 | struct ethtool_test test; | 682 | struct ethtool_test test; |
670 | const struct ethtool_ops *ops = dev->ethtool_ops; | 683 | const struct ethtool_ops *ops = dev->ethtool_ops; |
671 | u64 *data; | 684 | u64 *data; |
672 | int ret; | 685 | int ret, test_len; |
673 | 686 | ||
674 | if (!ops->self_test || !ops->self_test_count) | 687 | if (!ops->self_test) |
688 | return -EOPNOTSUPP; | ||
689 | if (!ops->get_sset_count && !ops->self_test_count) | ||
675 | return -EOPNOTSUPP; | 690 | return -EOPNOTSUPP; |
676 | 691 | ||
692 | if (ops->get_sset_count) | ||
693 | test_len = ops->get_sset_count(dev, ETH_SS_TEST); | ||
694 | else | ||
695 | /* code path for obsolete hook */ | ||
696 | test_len = ops->self_test_count(dev); | ||
697 | if (test_len < 0) | ||
698 | return test_len; | ||
699 | WARN_ON(test_len == 0); | ||
700 | |||
677 | if (copy_from_user(&test, useraddr, sizeof(test))) | 701 | if (copy_from_user(&test, useraddr, sizeof(test))) |
678 | return -EFAULT; | 702 | return -EFAULT; |
679 | 703 | ||
680 | test.len = ops->self_test_count(dev); | 704 | test.len = test_len; |
681 | data = kmalloc(test.len * sizeof(u64), GFP_USER); | 705 | data = kmalloc(test_len * sizeof(u64), GFP_USER); |
682 | if (!data) | 706 | if (!data) |
683 | return -ENOMEM; | 707 | return -ENOMEM; |
684 | 708 | ||
@@ -710,19 +734,29 @@ static int ethtool_get_strings(struct net_device *dev, void __user *useraddr) | |||
710 | if (copy_from_user(&gstrings, useraddr, sizeof(gstrings))) | 734 | if (copy_from_user(&gstrings, useraddr, sizeof(gstrings))) |
711 | return -EFAULT; | 735 | return -EFAULT; |
712 | 736 | ||
713 | switch (gstrings.string_set) { | 737 | if (ops->get_sset_count) { |
714 | case ETH_SS_TEST: | 738 | ret = ops->get_sset_count(dev, gstrings.string_set); |
715 | if (!ops->self_test_count) | 739 | if (ret < 0) |
716 | return -EOPNOTSUPP; | 740 | return ret; |
717 | gstrings.len = ops->self_test_count(dev); | 741 | |
718 | break; | 742 | gstrings.len = ret; |
719 | case ETH_SS_STATS: | 743 | } else { |
720 | if (!ops->get_stats_count) | 744 | /* code path for obsolete hooks */ |
721 | return -EOPNOTSUPP; | 745 | |
722 | gstrings.len = ops->get_stats_count(dev); | 746 | switch (gstrings.string_set) { |
723 | break; | 747 | case ETH_SS_TEST: |
724 | default: | 748 | if (!ops->self_test_count) |
725 | return -EINVAL; | 749 | return -EOPNOTSUPP; |
750 | gstrings.len = ops->self_test_count(dev); | ||
751 | break; | ||
752 | case ETH_SS_STATS: | ||
753 | if (!ops->get_stats_count) | ||
754 | return -EOPNOTSUPP; | ||
755 | gstrings.len = ops->get_stats_count(dev); | ||
756 | break; | ||
757 | default: | ||
758 | return -EINVAL; | ||
759 | } | ||
726 | } | 760 | } |
727 | 761 | ||
728 | data = kmalloc(gstrings.len * ETH_GSTRING_LEN, GFP_USER); | 762 | data = kmalloc(gstrings.len * ETH_GSTRING_LEN, GFP_USER); |
@@ -762,16 +796,27 @@ static int ethtool_get_stats(struct net_device *dev, void __user *useraddr) | |||
762 | struct ethtool_stats stats; | 796 | struct ethtool_stats stats; |
763 | const struct ethtool_ops *ops = dev->ethtool_ops; | 797 | const struct ethtool_ops *ops = dev->ethtool_ops; |
764 | u64 *data; | 798 | u64 *data; |
765 | int ret; | 799 | int ret, n_stats; |
766 | 800 | ||
767 | if (!ops->get_ethtool_stats || !ops->get_stats_count) | 801 | if (!ops->get_ethtool_stats) |
768 | return -EOPNOTSUPP; | 802 | return -EOPNOTSUPP; |
803 | if (!ops->get_sset_count && !ops->get_stats_count) | ||
804 | return -EOPNOTSUPP; | ||
805 | |||
806 | if (ops->get_sset_count) | ||
807 | n_stats = ops->get_sset_count(dev, ETH_SS_STATS); | ||
808 | else | ||
809 | /* code path for obsolete hook */ | ||
810 | n_stats = ops->get_stats_count(dev); | ||
811 | if (n_stats < 0) | ||
812 | return n_stats; | ||
813 | WARN_ON(n_stats == 0); | ||
769 | 814 | ||
770 | if (copy_from_user(&stats, useraddr, sizeof(stats))) | 815 | if (copy_from_user(&stats, useraddr, sizeof(stats))) |
771 | return -EFAULT; | 816 | return -EFAULT; |
772 | 817 | ||
773 | stats.n_stats = ops->get_stats_count(dev); | 818 | stats.n_stats = n_stats; |
774 | data = kmalloc(stats.n_stats * sizeof(u64), GFP_USER); | 819 | data = kmalloc(n_stats * sizeof(u64), GFP_USER); |
775 | if (!data) | 820 | if (!data) |
776 | return -ENOMEM; | 821 | return -ENOMEM; |
777 | 822 | ||