sched: wakeup-buddy tasks are cache-hot
[sfrench/cifs-2.6.git] / kernel / sched.c
index 3a4ba3dc0f498fe71d04d7b33b8cfe086695d4a5..3f7c5eb254e205c24bc95bf5ac264e28d918d9b8 100644 (file)
@@ -301,7 +301,7 @@ struct cfs_rq {
        /* 'curr' points to currently running entity on this cfs_rq.
         * It is set to NULL otherwise (i.e when none are currently running).
         */
-       struct sched_entity *curr;
+       struct sched_entity *curr, *next;
 
        unsigned long nr_spread_over;
 
@@ -1084,7 +1084,7 @@ calc_delta_mine(unsigned long delta_exec, unsigned long weight,
        u64 tmp;
 
        if (unlikely(!lw->inv_weight))
-               lw->inv_weight = (WMULT_CONST - lw->weight/2) / lw->weight + 1;
+               lw->inv_weight = (WMULT_CONST-lw->weight/2) / (lw->weight+1);
 
        tmp = (u64)delta_exec * weight;
        /*
@@ -1396,6 +1396,12 @@ task_hot(struct task_struct *p, u64 now, struct sched_domain *sd)
 {
        s64 delta;
 
+       /*
+        * Buddy candidates are cache hot:
+        */
+       if (&p->se == cfs_rq_of(&p->se)->next)
+               return 1;
+
        if (p->sched_class != &fair_sched_class)
                return 0;
 
@@ -1855,10 +1861,11 @@ out_activate:
                schedstat_inc(p, se.nr_wakeups_remote);
        update_rq_clock(rq);
        activate_task(rq, p, 1);
-       check_preempt_curr(rq, p);
        success = 1;
 
 out_running:
+       check_preempt_curr(rq, p);
+
        p->state = TASK_RUNNING;
 #ifdef CONFIG_SMP
        if (p->sched_class->task_wake_up)
@@ -1892,6 +1899,8 @@ static void __sched_fork(struct task_struct *p)
        p->se.exec_start                = 0;
        p->se.sum_exec_runtime          = 0;
        p->se.prev_sum_exec_runtime     = 0;
+       p->se.last_wakeup               = 0;
+       p->se.avg_overlap               = 0;
 
 #ifdef CONFIG_SCHEDSTATS
        p->se.wait_start                = 0;