Move paging out of memory

This commit is contained in:
Baptiste Wicht 2013-12-07 20:10:27 +01:00
parent ac36ee61ca
commit e0c38a1274
4 changed files with 92 additions and 17 deletions

22
kernel/include/paging.hpp Normal file
View File

@ -0,0 +1,22 @@
//=======================================================================
// Copyright Baptiste Wicht 2013.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
//=======================================================================
#ifndef PAGING_H
#define PAGING_H
#include "types.hpp"
namespace paging {
const int PAGE_SIZE = 4096;
bool identity_map(void* physical);
bool identity_map(void* physical, size_t pages);
} //end of namespace paging
#endif

View File

@ -9,6 +9,7 @@
#include "types.hpp" #include "types.hpp"
#include "kernel_utils.hpp" #include "kernel_utils.hpp"
#include "timer.hpp" #include "timer.hpp"
#include "paging.hpp"
#include "console.hpp" #include "console.hpp"
@ -200,8 +201,15 @@ int init_acpi(){
k_printf("%h\n", reinterpret_cast<uintptr_t>(ptr)); k_printf("%h\n", reinterpret_cast<uintptr_t>(ptr));
if(!paging::identity_map(ptr, 16)){
k_print_line("Impossible to map the ACPI tables");
return -1;
}
// check if address is correct ( if acpi is available on this pc ) // check if address is correct ( if acpi is available on this pc )
if (ptr && check_header(ptr, "RSDT") == 0){ if (ptr && check_header(ptr, "RSDT") == 0){
//k_print_line("2");
// the RSDT contains an unknown number of pointers to acpi tables // the RSDT contains an unknown number of pointers to acpi tables
int entrys = *(ptr + 1); int entrys = *(ptr + 1);
entrys = (entrys-36) /4; entrys = (entrys-36) /4;

View File

@ -85,23 +85,6 @@ uint64_t pdpt_index = 0;
uint64_t pdt_index = 0; uint64_t pdt_index = 0;
uint64_t pt_index = 256; uint64_t pt_index = 256;
void identity_map(void* physical){
//Find the correct indexes inside the paging table for the physical address
auto table = (reinterpret_cast<uintptr_t>(physical) >> 12) & 0x1FF;
auto directory = (reinterpret_cast<uintptr_t>(physical) >> 21) & 0x1FF;
auto directory_ptr = (reinterpret_cast<uintptr_t>(physical) >> 30) & 0x1FF;
auto pml4 = (reinterpret_cast<uintptr_t>(physical) >> 39) & 0x1FF;
//Find the entries
pml4t_t pml4t = reinterpret_cast<pml4t_t>(0x70000);
auto pdpt = reinterpret_cast<pdpt_t>(reinterpret_cast<uintptr_t>(pml4t[pml4]) & ~0xFFF);
auto pdt = reinterpret_cast<pdt_t>(reinterpret_cast<uintptr_t>(pdpt[directory_ptr]) & ~0xFFF);
auto pt = reinterpret_cast<pt_t>(reinterpret_cast<uintptr_t>(pdt[directory]) & ~0xFFF);
//Identity map the physical address
pt[table] = reinterpret_cast<page_entry>(reinterpret_cast<uintptr_t>(physical) | 0x3);
}
uint64_t* allocate_block(uint64_t blocks){ uint64_t* allocate_block(uint64_t blocks){
if(!current_mmap_entry){ if(!current_mmap_entry){
for(uint64_t i = 0; i < entry_count; ++i){ for(uint64_t i = 0; i < entry_count; ++i){

62
kernel/src/paging.cpp Normal file
View File

@ -0,0 +1,62 @@
//=======================================================================
// Copyright Baptiste Wicht 2013.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
//=======================================================================
#include "paging.hpp"
#include "types.hpp"
namespace {
typedef uint64_t* page_entry;
typedef page_entry* pt_t;
typedef pt_t* pdt_t;
typedef pdt_t* pdpt_t;
typedef pdpt_t* pml4t_t;
} //end of anonymous namespace
bool paging::identity_map(void* physical){
//The address must be page-aligned
if(reinterpret_cast<uintptr_t>(physical) % PAGE_SIZE != 0){
return false;
}
//Find the correct indexes inside the paging table for the physical address
auto table = (reinterpret_cast<uintptr_t>(physical) >> 12) & 0x1FF;
auto directory = (reinterpret_cast<uintptr_t>(physical) >> 21) & 0x1FF;
auto directory_ptr = (reinterpret_cast<uintptr_t>(physical) >> 30) & 0x1FF;
auto pml4 = (reinterpret_cast<uintptr_t>(physical) >> 39) & 0x1FF;
//Find the entries
pml4t_t pml4t = reinterpret_cast<pml4t_t>(0x70000);
auto pdpt = reinterpret_cast<pdpt_t>(reinterpret_cast<uintptr_t>(pml4t[pml4]) & ~0xFFF);
auto pdt = reinterpret_cast<pdt_t>(reinterpret_cast<uintptr_t>(pdpt[directory_ptr]) & ~0xFFF);
auto pt = reinterpret_cast<pt_t>(reinterpret_cast<uintptr_t>(pdt[directory]) & ~0xFFF);
//Identity map the physical address
pt[table] = reinterpret_cast<page_entry>(reinterpret_cast<uintptr_t>(physical) | 0x3);
//TODO Check if pt[table] is already used and if so, return false
return true;
}
bool paging::identity_map(void* physical, size_t pages){
//The address must be page-aligned
if(reinterpret_cast<uintptr_t>(physical) % PAGE_SIZE != 0){
return false;
}
//TODO This should first check each page for the present bit
for(size_t page = 0; page < pages; ++page){
if(!identity_map(reinterpret_cast<void*>(reinterpret_cast<uintptr_t>(physical) + page * PAGE_SIZE))){
return false;
}
}
return true;
}