wip: change memory to have access to page_tables and allocate these dynamically

This commit is contained in:
0x35c 2024-10-25 15:11:11 +02:00
parent f5147e78f9
commit a9bfb49bb8
7 changed files with 52 additions and 35 deletions

View File

@ -13,7 +13,10 @@
#define PD_SIZE 1024 #define PD_SIZE 1024
#define PAGE_MASK 0xFFFFF000 #define PAGE_MASK 0xFFFFF000
#define HEAP_END 0xC0000000 #define HEAP_END 0xC0000000
#define HEAP_START ((uint32_t) & _kernel_end - HEAP_END)
#define PT_START 256
extern uint32_t _kernel_end;
extern uint32_t boot_page_directory; extern uint32_t boot_page_directory;
extern uint32_t *page_directory; extern uint32_t *page_directory;
extern uint32_t page_table_default[1024]; extern uint32_t page_table_default[1024];
@ -22,5 +25,7 @@ uint32_t *virt_to_phys(uint32_t *virt_addr);
void init_memory(void); void init_memory(void);
void *alloc_frames(size_t size); void *alloc_frames(size_t size);
int free_frames(void *frame_ptr, size_t size); int free_frames(void *frame_ptr, size_t size);
void *alloc_pages(size_t size, uint32_t **frame_ptr); void *alloc_pages(size_t size);
int free_pages(void *page_ptr, size_t size); int free_pages(void *page_ptr, size_t size);
void init_page_table(uint32_t page_table[1024], uint16_t start);
int16_t create_page_table(uint16_t pd_index);

View File

@ -36,8 +36,9 @@ void kernel_main(void)
"I see no way to confuse an array of 256 seg:off pairs with a " "I see no way to confuse an array of 256 seg:off pairs with a "
"complex 8*unknown quantity -byte descriptor table. -- Troy " "complex 8*unknown quantity -byte descriptor table. -- Troy "
"Martin 03:50, 22 March 2009 (UTC)\n"); "Martin 03:50, 22 March 2009 (UTC)\n");
/* char *str = vmalloc(10); */ char *str = vmalloc(10);
/* strcpy(str, "hello"); */ if (str)
strcpy(str, "hello");
/* int i = 0; */ /* int i = 0; */
/* while (vmalloc(10)) */ /* while (vmalloc(10)) */
/* ; */ /* ; */
@ -45,9 +46,9 @@ void kernel_main(void)
/* kprintf("%d\n", i); */ /* kprintf("%d\n", i); */
/* void *tab[1024]; */ /* void *tab[1024]; */
/* for (int i = 0; i < 1023; i++) { */ /* for (int i = 0; i < 1023; i++) { */
/* tab[i] = alloc_pages(1); */ /* tab[i] = alloc_pages(1, NULL); */
/* PRINT_INT(i); */ /* PRINT_INT(i); */
/* PRINT_PTR(tab[i]); */ /* PRINT_PTR(tab[i]); */
/* if (!tab[i]) */ /* if (!tab[i]) */
/* break; */ /* break; */
/* memset(tab[i], i, 4096); */ /* memset(tab[i], i, 4096); */
@ -56,5 +57,5 @@ void kernel_main(void)
/* for (int i = 0; i < 10; i++) */ /* for (int i = 0; i < 10; i++) */
/* PRINT_UINT(((uint8_t *)tab[i])[0]); */ /* PRINT_UINT(((uint8_t *)tab[i])[0]); */
/* PRINT_PTR(tab[i]); */ /* PRINT_PTR(tab[i]); */
/* shell_init(); */ shell_init();
} }

View File

@ -14,7 +14,10 @@ static uint32_t remaining_frames = MAX_FRAMES;
static int32_t find_next_block(size_t nb_frames) static int32_t find_next_block(size_t nb_frames)
{ {
for (uint32_t i = 1024; i + nb_frames < MAX_FRAMES - 1; i++) { PRINT_UINT(CEIL(HEAP_START, PAGE_SIZE));
for (uint32_t i = CEIL(HEAP_START, PAGE_SIZE);
i + nb_frames < MAX_FRAMES; i++) {
PRINT_UINT(i);
uint32_t j; uint32_t j;
for (j = 0; frame_table[i + j] == 0 && j < nb_frames; j++) for (j = 0; frame_table[i + j] == 0 && j < nb_frames; j++)
; ;
@ -33,9 +36,8 @@ void *alloc_frames(size_t size)
return NULL; return NULL;
} }
int i = find_next_block(nb_frames); int i = find_next_block(nb_frames);
if (i == -1) { if (i < 0) {
kprintf(KERN_WARNING "Not enough frames available\n", kprintf(KERN_WARNING "Not enough frames available\n");
MAX_FRAMES);
return NULL; return NULL;
} }
for (size_t j = 0; j < nb_frames; j++) { for (size_t j = 0; j < nb_frames; j++) {
@ -44,7 +46,7 @@ void *alloc_frames(size_t size)
} }
assert(remaining_frames >= nb_frames); assert(remaining_frames >= nb_frames);
remaining_frames -= nb_frames; remaining_frames -= nb_frames;
return (void *)(i * PAGE_SIZE); // WARNING: address translation cramptés return (void *)(i * PAGE_SIZE);
} }
int free_frames(void *frame_ptr, size_t size) int free_frames(void *frame_ptr, size_t size)

View File

