Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 133952
b: refs/heads/master
c: 1224736
h: refs/heads/master
v: v3
  • Loading branch information
Jarek Poplawski authored and David S. Miller committed Feb 1, 2009
1 parent 8c62f81 commit 0f012d1
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 6 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: e82181de5ef4648074765912d2d82d6bd60115eb
refs/heads/master: 1224736d97e83367bb66e29c2bee0f570f09db3e
26 changes: 21 additions & 5 deletions trunk/net/sched/sch_htb.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
#include <linux/list.h>
#include <linux/compiler.h>
#include <linux/rbtree.h>
#include <linux/workqueue.h>
#include <net/netlink.h>
#include <net/pkt_sched.h>

Expand Down Expand Up @@ -156,6 +157,7 @@ struct htb_sched {

#define HTB_WARN_TOOMANYEVENTS 0x1
unsigned int warned; /* only one warning */
struct work_struct work;
};

/* find class in global hash table using given handle */
Expand Down Expand Up @@ -659,7 +661,7 @@ static void htb_charge_class(struct htb_sched *q, struct htb_class *cl,
* htb_do_events - make mode changes to classes at the level
*
* Scans event queue for pending events and applies them. Returns time of
* next pending event (0 for no event in pq).
* next pending event (0 for no event in pq, q->now for too many events).
* Note: Applied are events whose have cl->pq_key <= q->now.
*/
static psched_time_t htb_do_events(struct htb_sched *q, int level,
Expand Down Expand Up @@ -687,12 +689,14 @@ static psched_time_t htb_do_events(struct htb_sched *q, int level,
if (cl->cmode != HTB_CAN_SEND)
htb_add_to_wait_tree(q, cl, diff);
}
/* too much load - let's continue on next jiffie (including above) */

/* too much load - let's continue after a break for scheduling */
if (!(q->warned & HTB_WARN_TOOMANYEVENTS)) {
printk(KERN_WARNING "htb: too many events!\n");
q->warned |= HTB_WARN_TOOMANYEVENTS;
}
return q->now + 2 * PSCHED_TICKS_PER_SEC / HZ;

return q->now;
}

/* Returns class->node+prio from id-tree where classe's id is >= id. NULL
Expand Down Expand Up @@ -892,7 +896,10 @@ static struct sk_buff *htb_dequeue(struct Qdisc *sch)
}
}
sch->qstats.overlimits++;
qdisc_watchdog_schedule(&q->watchdog, next_event);
if (likely(next_event > q->now))
qdisc_watchdog_schedule(&q->watchdog, next_event);
else
schedule_work(&q->work);
fin:
return skb;
}
Expand Down Expand Up @@ -962,6 +969,14 @@ static const struct nla_policy htb_policy[TCA_HTB_MAX + 1] = {
[TCA_HTB_RTAB] = { .type = NLA_BINARY, .len = TC_RTAB_SIZE },
};

static void htb_work_func(struct work_struct *work)
{
struct htb_sched *q = container_of(work, struct htb_sched, work);
struct Qdisc *sch = q->watchdog.qdisc;

__netif_schedule(qdisc_root(sch));
}

static int htb_init(struct Qdisc *sch, struct nlattr *opt)
{
struct htb_sched *q = qdisc_priv(sch);
Expand Down Expand Up @@ -996,6 +1011,7 @@ static int htb_init(struct Qdisc *sch, struct nlattr *opt)
INIT_LIST_HEAD(q->drops + i);

qdisc_watchdog_init(&q->watchdog, sch);
INIT_WORK(&q->work, htb_work_func);
skb_queue_head_init(&q->direct_queue);

q->direct_qlen = qdisc_dev(sch)->tx_queue_len;
Expand Down Expand Up @@ -1188,14 +1204,14 @@ static void htb_destroy_class(struct Qdisc *sch, struct htb_class *cl)
kfree(cl);
}

/* always caled under BH & queue lock */
static void htb_destroy(struct Qdisc *sch)
{
struct htb_sched *q = qdisc_priv(sch);
struct hlist_node *n, *next;
struct htb_class *cl;
unsigned int i;

cancel_work_sync(&q->work);
qdisc_watchdog_cancel(&q->watchdog);
/* This line used to be after htb_destroy_class call below
and surprisingly it worked in 2.4. But it must precede it
Expand Down

0 comments on commit 0f012d1

Please sign in to comment.