aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--arch/x86_64/include/arch/memory/paging/active_page_table.hpp8
-rw-r--r--arch/x86_64/include/arch/memory/paging/inactive_page_table.hpp6
-rw-r--r--arch/x86_64/include/arch/memory/paging/temporary_page.hpp18
-rw-r--r--arch/x86_64/src/memory/paging/active_page_table.cpp10
-rw-r--r--arch/x86_64/src/memory/paging/inactive_page_table.cpp10
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