diff options
author | Jarek Poplawski <jarkao2@gmail.com> | 2008-10-31 03:47:01 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-10-31 03:47:01 -0400 |
commit | 77be155cba4e163e8bba9fd27222a8b6189ec4f7 (patch) | |
tree | 0819d4c0bb760080aaba8a00060a774205914034 /include | |
parent | 03c05f0d4bb0c267edf12d614025a40e33c5a6f9 (diff) |
pkt_sched: Add peek emulation for non-work-conserving qdiscs.
This patch adds qdisc_peek_dequeued() wrapper to emulate peek method
with qdisc->dequeue() and storing "peeked" skb in qdisc->gso_skb until
dequeuing. This is mainly for compatibility reasons not to break some
strange configs because peeking is expected for non-work-conserving
parent qdiscs to query work-conserving child qdiscs.
This implementation requires using qdisc_dequeue_peeked() wrapper
instead of directly calling qdisc->dequeue() for all qdiscs ever
querried with qdisc->ops->peek() or qdisc_peek_dequeued().
Signed-off-by: Jarek Poplawski <jarkao2@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'include')
-rw-r--r-- | include/net/sch_generic.h | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/include/net/sch_generic.h b/include/net/sch_generic.h index da6839a7ff50..9dcb5bfe094a 100644 --- a/include/net/sch_generic.h +++ b/include/net/sch_generic.h | |||
@@ -438,6 +438,29 @@ static inline struct sk_buff *qdisc_peek_head(struct Qdisc *sch) | |||
438 | return skb_peek(&sch->q); | 438 | return skb_peek(&sch->q); |
439 | } | 439 | } |
440 | 440 | ||
441 | /* generic pseudo peek method for non-work-conserving qdisc */ | ||
442 | static inline struct sk_buff *qdisc_peek_dequeued(struct Qdisc *sch) | ||
443 | { | ||
444 | /* we can reuse ->gso_skb because peek isn't called for root qdiscs */ | ||
445 | if (!sch->gso_skb) | ||
446 | sch->gso_skb = sch->dequeue(sch); | ||
447 | |||
448 | return sch->gso_skb; | ||
449 | } | ||
450 | |||
451 | /* use instead of qdisc->dequeue() for all qdiscs queried with ->peek() */ | ||
452 | static inline struct sk_buff *qdisc_dequeue_peeked(struct Qdisc *sch) | ||
453 | { | ||
454 | struct sk_buff *skb = sch->gso_skb; | ||
455 | |||
456 | if (skb) | ||
457 | sch->gso_skb = NULL; | ||
458 | else | ||
459 | skb = sch->dequeue(sch); | ||
460 | |||
461 | return skb; | ||
462 | } | ||
463 | |||
441 | static inline int __qdisc_requeue(struct sk_buff *skb, struct Qdisc *sch, | 464 | static inline int __qdisc_requeue(struct sk_buff *skb, struct Qdisc *sch, |
442 | struct sk_buff_head *list) | 465 | struct sk_buff_head *list) |
443 | { | 466 | { |