1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-31 08:58:11 +00:00

Kernel: Add support for kernel addresses other than 3-4GB

This commit is contained in:
Gunnar Beutner 2021-07-17 02:42:59 +02:00 committed by Andreas Kling
parent 6c6b778e2e
commit b708b23b13
5 changed files with 28 additions and 29 deletions

View file

@ -83,17 +83,16 @@ PageDirectory::PageDirectory(const RangeAllocator* parent_range_allocator)
m_directory_table = MM.allocate_user_physical_page();
if (!m_directory_table)
return;
m_directory_pages[0] = MM.allocate_user_physical_page();
if (!m_directory_pages[0])
return;
m_directory_pages[1] = MM.allocate_user_physical_page();
if (!m_directory_pages[1])
return;
m_directory_pages[2] = MM.allocate_user_physical_page();
if (!m_directory_pages[2])
return;
auto kernel_pd_index = (KERNEL_BASE >> 30) & 0xffu;
for (size_t i = 0; i < 4; i++) {
if (i == kernel_pd_index)
continue;
m_directory_pages[i] = MM.allocate_user_physical_page();
if (!m_directory_pages[i])
return;
}
// Share the top 1 GiB of kernel-only mappings (>=3GiB or >=KERNEL_BASE)
m_directory_pages[3] = MM.kernel_page_directory().m_directory_pages[3];
m_directory_pages[kernel_pd_index] = MM.kernel_page_directory().m_directory_pages[kernel_pd_index];
#if ARCH(X86_64)
{
@ -105,17 +104,15 @@ PageDirectory::PageDirectory(const RangeAllocator* parent_range_allocator)
{
auto& table = *(PageDirectoryPointerTable*)MM.quickmap_page(*m_directory_table);
for (size_t i = 0; i < sizeof(m_directory_pages) / sizeof(m_directory_pages[0]); i++) {
if (m_directory_pages[i]) {
#if ARCH(I386)
table.raw[0] = (FlatPtr)m_directory_pages[0]->paddr().as_ptr() | 1;
table.raw[1] = (FlatPtr)m_directory_pages[1]->paddr().as_ptr() | 1;
table.raw[2] = (FlatPtr)m_directory_pages[2]->paddr().as_ptr() | 1;
table.raw[3] = (FlatPtr)m_directory_pages[3]->paddr().as_ptr() | 1;
table.raw[i] = (FlatPtr)m_directory_pages[i]->paddr().as_ptr() | 1;
#else
table.raw[0] = (FlatPtr)m_directory_pages[0]->paddr().as_ptr() | 7;
table.raw[1] = (FlatPtr)m_directory_pages[1]->paddr().as_ptr() | 7;
table.raw[2] = (FlatPtr)m_directory_pages[2]->paddr().as_ptr() | 7;
table.raw[3] = (FlatPtr)m_directory_pages[3]->paddr().as_ptr() | 7;
table.raw[i] = (FlatPtr)m_directory_pages[i]->paddr().as_ptr() | 7;
#endif
}
}
// 2 ** MAXPHYADDR - 1
// Where MAXPHYADDR = physical_address_bit_width
@ -137,10 +134,8 @@ PageDirectory::PageDirectory(const RangeAllocator* parent_range_allocator)
// when writing out the PDPT pointer to CR3.
// The reason we're not checking the page directory's physical address directly is because
// we're checking for sign extension when putting it into a PDPTE. See issue #4584.
VERIFY((table.raw[0] & ~pdpte_bit_flags) <= max_physical_address);
VERIFY((table.raw[1] & ~pdpte_bit_flags) <= max_physical_address);
VERIFY((table.raw[2] & ~pdpte_bit_flags) <= max_physical_address);
VERIFY((table.raw[3] & ~pdpte_bit_flags) <= max_physical_address);
for (auto table_entry : table.raw)
VERIFY((table_entry & ~pdpte_bit_flags) <= max_physical_address);
MM.unquickmap_page();
}