From 64bf16fe0d2cb9af68de92d7698cf28b963636e4 Mon Sep 17 00:00:00 2001 From: Patrick Williams Date: Mon, 17 Dec 2012 10:41:54 -0600 Subject: ptmgr lacked support for physical mapped addrs. Added a new access type of BYPASS_HRMOR that the ptmgr will support when a PTE is added, so that blocks can support addresses which do not have the HRMOR applied. This is needed so that mm_linear_map will work correctly when HRMOR != 0. Change-Id: Ie4599d63a4454f425e0a0964b02fec7075c4401e RTC: 60665 Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/2733 Tested-by: Jenkins Server Reviewed-by: Daniel M. Crowell Reviewed-by: A. Patrick Williams III --- src/include/sys/mm.h | 1 + src/kernel/block.C | 41 +++++++++++++++++++++++++++++++++-------- src/kernel/ptmgr.C | 5 +++-- 3 files changed, 37 insertions(+), 10 deletions(-) (limited to 'src') diff --git a/src/include/sys/mm.h b/src/include/sys/mm.h index dca50d9a4..f3488b3d8 100644 --- a/src/include/sys/mm.h +++ b/src/include/sys/mm.h @@ -58,6 +58,7 @@ enum PAGE_PERMISSIONS ALLOCATE_FROM_ZERO = 0x00000010, NO_ALLOCATE_FROM_ZERO = 0x00000020, NO_ACCESS = 0x00000040, + BYPASS_HRMOR = 0x00000080, }; diff --git a/src/kernel/block.C b/src/kernel/block.C index c8546f760..c33529963 100644 --- a/src/kernel/block.C +++ b/src/kernel/block.C @@ -71,7 +71,7 @@ void Block::init(MessageQueue* i_msgQ, uint64_t *i_spteAddr) else // set the page table to reside at the address requested { // Doing a placement new to put the SPTE at the beginging - // of the block we allocated. + // of the block we allocated. iv_ptes = new(i_spteAddr) ShadowPTE[iv_size / PAGESIZE]; } @@ -176,12 +176,25 @@ bool Block::handlePageFault(task_t* i_task, uint64_t i_addr, bool i_store) } } + // Determine access type. + uint64_t l_access = (iv_mappedToPhysical ? BYPASS_HRMOR : 0); + if (pte->isExecutable()) + { + l_access |= EXECUTABLE; + } + else if (pte->isWritable() && pte->isDirty()) + { + l_access |= WRITABLE; + } + else + { + l_access |= READ_ONLY; + } + PageTableManager::addEntry( l_addr_palign, pte->getPage(), - (pte->isExecutable() ? EXECUTABLE : - ((pte->isWritable() && pte->isDirty()) ? WRITABLE : - READ_ONLY))); + l_access); return true; @@ -241,13 +254,25 @@ void Block::attachSPTE(void *i_vaddr) //Set the present bit for the address associated with this block l_pte->setPresent(true); + // Determine access type. + uint64_t l_access = (iv_mappedToPhysical ? BYPASS_HRMOR : 0); + if (l_pte->isExecutable()) + { + l_access |= EXECUTABLE; + } + else if (l_pte->isWritable() && l_pte->isDirty()) + { + l_access |= WRITABLE; + } + else + { + l_access |= READ_ONLY; + } + //Add page table entry PageTableManager::addEntry((l_vaddr / PAGESIZE) * PAGESIZE, l_pte->getPage(), - (l_pte->isExecutable() ? EXECUTABLE : - ((l_pte->isWritable() && l_pte->isDirty()) ? - WRITABLE : - READ_ONLY))); + l_access); // update permission for the page that corresponds to the physical page // addr now that we have handled the page fault. diff --git a/src/kernel/ptmgr.C b/src/kernel/ptmgr.C index 019563cd1..35f55873a 100644 --- a/src/kernel/ptmgr.C +++ b/src/kernel/ptmgr.C @@ -209,7 +209,8 @@ void PageTableManager::addEntry( uint64_t i_vAddr, uint64_t i_accessType ) { // adjust physical address for the HRMOR unless this is a mmio - if( SegmentManager::CI_ACCESS != i_accessType ) + if ((SegmentManager::CI_ACCESS != i_accessType) && + ((BYPASS_HRMOR & i_accessType) == 0)) { i_page |= (getHRMOR() / PAGESIZE); } @@ -252,7 +253,7 @@ void PageTableManager::delRangePN( uint64_t i_pnStart, i_pnStart |= (getHRMOR() / PAGESIZE); i_pnFinish |= (getHRMOR() / PAGESIZE); } - + return Singleton::instance()._delRangePN(i_pnStart,i_pnFinish); } -- cgit v1.2.3