Skip to content

Commit 12d0ad3

Browse files
msoltyspldavem330
authored andcommitted
net/sched/sch_hfsc.c: handle corner cases where head may change invalidating calculated deadline
Realtime scheduling implemented in HFSC uses head of the queue to make the decision about which packet to schedule next. But in case of any head drop, the deadline calculated for the previous head is not necessarily correct for the next head (unless both packets have the same length). Thanks to peek() function used during dequeue - which internally is a dequeue operation - hfsc is almost safe from this issue, as peek() dequeues and isolates the head storing it temporarily until the real dequeue happens. But there is one exception: if after the class activation a drop happens before the first dequeue operation, there's never a chance to do the peek(). Adding peek() call in enqueue - if this is the first packet in a new backlog period AND the scheduler has realtime curve defined - fixes that one corner case. The 1st hfsc_dequeue() will use that peeked packet, similarly as every subsequent hfsc_dequeue() call uses packet peeked by the previous call. Signed-off-by: Michal Soltys <soltys@ziu.info> Signed-off-by: David S. Miller <davem@davemloft.net>
1 parent 19689e3 commit 12d0ad3

File tree

1 file changed

+10
-1
lines changed

1 file changed

+10
-1
lines changed

net/sched/sch_hfsc.c

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1594,8 +1594,17 @@ hfsc_enqueue(struct sk_buff *skb, struct Qdisc *sch, struct sk_buff **to_free)
15941594
return err;
15951595
}
15961596

1597-
if (cl->qdisc->q.qlen == 1)
1597+
if (cl->qdisc->q.qlen == 1) {
15981598
set_active(cl, qdisc_pkt_len(skb));
1599+
/*
1600+
* If this is the first packet, isolate the head so an eventual
1601+
* head drop before the first dequeue operation has no chance
1602+
* to invalidate the deadline.
1603+
*/
1604+
if (cl->cl_flags & HFSC_RSC)
1605+
cl->qdisc->ops->peek(cl->qdisc);
1606+
1607+
}
15991608

16001609
qdisc_qstats_backlog_inc(sch, skb);
16011610
sch->q.qlen++;

0 commit comments

Comments
 (0)