diff options
Diffstat (limited to 'arch/x86_64')
5 files changed, 42 insertions, 10 deletions
diff --git a/arch/x86_64/include/arch/memory/paging/active_page_table.hpp b/arch/x86_64/include/arch/memory/paging/active_page_table.hpp index 8011ee0..3fb2e65 100644 --- a/arch/x86_64/include/arch/memory/paging/active_page_table.hpp +++ b/arch/x86_64/include/arch/memory/paging/active_page_table.hpp @@ -3,6 +3,8 @@ #include "arch/exception_handling/assert.hpp" #include "arch/memory/allocator/concept.hpp" +#include "arch/memory/paging/inactive_page_table.hpp" +#include "arch/memory/paging/temporary_page.hpp" #include "arch/memory/paging/virtual_page.hpp" #include <array> @@ -10,12 +12,15 @@ namespace teachos::arch::memory::paging { + /** * @brief Currently active level 4 page table, is used to ensure there is only ever one valid instance and it cannot * be copied or constructed again. */ struct active_page_table { + typedef void (*function)(active_page_table * active_page_table); + /** * @brief Creates a single instance of an active level 4 page table table and returns the created instance or * alternatively returns the previously created instance instead. The instance is owned by this method and is @@ -158,6 +163,8 @@ namespace teachos::arch::memory::paging invalidate_page_cache(page.start_address()); } + auto with(inactive_page_table inactive_page_table, temporary_page temporary_page, function f) -> void; + private: /** * @brief Private constructor should only be used by create or get method, which ensures to create only ever one @@ -213,6 +220,7 @@ namespace teachos::arch::memory::paging page_table_handle active_handle; }; + } // namespace teachos::arch::memory::paging #endif // TEACHOS_ARCH_X86_64_MEMORY_PAGING_ACTIVE_PAGE_TABLE_HPP diff --git a/arch/x86_64/include/arch/memory/paging/inactive_page_table.hpp b/arch/x86_64/include/arch/memory/paging/inactive_page_table.hpp index 4285fc2..62c196f 100644 --- a/arch/x86_64/include/arch/memory/paging/inactive_page_table.hpp +++ b/arch/x86_64/include/arch/memory/paging/inactive_page_table.hpp @@ -2,12 +2,16 @@ #define TEACHOS_ARCH_X86_64_MEMORY_PAGING_INACTIVE_PAGE_TABLE_HPP #include "arch/memory/allocator/physical_frame.hpp" +#include "arch/memory/paging/active_page_table.hpp" +#include "arch/memory/paging/temporary_page.hpp" namespace teachos::arch::memory::paging { struct inactive_page_table { - private: + inactive_page_table(allocator::physical_frame frame, active_page_table active_page_table, + temporary_page temporary_page); + allocator::physical_frame page_table_level_4_frame; }; } // namespace teachos::arch::memory::paging diff --git a/arch/x86_64/include/arch/memory/paging/temporary_page.hpp b/arch/x86_64/include/arch/memory/paging/temporary_page.hpp index b658f7a..a7552dd 100644 --- a/arch/x86_64/include/arch/memory/paging/temporary_page.hpp +++ b/arch/x86_64/include/arch/memory/paging/temporary_page.hpp @@ -36,31 +36,31 @@ namespace teachos::arch::memory::paging */ auto zero_entries(active_page_table & active_table) -> void; - private: /** - * @brief Map the temporary page to a frame. + * @brief Unmap the current page. * - * @param frame The frame to which the page is mapped. * @param active_table The current active page table. - * @return The virtual address of the page. */ - auto map_to_frame(allocator::physical_frame frame, active_page_table & active_table) -> virtual_address; + auto unmap(active_page_table & active_table) -> void; /** - * @brief Unmap the current page. + * @brief Map the temporary page to a frame. * + * @param frame The frame to which the page is mapped. * @param active_table The current active page table. + * @return level1 page table handle containing the mapped page. */ - auto unmap(active_page_table & active_table) -> void; + auto map_table_frame(allocator::physical_frame frame, active_page_table & active_table) -> page_table_handle; + private: /** * @brief Map the temporary page to a frame. * * @param frame The frame to which the page is mapped. * @param active_table The current active page table. - * @return level1 page table handle containing the mapped page. + * @return The virtual address of the page. */ - auto map_table_frame(allocator::physical_frame frame, active_page_table & active_table) -> page_table_handle; + auto map_to_frame(allocator::physical_frame frame, active_page_table & active_table) -> virtual_address; virtual_page page; allocator::tiny_frame_allocator allocator; diff --git a/arch/x86_64/src/memory/paging/active_page_table.cpp b/arch/x86_64/src/memory/paging/active_page_table.cpp index 38696f8..5f31f75 100644 --- a/arch/x86_64/src/memory/paging/active_page_table.cpp +++ b/arch/x86_64/src/memory/paging/active_page_table.cpp @@ -93,4 +93,14 @@ namespace teachos::arch::memory::paging { // Nothing to do } + + auto active_page_table::with(inactive_page_table inactive_page_table, temporary_page temporary_page, + active_page_table::function f) -> void + { + active_handle[511].set_entry(inactive_page_table.page_table_level_4_frame, entry::PRESENT | entry::WRITABLE); + invalidate_page_cache(PAGE_TABLE_LEVEL_4_ADDRESS); + + f(*mapper); + } + } // namespace teachos::arch::memory::paging diff --git a/arch/x86_64/src/memory/paging/inactive_page_table.cpp b/arch/x86_64/src/memory/paging/inactive_page_table.cpp index 1f36aa3..afba1f0 100644 --- a/arch/x86_64/src/memory/paging/inactive_page_table.cpp +++ b/arch/x86_64/src/memory/paging/inactive_page_table.cpp @@ -2,4 +2,14 @@ namespace teachos::arch::memory::paging { + inactive_page_table::inactive_page_table(allocator::physical_frame frame, active_page_table active_page_table, + temporary_page temporary_page) + : page_table_level_4_frame{frame} + { + auto table = temporary_page.map_table_frame(page_table_level_4_frame, active_page_table); + table.zero_entries(); + table[511].set_entry(page_table_level_4_frame, entry::PRESENT | entry::WRITABLE); + + temporary_page.unmap(active_page_table); + } } // namespace teachos::arch::memory::paging |
