summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPhil Sutter <phil@nwl.cc>2018-10-18 10:34:26 +0200
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2018-11-04 14:52:50 +0100
commitfd090ba395fb60c71abb0c35bd026c4dcf5a4a1d (patch)
treec215690d3f80cda1e53266a42100ab945fb091f1
parentbc478700368780c5460391282a098d5ba57464db (diff)
downloadlinux-stable-fd090ba395fb60c71abb0c35bd026c4dcf5a4a1d.tar.gz
linux-stable-fd090ba395fb60c71abb0c35bd026c4dcf5a4a1d.tar.bz2
linux-stable-fd090ba395fb60c71abb0c35bd026c4dcf5a4a1d.zip
net: sched: Fix for duplicate class dump
[ Upstream commit 3c53ed8fef6881a864f0ee8240ed2793ef73ad0d ] When dumping classes by parent, kernel would return classes twice: | # tc qdisc add dev lo root prio | # tc class show dev lo | class prio 8001:1 parent 8001: | class prio 8001:2 parent 8001: | class prio 8001:3 parent 8001: | # tc class show dev lo parent 8001: | class prio 8001:1 parent 8001: | class prio 8001:2 parent 8001: | class prio 8001:3 parent 8001: | class prio 8001:1 parent 8001: | class prio 8001:2 parent 8001: | class prio 8001:3 parent 8001: This comes from qdisc_match_from_root() potentially returning the root qdisc itself if its handle matched. Though in that case, root's classes were already dumped a few lines above. Fixes: cb395b2010879 ("net: sched: optimize class dumps") Signed-off-by: Phil Sutter <phil@nwl.cc> Reviewed-by: Jiri Pirko <jiri@mellanox.com> Reviewed-by: Eric Dumazet <edumazet@google.com> Signed-off-by: David S. Miller <davem@davemloft.net> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--net/sched/sch_api.c3
1 files changed, 2 insertions, 1 deletions
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c
index cd69aa067543..691ca96f7460 100644
--- a/net/sched/sch_api.c
+++ b/net/sched/sch_api.c
@@ -1917,7 +1917,8 @@ static int tc_dump_tclass_root(struct Qdisc *root, struct sk_buff *skb,
if (tcm->tcm_parent) {
q = qdisc_match_from_root(root, TC_H_MAJ(tcm->tcm_parent));
- if (q && tc_dump_tclass_qdisc(q, skb, tcm, cb, t_p, s_t) < 0)
+ if (q && q != root &&
+ tc_dump_tclass_qdisc(q, skb, tcm, cb, t_p, s_t) < 0)
return -1;
return 0;
}