syscalls: start adding fork syscall, not done yet
This commit is contained in:
@@ -40,6 +40,7 @@ void set_page_dir(uint32_t new_page_dir);
|
|||||||
uint32_t phys_to_virt(uint32_t phys);
|
uint32_t phys_to_virt(uint32_t phys);
|
||||||
uint32_t* create_page_dir();
|
uint32_t* create_page_dir();
|
||||||
void destroy_page_dir(uint32_t* page_dir);
|
void destroy_page_dir(uint32_t* page_dir);
|
||||||
|
uint32_t* copy_page_dir(uint32_t* page_dir_virt);
|
||||||
|
|
||||||
static inline uint32_t virt_to_phys(void* virt) {
|
static inline uint32_t virt_to_phys(void* virt) {
|
||||||
return (uint32_t)virt - 0xC0000000;
|
return (uint32_t)virt - 0xC0000000;
|
||||||
|
|||||||
+1
-1
@@ -14,7 +14,7 @@ int printf(const char* __restrict, ...);
|
|||||||
int putchar(int);
|
int putchar(int);
|
||||||
int puts(const char*);
|
int puts(const char*);
|
||||||
|
|
||||||
//#define KATAU_DEBUG
|
#define KATAU_DEBUG
|
||||||
|
|
||||||
#ifdef KATAU_DEBUG
|
#ifdef KATAU_DEBUG
|
||||||
#define debug_log printf
|
#define debug_log printf
|
||||||
|
|||||||
@@ -17,6 +17,8 @@
|
|||||||
|
|
||||||
#define MAX_OPEN_FILES 32
|
#define MAX_OPEN_FILES 32
|
||||||
|
|
||||||
|
#define KSTACKSIZE 4096
|
||||||
|
|
||||||
typedef enum TaskState
|
typedef enum TaskState
|
||||||
{
|
{
|
||||||
Ready,
|
Ready,
|
||||||
|
|||||||
+1
-1
@@ -218,7 +218,7 @@ void kmain(unsigned int magic, unsigned int info)
|
|||||||
printf("huy1 points to: 0x%X huy2 points to:0x%X\n", huy, huy2);
|
printf("huy1 points to: 0x%X huy2 points to:0x%X\n", huy, huy2);
|
||||||
printf("huy1: %s\nhuy2: %s", huy, huy2);
|
printf("huy1: %s\nhuy2: %s", huy, huy2);
|
||||||
|
|
||||||
exec_from_file("/ebalo/aaa");
|
exec_from_file("/ebalo/forktest");
|
||||||
|
|
||||||
while(1)
|
while(1)
|
||||||
{
|
{
|
||||||
|
|||||||
+1
-1
@@ -61,7 +61,7 @@ void* alloc_page() {
|
|||||||
if(page_num == 0)
|
if(page_num == 0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
debug_log("allocating page %X\n", page_num * PAGE_SIZE);
|
//debug_log("allocating page %X\n", page_num * PAGE_SIZE);
|
||||||
|
|
||||||
page_bitmap[i] |= (1 << j); // Помечаем как занятый
|
page_bitmap[i] |= (1 << j); // Помечаем как занятый
|
||||||
return (void*)(page_num * PAGE_SIZE);
|
return (void*)(page_num * PAGE_SIZE);
|
||||||
|
|||||||
@@ -189,3 +189,62 @@ void destroy_page_dir(uint32_t* page_dir_virt) {
|
|||||||
debug_log("freeing PD page %X\n", virt_to_phys(page_dir_virt));
|
debug_log("freeing PD page %X\n", virt_to_phys(page_dir_virt));
|
||||||
free_page((void*)virt_to_phys(page_dir_virt));
|
free_page((void*)virt_to_phys(page_dir_virt));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t* copy_page_dir(uint32_t* page_dir_virt)
|
||||||
|
{
|
||||||
|
if(page_dir_virt == NULL)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
uint32_t* new_pagedir = create_page_dir();
|
||||||
|
|
||||||
|
for(int i = 0; i < 768; i++)
|
||||||
|
{
|
||||||
|
uint32_t pde = page_dir_virt[i];
|
||||||
|
|
||||||
|
if(pde & PAGE_PRESENT)
|
||||||
|
{
|
||||||
|
debug_log("PDE %X present\n", pde);
|
||||||
|
uint32_t* new_page_table = (uint32_t*)alloc_page();
|
||||||
|
if(new_page_table == NULL) {
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get original page table (physical address from PDE)
|
||||||
|
uint32_t* orig_page_table = (uint32_t*)phys_to_virt(pde & ~0xFFF);
|
||||||
|
|
||||||
|
for(int j = 0; j < 1024; j++)
|
||||||
|
{
|
||||||
|
uint32_t pte = orig_page_table[j];
|
||||||
|
if(pte & PAGE_PRESENT)
|
||||||
|
{
|
||||||
|
void* new_phys_page = alloc_page();
|
||||||
|
if(!new_phys_page)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void* orig_phys_page = (void*)(pte & ~0xFFF);
|
||||||
|
|
||||||
|
debug_log("copying %X to %X...", orig_phys_page, new_phys_page);
|
||||||
|
memcpy(new_phys_page, orig_phys_page, PAGE_SIZE);
|
||||||
|
debug_log("done\n");
|
||||||
|
new_page_table[j] = (uint32_t)new_phys_page | (pte & 0xFFF);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
new_page_table[j] = pte;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Set the new PDE in the child's page directory
|
||||||
|
new_pagedir[i] = (uint32_t)virt_to_phys(new_page_table) | (pde & 0xFFF);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
new_pagedir[i] = pde;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
debug_log("ENDENDENDEND\n");
|
||||||
|
return new_pagedir;
|
||||||
|
}
|
||||||
@@ -2,6 +2,8 @@
|
|||||||
#include <stddef.h>
|
#include <stddef.h>
|
||||||
#include "../include/stdio.h"
|
#include "../include/stdio.h"
|
||||||
#include "../include/liballoc.h"
|
#include "../include/liballoc.h"
|
||||||
|
#include "../include/paging.h"
|
||||||
|
#include "../include/string.h"
|
||||||
|
|
||||||
#define STDIN_FILENO 0
|
#define STDIN_FILENO 0
|
||||||
#define STDOUT_FILENO 1
|
#define STDOUT_FILENO 1
|
||||||
@@ -56,6 +58,23 @@ int sys_exit(TrapFrame *tf)
|
|||||||
return error_code;
|
return error_code;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int sys_fork(TrapFrame *tf)
|
||||||
|
{
|
||||||
|
debug_log("FORKFORKFORKFORK\n");
|
||||||
|
|
||||||
|
uint32_t* new_pd = copy_page_dir(current->pagedir);
|
||||||
|
|
||||||
|
Process* child = task_create(0, 0, 3, new_pd);
|
||||||
|
|
||||||
|
memcpy(child, current, sizeof(Process));
|
||||||
|
memcpy(child->kstack, current->kstack, KSTACKSIZE);
|
||||||
|
|
||||||
|
child->tf->eax = 0;
|
||||||
|
tf->eax = child->pid;
|
||||||
|
|
||||||
|
return child->pid;
|
||||||
|
}
|
||||||
|
|
||||||
int sys_read(TrapFrame *tf)
|
int sys_read(TrapFrame *tf)
|
||||||
{
|
{
|
||||||
if(tf->ebx < 3)
|
if(tf->ebx < 3)
|
||||||
@@ -145,6 +164,7 @@ int sys_close(TrapFrame *tf)
|
|||||||
|
|
||||||
void handle_syscall(TrapFrame *tf)
|
void handle_syscall(TrapFrame *tf)
|
||||||
{
|
{
|
||||||
|
asm("cli");
|
||||||
/*
|
/*
|
||||||
debug_log("EAX: %X ", tf->eax);
|
debug_log("EAX: %X ", tf->eax);
|
||||||
debug_log("EBX: %X ", tf->ebx);
|
debug_log("EBX: %X ", tf->ebx);
|
||||||
@@ -158,6 +178,12 @@ void handle_syscall(TrapFrame *tf)
|
|||||||
tf->eax = r;
|
tf->eax = r;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(tf->eax == 2)
|
||||||
|
{
|
||||||
|
int r = sys_fork(tf);
|
||||||
|
tf->eax = r;
|
||||||
|
}
|
||||||
|
|
||||||
if(tf->eax == 3)//read
|
if(tf->eax == 3)//read
|
||||||
{
|
{
|
||||||
int r = sys_read(tf);
|
int r = sys_read(tf);
|
||||||
@@ -179,4 +205,5 @@ void handle_syscall(TrapFrame *tf)
|
|||||||
int r = sys_close(tf);
|
int r = sys_close(tf);
|
||||||
tf->eax = r;
|
tf->eax = r;
|
||||||
}
|
}
|
||||||
|
asm("sti");
|
||||||
}
|
}
|
||||||
@@ -13,8 +13,6 @@ uint32_t irq_disable_counter = 0;
|
|||||||
uint32_t pid_counter;
|
uint32_t pid_counter;
|
||||||
uint32_t task_count;
|
uint32_t task_count;
|
||||||
|
|
||||||
#define KSTACKSIZE 4096
|
|
||||||
|
|
||||||
extern void trapret(void);
|
extern void trapret(void);
|
||||||
extern void switchProcess(Process* next);
|
extern void switchProcess(Process* next);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user