diff options
author | Jussi Kivilinna <jussi.kivilinna@mbnet.fi> | 2008-07-20 00:08:47 -0700 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2008-07-20 00:08:47 -0700 |
commit | 175f9c1bba9b825d22b142d183c9e175488b260c (patch) | |
tree | 6b9cdb2e3802e7fc8422dc0d0cc200f6d4d1d0a5 /include/net | |
parent | 0abf77e55a2459aa9905be4b226e4729d5b4f0cb (diff) |
net_sched: Add size table for qdiscs
Add size table functions for qdiscs and calculate packet size in
qdisc_enqueue().
Based on patch by Patrick McHardy
http://marc.info/?l=linux-netdev&m=115201979221729&w=2
Signed-off-by: Jussi Kivilinna <jussi.kivilinna@mbnet.fi>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'include/net')
-rw-r--r-- | include/net/pkt_sched.h | 1 | ||||
-rw-r--r-- | include/net/sch_generic.h | 25 |
2 files changed, 25 insertions, 1 deletions
diff --git a/include/net/pkt_sched.h b/include/net/pkt_sched.h index e4e30052e4e..6affcfaa123 100644 --- a/include/net/pkt_sched.h +++ b/include/net/pkt_sched.h @@ -83,6 +83,7 @@ extern struct Qdisc *qdisc_lookup_class(struct net_device *dev, u32 handle); extern struct qdisc_rate_table *qdisc_get_rtab(struct tc_ratespec *r, struct nlattr *tab); extern void qdisc_put_rtab(struct qdisc_rate_table *tab); +extern void qdisc_put_stab(struct qdisc_size_table *tab); extern void __qdisc_run(struct Qdisc *q); diff --git a/include/net/sch_generic.h b/include/net/sch_generic.h index 8229520e088..db9ad655eb8 100644 --- a/include/net/sch_generic.h +++ b/include/net/sch_generic.h @@ -29,6 +29,13 @@ enum qdisc_state_t __QDISC_STATE_SCHED, }; +struct qdisc_size_table { + struct list_head list; + struct tc_sizespec szopts; + int refcnt; + u16 data[]; +}; + struct Qdisc { int (*enqueue)(struct sk_buff *skb, struct Qdisc *dev); @@ -39,6 +46,7 @@ struct Qdisc #define TCQ_F_INGRESS 4 int padded; struct Qdisc_ops *ops; + struct qdisc_size_table *stab; u32 handle; u32 parent; atomic_t refcnt; @@ -165,6 +173,16 @@ struct tcf_proto struct tcf_proto_ops *ops; }; +struct qdisc_skb_cb { + unsigned int pkt_len; + char data[]; +}; + +static inline struct qdisc_skb_cb *qdisc_skb_cb(struct sk_buff *skb) +{ + return (struct qdisc_skb_cb *)skb->cb; +} + static inline spinlock_t *qdisc_lock(struct Qdisc *qdisc) { return &qdisc->q.lock; @@ -257,6 +275,8 @@ extern struct Qdisc *qdisc_alloc(struct netdev_queue *dev_queue, extern struct Qdisc *qdisc_create_dflt(struct net_device *dev, struct netdev_queue *dev_queue, struct Qdisc_ops *ops, u32 parentid); +extern void qdisc_calculate_pkt_len(struct sk_buff *skb, + struct qdisc_size_table *stab); extern void tcf_destroy(struct tcf_proto *tp); extern void tcf_destroy_chain(struct tcf_proto **fl); @@ -308,16 +328,19 @@ static inline bool qdisc_tx_is_noop(const struct net_device *dev) static inline unsigned int qdisc_pkt_len(struct sk_buff *skb) { - return skb->len; + return qdisc_skb_cb(skb)->pkt_len; } static inline int qdisc_enqueue(struct sk_buff *skb, struct Qdisc *sch) { + if (sch->stab) + qdisc_calculate_pkt_len(skb, sch->stab); return sch->enqueue(skb, sch); } static inline int qdisc_enqueue_root(struct sk_buff *skb, struct Qdisc *sch) { + qdisc_skb_cb(skb)->pkt_len = skb->len; return qdisc_enqueue(skb, sch); } |