]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
net/sched: sch_drr: annotate data-races around cl->deficit
authorEric Dumazet <edumazet@google.com>
Tue, 19 May 2026 09:46:17 +0000 (09:46 +0000)
committerJakub Kicinski <kuba@kernel.org>
Thu, 21 May 2026 02:04:57 +0000 (19:04 -0700)
drr_dump_class_stats() runs without qdisc spinlock held.

Add missing READ_ONCE()/WRITE_ONCE() annotations around cl->deficit.

Fixes: edb09eb17ed8 ("net: sched: do not acquire qdisc spinlock in qdisc/class stats dump")
Signed-off-by: Eric Dumazet <edumazet@google.com>
Link: https://patch.msgid.link/20260519094618.2632073-2-edumazet@google.com
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
net/sched/sch_drr.c

index 3f6687fa9666257952be5d44f9e3460845fe2a40..7da8c7c8421b7f2477c7c07d3b5920b375ce029e 100644 (file)
@@ -270,7 +270,7 @@ static int drr_dump_class_stats(struct Qdisc *sch, unsigned long arg,
 
        memset(&xstats, 0, sizeof(xstats));
        if (qlen)
-               xstats.deficit = cl->deficit;
+               xstats.deficit = READ_ONCE(cl->deficit);
 
        if (gnet_stats_copy_basic(d, NULL, &cl->bstats, true) < 0 ||
            gnet_stats_copy_rate_est(d, &cl->rate_est) < 0 ||
@@ -362,7 +362,7 @@ static int drr_enqueue(struct sk_buff *skb, struct Qdisc *sch,
 
        if (!cl_is_active(cl)) {
                list_add_tail(&cl->alist, &q->active);
-               cl->deficit = cl->quantum;
+               WRITE_ONCE(cl->deficit, cl->quantum);
        }
 
        qstats_backlog_add(sch, len);
@@ -389,7 +389,7 @@ static struct sk_buff *drr_dequeue(struct Qdisc *sch)
 
                len = qdisc_pkt_len(skb);
                if (len <= cl->deficit) {
-                       cl->deficit -= len;
+                       WRITE_ONCE(cl->deficit, cl->deficit - len);
                        skb = qdisc_dequeue_peeked(cl->qdisc);
                        if (unlikely(skb == NULL))
                                goto out;
@@ -403,7 +403,7 @@ static struct sk_buff *drr_dequeue(struct Qdisc *sch)
                        return skb;
                }
 
-               cl->deficit += cl->quantum;
+               WRITE_ONCE(cl->deficit, cl->deficit + cl->quantum);
                list_move_tail(&cl->alist, &q->active);
        }
 out: