Changeset 15344 in vbox
- Timestamp:
- Dec 12, 2008 12:13:56 AM (16 years ago)
- Location:
- trunk
- Files:
-
- 9 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/include/VBox/pgm.h
r15284 r15344 448 448 VMMDECL(void) PGMDynMapStartAutoSet(PVMCPU pVCpu); 449 449 VMMDECL(void) PGMDynMapReleaseAutoSet(PVMCPU pVCpu); 450 VMMDECL(void) PGMDynMapFlushAutoSet(PVMCPU pVCpu); 450 451 VMMDECL(void) PGMDynMapMigrateAutoSet(PVMCPU pVCpu); 451 452 -
trunk/include/VBox/vm.h
r15236 r15344 130 130 struct PGMCPU s; 131 131 #endif 132 char padding[1 92];/* multiple of 64 */132 char padding[1024]; /* multiple of 64 */ 133 133 } pgm; 134 134 -
trunk/src/VBox/VMM/PGM.cpp
r15196 r15344 1136 1136 */ 1137 1137 pVM->pgm.s.offVM = RT_OFFSETOF(VM, pgm.s); 1138 pVM->pgm.s.offVCpu = RT_OFFSETOF(VMCPU, pgm.s); 1138 1139 pVM->pgm.s.enmShadowMode = PGMMODE_INVALID; 1139 1140 pVM->pgm.s.enmGuestMode = PGMMODE_INVALID; … … 1597 1598 1598 1599 /* R0 only: */ 1599 STAM_REG(pVM, &pPGM->StatR0DynMapHCPage, STAMTYPE_PROFILE, "/PGM/R0/DynMapPage/HCPage", STAMUNIT_OCCURENCES, "Calls to PGMDynMapHCPage (ring-0).");1600 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageSetOptimize, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/HCPageSetOptimize", STAMUNIT_OCCURENCES, "Calls to pgmDynMapOptimizeAutoSet.");1601 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageSetSearchHits, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/HCPageSetSearchHits", STAMUNIT_OCCURENCES, "Set search hits.");1602 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageSetSearchMisses, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/HCPageSetSearchMisses", STAMUNIT_OCCURENCES, "Set search misses.");1603 1600 STAM_REG(pVM, &pPGM->StatR0DynMapMigrateInvlPg, STAMTYPE_COUNTER, "/PGM/R0/DynMapMigrateInvlPg", STAMUNIT_OCCURENCES, "invlpg count in PGMDynMapMigrateAutoSet."); 1601 STAM_REG(pVM, &pPGM->StatR0DynMapGCPageInl, STAMTYPE_PROFILE, "/PGM/R0/DynMapPageGCPageInl", STAMUNIT_TICKS_PER_CALL, "Calls to pgmR0DynMapGCPageInlined."); 1602 STAM_REG(pVM, &pPGM->StatR0DynMapGCPageInlHits, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageGCPageInl/Hits", STAMUNIT_OCCURENCES, "Hash table lookup hits."); 1603 STAM_REG(pVM, &pPGM->StatR0DynMapGCPageInlMisses, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageGCPageInl/Misses", STAMUNIT_OCCURENCES, "Misses that falls back to code common with PGMDynMapHCPage."); 1604 STAM_REG(pVM, &pPGM->StatR0DynMapGCPageInlRamHits, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageGCPageInl/RamHits", STAMUNIT_OCCURENCES, "1st ram range hits."); 1605 STAM_REG(pVM, &pPGM->StatR0DynMapGCPageInlRamMisses, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageGCPageInl/RamMisses", STAMUNIT_OCCURENCES, "1st ram range misses, takes slow path."); 1606 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageInl, STAMTYPE_PROFILE, "/PGM/R0/DynMapPageHCPageInl", STAMUNIT_TICKS_PER_CALL, "Calls to pgmR0DynMapHCPageInlined."); 1607 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageInlHits, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageHCPageInl/Hits", STAMUNIT_OCCURENCES, "Hash table lookup hits."); 1608 STAM_REG(pVM, &pPGM->StatR0DynMapHCPageInlMisses, STAMTYPE_COUNTER, "/PGM/R0/DynMapPageHCPageInl/Misses", STAMUNIT_OCCURENCES, "Misses that falls back to code common with PGMDynMapHCPage."); 1604 1609 STAM_REG(pVM, &pPGM->StatR0DynMapPage, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage", STAMUNIT_OCCURENCES, "Calls to pgmR0DynMapPage"); 1605 STAM_REG(pVM, &pPGM->StatR0DynMapPageHit0, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hit0", STAMUNIT_OCCURENCES, "Hit at iPage+0"); 1606 STAM_REG(pVM, &pPGM->StatR0DynMapPageHit1, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hit1", STAMUNIT_OCCURENCES, "Hit at iPage+1"); 1607 STAM_REG(pVM, &pPGM->StatR0DynMapPageHit2, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hit2", STAMUNIT_OCCURENCES, "Hit at iPage+2"); 1610 STAM_REG(pVM, &pPGM->StatR0DynMapSetOptimize, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/SetOptimize", STAMUNIT_OCCURENCES, "Calls to pgmDynMapOptimizeAutoSet."); 1611 STAM_REG(pVM, &pPGM->StatR0DynMapSetSearchHits, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/SetSearchHits", STAMUNIT_OCCURENCES, "Set search hits."); 1612 STAM_REG(pVM, &pPGM->StatR0DynMapSetSearchMisses, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/SetSearchMisses", STAMUNIT_OCCURENCES, "Set search misses."); 1613 STAM_REG(pVM, &pPGM->StatR0DynMapHCPage, STAMTYPE_PROFILE, "/PGM/R0/DynMapPage/HCPage", STAMUNIT_TICKS_PER_CALL, "Calls to PGMDynMapHCPage (ring-0)."); 1614 STAM_REG(pVM, &pPGM->StatR0DynMapPageHits0, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hits0", STAMUNIT_OCCURENCES, "Hits at iPage+0"); 1615 STAM_REG(pVM, &pPGM->StatR0DynMapPageHits1, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hits1", STAMUNIT_OCCURENCES, "Hits at iPage+1"); 1616 STAM_REG(pVM, &pPGM->StatR0DynMapPageHits2, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Hits2", STAMUNIT_OCCURENCES, "Hits at iPage+2"); 1608 1617 STAM_REG(pVM, &pPGM->StatR0DynMapPageInvlPg, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/InvlPg", STAMUNIT_OCCURENCES, "invlpg count in pgmR0DynMapPageSlow."); 1609 1618 STAM_REG(pVM, &pPGM->StatR0DynMapPageSlow, STAMTYPE_COUNTER, "/PGM/R0/DynMapPage/Slow", STAMUNIT_OCCURENCES, "Calls to pgmR0DynMapPageSlow - subtract this from pgmR0DynMapPage to get 1st level hits."); -
trunk/src/VBox/VMM/PGMInternal.h
r15196 r15344 226 226 * @remark There is no need to assert on the result. 227 227 */ 228 #if defined(IN_RC) || defined(VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0)228 #ifdef IN_RC 229 229 # define PGM_HCPHYS_2_PTR(pVM, HCPhys, ppv) \ 230 230 PGMDynMapHCPage(pVM, HCPhys, (void **)(ppv)) 231 #elif defined(VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0) 232 # define PGM_HCPHYS_2_PTR(pVM, HCPhys, ppv) \ 233 pgmR0DynMapHCPageInlined(&(pVM)->pgm.s, HCPhys, (void **)(ppv)) 231 234 #else 232 235 # define PGM_HCPHYS_2_PTR(pVM, HCPhys, ppv) \ 233 236 MMPagePhys2PageEx(pVM, HCPhys, (void **)(ppv)) 237 #endif 238 239 /** @def PGM_HCPHYS_2_PTR_BY_PGM 240 * Maps a HC physical page pool address to a virtual address. 241 * 242 * @returns VBox status code. 243 * @param pPGM The PGM instance data. 244 * @param HCPhys The HC physical address to map to a virtual one. 245 * @param ppv Where to store the virtual address. No need to cast this. 246 * 247 * @remark In GC this uses PGMGCDynMapHCPage(), so it will consume of the 248 * small page window employeed by that function. Be careful. 249 * @remark There is no need to assert on the result. 250 */ 251 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 252 # define PGM_HCPHYS_2_PTR_BY_PGM(pPGM, HCPhys, ppv) \ 253 pgmR0DynMapHCPageInlined(pPGM, HCPhys, (void **)(ppv)) 254 #else 255 # define PGM_HCPHYS_2_PTR_BY_PGM(pPGM, HCPhys, ppv) \ 256 PGM_HCPHYS_2_PTR(PGM2VM(pPGM), HCPhys, (void **)(ppv)) 234 257 #endif 235 258 … … 246 269 * @remark There is no need to assert on the result. 247 270 */ 248 #if defined(IN_RC) || defined(VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0)271 #ifdef IN_RC 249 272 # define PGM_GCPHYS_2_PTR(pVM, GCPhys, ppv) \ 250 273 PGMDynMapGCPage(pVM, GCPhys, (void **)(ppv)) 274 #elif defined(VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0) 275 # define PGM_GCPHYS_2_PTR(pVM, GCPhys, ppv) \ 276 pgmR0DynMapGCPageInlined(&(pVM)->pgm.s, GCPhys, (void **)(ppv)) 251 277 #else 252 278 # define PGM_GCPHYS_2_PTR(pVM, GCPhys, ppv) \ 253 279 PGMPhysGCPhys2R3Ptr(pVM, GCPhys, 1 /* one page only */, (PRTR3PTR)(ppv)) /** @todo this isn't asserting, use PGMRamGCPhys2HCPtr! */ 280 #endif 281 282 /** @def PGM_GCPHYS_2_PTR_BY_PGM 283 * Maps a GC physical page address to a virtual address. 284 * 285 * @returns VBox status code. 286 * @param pPGM Pointer to the PGM instance data. 287 * @param GCPhys The GC physical address to map to a virtual one. 288 * @param ppv Where to store the virtual address. No need to cast this. 289 * 290 * @remark In GC this uses PGMGCDynMapGCPage(), so it will consume of the 291 * small page window employeed by that function. Be careful. 292 * @remark There is no need to assert on the result. 293 */ 294 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 295 # define PGM_GCPHYS_2_PTR_BY_PGM(pPGM, GCPhys, ppv) \ 296 pgmR0DynMapGCPageInlined(pPGM, GCPhys, (void **)(ppv)) 297 #else 298 # define PGM_GCPHYS_2_PTR_BY_PGM(pPGM, GCPhys, ppv) \ 299 PGM_GCPHYS_2_PTR(PGM2VM(pPGM), GCPhys, ppv) 254 300 #endif 255 301 … … 1253 1299 * The max is UINT16_MAX - 1. */ 1254 1300 uint16_t cRefs; 1301 /** Pointer to the page. */ 1302 RTR0PTR pvPage; 1303 /** The physical address for this entry. */ 1304 RTHCPHYS HCPhys; 1255 1305 } PGMMAPSETENTRY; 1256 1306 /** Pointer to a mapping cache usage set entry. */ … … 1271 1321 /** The entries. */ 1272 1322 PGMMAPSETENTRY aEntries[32]; 1323 /** HCPhys -> iEntry fast lookup table. 1324 * Use PGMMAPSET_HASH for hashing. 1325 * The entries may or may not be valid, check against cEntries. */ 1326 uint8_t aiHashTable[64]; 1273 1327 } PGMMAPSET; 1274 1328 /** Pointer to the mapping cache set. */ … … 1276 1330 1277 1331 /** PGMMAPSET::cEntries value for a closed set. */ 1278 #define PGMMAPSET_CLOSED UINT32_C(0xdeadc0fe) 1332 #define PGMMAPSET_CLOSED UINT32_C(0xdeadc0fe) 1333 1334 /** Hash function for aiHashTable. */ 1335 #define PGMMAPSET_HASH(HCPhys) (((HCPhys) >> PAGE_SHIFT) & 63) 1279 1336 1280 1337 … … 2042 2099 /** Offset to the VM structure. */ 2043 2100 RTINT offVM; 2101 /** Offset of the PGMCPU structure relative to VMCPU. */ 2102 int32_t offVCpu; 2103 /** Alignment padding. */ 2104 int32_t i32Alignment; 2044 2105 2045 2106 /* … … 2561 2622 2562 2623 /* R0 only: */ 2624 STAMCOUNTER StatR0DynMapMigrateInvlPg; /**< R0: invlpg in PGMDynMapMigrateAutoSet. */ 2625 STAMPROFILE StatR0DynMapGCPageInl; /**< R0: Calls to pgmR0DynMapGCPageInlined. */ 2626 STAMCOUNTER StatR0DynMapGCPageInlHits; /**< R0: Hash table lookup hits. */ 2627 STAMCOUNTER StatR0DynMapGCPageInlMisses; /**< R0: Misses that falls back to code common with PGMDynMapHCPage. */ 2628 STAMCOUNTER StatR0DynMapGCPageInlRamHits; /**< R0: 1st ram range hits. */ 2629 STAMCOUNTER StatR0DynMapGCPageInlRamMisses; /**< R0: 1st ram range misses, takes slow path. */ 2630 STAMPROFILE StatR0DynMapHCPageInl; /**< R0: Calls to pgmR0DynMapHCPageInlined. */ 2631 STAMCOUNTER StatR0DynMapHCPageInlHits; /**< R0: Hash table lookup hits. */ 2632 STAMCOUNTER StatR0DynMapHCPageInlMisses; /**< R0: Misses that falls back to code common with PGMDynMapHCPage. */ 2563 2633 STAMPROFILE StatR0DynMapHCPage; /**< R0: Calls to PGMDynMapHCPage. */ 2564 STAMCOUNTER StatR0DynMapHCPageSetOptimize; /**< R0: Calls to pgmDynMapOptimizeAutoSet. */ 2565 STAMCOUNTER StatR0DynMapHCPageSetSearchHits; /**< R0: Set search hits. */ 2566 STAMCOUNTER StatR0DynMapHCPageSetSearchMisses; /**< R0: Set search misses. */ 2567 STAMCOUNTER StatR0DynMapMigrateInvlPg; /**< R0: invlpg in PGMDynMapMigrateAutoSet. */ 2634 STAMCOUNTER StatR0DynMapSetOptimize; /**< R0: Calls to pgmDynMapOptimizeAutoSet. */ 2635 STAMCOUNTER StatR0DynMapSetSearchHits; /**< R0: Set search hits. */ 2636 STAMCOUNTER StatR0DynMapSetSearchMisses; /**< R0: Set search misses. */ 2568 2637 STAMCOUNTER StatR0DynMapPage; /**< R0: Calls to pgmR0DynMapPage. */ 2569 STAMCOUNTER StatR0DynMapPageHit 0; /**< R0: Hitat iPage+0. */2570 STAMCOUNTER StatR0DynMapPageHit 1; /**< R0: Hitat iPage+1. */2571 STAMCOUNTER StatR0DynMapPageHit 2; /**< R0: Hitat iPage+2. */2638 STAMCOUNTER StatR0DynMapPageHits0; /**< R0: Hits at iPage+0. */ 2639 STAMCOUNTER StatR0DynMapPageHits1; /**< R0: Hits at iPage+1. */ 2640 STAMCOUNTER StatR0DynMapPageHits2; /**< R0: Hits at iPage+2. */ 2572 2641 STAMCOUNTER StatR0DynMapPageInvlPg; /**< R0: invlpg. */ 2573 2642 STAMCOUNTER StatR0DynMapPageSlow; /**< R0: Calls to pgmR0DynMapPageSlow. */ … … 2813 2882 int pgmR3PhysRamReset(PVM pVM); 2814 2883 int pgmR3PhysRomReset(PVM pVM); 2815 # ifndef VBOX_WITH_NEW_PHYS_CODE2884 # ifndef VBOX_WITH_NEW_PHYS_CODE 2816 2885 int pgmr3PhysGrowRange(PVM pVM, RTGCPHYS GCPhys); 2817 # endif2886 # endif 2818 2887 2819 2888 int pgmR3PoolInit(PVM pVM); … … 2822 2891 2823 2892 #endif /* IN_RING3 */ 2893 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 2894 int pgmR0DynMapHCPageCommon(PVM pVM, PPGMMAPSET pSet, RTHCPHYS HCPhys, void **ppv); 2895 #endif 2824 2896 #if defined(IN_RC) || defined(VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0) 2825 2897 void *pgmPoolMapPage(PVM pVM, PPGMPOOLPAGE pPage); … … 3157 3229 } 3158 3230 3231 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3232 3233 /** 3234 * Inlined version of the ring-0 version of PGMDynMapHCPage that 3235 * optimizes access to pages already in the set. 3236 * 3237 * @returns See pgmR0DynMapHCPageCommon. 3238 * @param pPGM Pointer to the PVM instance data. 3239 * @param HCPhys The physical address of the page. 3240 * @param ppv Where to store the mapping address. 3241 */ 3242 DECLINLINE(int) pgmR0DynMapHCPageInlined(PPGM pPGM, RTHCPHYS HCPhys, void **ppv) 3243 { 3244 STAM_PROFILE_START(&pPGM->StatR0DynMapHCPageInl, a); 3245 PPGMMAPSET pSet = &((PPGMCPU)((uint8_t *)VMMGetCpu(PGM2VM(pPGM)) + pPGM->offVCpu))->AutoSet; /* very pretty ;-) */ 3246 Assert(!(HCPhys & PAGE_OFFSET_MASK)); 3247 Assert(pSet->cEntries <= RT_ELEMENTS(pSet->aEntries)); 3248 int rc; 3249 3250 unsigned iHash = PGMMAPSET_HASH(HCPhys); 3251 unsigned iEntry = pSet->aiHashTable[iHash]; 3252 if ( iEntry < pSet->cEntries 3253 && pSet->aEntries[iEntry].HCPhys == HCPhys) 3254 { 3255 *ppv = pSet->aEntries[iEntry].pvPage; 3256 STAM_COUNTER_INC(&pPGM->StatR0DynMapHCPageInlHits); 3257 rc = VINF_SUCCESS; 3258 } 3259 else 3260 { 3261 STAM_COUNTER_INC(&pPGM->StatR0DynMapHCPageInlMisses); 3262 rc = pgmR0DynMapHCPageCommon(PGM2VM(pPGM), pSet, HCPhys, ppv); 3263 } 3264 3265 STAM_PROFILE_STOP(&pPGM->StatR0DynMapHCPageInl, a); 3266 return rc; 3267 } 3268 3269 3270 /** 3271 * Inlined version of the ring-0 version of PGMDynMapGCPage that optimizes 3272 * access to pages already in the set. 3273 * 3274 * @returns See pgmR0DynMapHCPageCommon. 3275 * @param pPGM Pointer to the PVM instance data. 3276 * @param HCPhys The physical address of the page. 3277 * @param ppv Where to store the mapping address. 3278 */ 3279 DECLINLINE(int) pgmR0DynMapGCPageInlined(PPGM pPGM, RTGCPHYS GCPhys, void **ppv) 3280 { 3281 STAM_PROFILE_START(&pPGM->StatR0DynMapGCPageInl, a); 3282 Assert(!(GCPhys & PAGE_OFFSET_MASK)); 3283 3284 /* 3285 * Get the ram range. 3286 */ 3287 PPGMRAMRANGE pRam = pPGM->CTX_SUFF(pRamRanges); 3288 RTGCPHYS off = GCPhys - pRam->GCPhys; 3289 if (RT_UNLIKELY(off >= pRam->cb 3290 /** @todo || page state stuff */)) 3291 { 3292 /* This case is not counted into StatR0DynMapGCPageInl. */ 3293 STAM_COUNTER_INC(&pPGM->StatR0DynMapGCPageInlRamMisses); 3294 return PGMDynMapGCPage(PGM2VM(pPGM), GCPhys, ppv); 3295 } 3296 3297 RTHCPHYS HCPhys = PGM_PAGE_GET_HCPHYS(&pRam->aPages[off >> PAGE_SHIFT]); 3298 STAM_COUNTER_INC(&pPGM->StatR0DynMapGCPageInlRamHits); 3299 3300 /* 3301 * pgmR0DynMapHCPageInlined with out stats. 3302 */ 3303 PPGMMAPSET pSet = &((PPGMCPU)((uint8_t *)VMMGetCpu(PGM2VM(pPGM)) + pPGM->offVCpu))->AutoSet; /* very pretty ;-) */ 3304 Assert(!(HCPhys & PAGE_OFFSET_MASK)); 3305 Assert(pSet->cEntries <= RT_ELEMENTS(pSet->aEntries)); 3306 int rc; 3307 3308 unsigned iHash = PGMMAPSET_HASH(HCPhys); 3309 unsigned iEntry = pSet->aiHashTable[iHash]; 3310 if ( iEntry < pSet->cEntries 3311 && pSet->aEntries[iEntry].HCPhys == HCPhys) 3312 { 3313 *ppv = pSet->aEntries[iEntry].pvPage; 3314 STAM_COUNTER_INC(&pPGM->StatR0DynMapGCPageInlHits); 3315 rc = VINF_SUCCESS; 3316 } 3317 else 3318 { 3319 STAM_COUNTER_INC(&pPGM->StatR0DynMapGCPageInlMisses); 3320 rc = pgmR0DynMapHCPageCommon(PGM2VM(pPGM), pSet, HCPhys, ppv); 3321 } 3322 3323 STAM_PROFILE_STOP(&pPGM->StatR0DynMapGCPageInl, a); 3324 return rc; 3325 } 3326 3327 #endif /* VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 */ 3159 3328 3160 3329 #ifndef IN_RC … … 3393 3562 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3394 3563 PCX86PD pGuestPD = 0; 3395 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPD);3564 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPD); 3396 3565 if (RT_FAILURE(rc)) 3397 3566 { … … 3417 3586 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3418 3587 PX86PD pGuestPD = 0; 3419 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPD);3588 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPD); 3420 3589 AssertRCReturn(rc, 0); 3421 3590 return &pGuestPD->a[GCPtr >> X86_PD_SHIFT]; … … 3436 3605 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3437 3606 PX86PD pGuestPD = 0; 3438 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPD);3607 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPD); 3439 3608 AssertRCReturn(rc, 0); 3440 3609 return pGuestPD; … … 3456 3625 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3457 3626 PX86PDPT pGuestPDPT = 0; 3458 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPDPT);3627 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPDPT); 3459 3628 AssertRCReturn(rc, 0); 3460 3629 return pGuestPDPT; … … 3479 3648 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3480 3649 PX86PDPT pGuestPDPT = 0; 3481 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPDPT);3650 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPDPT); 3482 3651 AssertRCReturn(rc, 0); 3483 3652 return &pGuestPDPT->a[(GCPtr >> X86_PDPT_SHIFT) & X86_PDPT_MASK_PAE]; … … 3516 3685 /* cache is out-of-sync. */ 3517 3686 PX86PDPAE pPD; 3518 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3687 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3519 3688 if (RT_SUCCESS(rc)) 3520 3689 return pPD; … … 3555 3724 /* The cache is out-of-sync. */ 3556 3725 PX86PDPAE pPD; 3557 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3726 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3558 3727 if (RT_SUCCESS(rc)) 3559 3728 return &pPD->a[iPD]; … … 3595 3764 /* cache is out-of-sync. */ 3596 3765 PX86PDPAE pPD; 3597 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3766 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3598 3767 if (RT_SUCCESS(rc)) 3599 3768 return pPD->a[iPD]; … … 3643 3812 /* cache is out-of-sync. */ 3644 3813 PX86PDPAE pPD; 3645 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3814 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPDPT->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3646 3815 if (RT_SUCCESS(rc)) 3647 3816 { … … 3667 3836 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3668 3837 PX86PML4 pGuestPml4; 3669 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPml4);3838 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPml4); 3670 3839 AssertRCReturn(rc, NULL); 3671 3840 return pGuestPml4; … … 3688 3857 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3689 3858 PX86PML4 pGuestPml4; 3690 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPml4);3859 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPml4); 3691 3860 AssertRCReturn(rc, NULL); 3692 3861 return &pGuestPml4->a[iPml4]; … … 3709 3878 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 3710 3879 PX86PML4 pGuestPml4; 3711 int rc = PGMDynMapGCPage(PGM2VM(pPGM), pPGM->GCPhysCR3, (void **)&pGuestPml4);3880 int rc = pgmR0DynMapGCPageInlined(pPGM, pPGM->GCPhysCR3, (void **)&pGuestPml4); 3712 3881 if (RT_FAILURE(rc)) 3713 3882 { … … 3740 3909 { 3741 3910 PX86PDPT pPdpt; 3742 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPml4e->u & X86_PML4E_PG_MASK, &pPdpt);3911 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPml4e->u & X86_PML4E_PG_MASK, &pPdpt); 3743 3912 AssertRCReturn(rc, NULL); 3744 3913 … … 3769 3938 { 3770 3939 PCX86PDPT pPdptTemp; 3771 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPml4e->u & X86_PML4E_PG_MASK, &pPdptTemp);3940 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPml4e->u & X86_PML4E_PG_MASK, &pPdptTemp); 3772 3941 AssertRCReturn(rc, ZeroPde); 3773 3942 … … 3777 3946 { 3778 3947 PCX86PDPAE pPD; 3779 rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3948 rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3780 3949 AssertRCReturn(rc, ZeroPde); 3781 3950 … … 3805 3974 { 3806 3975 PCX86PDPT pPdptTemp; 3807 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp);3976 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp); 3808 3977 AssertRCReturn(rc, ZeroPde); 3809 3978 … … 3812 3981 { 3813 3982 PCX86PDPAE pPD; 3814 rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);3983 rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3815 3984 AssertRCReturn(rc, ZeroPde); 3816 3985 … … 3838 4007 { 3839 4008 PCX86PDPT pPdptTemp; 3840 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp);4009 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp); 3841 4010 AssertRCReturn(rc, NULL); 3842 4011 … … 3845 4014 { 3846 4015 PX86PDPAE pPD; 3847 rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);4016 rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3848 4017 AssertRCReturn(rc, NULL); 3849 4018 … … 3875 4044 { 3876 4045 PCX86PDPT pPdptTemp; 3877 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPml4e->u & X86_PML4E_PG_MASK, &pPdptTemp);4046 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPml4e->u & X86_PML4E_PG_MASK, &pPdptTemp); 3878 4047 AssertRCReturn(rc, NULL); 3879 4048 … … 3883 4052 { 3884 4053 PX86PDPAE pPD; 3885 rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);4054 rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 3886 4055 AssertRCReturn(rc, NULL); 3887 4056 … … 3910 4079 PX86PD pShwPd; 3911 4080 Assert(pPGM->HCPhysShw32BitPD != 0 && pPGM->HCPhysShw32BitPD != NIL_RTHCPHYS); 3912 int rc = PGM_HCPHYS_2_PTR (PGM2VM(pPGM), pPGM->HCPhysShw32BitPD, &pShwPd);4081 int rc = PGM_HCPHYS_2_PTR_BY_PGM(pPGM, pPGM->HCPhysShw32BitPD, &pShwPd); 3913 4082 AssertRCReturn(rc, NULL); 3914 4083 return pShwPd; … … 3973 4142 PX86PDPT pShwPdpt; 3974 4143 Assert(pPGM->HCPhysShwPaePdpt != 0 && pPGM->HCPhysShwPaePdpt != NIL_RTHCPHYS); 3975 int rc = PGM_HCPHYS_2_PTR (PGM2VM(pPGM), pPGM->HCPhysShwPaePdpt, &pShwPdpt);4144 int rc = PGM_HCPHYS_2_PTR_BY_PGM(pPGM, pPGM->HCPhysShwPaePdpt, &pShwPdpt); 3976 4145 AssertRCReturn(rc, 0); 3977 4146 return pShwPdpt; … … 4005 4174 # ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 4006 4175 PX86PDPAE pPD; 4007 int rc = PGM_HCPHYS_2_PTR (PGM2VM(pPGM), pPGM->aHCPhysPaePDs[iPdpt], &pPD);4176 int rc = PGM_HCPHYS_2_PTR_BY_PGM(pPGM, pPGM->aHCPhysPaePDs[iPdpt], &pPD); 4008 4177 AssertRCReturn(rc, 0); 4009 4178 return pPD; … … 4070 4239 PX86PML4 pShwPml4; 4071 4240 Assert(pPGM->HCPhysShwPaePml4 != 0 && pPGM->HCPhysShwPaePml4 != NIL_RTHCPHYS); 4072 int rc = PGM_HCPHYS_2_PTR (PGM2VM(pPGM), pPGM->HCPhysShwPaePml4, &pShwPml4);4241 int rc = PGM_HCPHYS_2_PTR_BY_PGM(pPGM, pPGM->HCPhysShwPaePml4, &pShwPml4); 4073 4242 AssertRCReturn(rc, 0); 4074 4243 return pShwPml4; … … 4136 4305 { 4137 4306 PCX86PDPT pPdptTemp; 4138 int rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp);4307 int rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pGuestPml4->a[iPml4].u & X86_PML4E_PG_MASK, &pPdptTemp); 4139 4308 AssertRCReturn(rc, NULL); 4140 4309 … … 4143 4312 { 4144 4313 PX86PDPAE pPD; 4145 rc = PGM_GCPHYS_2_PTR (PGM2VM(pPGM), pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD);4314 rc = PGM_GCPHYS_2_PTR_BY_PGM(pPGM, pPdptTemp->a[iPdPt].u & X86_PDPE_PG_MASK, &pPD); 4146 4315 AssertRCReturn(rc, NULL); 4147 4316 -
trunk/src/VBox/VMM/VMMAll/PGMAll.cpp
r15226 r15344 1850 1850 RTHCPHYS HCPhys = PGM_PAGE_GET_HCPHYS(&pRam->aPages[(GCPhys - pRam->GCPhys) >> PAGE_SHIFT]); 1851 1851 //Log(("PGMDynMapGCPage: GCPhys=%RGp HCPhys=%RHp\n", GCPhys, HCPhys)); 1852 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 1853 return pgmR0DynMapHCPageInlined(&pVM->pgm.s, HCPhys, ppv); 1854 #else 1852 1855 return PGMDynMapHCPage(pVM, HCPhys, ppv); 1856 #endif 1853 1857 } 1854 1858 … … 1887 1891 */ 1888 1892 RTHCPHYS HCPhys = PGM_PAGE_GET_HCPHYS(&pRam->aPages[(GCPhys - pRam->GCPhys) >> PAGE_SHIFT]); 1893 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 1894 int rc = pgmR0DynMapHCPageInlined(&pVM->pgm.s, HCPhys, ppv); 1895 #else 1889 1896 int rc = PGMDynMapHCPage(pVM, HCPhys, ppv); 1897 #endif 1890 1898 if (RT_SUCCESS(rc)) 1891 1899 *ppv = (void *)((uintptr_t)*ppv | (GCPhys & PAGE_OFFSET_MASK)); -
trunk/src/VBox/VMM/VMMAll/PGMAllPhys.cpp
r15284 r15344 500 500 RTHCPHYS HCPhys = PGM_PAGE_GET_HCPHYS(pPage); 501 501 Assert(HCPhys != pVM->pgm.s.HCPhysZeroPg); 502 # ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 503 return pgmR0DynMapHCPageInlined(&pVM->pgm.s, HCPhys, ppv); 504 # else 502 505 return PGMDynMapHCPage(pVM, HCPhys, ppv); 506 # endif 503 507 504 508 #else /* IN_RING3 || IN_RING0 */ -
trunk/src/VBox/VMM/VMMAll/PGMAllPool.cpp
r14809 r15344 102 102 Assert(pPage->idx < pVM->pgm.s.CTX_SUFF(pPool)->cCurPages); 103 103 void *pv; 104 # ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 105 int rc = pgmR0DynMapHCPageInlined(&pVM->pgm.s, pPage->Core.Key, &pv); 106 # else 104 107 int rc = PGMDynMapHCPage(pVM, pPage->Core.Key, &pv); 108 # endif 105 109 AssertReleaseRC(rc); 106 110 return pv; … … 159 163 } 160 164 void *pv; 161 int rc = PGMDynMapHCPage(pVM, HCPhys, &pv);165 int rc = pgmR0DynMapHCPageInlined(&pVM->pgm.s, HCPhys, &pv); 162 166 AssertReleaseRC(rc); 163 167 return pv; -
trunk/src/VBox/VMM/VMMR0/HWVMXR0.cpp
r15307 r15344 2040 2040 #endif 2041 2041 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R0 2042 PGMDynMap ReleaseAutoSet(pVCpu);2042 PGMDynMapFlushAutoSet(pVCpu); 2043 2043 #endif 2044 2044 … … 2195 2195 STAM_PROFILE_ADV_STOP(&pVCpu->hwaccm.s.StatExit1, v); 2196 2196 STAM_STATS({ STAM_PROFILE_ADV_START(&pVCpu->hwaccm.s.StatExit2, y); fStatExit2Started = true; }); 2197 2198 #ifdef VBOX_WITH_2X_4GB_ADDR_SPACE_IN_R02199 PGMDynMapStartAutoSet(pVCpu);2200 #endif2201 2197 2202 2198 /* Some cases don't need a complete resync of the guest CPU state; handle them here. */ -
trunk/src/VBox/VMM/VMMR0/PGMR0DynMap.cpp
r15257 r15344 361 361 while (j-- > 0) 362 362 { 363 pSet->aEntries[j].iPage = UINT16_MAX; 364 pSet->aEntries[j].cRefs = 0; 363 pSet->aEntries[j].iPage = UINT16_MAX; 364 pSet->aEntries[j].cRefs = 0; 365 pSet->aEntries[j].pvPage = NULL; 366 pSet->aEntries[j].HCPhys = NIL_RTHCPHYS; 365 367 } 366 368 pSet->cEntries = PGMMAPSET_CLOSED; 369 memset(&pSet->aiHashTable[0], 0xff, sizeof(pSet->aiHashTable)); 367 370 } 368 371 … … 456 459 AssertLogRelMsgFailed(("cRefs=%d iPage=%#x cPages=%u\n", cRefs, iPage, pThis->cPages)); 457 460 458 pSet->aEntries[j].iPage = UINT16_MAX; 459 pSet->aEntries[j].cRefs = 0; 461 pSet->aEntries[j].iPage = UINT16_MAX; 462 pSet->aEntries[j].cRefs = 0; 463 pSet->aEntries[j].pvPage = NULL; 464 pSet->aEntries[j].HCPhys = NIL_RTHCPHYS; 460 465 } 461 466 pSet->cEntries = PGMMAPSET_CLOSED; … … 1289 1294 PPGMR0DYNMAPENTRY paPages = pThis->paPages; 1290 1295 if (RT_LIKELY(paPages[iPage].HCPhys == HCPhys)) 1291 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHit 0);1296 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHits0); 1292 1297 else 1293 1298 { … … 1296 1301 { 1297 1302 iPage = iPage2; 1298 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHit 1);1303 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHits1); 1299 1304 } 1300 1305 else … … 1304 1309 { 1305 1310 iPage = iPage2; 1306 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHit 2);1311 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapPageHits2); 1307 1312 } 1308 1313 else … … 1496 1501 1497 1502 /** 1503 * Worker that performs the actual flushing of the set. 1504 * 1505 * @param pSet The set to flush. 1506 * @param cEntries The number of entries. 1507 */ 1508 DECLINLINE(void) pgmDynMapFlushAutoSetWorker(PPGMMAPSET pSet, uint32_t cEntries) 1509 { 1510 /* 1511 * Release any pages it's referencing. 1512 */ 1513 if ( cEntries != 0 1514 && RT_LIKELY(cEntries <= RT_ELEMENTS(pSet->aEntries))) 1515 { 1516 PPGMR0DYNMAP pThis = g_pPGMR0DynMap; 1517 RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER; 1518 RTSpinlockAcquire(pThis->hSpinlock, &Tmp); 1519 1520 uint32_t i = cEntries; 1521 while (i-- > 0) 1522 { 1523 uint32_t iPage = pSet->aEntries[i].iPage; 1524 Assert(iPage < pThis->cPages); 1525 int32_t cRefs = pSet->aEntries[i].cRefs; 1526 Assert(cRefs > 0); 1527 pgmR0DynMapReleasePageLocked(pThis, iPage, cRefs); 1528 1529 pSet->aEntries[i].iPage = UINT16_MAX; 1530 pSet->aEntries[i].cRefs = 0; 1531 } 1532 1533 Assert(pThis->cLoad <= pThis->cPages - pThis->cGuardPages); 1534 RTSpinlockRelease(pThis->hSpinlock, &Tmp); 1535 } 1536 } 1537 1538 1539 /** 1498 1540 * Releases the dynamic memory mappings made by PGMDynMapHCPage and associates 1499 1541 * since the PGMDynMapStartAutoSet call. 1500 1542 * 1501 * If the set is already closed, nothing will be done.1502 *1503 1543 * @param pVCpu The shared data for the current virtual CPU. 1504 1544 */ … … 1508 1548 1509 1549 /* 1510 * Is the set open? 1511 * 1512 * We might be closed before VM execution and not reopened again before 1513 * we leave for ring-3 or something. 1514 */ 1515 uint32_t i = pSet->cEntries; 1516 if (i != PGMMAPSET_CLOSED) 1517 { 1518 /* 1519 * Close the set 1520 */ 1521 AssertMsg(i <= RT_ELEMENTS(pSet->aEntries), ("%#x (%u)\n", i, i)); 1522 pSet->cEntries = PGMMAPSET_CLOSED; 1523 1524 /* 1525 * Release any pages it's referencing. 1526 */ 1527 if (i != 0 && RT_LIKELY(i <= RT_ELEMENTS(pSet->aEntries))) 1528 { 1529 PPGMR0DYNMAP pThis = g_pPGMR0DynMap; 1530 RTSPINLOCKTMP Tmp = RTSPINLOCKTMP_INITIALIZER; 1531 RTSpinlockAcquire(pThis->hSpinlock, &Tmp); 1532 1533 while (i-- > 0) 1534 { 1535 uint32_t iPage = pSet->aEntries[i].iPage; 1536 Assert(iPage < pThis->cPages); 1537 int32_t cRefs = pSet->aEntries[i].cRefs; 1538 Assert(cRefs > 0); 1539 pgmR0DynMapReleasePageLocked(pThis, iPage, cRefs); 1540 1541 pSet->aEntries[i].iPage = UINT16_MAX; 1542 pSet->aEntries[i].cRefs = 0; 1543 } 1544 1545 Assert(pThis->cLoad <= pThis->cPages - pThis->cGuardPages); 1546 RTSpinlockRelease(pThis->hSpinlock, &Tmp); 1547 } 1548 } 1549 } 1550 * Close and flush the set. 1551 */ 1552 uint32_t cEntries = pSet->cEntries; 1553 AssertReturnVoid(cEntries != PGMMAPSET_CLOSED); 1554 AssertMsg(cEntries <= RT_ELEMENTS(pSet->aEntries), ("%#x (%u)\n", cEntries, cEntries)); 1555 pSet->cEntries = PGMMAPSET_CLOSED; 1556 1557 pgmDynMapFlushAutoSetWorker(pSet, cEntries); 1558 } 1559 1560 1561 /** 1562 * Flushes the set if it's above a certain threshold. 1563 * 1564 * @param pVCpu The shared data for the current virtual CPU. 1565 */ 1566 VMMDECL(void) PGMDynMapFlushAutoSet(PVMCPU pVCpu) 1567 { 1568 PPGMMAPSET pSet = &pVCpu->pgm.s.AutoSet; 1569 1570 /* 1571 * Only flush it if it's 50% full. 1572 */ 1573 uint32_t cEntries = pSet->cEntries; 1574 AssertReturnVoid(cEntries != PGMMAPSET_CLOSED); 1575 if (cEntries >= RT_ELEMENTS(pSet->aEntries) / 2) 1576 { 1577 AssertMsg(cEntries <= RT_ELEMENTS(pSet->aEntries), ("%#x (%u)\n", cEntries, cEntries)); 1578 pSet->cEntries = 0; 1579 1580 pgmDynMapFlushAutoSetWorker(pSet, cEntries); 1581 } 1582 } 1583 1550 1584 1551 1585 … … 1638 1672 1639 1673 1640 /* documented elsewhere - a bit of a mess. 1641 This is a VERY hot path. */ 1642 VMMDECL(int) PGMDynMapHCPage(PVM pVM, RTHCPHYS HCPhys, void **ppv) 1643 { 1644 /* 1645 * Validate state. 1646 */ 1647 STAM_PROFILE_START(&pVM->pgm.s.StatR0DynMapHCPage, a); 1648 AssertPtr(ppv); 1649 *ppv = NULL; 1650 AssertMsgReturn(pVM->pgm.s.pvR0DynMapUsed == g_pPGMR0DynMap, 1651 ("%p != %p\n", pVM->pgm.s.pvR0DynMapUsed, g_pPGMR0DynMap), 1652 VERR_ACCESS_DENIED); 1653 AssertMsg(!(HCPhys & PAGE_OFFSET_MASK), ("HCPhys=%RHp\n", HCPhys)); 1654 PVMCPU pVCpu = VMMGetCpu(pVM); 1655 PPGMMAPSET pSet = &pVCpu->pgm.s.AutoSet; 1656 AssertPtrReturn(pVCpu, VERR_INTERNAL_ERROR); 1657 AssertMsgReturn(pSet->cEntries <= RT_ELEMENTS(pSet->aEntries), 1658 ("%#x (%u)\n", pSet->cEntries, pSet->cEntries), VERR_WRONG_ORDER); 1659 1674 /** 1675 * Common worker code for PGMDynMapHCPhys, pgmR0DynMapHCPageInlined and 1676 * pgmR0DynMapGCPageInlined. 1677 * 1678 * @returns VBox status code. 1679 * @param pVM The shared VM structure (for statistics). 1680 * @param pSet The set. 1681 * @param HCPhys The physical address of the page. 1682 * @param ppv Where to store the address of the mapping on success. 1683 */ 1684 int pgmR0DynMapHCPageCommon(PVM pVM, PPGMMAPSET pSet, RTHCPHYS HCPhys, void **ppv) 1685 { 1660 1686 /* 1661 1687 * Map it. 1662 1688 */ 1663 uint32_t const iPage = pgmR0DynMapPage(g_pPGMR0DynMap, HCPhys, pVM, ppv); 1689 void *pvPage; 1690 uint32_t const iPage = pgmR0DynMapPage(g_pPGMR0DynMap, HCPhys, pVM, &pvPage); 1664 1691 if (RT_UNLIKELY(iPage == UINT32_MAX)) 1665 1692 { 1666 STAM_PROFILE_STOP(&pVM->pgm.s.StatR0DynMapHCPage, a);1667 1693 static uint32_t s_cBitched = 0; 1668 1694 if (++s_cBitched < 10) 1669 1695 LogRel(("PGMDynMapHCPage: cLoad=%u/%u cPages=%u cGuardPages=%u\n", 1670 1696 g_pPGMR0DynMap->cLoad, g_pPGMR0DynMap->cMaxLoad, g_pPGMR0DynMap->cPages, g_pPGMR0DynMap->cGuardPages)); 1697 *ppv = NULL; 1671 1698 return VERR_PGM_DYNMAP_FAILED; 1672 1699 } … … 1684 1711 if (i-- < 5) 1685 1712 { 1686 pSet->aEntries[pSet->cEntries].cRefs = 1; 1687 pSet->aEntries[pSet->cEntries].iPage = iPage; 1688 pSet->cEntries++; 1713 unsigned iEntry = pSet->cEntries++; 1714 pSet->aEntries[iEntry].cRefs = 1; 1715 pSet->aEntries[iEntry].iPage = iPage; 1716 pSet->aEntries[iEntry].pvPage = pvPage; 1717 pSet->aEntries[iEntry].HCPhys = HCPhys; 1718 pSet->aiHashTable[PGMMAPSET_HASH(HCPhys)] = iEntry; 1689 1719 } 1690 1720 /* Any of the last 5 pages? */ … … 1707 1737 else if (RT_LIKELY(i <= (int32_t)RT_ELEMENTS(pSet->aEntries) / 4 * 3)) 1708 1738 { 1709 pSet->aEntries[pSet->cEntries].cRefs = 1; 1710 pSet->aEntries[pSet->cEntries].iPage = iPage; 1711 pSet->cEntries++; 1739 unsigned iEntry = pSet->cEntries++; 1740 pSet->aEntries[iEntry].cRefs = 1; 1741 pSet->aEntries[iEntry].iPage = iPage; 1742 pSet->aEntries[iEntry].pvPage = pvPage; 1743 pSet->aEntries[iEntry].HCPhys = HCPhys; 1744 pSet->aiHashTable[PGMMAPSET_HASH(HCPhys)] = iEntry; 1712 1745 } 1713 1746 else … … 1721 1754 { 1722 1755 pSet->aEntries[i].cRefs++; 1723 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMap HCPageSetSearchHits);1756 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapSetSearchHits); 1724 1757 break; 1725 1758 } 1726 1759 if (i < 0) 1727 1760 { 1728 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMap HCPageSetSearchMisses);1761 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapSetSearchMisses); 1729 1762 if (RT_UNLIKELY(pSet->cEntries >= RT_ELEMENTS(pSet->aEntries))) 1730 1763 { 1731 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMap HCPageSetOptimize);1764 STAM_COUNTER_INC(&pVM->pgm.s.StatR0DynMapSetOptimize); 1732 1765 pgmDynMapOptimizeAutoSet(pSet); 1733 1766 } 1734 1767 if (RT_LIKELY(pSet->cEntries < RT_ELEMENTS(pSet->aEntries))) 1735 1768 { 1736 pSet->aEntries[pSet->cEntries].cRefs = 1; 1737 pSet->aEntries[pSet->cEntries].iPage = iPage; 1738 pSet->cEntries++; 1769 unsigned iEntry = pSet->cEntries++; 1770 pSet->aEntries[iEntry].cRefs = 1; 1771 pSet->aEntries[iEntry].iPage = iPage; 1772 pSet->aEntries[iEntry].pvPage = pvPage; 1773 pSet->aEntries[iEntry].HCPhys = HCPhys; 1774 pSet->aiHashTable[PGMMAPSET_HASH(HCPhys)] = iEntry; 1739 1775 } 1740 1776 else … … 1743 1779 pgmR0DynMapReleasePage(g_pPGMR0DynMap, iPage, 1); 1744 1780 1745 STAM_PROFILE_STOP(&pVM->pgm.s.StatR0DynMapHCPage, a);1746 1781 static uint32_t s_cBitched = 0; 1747 1782 if (++s_cBitched < 10) … … 1753 1788 } 1754 1789 1790 *ppv = pvPage; 1791 return VINF_SUCCESS; 1792 } 1793 1794 1795 /* documented elsewhere - a bit of a mess. 1796 This is a VERY hot path. */ 1797 VMMDECL(int) PGMDynMapHCPage(PVM pVM, RTHCPHYS HCPhys, void **ppv) 1798 { 1799 /* 1800 * Validate state. 1801 */ 1802 STAM_PROFILE_START(&pVM->pgm.s.StatR0DynMapHCPage, a); 1803 AssertPtr(ppv); 1804 AssertMsgReturn(pVM->pgm.s.pvR0DynMapUsed == g_pPGMR0DynMap, 1805 ("%p != %p\n", pVM->pgm.s.pvR0DynMapUsed, g_pPGMR0DynMap), 1806 VERR_ACCESS_DENIED); 1807 AssertMsg(!(HCPhys & PAGE_OFFSET_MASK), ("HCPhys=%RHp\n", HCPhys)); 1808 PVMCPU pVCpu = VMMGetCpu(pVM); 1809 PPGMMAPSET pSet = &pVCpu->pgm.s.AutoSet; 1810 AssertPtrReturn(pVCpu, VERR_INTERNAL_ERROR); 1811 AssertMsgReturn(pSet->cEntries <= RT_ELEMENTS(pSet->aEntries), 1812 ("%#x (%u)\n", pSet->cEntries, pSet->cEntries), VERR_WRONG_ORDER); 1813 1814 /* 1815 * Call common code. 1816 */ 1817 int rc = pgmR0DynMapHCPageCommon(pVM, pSet, HCPhys, ppv); 1818 1755 1819 STAM_PROFILE_STOP(&pVM->pgm.s.StatR0DynMapHCPage, a); 1756 return VINF_SUCCESS;1820 return rc; 1757 1821 } 1758 1822 … … 1979 2043 ASMIntDisable(); 1980 2044 PGMDynMapMigrateAutoSet(&pVM->aCpus[0]); 2045 PGMDynMapFlushAutoSet(&pVM->aCpus[0]); 1981 2046 PGMDynMapReleaseAutoSet(&pVM->aCpus[0]); 1982 2047 ASMIntEnable();
Note:
See TracChangeset
for help on using the changeset viewer.