switch from bitfields to enums
This commit is contained in:
@@ -8,58 +8,59 @@ PageTableManager::PageTableManager(PageTable* PML4Address) {
|
||||
this->PML4 = PML4Address;
|
||||
}
|
||||
|
||||
void PageTableManager::MapMemory(void* virtualMemory, void* physicalMemory) {
|
||||
PageMapIndexer indexer = PageMapIndexer((uint64_t)virtualMemory);
|
||||
PageDirectoryEntry PDE;
|
||||
void PageTableManager::MapMemory(void* virtualMemory, void* physicalMemory){
|
||||
PageMapIndexer indexer = PageMapIndexer((uint64_t)virtualMemory);
|
||||
PageDirectoryEntry PDE;
|
||||
|
||||
PDE = PML4->entries[indexer.PDP_i];
|
||||
PageTable* PDP;
|
||||
PDE = PML4->entries[indexer.PDP_i];
|
||||
PageTable* PDP;
|
||||
if (!PDE.GetFlag(PT_Flag::Present)){
|
||||
PDP = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PDP, 0, 0x1000);
|
||||
PDE.SetAddress((uint64_t)PDP >> 12);
|
||||
PDE.SetFlag(PT_Flag::Present, true);
|
||||
PDE.SetFlag(PT_Flag::ReadWrite, true);
|
||||
PML4->entries[indexer.PDP_i] = PDE;
|
||||
}
|
||||
else
|
||||
{
|
||||
PDP = (PageTable*)((uint64_t)PDE.GetAddress() << 12);
|
||||
}
|
||||
|
||||
|
||||
PDE = PDP->entries[indexer.PD_i];
|
||||
PageTable* PD;
|
||||
if (!PDE.GetFlag(PT_Flag::Present)){
|
||||
PD = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PD, 0, 0x1000);
|
||||
PDE.SetAddress((uint64_t)PD >> 12);
|
||||
PDE.SetFlag(PT_Flag::Present, true);
|
||||
PDE.SetFlag(PT_Flag::ReadWrite, true);
|
||||
PDP->entries[indexer.PD_i] = PDE;
|
||||
}
|
||||
else
|
||||
{
|
||||
PD = (PageTable*)((uint64_t)PDE.GetAddress() << 12);
|
||||
}
|
||||
|
||||
if (!PDE.Present) {
|
||||
PDP = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PDP, 0, 4096); // zero out the new page
|
||||
PDE = PD->entries[indexer.PT_i];
|
||||
PageTable* PT;
|
||||
if (!PDE.GetFlag(PT_Flag::Present)){
|
||||
PT = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PT, 0, 0x1000);
|
||||
PDE.SetAddress((uint64_t)PT >> 12);
|
||||
PDE.SetFlag(PT_Flag::Present, true);
|
||||
PDE.SetFlag(PT_Flag::ReadWrite, true);
|
||||
PD->entries[indexer.PT_i] = PDE;
|
||||
}
|
||||
else
|
||||
{
|
||||
PT = (PageTable*)((uint64_t)PDE.GetAddress() << 12);
|
||||
}
|
||||
|
||||
PDE.Address = (uint64_t)PDP >> 12;
|
||||
PDE.Present = true;
|
||||
PDE.ReadWrite = true;
|
||||
PML4->entries[indexer.PDP_i] = PDE;
|
||||
} else {
|
||||
PDP = (PageTable*)((uint64_t)PDE.Address << 12);
|
||||
}
|
||||
|
||||
PDE = PDP->entries[indexer.PD_i];
|
||||
PageTable* PD;
|
||||
|
||||
if (!PDE.Present) {
|
||||
PD = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PD, 0, 4096); // zero out the new page
|
||||
|
||||
PDE.Address = (uint64_t)PD >> 12;
|
||||
PDE.Present = true;
|
||||
PDE.ReadWrite = true;
|
||||
PDP->entries[indexer.PD_i] = PDE;
|
||||
} else {
|
||||
PD = (PageTable*)((uint64_t)PDE.Address << 12);
|
||||
}
|
||||
|
||||
PDE = PD->entries[indexer.PT_i];
|
||||
PageTable* PT;
|
||||
|
||||
if (!PDE.Present) {
|
||||
PT = (PageTable*)GlobalAllocator.RequestPage();
|
||||
memset(PT, 0, 4096); // zero out the new page
|
||||
|
||||
PDE.Address = (uint64_t)PT >> 12;
|
||||
PDE.Present = true;
|
||||
PDE.ReadWrite = true;
|
||||
PD->entries[indexer.PT_i] = PDE;
|
||||
} else {
|
||||
PT = (PageTable*)((uint64_t)PDE.Address << 12);
|
||||
}
|
||||
|
||||
PDE = PT->entries[indexer.P_i];
|
||||
PDE.Address = (uint64_t)physicalMemory >> 12;
|
||||
PDE.Present = true;
|
||||
PDE.ReadWrite = true;
|
||||
PT->entries[indexer.P_i] = PDE;
|
||||
PDE = PT->entries[indexer.P_i];
|
||||
PDE.SetAddress((uint64_t)physicalMemory >> 12);
|
||||
PDE.SetFlag(PT_Flag::Present, true);
|
||||
PDE.SetFlag(PT_Flag::ReadWrite, true);
|
||||
PT->entries[indexer.P_i] = PDE;
|
||||
}
|
||||
25
kernel/src/paging/paging.cpp
Normal file
25
kernel/src/paging/paging.cpp
Normal file
@@ -0,0 +1,25 @@
|
||||
#include "paging.h"
|
||||
|
||||
void PageDirectoryEntry::SetFlag(PT_Flag flag, bool enabled) {
|
||||
uint64_t bitSelector = (uint64_t)1 << flag;
|
||||
Value %= ~bitSelector;
|
||||
|
||||
if (enabled) {
|
||||
Value |= bitSelector;
|
||||
}
|
||||
}
|
||||
|
||||
bool PageDirectoryEntry::GetFlag(PT_Flag flag) {
|
||||
uint64_t bitSelector = (uint64_t)1 << flag;
|
||||
return Value & bitSelector > 0 ? true : false;
|
||||
}
|
||||
|
||||
uint64_t PageDirectoryEntry::GetAddress() {
|
||||
return (Value & 0x000FFFFFFFFFF000) >> 12;
|
||||
}
|
||||
|
||||
void PageDirectoryEntry::SetAddress(uint64_t address) {
|
||||
address &= 0x000000FFFFFFFFFF;
|
||||
Value &= 0xFFF0000000000FFF;
|
||||
Value |= (address << 12);
|
||||
}
|
||||
@@ -1,21 +1,28 @@
|
||||
#pragma once
|
||||
#include <stdint.h>
|
||||
|
||||
struct PageDirectoryEntry {
|
||||
bool Present : 1; // memory exists and can be accessed
|
||||
bool ReadWrite : 1; //
|
||||
bool UserSuper : 1; // memory can only be accessed by supervisor or both user and supervisor
|
||||
bool WriteThrough : 1; //
|
||||
bool CacheDisabled : 1; //
|
||||
bool Accessed : 1; // set when cpu accesses page
|
||||
bool ignore0 : 1; //
|
||||
bool LargerPages : 1; //
|
||||
bool ignore1 : 1; //
|
||||
uint8_t Available : 3; //
|
||||
uint64_t Address : 52; // physical address
|
||||
|
||||
enum PT_Flag {
|
||||
Present = 0,
|
||||
ReadWrite = 1,
|
||||
UserSuper = 2,
|
||||
WriteThrough = 3,
|
||||
CacheDisabled = 4,
|
||||
Accessed = 5,
|
||||
LargerPages = 7,
|
||||
Custom0 = 9,
|
||||
Custom1 = 10,
|
||||
Custom2 = 11,
|
||||
NX = 63 // no-execute, only if supported
|
||||
};
|
||||
|
||||
struct PageTable {
|
||||
PageDirectoryEntry entries[512];
|
||||
struct PageDirectoryEntry {
|
||||
uint64_t Value;
|
||||
void SetFlag(PT_Flag flag, bool enabled);
|
||||
bool GetFlag(PT_Flag flag);
|
||||
void SetAddress(uint64_t address);
|
||||
uint64_t GetAddress();
|
||||
};
|
||||
|
||||
struct PageTable {
|
||||
PageDirectoryEntry entries [512];
|
||||
}__attribute__((aligned(0x1000)));
|
||||
Reference in New Issue
Block a user