aboutsummaryrefslogtreecommitdiffstats
path: root/net/core
diff options
context:
space:
mode:
authorJohn Fastabend <john.r.fastabend@intel.com>2015-03-18 08:57:33 -0400
committerDavid S. Miller <davem@davemloft.net>2015-03-18 14:55:18 -0400
commit822b3b2ebfff8e9b3d006086c527738a7ca00cd0 (patch)
treed3e6b25328bf4716982026b04dee8c0d2718a5d5 /net/core
parentb65885d29d41c7245bbd98769e781f77e8d9ed5b (diff)
net: Add max rate tx queue attribute
This adds a tx_maxrate attribute to the tx queue sysfs entry allowing for max-rate limiting. Along with DCB-ETS and BQL this provides another knob to tune queue performance. The limit units are Mbps. By default it is disabled. To disable the rate limitation after it has been set for a queue, it should be set to zero. Signed-off-by: John Fastabend <john.r.fastabend@intel.com> Signed-off-by: Or Gerlitz <ogerlitz@mellanox.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/core')
-rw-r--r--net/core/net-sysfs.c67
1 files changed, 55 insertions, 12 deletions
diff --git a/net/core/net-sysfs.c b/net/core/net-sysfs.c
index cf30620a88e1..7e58bd7ec232 100644
--- a/net/core/net-sysfs.c
+++ b/net/core/net-sysfs.c
@@ -951,6 +951,60 @@ static ssize_t show_trans_timeout(struct netdev_queue *queue,
951 return sprintf(buf, "%lu", trans_timeout); 951 return sprintf(buf, "%lu", trans_timeout);
952} 952}
953 953
954#ifdef CONFIG_XPS
955static inline unsigned int get_netdev_queue_index(struct netdev_queue *queue)
956{
957 struct net_device *dev = queue->dev;
958 int i;
959
960 for (i = 0; i < dev->num_tx_queues; i++)
961 if (queue == &dev->_tx[i])
962 break;
963
964 BUG_ON(i >= dev->num_tx_queues);
965
966 return i;
967}
968
969static ssize_t show_tx_maxrate(struct netdev_queue *queue,
970 struct netdev_queue_attribute *attribute,
971 char *buf)
972{
973 return sprintf(buf, "%lu\n", queue->tx_maxrate);
974}
975
976static ssize_t set_tx_maxrate(struct netdev_queue *queue,
977 struct netdev_queue_attribute *attribute,
978 const char *buf, size_t len)
979{
980 struct net_device *dev = queue->dev;
981 int err, index = get_netdev_queue_index(queue);
982 u32 rate = 0;
983
984 err = kstrtou32(buf, 10, &rate);
985 if (err < 0)
986 return err;
987
988 if (!rtnl_trylock())
989 return restart_syscall();
990
991 err = -EOPNOTSUPP;
992 if (dev->netdev_ops->ndo_set_tx_maxrate)
993 err = dev->netdev_ops->ndo_set_tx_maxrate(dev, index, rate);
994
995 rtnl_unlock();
996 if (!err) {
997 queue->tx_maxrate = rate;
998 return len;
999 }
1000 return err;
1001}
1002
1003static struct netdev_queue_attribute queue_tx_maxrate =
1004 __ATTR(tx_maxrate, S_IRUGO | S_IWUSR,
1005 show_tx_maxrate, set_tx_maxrate);
1006#endif
1007
954static struct netdev_queue_attribute queue_trans_timeout = 1008static struct netdev_queue_attribute queue_trans_timeout =
955 __ATTR(tx_timeout, S_IRUGO, show_trans_timeout, NULL); 1009 __ATTR(tx_timeout, S_IRUGO, show_trans_timeout, NULL);
956 1010
@@ -1065,18 +1119,6 @@ static struct attribute_group dql_group = {
1065#endif /* CONFIG_BQL */ 1119#endif /* CONFIG_BQL */
1066 1120
1067#ifdef CONFIG_XPS 1121#ifdef CONFIG_XPS
1068static unsigned int get_netdev_queue_index(struct netdev_queue *queue)
1069{
1070 struct net_device *dev = queue->dev;
1071 unsigned int i;
1072
1073 i = queue - dev->_tx;
1074 BUG_ON(i >= dev->num_tx_queues);
1075
1076 return i;
1077}
1078
1079
1080static ssize_t show_xps_map(struct netdev_queue *queue, 1122static ssize_t show_xps_map(struct netdev_queue *queue,
1081 struct netdev_queue_attribute *attribute, char *buf) 1123 struct netdev_queue_attribute *attribute, char *buf)
1082{ 1124{
@@ -1153,6 +1195,7 @@ static struct attribute *netdev_queue_default_attrs[] = {
1153 &queue_trans_timeout.attr, 1195 &queue_trans_timeout.attr,
1154#ifdef CONFIG_XPS 1196#ifdef CONFIG_XPS
1155 &xps_cpus_attribute.attr, 1197 &xps_cpus_attribute.attr,
1198 &queue_tx_maxrate.attr,
1156#endif 1199#endif
1157 NULL 1200 NULL
1158}; 1201};