21 #include <boot/multiboot.h> 24 #define MAX_TASKS 1024 26 static task_t* tasks[MAX_TASKS]; 35 println(
"%4aTask %d does not exist%a", pid);
51 panic(
"Maximum task number reached");
77 size_t user_stack_len,
elf_t* elf,
size_t code_segment,
size_t data_segment) {
79 logln(
"TASK",
"Creating task with %dKB kernel and %dKB user stack",
80 kernel_stack_len, user_stack_len);
87 task->
state = TASK_RUNNING;
105 cpu->
eip = (uintptr_t) entry_point;
129 size_t kernel_stack_len) {
144 size_t kernel_stack_len,
size_t user_stack_len,
void* elf) {
163 if (
task_get(pid)->state == TASK_RUNNING) {
164 println(
"%4aYou may not destroy a running task%a");
167 logln(
"TASK",
"Destroying task %d", pid);
230 uint32_t old_ticks = task->
ticks;
285 logln(
"TASK",
"Task list:");
287 logln(
"TASK",
"There are no tasks.");
291 logln(
"TASK",
"%s task with pid %d%s",
292 task_get(pid)->state ?
"Running" :
"Stopped", pid,
293 task_get(pid)->vm86 ?
" (VM86)" :
"");
#define GDT_RING3_DATA_SEG
user data segment index
page_directory_t * vmm_create_page_directory()
Creates an empty page directory.
uint8_t task_get_vm86(task_pid_t pid)
Returns whether a task is a VM86 task.
uint8_t isr_enable_interrupts(uint8_t enable)
Enables or disables interrupts.
void * elf
if this is an ELF task, this points to the ELF file
task_pid_t task_get_next_task(task_pid_t pid)
Returns the next task from the task list.
uint16_t gs
GS segment register.
task_state_t state
whether the task is running or stopped
task_pid_t task_create_kernel(void *entry_point, page_directory_t *page_directory, size_t kernel_stack_len)
Creates a kernel task.
task_stack_t * kernel_stack
stack for handling interrupts
uint32_t edx
data register
static task_pid_t task_create_detailed(void *entry_point, page_directory_t *page_directory, size_t kernel_stack_len, size_t user_stack_len, elf_t *elf, size_t code_segment, size_t data_segment)
Creates a task.
static page_directory_t * page_directory
the current page directory
uint32_t ticks
how many ticks the task may run per time slice
void vmm_modified_page_directory()
Ends a page directory modification.
The CPU's state when an interrupt occurs.
void * vmm_alloc(size_t len, vmm_flags_t flags)
Marks some page(s) as used and maps them somewhere into memory.
task_pid_t task_create_user(void *entry_point, page_directory_t *page_directory, size_t kernel_stack_len, size_t user_stack_len, void *elf)
Creates a user task.
#define GDT_RING3_CODE_SEG
user code segment index
#define GDT_RING0_DATA_SEG
kernel data segment index
task_pid_t task_add(task_t *task)
Adds a new task to the task list and associates a PID.
cpu_state_t * cpu
saved CPU state when entering/leaving interrupts
size_t kernel_stack_len
kernel stack length
size_t user_stack_len
user stack length
static uint8_t old_interrupts
for temporary modifications
void task_set_cpu(task_pid_t pid, cpu_state_t *cpu)
Sets a task's CPU state.
uint32_t user_ss
stack segment (only pushed and popped in user space)
cpu_state_t * task_get_cpu(task_pid_t pid)
Returns a task's CPU state.
uint8_t _if
interrupt flag
page_directory_t * page_directory
this task's virtual memory map
uint32_t eip
the instruction to return to after the interrupt
uint32_t task_pid_t
unique process ID
internal representation of a task
task_pid_t task_get_next_task_with_state(task_pid_t pid, task_state_t state)
Returns the next task from the task list with a specified state.
void task_dump()
Dumps the task list.
uint16_t gdt_get_selector(size_t entry)
Returns a selector ready to be loaded in a segment register.
uint16_t es
ES segment register.
uint8_t vm86
whether this task is running in Virtual 8086 mode
void vmm_free(void *vaddr, size_t len)
Frees the given page(s) and unmaps them from memory.
uint32_t dword
useful for casting
uint32_t esi
source index register
void task_stop(task_pid_t pid)
Stops a task.
void vmm_destroy_page_directory(page_directory_t *dir_phys)
Destroys a page directory.
#define MAX_TASKS
maximum number of tasks
task_stack_t * user_stack
stack for the actual task's code
An entry in a page directory.
static task_t * tasks[MAX_TASKS]
Array of tasks.
uint32_t ebp
base pointer register
uint16_t fs
FS segment register.
uint8_t reserved
always one
void vmm_modify_page_directory(page_directory_t *new_directory)
Loads a page directory for temporary modification.
struct isr_eflags_t::@8 bits
bit field
uint32_t eax
accumulator register
uint16_t cs
the code segment to return to after the interrupt
page_directory_t * task_get_page_directory(task_pid_t pid)
Returns a task's page directory.
task_state_t
state of a task
uint16_t isr_eflags_t eflags
the EFLAGS register before the interrupt was fired
void * task_get_elf(task_pid_t pid)
Returns a task's ELF file.
task_state_t task_get_ticks(task_pid_t pid)
Returns a task's number of remaining ticks.
uint32_t ebx
base register
static task_t * task_get(task_pid_t pid)
Returns the internal task structure associated with the given PID.
void task_destroy(task_pid_t pid)
Destroys a task.
uint32_t edi
destination index register
uint32_t user_esp
stack pointer (only pushed and popped in user space)
uint16_t ds
DS segment register.
uint32_t ecx
counter register
static void task_remove(task_pid_t pid)
Removes a task from the task list.
uint32_t task_set_ticks(task_pid_t pid, uint32_t ticks)
Sets a task's number of remaining ticks.
uint16_t isr_registers_t r
The general purpose registers.
#define GDT_RING0_CODE_SEG
kernel code segment index