diff -urNp linux-2.5.55-ms-ilb-nb/include/linux/sched.h linux-2.5.55-ms-ilb-nba/include/linux/sched.h --- linux-2.5.55-ms-ilb-nb/include/linux/sched.h 2003-01-11 17:19:49.000000000 +0100 +++ linux-2.5.55-ms-ilb-nba/include/linux/sched.h 2003-01-11 17:17:53.000000000 +0100 @@ -451,12 +451,14 @@ extern void node_nr_running_init(void); #define nr_running_dec(rq) atomic_dec(rq->node_ptr); \ rq->nr_running-- #define decl_numa_int(ctr) int ctr +#define decl_numa_nodeint(v) int v[MAX_NUMNODES] #else #define sched_balance_exec() {} #define node_nr_running_init() {} #define nr_running_inc(rq) rq->nr_running++ #define nr_running_dec(rq) rq->nr_running-- #define decl_numa_int(ctr) {} +#define decl_numa_nodeint(v) {} #endif extern void set_user_nice(task_t *p, long nice); diff -urNp linux-2.5.55-ms-ilb-nb/kernel/sched.c linux-2.5.55-ms-ilb-nba/kernel/sched.c --- linux-2.5.55-ms-ilb-nb/kernel/sched.c 2003-01-12 18:18:16.000000000 +0100 +++ linux-2.5.55-ms-ilb-nba/kernel/sched.c 2003-01-12 18:15:34.000000000 +0100 @@ -155,6 +155,7 @@ struct runqueue { int prev_nr_running[NR_CPUS]; atomic_t * node_ptr; decl_numa_int(lb_cntr); + decl_numa_nodeint(prev_node_load); task_t *migration_thread; struct list_head migration_queue; @@ -705,15 +706,25 @@ void sched_balance_exec(void) } } +/* + * Find the busiest node. All previous node loads contribute with a geometrically + * deccaying weight to the load measure: + * load_{t} = load_{t-1}/2 + nr_node_running_{t} + * This way sudden load peaks are flattened out a bit. + */ static int find_busiest_node(int this_node) { int i, node = this_node, load, this_load, maxload; - this_load = maxload = atomic_read(&node_nr_running[this_node]); + this_load = maxload = (this_rq()->prev_node_load[this_node] >> 1) + + atomic_read(&node_nr_running[this_node]); + this_rq()->prev_node_load[this_node] = this_load; for (i = 0; i < numnodes; i++) { if (i == this_node) continue; - load = atomic_read(&node_nr_running[i]); + load = (this_rq()->prev_node_load[i] >> 1) + + atomic_read(&node_nr_running[i]); + this_rq()->prev_node_load[i] = load; if (load > maxload && (4*load > ((5*4*this_load)/4))) { maxload = load; node = i;