aboutsummaryrefslogtreecommitdiff
path: root/src/kernel/memory/paging.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/kernel/memory/paging.c')
-rw-r--r--src/kernel/memory/paging.c62
1 files changed, 20 insertions, 42 deletions
diff --git a/src/kernel/memory/paging.c b/src/kernel/memory/paging.c
index fd5ae3b..432b51c 100644
--- a/src/kernel/memory/paging.c
+++ b/src/kernel/memory/paging.c
@@ -4,55 +4,34 @@
#include <stdint.h>
#include <system.h>
-u32 **current_page_directory;
-u32 kernel_page_directory[PAGE_COUNT] __attribute__((aligned(PAGE_ALIGN)));
-u32 kernel_page_tables[PAGE_COUNT][PAGE_COUNT] __attribute__((aligned(PAGE_ALIGN)));
-u32 *temp_dir[PAGE_COUNT] __attribute__((aligned(PAGE_ALIGN)));
+u32 page_directory[1024] __attribute__((aligned(4096)));
+u32 page_tables[1024][1024] __attribute__((aligned(4096)));
-void paging_init(u32 **dir)
+void paging_init()
{
for (u32 i = 0; i < PAGE_COUNT; i++) {
for (u32 j = 0; j < PAGE_COUNT; j++) {
- dir[i][j] = ((j * PAGE_ALIGN) + (i * PAGE_SIZE)) | PT_RW | PT_USER;
+ page_tables[i][j] = ((j * PAGE_ALIGN) + (i * PAGE_SIZE)) | PT_RW | PT_USER;
}
}
for (u32 i = 0; i < PAGE_COUNT; i++) {
- dir[i] = ((u32)dir[i]) | PD_RW | PD_PRESENT | PD_USER;
+ page_directory[i] = (u32)page_tables[i] | PD_RW | PD_PRESENT | PD_USER;
}
}
-void paging_kernel_init(u32 *dir)
-{
- for (u32 i = 0; i < PAGE_COUNT; i++) {
- for (u32 j = 0; j < PAGE_COUNT; j++) {
- kernel_page_tables[i][j] = ((j * PAGE_ALIGN) + (i * PAGE_SIZE)) | PT_RW;
- }
- }
-
- for (u32 i = 0; i < PAGE_COUNT; i++) {
- kernel_page_directory[i] = ((u32)kernel_page_tables[i]) | PD_RW | PD_PRESENT;
- }
-
- current_page_directory = temp_dir;
- for (int i = 0; i < PAGE_COUNT; i++) {
- current_page_directory[i] = kernel_page_tables[i];
- for (int j = 0; j < PAGE_COUNT; j++) {
- current_page_directory[i][j] = kernel_page_tables[i][j];
- }
- }
-}
-
-extern void KERNEL_END();
void paging_install()
{
- paging_switch_directory((u32 **)kernel_page_directory);
- paging_kernel_init(kernel_page_directory);
+ paging_init();
if (!memory_init())
paging_set_present(0, memory_get_all() >> 3);
- paging_set_used(0, ((u32)KERNEL_END >> 12) + 1);
+ paging_set_used(0, ((u32)&kernel_end >> 12) + 1);
+ u32 cr4;
+ asm volatile("mov %%cr4, %0" : "=r"(cr4));
+ cr4 &= 0xffffffef;
+ asm volatile("mov %0, %%cr4" ::"r"(cr4));
paging_enable();
log("Installed paging");
@@ -99,6 +78,7 @@ void paging_disable()
void paging_enable()
{
+ asm("mov %0, %%cr3" ::"r"(page_directory));
u32 cr0;
asm("mov %%cr0, %0" : "=r"(cr0));
cr0 |= 0x80000000;
@@ -108,8 +88,7 @@ void paging_enable()
void paging_switch_directory(u32 **dir)
{
- current_page_directory = dir;
- asm("mov %0, %%cr3" ::"r"(current_page_directory));
+ asm("mov %0, %%cr3" ::"r"(dir));
}
void invlpg(u32 addr)
@@ -121,7 +100,7 @@ void paging_map(u32 phy, u32 virt, u16 flags)
{
u32 pdi = virt >> 22;
u32 pti = virt >> 12 & 0x03FF;
- current_page_directory[pdi][pti] = phy | flags;
+ page_tables[pdi][pti] = phy | flags;
invlpg(virt);
}
@@ -129,21 +108,21 @@ u32 paging_get_phys(u32 virt)
{
u32 pdi = virt >> 22;
u32 pti = (virt >> 12) & 0x03FF;
- return current_page_directory[pdi][pti] & 0xFFFFF000;
+ return page_tables[pdi][pti] & 0xFFFFF000;
}
u16 paging_get_flags(u32 virt)
{
u32 pdi = virt >> 22;
u32 pti = (virt >> 12) & 0x03FF;
- return current_page_directory[pdi][pti] & 0xFFF;
+ return page_tables[pdi][pti] & 0xFFF;
}
void paging_set_flag_up(u32 virt, u32 count, u32 flag)
{
u32 page_n = virt / PAGE_ALIGN;
for (u32 i = page_n; i < page_n + count; i++) {
- current_page_directory[i / PAGE_COUNT][i % PAGE_COUNT] |= flag;
+ page_tables[i / PAGE_COUNT][i % PAGE_COUNT] |= flag;
invlpg(i * PAGE_ALIGN);
}
}
@@ -152,7 +131,7 @@ void paging_set_flag_down(u32 virt, u32 count, u32 flag)
{
u32 page_n = virt / PAGE_ALIGN;
for (u32 i = page_n; i < page_n + count; i++) {
- current_page_directory[i / PAGE_COUNT][i % PAGE_COUNT] &= ~flag;
+ page_tables[i / PAGE_COUNT][i % PAGE_COUNT] &= ~flag;
invlpg(i * PAGE_ALIGN);
}
}
@@ -184,8 +163,7 @@ u32 paging_find_pages(u32 count)
u32 start_page = 0;
for (u32 i = 0; i < PAGE_COUNT; i++) {
for (u32 j = 0; j < PAGE_COUNT; j++) {
- if (!(current_page_directory[i][j] & PT_PRESENT) ||
- (current_page_directory[i][j] & PT_USED)) {
+ if (!(page_tables[i][j] & PT_PRESENT) || (page_tables[i][j] & PT_USED)) {
continuous = 0;
start_dir = i;
start_page = j + 1;
@@ -212,7 +190,7 @@ u32 paging_get_used_pages()
u32 n = 0;
for (u32 i = 0; i < PAGE_COUNT; i++) {
for (u32 j = 0; j < PAGE_COUNT; j++) {
- u8 flags = current_page_directory[i][j] & PT_USED;
+ u8 flags = page_tables[i][j] & PT_USED;
if (flags == 1)
n++;
}