diff options
| author | Matteo Gmür <matteo.gmuer1@ost.ch> | 2024-10-16 14:10:32 +0000 |
|---|---|---|
| committer | Matteo Gmür <matteo.gmuer1@ost.ch> | 2024-10-16 14:10:32 +0000 |
| commit | 35e25757b6cffbcb2ff1eea8daf4c5f1ca421cb0 (patch) | |
| tree | cbdf50536e8a2b2143bf067947d562b6d8407438 /arch/x86_64/src | |
| parent | 934822e48a7c5a3e65ed74261ce5ab4315595f64 (diff) | |
| download | teachos-35e25757b6cffbcb2ff1eea8daf4c5f1ca421cb0.tar.xz teachos-35e25757b6cffbcb2ff1eea8daf4c5f1ca421cb0.zip | |
Adjust table accessing code to make it safer (always out of bounds checked)
Diffstat (limited to 'arch/x86_64/src')
| -rw-r--r-- | arch/x86_64/src/memory/paging.cpp | 47 |
1 files changed, 33 insertions, 14 deletions
diff --git a/arch/x86_64/src/memory/paging.cpp b/arch/x86_64/src/memory/paging.cpp index a07b2c0..a8f2c40 100644 --- a/arch/x86_64/src/memory/paging.cpp +++ b/arch/x86_64/src/memory/paging.cpp @@ -40,25 +40,21 @@ namespace teachos::arch::memory flags = std::bitset<64U>(frame.start_address()) | flags; } - auto page_table::zero_entries() -> void + page_table::page_table() + : entries() + , p4(reinterpret_cast<page_table *>(0xfffffffffffff000)) { - for (size_t i = 0; i < sizeof(entries) / sizeof(entries[0]); ++i) - { - entries[i].set_unused(); - } + // Nothing to do } - auto page_table::next_table_address(std::size_t index) const -> std::optional<std::size_t> + auto page_table::zero_entries() -> void { - auto entry = entries[index]; - - if (entry.contains_flags(entry.PRESENT) && !entry.contains_flags(entry.HUGE_PAGE)) + constexpr size_t entry_amount = sizeof(entries) / sizeof(entries[0]); + for (size_t i = 0; i < entry_amount; ++i) { - std::size_t table_address = reinterpret_cast<std::size_t>(this); - return (table_address << 9) | (index << 12); + auto entry = this->operator[](i); + entry.set_unused(); } - // TODO: Implement behaviour for huge pages currently not done - return std::nullopt; } auto page_table::next_table(std::size_t index) const -> std::optional<page_table const *> @@ -73,9 +69,32 @@ namespace teachos::arch::memory return std::nullopt; } - entry & page_table::operator[](std::size_t index) + auto page_table::operator[](std::size_t index) -> entry & + { + // C array is not bounds checked, therefore we have to check ourselves, to ensure no out of bounds reads, which + // could be incredibly hard to debug later. + arch::exception_handling::assert(index < PAGE_TABLE_ENTRY_COUNT, "[Page Table] index out of bounds"); + return entries[index]; + } + + auto page_table::operator[](std::size_t index) const -> entry const & { + // C array is not bounds checked, therefore we have to check ourselves, to ensure no out of bounds reads, which + // could be incredibly hard to debug later. arch::exception_handling::assert(index < PAGE_TABLE_ENTRY_COUNT, "[Page Table] index out of bounds"); return entries[index]; } + + auto page_table::next_table_address(std::size_t index) const -> std::optional<std::size_t> + { + auto entry = this->operator[](index); + + if (entry.contains_flags(entry::PRESENT) && !entry.contains_flags(entry::HUGE_PAGE)) + { + std::size_t const table_address = reinterpret_cast<std::size_t>(this); + return (table_address << 9) | (index << 12); + } + // TODO: Implement behaviour for huge pages currently not done + return std::nullopt; + } } // namespace teachos::arch::memory |
