summaryrefslogtreecommitdiff
path: root/kernel/task.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/task.c')
-rw-r--r--kernel/task.c223
1 files changed, 0 insertions, 223 deletions
diff --git a/kernel/task.c b/kernel/task.c
deleted file mode 100644
index 395c196..0000000
--- a/kernel/task.c
+++ /dev/null
@@ -1,223 +0,0 @@
-// http://hosted.cjmovie.net/TutMultitask.htm
-//
-//
-#define FOOLOS_MODULE_NAME "task"
-
-#include "kernel.h"
-#include "lib/logger/log.h" // logger facilities
-#include "mem.h"
-#include "timer.h"
-#include "asm/x86.h"
-
-#include "vmem.h"
-#include "syscalls.h"
-#include "fs/fs.h"
-#include "fs/ext2.h"
-
-#define MAX_TASKS 10
-
-static volatile int volatile current_task=-1;
-
-static volatile struct task_list_struct
-{
- volatile int parent;
- volatile bool active;
- volatile uint32_t esp; // stack pointer of the task;
- volatile pdirectory *vmem; // number of virtual memory table to switch to
- volatile bool waiting;
- volatile bool skipwait;
- volatile uint32_t brk;
-
-}volatile task_list[MAX_TASKS];
-
-volatile int add_task(uint32_t esp, uint32_t vmem)
-{
-
- for(int i=0;i<MAX_TASKS;i++)
- {
- if(task_list[i].active!=true)
- {
-
- task_list[i].parent=current_task;
- task_list[i].vmem=vmem;
- task_list[i].esp=esp;
- task_list[i].active=true;
- task_list[i].waiting=false;
- task_list[i].skipwait=false;
- task_list[i].brk=task_list[current_task].brk;
- return i;
- }
- }
-
- panic(FOOLOS_MODULE_NAME,"out of task slots!");
-}
-
-//
-// REMEMBER WE ARE INSIDE AN INTERRUPT HERE - DON'T WASTE TIME!
-//
-// oldesp - is the adress of the stack pointer when pit_interrupt_handler was entered.
-// registers have been pushed with pusha to this old stack.
-//
-// stack pointer was moved to the 16kb stack we have from multiboot.s
-//
-// we need to return a NEW stack pointer where popa will get the registers the new task requires
-//
-static int first=1;
-volatile uint32_t my_scheduler(uint32_t oldesp)
-{
-
- // allows skipping scheduling from gdb
- volatile int skippy=0;
- if(skippy)return oldesp;
-
- if(!first)
- {
- task_list[current_task].esp=oldesp;
- }
- first=0;
-
- for(int i=0;i<MAX_TASKS;i++)
- {
- int pid=(current_task+1+i)%MAX_TASKS; // schedule round robin style
-
- if(task_list[pid].active && !task_list[pid].waiting)
- {
-// if(current_task!=pid)
-// log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"switch from %d to %d", current_task, pid);
-
- current_task=pid;
-
- vmem_set_dir(task_list[pid].vmem);
- return task_list[pid].esp;
- }
-
- }
-
- panic(FOOLOS_MODULE_NAME,"nothing to schedule!");
-}
-
-// this gets called by our clock interrupt regularly!
-volatile uint32_t task_switch_next(uint32_t oldesp)
-{
- // check if multitasking has been started
- if(current_task<0)return oldesp;
- return my_scheduler(oldesp);
-}
-
-//TODO: free vmem too!
-//TODO: notify waiting parent when child finished;
-volatile uint32_t task_exit(uint32_t oldesp)
-{
-
- task_list[current_task].active=false;
- int parent_pid=task_list[current_task].parent;
-
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"[%d] exit ", current_task);
-
- if(task_list[parent_pid].active)
- {
- if(task_list[parent_pid].waiting)
- {
-
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"[%d] wake up", parent_pid);
- task_list[parent_pid].waiting=false;
- }
- else
- {
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"[%d] skipwait", parent_pid);
- task_list[parent_pid].skipwait=true;
- }
-
- }
-
- vmem_free_dir(task_list[current_task].vmem);
-
- return my_scheduler(oldesp);
-
-}
-
-volatile uint32_t task_wait(uint32_t oldesp)
-{
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"[%d] wait", current_task);
- if(task_list[current_task].skipwait)
- {
- task_list[current_task].skipwait=false;
- }
- else
- {
- task_list[current_task].waiting=true;
- }
- return my_scheduler(oldesp);
-}
-
-volatile uint32_t task_fork(uint32_t oldesp)
-{
- int pid=add_task(oldesp,vmem_new_space_dir(task_list[current_task].vmem));
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"[%d] forked -> [%d] (free blocks remaining: %d )", current_task, pid,mem_get_free_blocks_count());
- return pid;
-}
-
-// init task (root of all other tasks / processes) //
-volatile void task_init(pdirectory *dir)
-{
- current_task=0;
-
- // this is our main task on slot 0
- task_list[0].parent=0;
- task_list[0].active=true;
- task_list[0].waiting=false;
- task_list[0].vmem=dir;
- task_list[0].esp = kballoc(4); // 0; // will be set by next task_switch_next() call.
-
- task_list[1].parent=0;
- task_list[1].active=true;
- task_list[1].waiting=false;
- task_list[1].vmem=dir;
- task_list[1].esp = kballoc(4); // fresh 16kb stack from here.
-
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"fresh esp on: 0x%08X",1,task_list[1].esp);
- log(FOOLOS_MODULE_NAME,FOOLOS_LOG_INFO,"fresh esp on: 0x%08X",0,task_list[0].esp);
-
- task_pusha(task_list[1].esp); // pusha but to alternative location
- task_pusha(task_list[0].esp); // pusha but to alternative location
-
- /*
- current_task=0;
- unsigned esp, ebp, eax, ebx, ecx, edx;
-
- asm(
- "movl %%esp, %0;"
- "movl %%ebp, %1;"
- "movl %%eax, %2;"
- "movl %%ebx, %3;"
- "movl %%ecx, %4;"
- "movl %%edx, %5;"
- :"=r"(esp), "=r"(ebp), "=r"(eax), "=r"(ebx), "=r"(ecx), "=r"(edx)
- );
-
- // TODO: prepare stack so popa get's what it wants!
- int i=task_fork(esp);
- */
-
- // finally enable interrrupts so the scheduler is called (by timer)
- x86_sti();
-
- // loop until scheduler kicks in and reschedules us...
- while(1);
-
-}
-
-volatile int task_get_current_pid()
-{
- return current_task;
-}
-
-volatile uint32_t task_get_brk()
-{
- return task_list[current_task].brk;
-}
-
-volatile void task_set_brk(uint32_t brk)
-{
- task_list[current_task].brk=brk;
-}