diff options
author | Jarek Poplawski <jarkao2@gmail.com> | 2008-08-18 23:53:34 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-08-19 00:06:09 -0400 |
commit | 25bfcd5a78a377ea4c54a3c21e44590e2fc478a6 (patch) | |
tree | 6abe3cb036c724206ec0996351aa8eec12d12b42 /net/sched/sch_api.c | |
parent | 8608db031b4d2932d645709e2cfe8fbcd91a7305 (diff) |
pkt_sched: Add lockdep annotation for qdisc locks
Qdisc locks are initialized in the same function, qdisc_alloc(), so
lockdep can't distinguish tx qdisc lock from rx and reports "possible
recursive locking detected" when both these locks are taken eg. while
using act_mirred with ifb. This looks like a false positive. Anyway,
after this patch these locks will be reported more exactly.
Reported-by: Denys Fedoryshchenko <denys@visp.net.lb>
Signed-off-by: Jarek Poplawski <jarkao2@gmail.com>
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 | 7 |
1 files changed, 7 insertions, 0 deletions
diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c index 98c00847a3d2..7d7070b1eebd 100644 --- a/net/sched/sch_api.c +++ b/net/sched/sch_api.c | |||
@@ -27,6 +27,7 @@ | |||
27 | #include <linux/kmod.h> | 27 | #include <linux/kmod.h> |
28 | #include <linux/list.h> | 28 | #include <linux/list.h> |
29 | #include <linux/hrtimer.h> | 29 | #include <linux/hrtimer.h> |
30 | #include <linux/lockdep.h> | ||
30 | 31 | ||
31 | #include <net/net_namespace.h> | 32 | #include <net/net_namespace.h> |
32 | #include <net/sock.h> | 33 | #include <net/sock.h> |
@@ -707,6 +708,10 @@ static int qdisc_graft(struct net_device *dev, struct Qdisc *parent, | |||
707 | return err; | 708 | return err; |
708 | } | 709 | } |
709 | 710 | ||
711 | /* lockdep annotation is needed for ingress; egress gets it only for name */ | ||
712 | static struct lock_class_key qdisc_tx_lock; | ||
713 | static struct lock_class_key qdisc_rx_lock; | ||
714 | |||
710 | /* | 715 | /* |
711 | Allocate and initialize new qdisc. | 716 | Allocate and initialize new qdisc. |
712 | 717 | ||
@@ -767,6 +772,7 @@ qdisc_create(struct net_device *dev, struct netdev_queue *dev_queue, | |||
767 | if (handle == TC_H_INGRESS) { | 772 | if (handle == TC_H_INGRESS) { |
768 | sch->flags |= TCQ_F_INGRESS; | 773 | sch->flags |= TCQ_F_INGRESS; |
769 | handle = TC_H_MAKE(TC_H_INGRESS, 0); | 774 | handle = TC_H_MAKE(TC_H_INGRESS, 0); |
775 | lockdep_set_class(qdisc_lock(sch), &qdisc_rx_lock); | ||
770 | } else { | 776 | } else { |
771 | if (handle == 0) { | 777 | if (handle == 0) { |
772 | handle = qdisc_alloc_handle(dev); | 778 | handle = qdisc_alloc_handle(dev); |
@@ -774,6 +780,7 @@ qdisc_create(struct net_device *dev, struct netdev_queue *dev_queue, | |||
774 | if (handle == 0) | 780 | if (handle == 0) |
775 | goto err_out3; | 781 | goto err_out3; |
776 | } | 782 | } |
783 | lockdep_set_class(qdisc_lock(sch), &qdisc_tx_lock); | ||
777 | } | 784 | } |
778 | 785 | ||
779 | sch->handle = handle; | 786 | sch->handle = handle; |