[PATCH] SCHED_FIFO and SCHED_RR scheduler fix, kernel 2.2.21

Bhavesh P. Davda (bhavesh@avaya.com)
Fri, 21 Jun 2002 16:12:56 -0600 (MDT)


The 2.2.21 kernel was behaving incorrectly for SCHED_FIFO and SCHED_RR
scheduling.

The correct behaviour for SCHED_FIFO is priority preemption: run to
completion, or system call, or preemption by higher priority process. The
correct behaviour for SCHED_RR is the same as SCHED_FIFO for the
preemption case, or run for a time slice, and go to the back of the run
queue for that priority.

More details can be found at:

http://www.opengroup.org/onlinepubs/7908799/xsh/realtime.html

This is a small patch, but fixes the behaviour for SCHED_FIFO and SCHED_RR
scheduling in the 2.2.21 kernel. It also improves the efficiency of the
kernel by NOT calling schedule() for every tick for a SCHED_FIFO process.

--
Bhavesh P. Davda
Avaya, Inc.
bhavesh@avaya.com

diff -aur linux-2.2.21/kernel/sched.c linux-2.2.21-bpd/kernel/sched.c --- linux-2.2.21/kernel/sched.c Sun Mar 25 09:37:40 2001 +++ linux-2.2.21-bpd/kernel/sched.c Fri Jun 21 09:54:55 2002 @@ -749,7 +749,16 @@ /* Default process to select.. */ next = idle_task(this_cpu); c = -1000; - if (prev->state == TASK_RUNNING) + /* + * If a SCHED_RR task has exhausted its time slice, + * it is at the back of the runqueue, even if it is + * still running. On the other hand, if a SCHED_RR task + * is still running and still has time left in its + * time slice, then it is still the first process in its + * priority band, so it will run next if it is the first + * highest priority SCHED_RR task + */ + if ((prev->state == TASK_RUNNING) && (prev->policy != SCHED_RR)) goto still_running; still_running_back: @@ -1492,7 +1501,12 @@ p->counter -= ticks; if (p->counter < 0) { p->counter = 0; - p->need_resched = 1; + /* SCHED_FIFO is priority preemption, so this is + * not the place to reschedule it + */ + if (p->policy != SCHED_FIFO) { + p->need_resched = 1; + } } if (p->priority < DEF_PRIORITY) kstat.cpu_nice += user; @@ -1785,8 +1799,6 @@ retval = 0; p->policy = policy; p->rt_priority = lp.sched_priority; - if (p->next_run) - move_first_runqueue(p); current->need_resched = 1;

- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/