@ -7,24 +7,11 @@
uint32_t *page_directory = &boot_page_directory; uint32_t *page_directory = &boot_page_directory;
uint32_t page_table_default[1024] __attribute__((aligned(4096))); uint32_t page_table_default[1024] __attribute__((aligned(4096)));
static void alloc_page_tables(void)
{
uint32_t *frame_ptr = NULL;
for (int16_t i = 1; i < 768; i++) {
uint32_t *page_table = alloc_pages(PAGE_SIZE, &frame_ptr);
for (int16_t j = 0; j < 1024; j++)
page_table[j] = j << 12 | 0x03;
page_directory[i] = ((uint32_t)frame_ptr & PAGE_MASK) | 0x03;
}
}
void init_memory(void) void init_memory(void)
{ {
assert(page_directory); assert(page_directory);
for (int16_t i = 0; i < 0x300; i++) for (uint16_t i = 0; i < 0x300; i++)
page_directory[i] = 0x02; page_directory[i] = 0x02;
for (int16_t i = 0; i < 1024; i++) init_page_table(page_table_default, 0);
page_table_default[i] = (i << 12) | 0x03;
page_directory[0] = ((uint32_t)page_table_default - HEAP_END) | 0x03; page_directory[0] = ((uint32_t)page_table_default - HEAP_END) | 0x03;
alloc_page_tables();
} }

View File

@ -2,7 +2,6 @@
#include <stddef.h> #include <stddef.h>
#include <stdint.h> #include <stdint.h>
#include "debug.h"
#include "kprintf.h" #include "kprintf.h"
#include "memory.h" #include "memory.h"
#include "utils.h" #include "utils.h"
@ -10,12 +9,18 @@
#define MAX_TLB_ENTRIES 32 #define MAX_TLB_ENTRIES 32
static uint32_t *current_page_table; static uint32_t *current_page_table;
static uint16_t current_pd_index;
static int16_t find_next_block(size_t nb_pages) static int16_t find_next_block(size_t nb_pages)
{ {
for (uint16_t pd_index = 0; pd_index < 768; pd_index++) { for (uint16_t pd_index = 0; pd_index < 768; pd_index++) {
if (page_directory[pd_index] == 0x02) {
if (create_page_table(pd_index) < 0)
return -2;
}
current_pd_index = pd_index;
current_page_table = current_page_table =
(uint32_t *)(page_directory[pd_index] >> 12); (uint32_t *)((PT_START + pd_index) * PAGE_SIZE);
for (uint16_t i = 0; i + nb_pages < PT_SIZE; i++) { for (uint16_t i = 0; i + nb_pages < PT_SIZE; i++) {
uint16_t j; uint16_t j;
for (j = 0; current_page_table[i + j] >> 12 == i + j && for (j = 0; current_page_table[i + j] >> 12 == i + j &&
@ -30,13 +35,14 @@ static int16_t find_next_block(size_t nb_pages)
return -1; return -1;
} }
void *alloc_pages(size_t size, uint32_t **frame_ptr) void *alloc_pages(size_t size)
{ {
const uint32_t nb_pages = CEIL(size, PAGE_SIZE); const uint32_t nb_pages = CEIL(size, PAGE_SIZE);
const int16_t index = find_next_block(nb_pages); const int16_t index = find_next_block(nb_pages);
if (index < 0) { if (index < 0) {
kprintf(KERN_CRIT "Not enough pages (max: %d)\n", PT_SIZE); kprintf(KERN_CRIT "%d: Not enough pages (max: %d)\n", index,
PT_SIZE);
return NULL; return NULL;
} }
for (size_t i = index; i - (size_t)index < nb_pages; i++) { for (size_t i = index; i - (size_t)index < nb_pages; i++) {
@ -48,12 +54,10 @@ void *alloc_pages(size_t size, uint32_t **frame_ptr)
PAGE_SIZE); PAGE_SIZE);
return NULL; return NULL;
} }
if (frame_ptr)
*frame_ptr = frame;
current_page_table[i] = current_page_table[i] =
((uint32_t)frame & PAGE_MASK) | INIT_FLAGS; ((uint32_t)frame & PAGE_MASK) | INIT_FLAGS;
} }
return (void *)((0 * 1024 + index) * PAGE_SIZE); return (void *)(((current_pd_index * 1024) + index) * PAGE_SIZE);
} }
int free_pages(void *page_ptr, size_t size) int free_pages(void *page_ptr, size_t size)

18
src/memory/page_table.c Normal file
View File

@ -0,0 +1,18 @@
#include "memory.h"
void init_page_table(uint32_t page_table[1024], uint16_t start)
{
for (uint16_t i = start; i < 1024; i++)
page_table[i] = (i << 12) | 0x03;
}
int16_t create_page_table(uint16_t pd_index)
{
void *frame = alloc_frames(PAGE_SIZE);
if (!frame)
return -1;
page_directory[pd_index] = ((uint32_t)frame & PAGE_MASK) | 0x03;
uint32_t *page_table = (uint32_t *)((PT_START + pd_index) * PAGE_SIZE);
init_page_table(page_table, 0);
return 0;
}

View File

@ -49,7 +49,7 @@ static void new_block(Zone *zone, uint32_t zone_size)
int new_vzone(block_type_t type, uint32_t size) int new_vzone(block_type_t type, uint32_t size)
{ {
void *heap = alloc_pages(size, NULL); void *heap = alloc_pages(size);
if (heap == NULL) { if (heap == NULL) {
kprintf(KERN_ERR "error: alloc_pages failed\n"); kprintf(KERN_ERR "error: alloc_pages failed\n");
return (-1); return (-1);