示例#1
0
void _arch_irq_task_switch(void * _cpu_state) {
  
  if(run_queue) {

    spinlock_lock(&run_queue->spinlock);

    get_system_time(&run_queue->sched_time);

    struct kthread * c = run_queue_current();
    struct kthread * n = run_queue_next();
		
    spinlock_unlock(&run_queue->spinlock);

    _BUG_ON(!n);
    _BUG_ON(!c);

    if(stack_check(&(c->stack))<0)
      _BUG(); // TASK WE JUST PUT TO SLEEP BLEW ITS STACK!
    
    _switch(c,n,_cpu_state);
    
    // schedule next switch.
    _sched_next_task(NULL);
  }
}
示例#2
0
/**
 * @brief Best effort (BE) scheduler (callback).
 *
 * @return Best effort task id.
 *
 * The algorithm is Round Robin.
 * 	- Take a task from the run queue, copy its entry and put it back at the tail of the run queue.
 * 	- If the task is in the blocked state (it may be simply blocked or waiting in a semaphore), it is
 * 	  put back at the tail of the run queue and the next task is picked up.
 * 	- So, if all tasks are blocked, at least the idle task can execute (it is never
 *	  blocked, at least it is what we hope!).
 * 	- Tasks in the blocked state are never removed from the run queue (they are
 *	  ignored), although they may be in another queue waiting for a resource.
 */
int32_t sched_rr(void)
{
	if (hf_queue_count(krnl_run_queue) == 0)
		panic(PANIC_NO_TASKS_RUN);
	do {
		run_queue_next();
	} while (krnl_task->state == TASK_BLOCKED);
	krnl_task->bgjobs++;

	return krnl_task->id;
}
示例#3
0
/**
 * @brief Best effort (BE) scheduler (callback).
 *
 * @return Best effort task id.
 *
 * The algorithm is priority based Round Robin.
 * 	- Take the first task and put it at the end of the run queue (to advance the queue and avoid deadlocks)
 * 	- Perform a run in the queue, searching for the task with the highest priority (non blocked, lowest remaining priority)
 * 		- While we are at it, check if there is a critical task. If so, schedule it, and get out.
 * 	- Perform another run in the queue, updating the remaining priorities of all tasks by subtracting the priority
 * 	  of the task with the lowest remaining priority (task with the highest priority) from the remaining priority of
 * 	  all other tasks.
 */
int32_t sched_priorityrr(void)
{
	int32_t i, k;
	uint8_t highestp = 255;
	struct tcb_entry *krnl_task2 = NULL;

	k = hf_queue_count(krnl_run_queue);
	if (k == 0)
		panic(PANIC_NO_TASKS_RUN);

	/* advance the queue to prevent deadlocks */
	run_queue_next();

	/* search for the highest priority task */
	for (i = 0; i < k; i++){
		run_queue_next();
		/* critical event, bypass the queue */
		if (krnl_task->critical && krnl_task->state != TASK_BLOCKED){
			krnl_task->critical = 0;
			goto done;
		}
		if (highestp > krnl_task->priority_rem && krnl_task->state != TASK_BLOCKED){
			highestp = krnl_task->priority_rem;
			krnl_task2 = krnl_task;
		}
	}

	/* update priorities of all tasks */
	for (i = 0; i < k; i++){
		run_queue_next();
		if (krnl_task != krnl_task2)
			krnl_task->priority_rem -= krnl_task2->priority_rem;
	}

	krnl_task = krnl_task2;
	krnl_task->priority_rem = krnl_task->priority;
done:
	krnl_task->bgjobs++;

	return krnl_task->id;
}
示例#4
0
/**
 * @brief Best effort (BE) scheduler (callback).
 *
 * @return Best effort task id.
 *
 * The algorithm is Lottery Scheduling.
 * 	- Take a task from the run queue, copy its entry and put it back at the tail of the run queue.
 * 	- If the task is in the blocked state (it may be simply blocked or waiting in a semaphore) or
 * its not the ticket, it is put back at the tail of the run queue and the next task is picked up.
 */
int32_t sched_lottery(void)
{
	int32_t r, i = 0;

	r = random() % krnl_tasks;
	if (hf_queue_count(krnl_run_queue) == 0)
		panic(PANIC_NO_TASKS_RUN);
	do {
		run_queue_next();
	} while ((krnl_task->state == TASK_BLOCKED) || ((i++ % krnl_tasks) != r));
	krnl_task->bgjobs++;

	return krnl_task->id;
}