diff options
Diffstat (limited to 'dev/kernel/HALKit')
| -rw-r--r-- | dev/kernel/HALKit/AMD64/HalPagingMgrAMD64.cc | 89 | ||||
| -rw-r--r-- | dev/kernel/HALKit/AMD64/Paging.h | 27 | ||||
| -rw-r--r-- | dev/kernel/HALKit/AMD64/Processor.h | 11 | ||||
| -rw-r--r-- | dev/kernel/HALKit/AMD64/Storage/AHCI+Generic.cc | 6 |
4 files changed, 66 insertions, 67 deletions
diff --git a/dev/kernel/HALKit/AMD64/HalPagingMgrAMD64.cc b/dev/kernel/HALKit/AMD64/HalPagingMgrAMD64.cc index 040b6fd9..bb7274b5 100644 --- a/dev/kernel/HALKit/AMD64/HalPagingMgrAMD64.cc +++ b/dev/kernel/HALKit/AMD64/HalPagingMgrAMD64.cc @@ -12,6 +12,41 @@ namespace Kernel::HAL { + namespace Detail + { + struct PTE + { + UInt64 Present : 1; + UInt64 Wr : 1; + UInt64 User : 1; + UInt64 Pwt : 1; // Page-level Write-Through + UInt64 Pcd : 1; // Page-level Cache Disable + UInt64 Accessed : 1; + UInt64 Dirty : 1; + UInt64 Pat : 1; // Page Attribute Table (or PS for PDE) + UInt64 Global : 1; + UInt64 Ignored1 : 3; // Available to software + UInt64 PhysicalAddress : 40; // Physical page frame address (bits 12–51) + UInt64 Ignored2 : 7; // More software bits / reserved + UInt64 Protection_key : 4; // Optional (if PKU enabled) + UInt64 Reserved : 1; // Usually reserved + UInt64 Nx : 1; // No Execute + }; + } // namespace Detail + + /***********************************************************************************/ + /// \brief Retrieve the page status of a PTE. + /// \param pte Page Table Entry pointer. + /***********************************************************************************/ + STATIC Void mmi_page_status(Detail::PTE* pte) + { + kout << (pte->Present ? "Present" : "Not Present") << kendl; + kout << (pte->Wr ? "W/R" : "Not W/R") << kendl; + kout << (pte->Nx ? "NX" : "Not NX") << kendl; + kout << (pte->User ? "User" : "Not User") << kendl; + kout << (pte->Pcd ? "Not Cached" : "Cached") << kendl; + } + /***********************************************************************************/ /// @brief Gets a physical address from a virtual address. /// @param virt a valid virtual address. @@ -25,6 +60,8 @@ namespace Kernel::HAL UInt64 cr3 = (UInt64)hal_read_cr3() & ~kPageOffsetMask; + hal_invl_tlb(virt); + // Level 4 auto pml4 = reinterpret_cast<UInt64*>(cr3); UInt64 pml4e = pml4[(vaddr >> 39) & kMask9Bits]; @@ -54,28 +91,16 @@ namespace Kernel::HAL // Level 1 auto pt = reinterpret_cast<UInt64*>(pde & ~kPageOffsetMask); - UInt64 pte = pt[(vaddr >> 12) & kMask9Bits]; + Detail::PTE* pte = (Detail::PTE*)pt[(vaddr >> 12) & kMask9Bits]; - if (!(pte & 1)) + if (!pte->Present) return 0; - return (pte & ~kPageOffsetMask) | (vaddr & kPageOffsetMask); - } + mmi_page_status((Detail::PTE*)pte); - /***********************************************************************************/ - /// \brief Retrieve the page status of a PTE. - /// \param pte Page Table Entry pointer. - /***********************************************************************************/ - STATIC Void mmi_page_status(PTE* pte) - { - kout << (pte->Present ? "Present" : "Not Present") << kendl; - kout << (pte->Wr ? "W/R" : "Not W/R") << kendl; - kout << (pte->ExecDisable ? "NX" : "Not NX") << kendl; - kout << (pte->User ? "User" : "Not User") << kendl; + return pte->PhysicalAddress; } - STATIC Int32 mmi_map_page_table_entry(UIntPtr virtual_address, UInt32 physical_address, UInt32 flags, NE_PTE* pt_entry, NE_PDE* pd_entry); - /***********************************************************************************/ /// @brief Maps or allocates a page from virtual_address. /// @param virtual_address a valid virtual address. @@ -95,39 +120,33 @@ namespace Kernel::HAL UInt64 pml4e = pml4[(vaddr >> 39) & kMask9]; if (!(pml4e & 1)) - return 1; + return kErrorInvalidData; auto pdpt = reinterpret_cast<UInt64*>(pml4e & ~kPageMask); UInt64 pdpte = pdpt[(vaddr >> 30) & kMask9]; if (!(pdpte & 1)) - return 1; + return kErrorInvalidData; auto pd = reinterpret_cast<UInt64*>(pdpte & ~kPageMask); UInt64 pde = pd[(vaddr >> 21) & kMask9]; if (!(pde & 1)) - return 1; - - auto pt = reinterpret_cast<UInt64*>(pde & ~kPageMask); - UInt64& pte = pt[(vaddr >> 12) & kMask9]; + return kErrorInvalidData; - // Set the new PTE - pte = (reinterpret_cast<UInt64>(physical_address) & ~0xFFFULL) | 0x01ULL; // Present + UInt64* pt = reinterpret_cast<UInt64*>(pde & ~kPageMask); + Detail::PTE* pte = (Detail::PTE*)pt[(vaddr >> 12) & kMask9]; - if (flags & ~kMMFlagsPresent) - pte &= ~(0x01ULL); // Not Present + pte->Present = !!(flags & kMMFlagsPresent); + pte->Wr = !!(flags & kMMFlagsWr); + pte->User = !!(flags & kMMFlagsUser); + pte->Nx = !!(flags & kMMFlagsNX); + pte->Pcd = !(flags & kMMFlagsUncached); - if (flags & kMMFlagsWr) - pte |= 1 << 1; // Writable - - if (flags & kMMFlagsUser) - pte |= 1 << 2; // User + hal_invl_tlb(virtual_address); - if (flags & kMMFlagsNX) - pte |= 1ULL << 63; // NX + mmi_page_status(pte); - hal_invl_tlb(virtual_address); - return 0; + return kErrorSuccess; } } // namespace Kernel::HAL diff --git a/dev/kernel/HALKit/AMD64/Paging.h b/dev/kernel/HALKit/AMD64/Paging.h index 474c74e7..6299d9b4 100644 --- a/dev/kernel/HALKit/AMD64/Paging.h +++ b/dev/kernel/HALKit/AMD64/Paging.h @@ -41,25 +41,6 @@ EXTERN_C Kernel::VoidPtr hal_read_cr3(); // @brief Page table. namespace Kernel::HAL { - /// @brief Final page entry (Not PML, PDPT) - struct PACKED NE_PTE final - { - UInt64 Present : 1; - UInt64 Wr : 1; - UInt64 User : 1; - UInt64 Wt : 1; - UInt64 Cache : 1; - UInt64 Accessed : 1; - UInt64 Dirty : 1; - UInt64 MemoryType : 1; - UInt64 Global : 1; - UInt64 Resvered1 : 3; - UInt64 PhysicalAddress : 36; - UInt64 Reserved2 : 10; - UInt64 ProtectionKey : 5; - UInt64 ExecDisable : 1; - }; - namespace Detail { enum class ControlRegisterBits @@ -83,10 +64,6 @@ namespace Kernel::HAL } } // namespace Detail - struct NE_PDE final - { - NE_PTE* ALIGN(kPageAlign) fEntries[kPageMax]; - }; auto mm_alloc_bitmap(Boolean wr, Boolean user, SizeT size, Bool is_page, const SizeT pad = 0) -> VoidPtr; auto mm_free_bitmap(VoidPtr page_ptr) -> Bool; @@ -94,6 +71,6 @@ namespace Kernel::HAL namespace Kernel { - typedef HAL::NE_PTE PTE; - typedef HAL::NE_PDE PDE; + typedef VoidPtr PTE; + typedef VoidPtr PDE; } // namespace Kernel diff --git a/dev/kernel/HALKit/AMD64/Processor.h b/dev/kernel/HALKit/AMD64/Processor.h index eff0292b..ff9d13a5 100644 --- a/dev/kernel/HALKit/AMD64/Processor.h +++ b/dev/kernel/HALKit/AMD64/Processor.h @@ -68,11 +68,12 @@ namespace Kernel::HAL /// @brief Memory Manager mapping flags. enum { - kMMFlagsInvalid = 0 << 0, - kMMFlagsPresent = 1 << 0, - kMMFlagsWr = 1 << 1, - kMMFlagsUser = 1 << 2, - kMMFlagsNX = 1 << 3, + kMMFlagsInvalid = 1 << 0, + kMMFlagsPresent = 1 << 1, + kMMFlagsWr = 1 << 2, + kMMFlagsUser = 1 << 3, + kMMFlagsNX = 1 << 4, + kMMFlagsUncached = 1 << 5, kMMFlagsCount = 4, }; diff --git a/dev/kernel/HALKit/AMD64/Storage/AHCI+Generic.cc b/dev/kernel/HALKit/AMD64/Storage/AHCI+Generic.cc index 41aabca2..a1a9a164 100644 --- a/dev/kernel/HALKit/AMD64/Storage/AHCI+Generic.cc +++ b/dev/kernel/HALKit/AMD64/Storage/AHCI+Generic.cc @@ -87,7 +87,7 @@ STATIC Void drv_compute_disk_ahci() noexcept kSATASectorCount = 0UL; /// Normally 512 bytes, but add an additional 512 bytes to make 1 KIB. - const UInt16 kSzIdent = 256; + const UInt16 kSzIdent = 512; /// Push it to the stack UInt16* identify_data = AHCI::Detail::ahci_align_address<UInt16>(new UInt16[kSzIdent], kib_cast(1)); @@ -186,7 +186,7 @@ STATIC Void drv_std_input_output_ahci(UInt64 lba, UInt8* buffer, SizeT sector_sz command_table->Prdt[0].Dba = (UInt32)(buffer_phys & 0xFFFFFFFF); command_table->Prdt[0].Dbau = (UInt32)(buffer_phys >> 32); command_table->Prdt[0].Dbc = bytes_remaining - 1; - command_table->Prdt[0].Ie = 1; + command_table->Prdt[0].Ie = NO; volatile FisRegH2D* h2d_fis = (volatile FisRegH2D*)(&command_table->Cfis[0]); @@ -300,6 +300,8 @@ STATIC Bool drv_std_init_ahci(UInt16& pi, BOOL& atapi) kSATADev.EnableMmio(); kSATADev.BecomeBusMaster(); + HAL::mm_map_page((VoidPtr)mem_ahci, (VoidPtr)mem_ahci, HAL::kMMFlagsPresent | HAL::kMMFlagsWr | HAL::kMMFlagsUncached); + UInt32 ports_implemented = mem_ahci->Pi; UInt16 ahci_index = 0; |
