# HG changeset patch # User John Tsiombikas # Date 1311637293 -10800 # Node ID b8f02479e3f4d1f29d2b99cd45861f77aa62e665 # Parent 7bc74736c7e872679176284c8d86e4c8a3db03dd mainly additions to the VM to support processes etc. not complete diff -r 7bc74736c7e8 -r b8f02479e3f4 src/proc.c --- a/src/proc.c Mon Jul 25 11:29:57 2011 +0300 +++ b/src/proc.c Tue Jul 26 02:41:33 2011 +0300 @@ -1,22 +1,36 @@ #include "proc.h" #include "tss.h" +#include "vm.h" static struct process proc[MAX_PROC]; static int cur_pid; void init_proc(void) { + int proc_size_pg, img_start_pg; + void *img_start; cur_pid = -1; /* prepare the first process */ - /* create the virtual address space for this process */ - proc[0].ctx.pgtbl_paddr = clone_vmem(); - /* allocate a chunk of memory for the process image * and copy the code of test_proc there. * (should be mapped at a fixed address) */ + proc_size_pg = (test_proc_end - test_proc) / PGSIZE + 1; + if((img_start_pg = pgalloc(proc_size_pg, MEM_USER)) == -1) { + panic("failed to allocate space for the init process image\n"); + } + img_start = (void*)PAGE_TO_ADDR(img_start_pg); + memcpy(img_start, test_proc, proc_size_pg * PGSIZE); + + /* create the virtual address space for this process */ + proc[0].ctx.pgtbl_paddr = clone_vmem(); + + /* we don't need the image in this address space */ + unmap_pa + pgfree(img_start_pg, proc_size_pg); + /* fill in the proc[0].ctx with the appropriate process stack * and instruction pointers diff -r 7bc74736c7e8 -r b8f02479e3f4 src/vm.c --- a/src/vm.c Mon Jul 25 11:29:57 2011 +0300 +++ b/src/vm.c Tue Jul 26 02:41:33 2011 +0300 @@ -250,6 +250,7 @@ { int intr_state, ret = -1; struct page_range *node, *prev, dummy; + unsigned int attr = 0; /* TODO */ intr_state = get_intr_state(); disable_intr(); @@ -281,7 +282,60 @@ if(ret >= 0) { /* allocate physical storage and map */ - if(map_page_range(ret, num, -1, 0) == -1) { + if(map_page_range(ret, num, -1, attr) == -1) { + ret = -1; + } + } + + set_intr_state(intr_state); + return ret; +} + +int pgalloc_vrange(int start, int num) +{ + struct page_range *node, *prev, dummy; + int area, intr_state, ret = -1; + unsigned int attr = 0; /* TODO */ + + area = (start >= ADDR_TO_PAGE(KMEM_START)) ? MEM_KERNEL : MEM_USER; + if(area == KMEM_USER && start + num > ADDR_TO_PAGE(KMEM_START)) { + printf("pgalloc_vrange: invalid range request crossing user/kernel split\n"); + return -1; + } + + intr_state = get_intr_state(); + disable_intr(); + + dummy.next = pglist[area]; + node = pglist[area]; + prev = &dummy; + + /* check to see if the requested VM range is available */ + node = pglist[area]; + while(node) { + if(start >= node->start && start + num <= node->end) { + ret = node->start; + node->start += num; + + if(node->start == node->end) { + prev->next = node->next; + node->next = 0; + + if(node == pglist[area]) { + pglist[area] = 0; + } + free_node(node); + } + break; + } + + prev = node; + node = node->next; + } + + if(ret >= 0) { + /* allocate physical storage and map */ + if(map_page_range(ret, num, -1, attr) == -1) { ret = -1; } }