Changeset 77193 in vbox for trunk/src/VBox
- Timestamp:
- Feb 7, 2019 10:06:19 AM (6 years ago)
- Location:
- trunk/src/VBox/Devices/Graphics
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Graphics/DevVGA-SVGA.cpp
r77151 r77193 143 143 # include <iprt/ctype.h> 144 144 # include <iprt/mem.h> 145 // # ifdef DEBUG 146 # include <iprt/time.h> 147 // # endif 145 148 #endif 146 149 … … 242 245 /** Information obout screens. */ 243 246 VMSVGASCREENOBJECT aScreens[64]; 247 248 // #ifdef DEBUG 249 /** The time the access handler for the FIFO last triggered. This should 250 * never happen less than a certain interval from the last access, and we 251 * assert this. */ 252 uint64_t TimeLastFIFOIntercept; 253 // #endif 244 254 245 255 /** Tracks how much time we waste reading SVGA_REG_BUSY with a busy FIFO. */ … … 314 324 STAMCOUNTER StatFifoTodoWoken; 315 325 STAMPROFILE StatFifoStalls; 326 STAMCOUNTER StatFifoAccessHandler; 316 327 317 328 } VMSVGAR3STATE, *PVMSVGAR3STATE; … … 323 334 *********************************************************************************************************************************/ 324 335 #ifdef IN_RING3 325 # ifdef DEBUG_FIFO_ACCESS326 336 static FNPGMPHYSHANDLER vmsvgaR3FIFOAccessHandler; 327 # endif328 337 # ifdef DEBUG_GMR_ACCESS 329 338 static FNPGMPHYSHANDLER vmsvgaR3GMRAccessHandler; … … 399 408 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, hBusyDelayedEmts), 400 409 #endif 410 // #ifdef DEBUG 411 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, TimeLastFIFOIntercept), 412 // #endif 401 413 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, StatBusyDelayEmts), 402 414 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, StatR3Cmd3dPresentProf), … … 468 480 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, StatFifoTodoWoken), 469 481 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, StatFifoStalls), 482 SSMFIELD_ENTRY_IGNORE( VMSVGAR3STATE, StatFifoAccessHandler), 470 483 SSMFIELD_ENTRY_TERM() 471 484 }; … … 1997 2010 } 1998 2011 1999 #ifdef DEBUG_FIFO_ACCESS2000 2001 # ifdef IN_RING32012 #ifdef IN_RING3 2013 2014 # ifdef DEBUG_FIFO_ACCESS 2002 2015 /** 2003 2016 * Handle FIFO memory access. … … 2008 2021 * @param fWriteAccess Read or write access 2009 2022 */ 2010 static int vmsvga FIFOAccess(PVM pVM, PVGASTATE pThis, RTGCPHYS GCPhys, bool fWriteAccess)2023 static int vmsvgaDebugFIFOAccess(PVM pVM, PVGASTATE pThis, RTGCPHYS GCPhys, bool fWriteAccess) 2011 2024 { 2012 2025 RT_NOREF(pVM); … … 2338 2351 return VINF_EM_RAW_EMULATE_INSTR; 2339 2352 } 2353 2354 # endif /* DEBUG_FIFO_ACCESS */ 2340 2355 2341 2356 /** … … 2364 2379 NOREF(pVCpu); NOREF(pvPhys); NOREF(pvBuf); NOREF(cbBuf); NOREF(enmOrigin); 2365 2380 2366 rc = vmsvgaFIFOAccess(pVM, pThis, GCPhys, enmAccessType == PGMACCESSTYPE_WRITE); 2381 SUPSemEventSignal(pThis->svga.pSupDrvSession, pThis->svga.FIFORequestSem); 2382 # ifdef DEBUG_FIFO_ACCESS 2383 rc = vmsvgaDebugFIFOAccess(pVM, pThis, GCPhys, enmAccessType == PGMACCESSTYPE_WRITE); 2384 # else 2385 NOREF(enmAccessType); 2386 // # ifdef DEBUG 2387 /* Invariant: the access handler should never trigger twice within a certain 2388 * time span; calling it 500ms here for simplicity. */ 2389 uint64_t TimeNow = RTTimeMilliTS(); 2390 Assert(TimeNow - pThis->svga.pSvgaR3State->TimeLastFIFOIntercept > 500); 2391 pThis->svga.pSvgaR3State->TimeLastFIFOIntercept = TimeNow; 2392 // # endif 2393 STAM_REL_COUNTER_INC(&pThis->svga.pSvgaR3State->StatFifoAccessHandler); 2394 rc = PGMHandlerPhysicalPageTempOff(pVM, pThis->svga.GCPhysFIFO, pThis->svga.GCPhysFIFO); 2395 # endif 2367 2396 if (RT_SUCCESS(rc)) 2368 2397 return VINF_PGM_HANDLER_DO_DEFAULT; … … 2371 2400 } 2372 2401 2373 # endif /* IN_RING3 */ 2374 #endif /* DEBUG_FIFO_ACCESS */ 2402 #endif /* IN_RING3 */ 2375 2403 2376 2404 #ifdef DEBUG_GMR_ACCESS … … 3214 3242 } 3215 3243 3244 static bool vmsvgaFIFOHasWork(uint32_t RT_UNTRUSTED_VOLATILE_GUEST * const pFIFO, 3245 uint32_t cCursorCount) 3246 { 3247 return pFIFO[SVGA_FIFO_NEXT_CMD] != pFIFO[SVGA_FIFO_STOP] 3248 || cCursorCount != pFIFO[SVGA_FIFO_CURSOR_COUNT]; 3249 } 3250 3216 3251 /* The async FIFO handling thread. */ 3217 3252 static DECLCALLBACK(int) vmsvgaFIFOLoop(PPDMDEVINS pDevIns, PPDMTHREAD pThread) … … 3259 3294 * We wait for an a short interval if the guest has recently given us work 3260 3295 * to do, but the interval increases the longer we're kept idle. With the 3261 * current parameters we'll be at a 6 4ms poll interval after 1 idle second,3262 * at 90ms after 2 seconds, and reach the max 250ms interval after about3263 * 16 seconds.3296 * current parameters we'll be at a 66ms poll interval after 1 idle second. 3297 * When we reach the maximum we switch to intercepting accesses and after 3298 * one intercept we restart polling at minimum. 3264 3299 */ 3265 3300 RTMSINTERVAL const cMsMinSleep = 16; 3266 3301 RTMSINTERVAL const cMsIncSleep = 2; 3267 RTMSINTERVAL const cMsMaxSleep = 250;3302 RTMSINTERVAL const cMsMaxSleep = 66; 3268 3303 RTMSINTERVAL cMsSleep = cMsMaxSleep; 3269 3304 … … 3296 3331 * (See polling/sleep interval config above.) 3297 3332 */ 3298 if ( fBadOrDisabledFifo 3299 || pFIFO[SVGA_FIFO_NEXT_CMD] == pFIFO[SVGA_FIFO_STOP]) 3300 { 3301 rc = SUPSemEventWaitNoResume(pThis->svga.pSupDrvSession, pThis->svga.FIFORequestSem, cMsSleep); 3333 if (fBadOrDisabledFifo || !vmsvgaFIFOHasWork(pFIFO, cCursorCount)) 3334 { 3335 if (cMsSleep >= cMsMaxSleep && pThis->svga.GCPhysFIFO) 3336 { 3337 rc = PGMHandlerPhysicalReset(PDMDevHlpGetVM(pDevIns), pThis->svga.GCPhysFIFO); 3338 AssertBreak(RT_SUCCESS(rc)); 3339 rc = SUPSemEventWaitNoResume(pThis->svga.pSupDrvSession, pThis->svga.FIFORequestSem, RT_INDEFINITE_WAIT); 3340 } 3341 else 3342 rc = SUPSemEventWaitNoResume(pThis->svga.pSupDrvSession, pThis->svga.FIFORequestSem, cMsSleep); 3302 3343 AssertBreak(RT_SUCCESS(rc) || rc == VERR_TIMEOUT || rc == VERR_INTERRUPTED); 3303 3344 if (pThread->enmState != PDMTHREADSTATE_RUNNING) … … 3312 3353 if (rc == VERR_TIMEOUT) 3313 3354 { 3314 if ( pFIFO[SVGA_FIFO_NEXT_CMD] == pFIFO[SVGA_FIFO_STOP] 3315 && cCursorCount == pFIFO[SVGA_FIFO_CURSOR_COUNT]) 3355 /* Invariant: we should never have been doing a timed wait if the 3356 * interval is already at maximum. Instead we should have been 3357 * intercepting accesses. */ 3358 Assert(cMsSleep < cMsMaxSleep); 3359 if (!vmsvgaFIFOHasWork(pFIFO, cCursorCount)) 3316 3360 { 3317 3361 cMsSleep = RT_MIN(cMsSleep + cMsIncSleep, cMsMaxSleep); … … 3322 3366 Log(("vmsvgaFIFOLoop: timeout\n")); 3323 3367 } 3324 else if ( pFIFO[SVGA_FIFO_NEXT_CMD] != pFIFO[SVGA_FIFO_STOP])3368 else if (vmsvgaFIFOHasWork(pFIFO, cCursorCount)) 3325 3369 STAM_REL_COUNTER_INC(&pSVGAState->StatFifoTodoWoken); 3326 3370 cMsSleep = cMsMinSleep; … … 5099 5143 AssertRC(rc); 5100 5144 5101 # ifdef DEBUG_FIFO_ACCESS5102 5145 if (RT_SUCCESS(rc)) 5103 5146 { 5104 rc = PGMHandlerPhysicalRegister(PDMDevHlpGetVM(pDevIns), GCPhysAddress, GCPhysAddress + (pThis->svga.cbFIFO - 1), 5147 rc = PGMHandlerPhysicalRegister(PDMDevHlpGetVM(pDevIns), GCPhysAddress, 5148 #ifdef DEBUG_FIFO_ACCESS 5149 GCPhysAddress + (pThis->svga.cbFIFO - 1), 5150 #else 5151 GCPhysAddress + PAGE_SIZE - 1, 5152 #endif 5105 5153 pThis->svga.hFifoAccessHandlerType, pThis, NIL_RTR0PTR, NIL_RTRCPTR, 5106 5154 "VMSVGA FIFO"); 5107 5155 AssertRC(rc); 5108 5156 } 5109 # endif5110 5157 if (RT_SUCCESS(rc)) 5111 5158 { … … 5117 5164 { 5118 5165 Assert(pThis->svga.GCPhysFIFO); 5119 # ifdef DEBUG_FIFO_ACCESS5120 5166 rc = PGMHandlerPhysicalDeregister(PDMDevHlpGetVM(pDevIns), pThis->svga.GCPhysFIFO); 5121 5167 AssertRC(rc); 5122 # endif5123 5168 pThis->svga.GCPhysFIFO = 0; 5124 5169 } … … 5824 5869 AssertRCReturn(rc, rc); 5825 5870 # endif 5871 rc = PGMR3HandlerPhysicalTypeRegister(PDMDevHlpGetVM(pThis->pDevInsR3), 5826 5872 # ifdef DEBUG_FIFO_ACCESS 5827 rc = PGMR3HandlerPhysicalTypeRegister(PDMDevHlpGetVM(pThis->pDevInsR3), PGMPHYSHANDLERKIND_ALL, 5873 PGMPHYSHANDLERKIND_ALL, 5874 #else 5875 PGMPHYSHANDLERKIND_WRITE, 5876 #endif 5828 5877 vmsvgaR3FIFOAccessHandler, 5829 5878 NULL, NULL, NULL, … … 5831 5880 "VMSVGA FIFO", &pThis->svga.hFifoAccessHandlerType); 5832 5881 AssertRCReturn(rc, rc); 5833 #endif5834 5882 5835 5883 /* Create the async IO thread. */ … … 5992 6040 STAM_REL_REG(pVM, &pSVGAState->StatFifoTodoWoken, STAMTYPE_COUNTER, "/Devices/VMSVGA/FifoTodoWoken", STAMUNIT_OCCURENCES, "Number of times we discovered pending work after being woken up."); 5993 6041 STAM_REL_REG(pVM, &pSVGAState->StatFifoStalls, STAMTYPE_PROFILE, "/Devices/VMSVGA/FifoStalls", STAMUNIT_TICKS_PER_CALL, "Profiling of FIFO stalls (waiting for guest to finish copying data)."); 6042 STAM_REL_REG(pVM, &pSVGAState->StatFifoAccessHandler, STAMTYPE_COUNTER, "/Devices/VMSVGA/FifoAccessHandler", STAMUNIT_OCCURENCES, "Number of times the FIFO access handler triggered."); 5994 6043 5995 6044 /* -
trunk/src/VBox/Devices/Graphics/DevVGA-SVGA.h
r76565 r77193 259 259 * thread and does not want it do anything but the command. */ 260 260 bool volatile fFifoExtCommandWakeup; 261 #if defined(DEBUG_GMR_ACCESS) || defined(DEBUG_FIFO_ACCESS) 261 // #if defined(DEBUG_GMR_ACCESS) /* Needed for alignment. */ 262 262 /** GMR debug access handler type handle. */ 263 263 PGMPHYSHANDLERTYPE hGmrAccessHandlerType; 264 // #endif 264 265 /** FIFO debug access handler type handle. */ 265 266 PGMPHYSHANDLERTYPE hFifoAccessHandlerType; 266 #endif267 267 /** Number of GMRs. */ 268 268 uint32_t cGMR;
Note:
See TracChangeset
for help on using the changeset viewer.