Changeset 42337 in vbox
- Timestamp:
- Jul 24, 2012 7:50:38 AM (13 years ago)
- Location:
- trunk
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/include/VBox/vmm/cpumctx.h
r42165 r42337 77 77 #define CPUMSELREG_FLAGS_VALID UINT16_C(0x0001) 78 78 #define CPUMSELREG_FLAGS_STALE UINT16_C(0x0002) 79 #define CPUMSELREG_FLAGS_VALID_MASK UINT16_C(0x0003) 79 80 /** @} */ 80 81 … … 398 399 # define CPUMCTX2CORE(pCtx) ((PCPUMCTXCORE)(void *)&(pCtx)->rax) 399 400 400 #endif /* VBOX_FOR_DTRACE_LIB */ 401 /** 402 * Gets the first selector register of a CPUMCTX. 403 * 404 * Use this with X86_SREG_COUNT to loop thru the selector registers. 405 */ 406 # define CPUMCTX_FIRST_SREG(a_pCtx) (&(a_pCtx)->es) 407 408 #endif /* !VBOX_FOR_DTRACE_LIB */ 401 409 402 410 /** -
trunk/include/iprt/x86.h
r42157 r42337 3141 3141 #define X86_SREG_GS 5 3142 3142 /** @} */ 3143 /** Segment register count. */ 3144 #define X86_SREG_COUNT 6 3143 3145 3144 3146 -
trunk/src/VBox/VMM/VMMR3/CPUM.cpp
r42191 r42337 64 64 * Defined Constants And Macros * 65 65 *******************************************************************************/ 66 #if 0 /* later when actual changes have been made */67 66 /** The current saved state version. */ 68 67 #define CPUM_SAVED_STATE_VERSION 14 69 #else70 # define CPUM_SAVED_STATE_VERSION CPUM_SAVED_STATE_VERSION_MEM71 #endif72 68 /** The current saved state version before using SSMR3PutStruct. */ 73 69 #define CPUM_SAVED_STATE_VERSION_MEM 13 … … 129 125 /** Saved state field descriptors for CPUMCTX. */ 130 126 static const SSMFIELD g_aCpumCtxFields[] = 127 { 128 SSMFIELD_ENTRY( CPUMCTX, fpu.FCW), 129 SSMFIELD_ENTRY( CPUMCTX, fpu.FSW), 130 SSMFIELD_ENTRY( CPUMCTX, fpu.FTW), 131 SSMFIELD_ENTRY( CPUMCTX, fpu.FOP), 132 SSMFIELD_ENTRY( CPUMCTX, fpu.FPUIP), 133 SSMFIELD_ENTRY( CPUMCTX, fpu.CS), 134 SSMFIELD_ENTRY( CPUMCTX, fpu.Rsrvd1), 135 SSMFIELD_ENTRY( CPUMCTX, fpu.FPUDP), 136 SSMFIELD_ENTRY( CPUMCTX, fpu.DS), 137 SSMFIELD_ENTRY( CPUMCTX, fpu.Rsrvd2), 138 SSMFIELD_ENTRY( CPUMCTX, fpu.MXCSR), 139 SSMFIELD_ENTRY( CPUMCTX, fpu.MXCSR_MASK), 140 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[0]), 141 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[1]), 142 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[2]), 143 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[3]), 144 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[4]), 145 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[5]), 146 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[6]), 147 SSMFIELD_ENTRY( CPUMCTX, fpu.aRegs[7]), 148 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[0]), 149 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[1]), 150 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[2]), 151 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[3]), 152 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[4]), 153 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[5]), 154 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[6]), 155 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[7]), 156 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[8]), 157 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[9]), 158 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[10]), 159 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[11]), 160 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[12]), 161 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[13]), 162 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[14]), 163 SSMFIELD_ENTRY( CPUMCTX, fpu.aXMM[15]), 164 SSMFIELD_ENTRY( CPUMCTX, rdi), 165 SSMFIELD_ENTRY( CPUMCTX, rsi), 166 SSMFIELD_ENTRY( CPUMCTX, rbp), 167 SSMFIELD_ENTRY( CPUMCTX, rax), 168 SSMFIELD_ENTRY( CPUMCTX, rbx), 169 SSMFIELD_ENTRY( CPUMCTX, rdx), 170 SSMFIELD_ENTRY( CPUMCTX, rcx), 171 SSMFIELD_ENTRY( CPUMCTX, rsp), 172 SSMFIELD_ENTRY( CPUMCTX, rflags), 173 SSMFIELD_ENTRY( CPUMCTX, rip), 174 SSMFIELD_ENTRY( CPUMCTX, r8), 175 SSMFIELD_ENTRY( CPUMCTX, r9), 176 SSMFIELD_ENTRY( CPUMCTX, r10), 177 SSMFIELD_ENTRY( CPUMCTX, r11), 178 SSMFIELD_ENTRY( CPUMCTX, r12), 179 SSMFIELD_ENTRY( CPUMCTX, r13), 180 SSMFIELD_ENTRY( CPUMCTX, r14), 181 SSMFIELD_ENTRY( CPUMCTX, r15), 182 SSMFIELD_ENTRY( CPUMCTX, es.Sel), 183 SSMFIELD_ENTRY( CPUMCTX, es.ValidSel), 184 SSMFIELD_ENTRY( CPUMCTX, es.fFlags), 185 SSMFIELD_ENTRY( CPUMCTX, es.u64Base), 186 SSMFIELD_ENTRY( CPUMCTX, es.u32Limit), 187 SSMFIELD_ENTRY( CPUMCTX, es.Attr), 188 SSMFIELD_ENTRY( CPUMCTX, cs.Sel), 189 SSMFIELD_ENTRY( CPUMCTX, cs.ValidSel), 190 SSMFIELD_ENTRY( CPUMCTX, cs.fFlags), 191 SSMFIELD_ENTRY( CPUMCTX, cs.u64Base), 192 SSMFIELD_ENTRY( CPUMCTX, cs.u32Limit), 193 SSMFIELD_ENTRY( CPUMCTX, cs.Attr), 194 SSMFIELD_ENTRY( CPUMCTX, ss.Sel), 195 SSMFIELD_ENTRY( CPUMCTX, ss.ValidSel), 196 SSMFIELD_ENTRY( CPUMCTX, ss.fFlags), 197 SSMFIELD_ENTRY( CPUMCTX, ss.u64Base), 198 SSMFIELD_ENTRY( CPUMCTX, ss.u32Limit), 199 SSMFIELD_ENTRY( CPUMCTX, ss.Attr), 200 SSMFIELD_ENTRY( CPUMCTX, ds.Sel), 201 SSMFIELD_ENTRY( CPUMCTX, ds.ValidSel), 202 SSMFIELD_ENTRY( CPUMCTX, ds.fFlags), 203 SSMFIELD_ENTRY( CPUMCTX, ds.u64Base), 204 SSMFIELD_ENTRY( CPUMCTX, ds.u32Limit), 205 SSMFIELD_ENTRY( CPUMCTX, ds.Attr), 206 SSMFIELD_ENTRY( CPUMCTX, fs.Sel), 207 SSMFIELD_ENTRY( CPUMCTX, fs.ValidSel), 208 SSMFIELD_ENTRY( CPUMCTX, fs.fFlags), 209 SSMFIELD_ENTRY( CPUMCTX, fs.u64Base), 210 SSMFIELD_ENTRY( CPUMCTX, fs.u32Limit), 211 SSMFIELD_ENTRY( CPUMCTX, fs.Attr), 212 SSMFIELD_ENTRY( CPUMCTX, gs.Sel), 213 SSMFIELD_ENTRY( CPUMCTX, gs.ValidSel), 214 SSMFIELD_ENTRY( CPUMCTX, gs.fFlags), 215 SSMFIELD_ENTRY( CPUMCTX, gs.u64Base), 216 SSMFIELD_ENTRY( CPUMCTX, gs.u32Limit), 217 SSMFIELD_ENTRY( CPUMCTX, gs.Attr), 218 SSMFIELD_ENTRY( CPUMCTX, cr0), 219 SSMFIELD_ENTRY( CPUMCTX, cr2), 220 SSMFIELD_ENTRY( CPUMCTX, cr3), 221 SSMFIELD_ENTRY( CPUMCTX, cr4), 222 SSMFIELD_ENTRY( CPUMCTX, dr[0]), 223 SSMFIELD_ENTRY( CPUMCTX, dr[1]), 224 SSMFIELD_ENTRY( CPUMCTX, dr[2]), 225 SSMFIELD_ENTRY( CPUMCTX, dr[3]), 226 SSMFIELD_ENTRY( CPUMCTX, dr[6]), 227 SSMFIELD_ENTRY( CPUMCTX, dr[7]), 228 SSMFIELD_ENTRY( CPUMCTX, gdtr.cbGdt), 229 SSMFIELD_ENTRY( CPUMCTX, gdtr.pGdt), 230 SSMFIELD_ENTRY( CPUMCTX, idtr.cbIdt), 231 SSMFIELD_ENTRY( CPUMCTX, idtr.pIdt), 232 SSMFIELD_ENTRY( CPUMCTX, SysEnter.cs), 233 SSMFIELD_ENTRY( CPUMCTX, SysEnter.eip), 234 SSMFIELD_ENTRY( CPUMCTX, SysEnter.esp), 235 SSMFIELD_ENTRY( CPUMCTX, msrEFER), 236 SSMFIELD_ENTRY( CPUMCTX, msrSTAR), 237 SSMFIELD_ENTRY( CPUMCTX, msrPAT), 238 SSMFIELD_ENTRY( CPUMCTX, msrLSTAR), 239 SSMFIELD_ENTRY( CPUMCTX, msrCSTAR), 240 SSMFIELD_ENTRY( CPUMCTX, msrSFMASK), 241 SSMFIELD_ENTRY( CPUMCTX, msrKERNELGSBASE), 242 SSMFIELD_ENTRY( CPUMCTX, ldtr.Sel), 243 SSMFIELD_ENTRY( CPUMCTX, ldtr.ValidSel), 244 SSMFIELD_ENTRY( CPUMCTX, ldtr.fFlags), 245 SSMFIELD_ENTRY( CPUMCTX, ldtr.u64Base), 246 SSMFIELD_ENTRY( CPUMCTX, ldtr.u32Limit), 247 SSMFIELD_ENTRY( CPUMCTX, ldtr.Attr), 248 SSMFIELD_ENTRY( CPUMCTX, tr.Sel), 249 SSMFIELD_ENTRY( CPUMCTX, tr.ValidSel), 250 SSMFIELD_ENTRY( CPUMCTX, tr.fFlags), 251 SSMFIELD_ENTRY( CPUMCTX, tr.u64Base), 252 SSMFIELD_ENTRY( CPUMCTX, tr.u32Limit), 253 SSMFIELD_ENTRY( CPUMCTX, tr.Attr), 254 SSMFIELD_ENTRY_TERM() 255 }; 256 257 /** Saved state field descriptors for CPUMCTX in V4.1 before the hidden selector 258 * registeres changed. */ 259 static const SSMFIELD g_aCpumCtxFieldsMem[] = 131 260 { 132 261 SSMFIELD_ENTRY( CPUMCTX, fpu.FCW), … … 2226 2355 { 2227 2356 PVMCPU pVCpu = &pVM->aCpus[i]; 2228 #ifdef CPUM_WITH_CHANGED_CPUMCTX 2229 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Hyper, sizeof(pVCpu->cpum.s.Hyper), SSMSTRUCT_FLAGS_MEM_BAND_AID_RELAXED, 2230 g_aCpumCtxFields, NULL); 2231 #else 2232 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Hyper, sizeof(pVCpu->cpum.s.Hyper), SSMSTRUCT_FLAGS_MEM_BAND_AID, 2233 g_aCpumCtxFields, NULL); 2234 #endif 2357 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Hyper, sizeof(pVCpu->cpum.s.Hyper), 0, g_aCpumCtxFields, NULL); 2235 2358 } 2236 2359 2237 2360 SSMR3PutU32(pSSM, pVM->cCpus); 2238 2361 SSMR3PutU32(pSSM, sizeof(pVM->aCpus[0].cpum.s.GuestMsrs.msr)); 2239 for (VMCPUID i = 0; i < pVM->cCpus; i++) 2240 { 2241 PVMCPU pVCpu = &pVM->aCpus[i]; 2242 2243 #ifdef CPUM_WITH_CHANGED_CPUMCTX 2244 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Guest, sizeof(pVCpu->cpum.s.Guest), SSMSTRUCT_FLAGS_MEM_BAND_AID_RELAXED, 2245 g_aCpumCtxFields, NULL); 2246 #else 2247 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Guest, sizeof(pVCpu->cpum.s.Guest), SSMSTRUCT_FLAGS_MEM_BAND_AID, 2248 g_aCpumCtxFields, NULL); 2249 #endif 2362 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2363 { 2364 PVMCPU pVCpu = &pVM->aCpus[iCpu]; 2365 2366 SSMR3PutStructEx(pSSM, &pVCpu->cpum.s.Guest, sizeof(pVCpu->cpum.s.Guest), 0, g_aCpumCtxFields, NULL); 2250 2367 SSMR3PutU32(pSSM, pVCpu->cpum.s.fUseFlags); 2251 2368 SSMR3PutU32(pSSM, pVCpu->cpum.s.fChanged); 2252 AssertCompileSizeAlignment(pV M->aCpus[i].cpum.s.GuestMsrs.msr, sizeof(uint64_t));2253 SSMR3PutMem(pSSM, &pVCpu->cpum.s.GuestMsrs, sizeof(pV M->aCpus[i].cpum.s.GuestMsrs.msr));2369 AssertCompileSizeAlignment(pVCpu->cpum.s.GuestMsrs.msr, sizeof(uint64_t)); 2370 SSMR3PutMem(pSSM, &pVCpu->cpum.s.GuestMsrs, sizeof(pVCpu->cpum.s.GuestMsrs.msr)); 2254 2371 } 2255 2372 … … 2302 2419 SSMR3HandleSetGCPtrSize(pSSM, HC_ARCH_BITS == 32 ? sizeof(RTGCPTR32) : sizeof(RTGCPTR)); 2303 2420 2304 PCSSMFIELD paCpumCtxFields = g_aCpumCtxFields; 2421 uint32_t const fLoad = uVersion > CPUM_SAVED_STATE_VERSION_MEM ? 0 : SSMSTRUCT_FLAGS_MEM_BAND_AID_RELAXED; 2422 PCSSMFIELD paCpumCtxFields = g_aCpumCtxFields; 2305 2423 if (uVersion == CPUM_SAVED_STATE_VERSION_VER1_6) 2306 2424 paCpumCtxFields = g_aCpumCtxFieldsV16; 2307 uint32_t fLoad = 0; 2308 if (uVersion <= CPUM_SAVED_STATE_VERSION_MEM) 2309 #ifdef CPUM_WITH_CHANGED_CPUMCTX 2310 fLoad = SSMSTRUCT_FLAGS_MEM_BAND_AID_RELAXED; 2311 #else 2312 fLoad = SSMSTRUCT_FLAGS_MEM_BAND_AID; 2313 #endif 2425 else if (uVersion <= CPUM_SAVED_STATE_VERSION_MEM) 2426 paCpumCtxFields = g_aCpumCtxFieldsMem; 2314 2427 2315 2428 /* 2316 2429 * Restore. 2317 2430 */ 2318 for (VMCPUID i = 0; i < pVM->cCpus; i++)2431 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2319 2432 { 2320 PVMCPU pVCpu = &pVM->aCpus[i ];2433 PVMCPU pVCpu = &pVM->aCpus[iCpu]; 2321 2434 uint64_t uCR3 = pVCpu->cpum.s.Hyper.cr3; 2322 2435 uint64_t uRSP = pVCpu->cpum.s.Hyper.rsp; /* see VMMR3Relocate(). */ … … 2348 2461 } 2349 2462 2350 for (VMCPUID i = 0; i < pVM->cCpus; i++)2463 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2351 2464 { 2352 SSMR3GetStructEx(pSSM, &pVM->aCpus[i].cpum.s.Guest, sizeof(pVM->aCpus[i].cpum.s.Guest), fLoad, 2465 PVMCPU pVCpu = &pVM->aCpus[iCpu]; 2466 SSMR3GetStructEx(pSSM, &pVCpu->cpum.s.Guest, sizeof(pVCpu->cpum.s.Guest), fLoad, 2353 2467 paCpumCtxFields, NULL); 2354 SSMR3GetU32(pSSM, &pV M->aCpus[i].cpum.s.fUseFlags);2355 SSMR3GetU32(pSSM, &pV M->aCpus[i].cpum.s.fChanged);2468 SSMR3GetU32(pSSM, &pVCpu->cpum.s.fUseFlags); 2469 SSMR3GetU32(pSSM, &pVCpu->cpum.s.fChanged); 2356 2470 if (uVersion > CPUM_SAVED_STATE_VERSION_NO_MSR_SIZE) 2357 SSMR3GetMem(pSSM, &pV M->aCpus[i].cpum.s.GuestMsrs.au64[0], cbMsrs);2471 SSMR3GetMem(pSSM, &pVCpu->cpum.s.GuestMsrs.au64[0], cbMsrs); 2358 2472 else if (uVersion >= CPUM_SAVED_STATE_VERSION_VER3_0) 2359 2473 { 2360 SSMR3GetMem(pSSM, &pV M->aCpus[i].cpum.s.GuestMsrs.au64[0], 2 * sizeof(uint64_t)); /* Restore two MSRs. */2474 SSMR3GetMem(pSSM, &pVCpu->cpum.s.GuestMsrs.au64[0], 2 * sizeof(uint64_t)); /* Restore two MSRs. */ 2361 2475 SSMR3Skip(pSSM, 62 * sizeof(uint64_t)); 2362 2476 } 2363 2477 } 2364 2478 2479 /* Older states does not have the internal selector register flags 2480 and valid selector value. Supply those. */ 2481 if (uVersion <= CPUM_SAVED_STATE_VERSION_MEM) 2482 { 2483 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2484 { 2485 PVMCPU pVCpu = &pVM->aCpus[iCpu]; 2486 bool const fValid = HWACCMIsEnabled(pVM) 2487 || ( uVersion > CPUM_SAVED_STATE_VERSION_VER3_2 2488 && !(pVCpu->cpum.s.fChanged & CPUM_CHANGED_HIDDEN_SEL_REGS_INVALID)); 2489 PCPUMSELREG paSelReg = CPUMCTX_FIRST_SREG(&pVCpu->cpum.s.Guest); 2490 if (fValid) 2491 { 2492 for (uint32_t iSelReg = 0; iSelReg < X86_SREG_COUNT; iSelReg++) 2493 { 2494 paSelReg[iSelReg].fFlags = CPUMSELREG_FLAGS_VALID; 2495 paSelReg[iSelReg].ValidSel = paSelReg[iSelReg].Sel; 2496 } 2497 2498 pVCpu->cpum.s.Guest.ldtr.fFlags = CPUMSELREG_FLAGS_VALID; 2499 pVCpu->cpum.s.Guest.ldtr.ValidSel = pVCpu->cpum.s.Guest.ldtr.Sel; 2500 pVCpu->cpum.s.Guest.tr.fFlags = CPUMSELREG_FLAGS_VALID; 2501 pVCpu->cpum.s.Guest.tr.ValidSel = pVCpu->cpum.s.Guest.tr.Sel; 2502 } 2503 else 2504 { 2505 for (uint32_t iSelReg = 0; iSelReg < X86_SREG_COUNT; iSelReg++) 2506 { 2507 paSelReg[iSelReg].fFlags = 0; 2508 paSelReg[iSelReg].ValidSel = 0; 2509 } 2510 2511 /** @todo fix this. We can get most of the details from SELM after restore is 2512 * done. */ 2513 pVCpu->cpum.s.Guest.ldtr.fFlags = 0; 2514 pVCpu->cpum.s.Guest.ldtr.ValidSel = 0; 2515 pVCpu->cpum.s.Guest.tr.fFlags = 0; 2516 pVCpu->cpum.s.Guest.tr.ValidSel = 0; 2517 } 2518 2519 } 2520 } 2521 2365 2522 /* Older states does not set CPUM_CHANGED_HIDDEN_SEL_REGS_INVALID for 2366 2523 raw-mode guest, so we have to do it ourselves. */ 2524 /** @todo eliminate CPUM_CHANGED_HIDDEN_SEL_REGS_INVALID. */ 2367 2525 if ( uVersion <= CPUM_SAVED_STATE_VERSION_VER3_2 2368 2526 && !HWACCMIsEnabled(pVM)) 2369 2527 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2370 2528 pVM->aCpus[iCpu].cpum.s.fChanged |= CPUM_CHANGED_HIDDEN_SEL_REGS_INVALID; 2529 2530 /* 2531 * A quick sanity check. 2532 */ 2533 for (VMCPUID iCpu = 0; iCpu < pVM->cCpus; iCpu++) 2534 { 2535 PVMCPU pVCpu = &pVM->aCpus[iCpu]; 2536 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.es.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2537 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.cs.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2538 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.ss.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2539 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.ds.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2540 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.fs.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2541 AssertLogRelReturn(!(pVCpu->cpum.s.Guest.gs.fFlags & !CPUMSELREG_FLAGS_VALID_MASK), VERR_SSM_UNEXPECTED_DATA); 2542 } 2371 2543 } 2372 2544
Note:
See TracChangeset
for help on using the changeset viewer.