diff options
author | David S. Miller <davem@davemloft.net> | 2008-07-17 03:34:19 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-07-17 22:21:00 -0400 |
commit | e8a0464cc950972824e2e128028ae3db666ec1ed (patch) | |
tree | 5022b95396c0f3b313531bc39b19543c03551b9a /net/sched/sch_api.c | |
parent | 070825b3840a743e21ebcc44f8279708a4fed977 (diff) |
netdev: Allocate multiple queues for TX.
alloc_netdev_mq() now allocates an array of netdev_queue
structures for TX, based upon the queue_count argument.
Furthermore, all accesses to the TX queues are now vectored
through the netdev_get_tx_queue() and netdev_for_each_tx_queue()
interfaces. This makes it easy to grep the tree for all
things that want to get to a TX queue of a net device.
Problem spots which are not really multiqueue aware yet, and
only work with one queue, can easily be spotted by grepping
for all netdev_get_tx_queue() calls that pass in a zero index.
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/sched/sch_api.c')
-rw-r--r-- | net/sched/sch_api.c | 32 |
1 files changed, 23 insertions, 9 deletions
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c index 95873f8dd37c..830ccc544a15 100644 --- a/net/sched/sch_api.c +++ b/net/sched/sch_api.c | |||
@@ -183,9 +183,8 @@ EXPORT_SYMBOL(unregister_qdisc); | |||
183 | (root qdisc, all its children, children of children etc.) | 183 | (root qdisc, all its children, children of children etc.) |
184 | */ | 184 | */ |
185 | 185 | ||
186 | struct Qdisc *qdisc_lookup(struct net_device *dev, u32 handle) | 186 | static struct Qdisc *__qdisc_lookup(struct netdev_queue *dev_queue, u32 handle) |
187 | { | 187 | { |
188 | struct netdev_queue *dev_queue = &dev->tx_queue; | ||
189 | struct Qdisc *q; | 188 | struct Qdisc *q; |
190 | 189 | ||
191 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { | 190 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { |
@@ -195,6 +194,19 @@ struct Qdisc *qdisc_lookup(struct net_device *dev, u32 handle) | |||
195 | return NULL; | 194 | return NULL; |
196 | } | 195 | } |
197 | 196 | ||
197 | struct Qdisc *qdisc_lookup(struct net_device *dev, u32 handle) | ||
198 | { | ||
199 | unsigned int i; | ||
200 | |||
201 | for (i = 0; i < dev->num_tx_queues; i++) { | ||
202 | struct netdev_queue *txq = netdev_get_tx_queue(dev, i); | ||
203 | struct Qdisc *q = __qdisc_lookup(txq, handle); | ||
204 | if (q) | ||
205 | return q; | ||
206 | } | ||
207 | return NULL; | ||
208 | } | ||
209 | |||
198 | static struct Qdisc *qdisc_leaf(struct Qdisc *p, u32 classid) | 210 | static struct Qdisc *qdisc_leaf(struct Qdisc *p, u32 classid) |
199 | { | 211 | { |
200 | unsigned long cl; | 212 | unsigned long cl; |
@@ -462,7 +474,7 @@ dev_graft_qdisc(struct net_device *dev, struct Qdisc *qdisc) | |||
462 | } | 474 | } |
463 | 475 | ||
464 | } else { | 476 | } else { |
465 | dev_queue = &dev->tx_queue; | 477 | dev_queue = netdev_get_tx_queue(dev, 0); |
466 | oqdisc = dev_queue->qdisc_sleeping; | 478 | oqdisc = dev_queue->qdisc_sleeping; |
467 | 479 | ||
468 | /* Prune old scheduler */ | 480 | /* Prune old scheduler */ |
@@ -742,7 +754,8 @@ static int tc_get_qdisc(struct sk_buff *skb, struct nlmsghdr *n, void *arg) | |||
742 | q = dev->rx_queue.qdisc; | 754 | q = dev->rx_queue.qdisc; |
743 | } | 755 | } |
744 | } else { | 756 | } else { |
745 | struct netdev_queue *dev_queue = &dev->tx_queue; | 757 | struct netdev_queue *dev_queue; |
758 | dev_queue = netdev_get_tx_queue(dev, 0); | ||
746 | q = dev_queue->qdisc_sleeping; | 759 | q = dev_queue->qdisc_sleeping; |
747 | } | 760 | } |
748 | if (!q) | 761 | if (!q) |
@@ -817,7 +830,8 @@ replay: | |||
817 | q = dev->rx_queue.qdisc; | 830 | q = dev->rx_queue.qdisc; |
818 | } | 831 | } |
819 | } else { | 832 | } else { |
820 | struct netdev_queue *dev_queue = &dev->tx_queue; | 833 | struct netdev_queue *dev_queue; |
834 | dev_queue = netdev_get_tx_queue(dev, 0); | ||
821 | q = dev_queue->qdisc_sleeping; | 835 | q = dev_queue->qdisc_sleeping; |
822 | } | 836 | } |
823 | 837 | ||
@@ -899,7 +913,7 @@ create_n_graft: | |||
899 | tcm->tcm_parent, tcm->tcm_parent, | 913 | tcm->tcm_parent, tcm->tcm_parent, |
900 | tca, &err); | 914 | tca, &err); |
901 | else | 915 | else |
902 | q = qdisc_create(dev, &dev->tx_queue, | 916 | q = qdisc_create(dev, netdev_get_tx_queue(dev, 0), |
903 | tcm->tcm_parent, tcm->tcm_handle, | 917 | tcm->tcm_parent, tcm->tcm_handle, |
904 | tca, &err); | 918 | tca, &err); |
905 | if (q == NULL) { | 919 | if (q == NULL) { |
@@ -1025,7 +1039,7 @@ static int tc_dump_qdisc(struct sk_buff *skb, struct netlink_callback *cb) | |||
1025 | if (idx > s_idx) | 1039 | if (idx > s_idx) |
1026 | s_q_idx = 0; | 1040 | s_q_idx = 0; |
1027 | q_idx = 0; | 1041 | q_idx = 0; |
1028 | dev_queue = &dev->tx_queue; | 1042 | dev_queue = netdev_get_tx_queue(dev, 0); |
1029 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { | 1043 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { |
1030 | if (q_idx < s_q_idx) { | 1044 | if (q_idx < s_q_idx) { |
1031 | q_idx++; | 1045 | q_idx++; |
@@ -1098,7 +1112,7 @@ static int tc_ctl_tclass(struct sk_buff *skb, struct nlmsghdr *n, void *arg) | |||
1098 | 1112 | ||
1099 | /* Step 1. Determine qdisc handle X:0 */ | 1113 | /* Step 1. Determine qdisc handle X:0 */ |
1100 | 1114 | ||
1101 | dev_queue = &dev->tx_queue; | 1115 | dev_queue = netdev_get_tx_queue(dev, 0); |
1102 | if (pid != TC_H_ROOT) { | 1116 | if (pid != TC_H_ROOT) { |
1103 | u32 qid1 = TC_H_MAJ(pid); | 1117 | u32 qid1 = TC_H_MAJ(pid); |
1104 | 1118 | ||
@@ -1275,7 +1289,7 @@ static int tc_dump_tclass(struct sk_buff *skb, struct netlink_callback *cb) | |||
1275 | s_t = cb->args[0]; | 1289 | s_t = cb->args[0]; |
1276 | t = 0; | 1290 | t = 0; |
1277 | 1291 | ||
1278 | dev_queue = &dev->tx_queue; | 1292 | dev_queue = netdev_get_tx_queue(dev, 0); |
1279 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { | 1293 | list_for_each_entry(q, &dev_queue->qdisc_list, list) { |
1280 | if (t < s_t || !q->ops->cl_ops || | 1294 | if (t < s_t || !q->ops->cl_ops || |
1281 | (tcm->tcm_parent && | 1295 | (tcm->tcm_parent && |