Changeset 64255 in vbox for trunk/src/VBox/HostDrivers
- Timestamp:
- Oct 13, 2016 3:18:21 PM (8 years ago)
- Location:
- trunk/src/VBox/HostDrivers/Support
- Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/HostDrivers/Support/SUPDrvGip.cpp
r64236 r64255 274 274 && RT_IS_POWER_OF_TWO(RTCPUSET_MAX_CPUS)) 275 275 { 276 PSUPGIPCPU pGipCpu = SUPGetGipCpuBySetIndex(pGip, iCpuSet); 277 276 278 /* 277 279 * Check whether the IDTR.LIMIT contains a CPU number. … … 305 307 && (ASMCpuId_EDX(UINT32_C(0x80000001)) & X86_CPUID_EXT_FEATURE_EDX_RDTSCP) ) 306 308 { 307 uint32_t uAux; 309 uint32_t const uGroupedAux = (uint8_t)pGipCpu->iCpuGroupMember | ((uint32_t)pGipCpu->iCpuGroup << 8); 310 uint32_t uAux; 308 311 ASMReadTscWithAux(&uAux); 309 312 if ((uAux & (RTCPUSET_MAX_CPUS - 1)) == idCpu) … … 313 316 if ((uAux & (RTCPUSET_MAX_CPUS - 1)) == idCpu) 314 317 fSupported |= SUPGIPGETCPU_RDTSCP_MASK_MAX_SET_CPUS; 318 } 319 320 if ( (uAux & UINT16_MAX) == uGroupedAux 321 && pGipCpu->iCpuGroupMember <= UINT8_MAX) 322 { 323 ASMNopPause(); 324 ASMReadTscWithAux(&uAux); 325 if ((uAux & UINT16_MAX) == uGroupedAux) 326 fSupported |= SUPGIPGETCPU_RDTSCP_GROUP_IN_CH_NUMBER_IN_CL; 315 327 } 316 328 } … … 1259 1271 static void supdrvGipMpEventOnlineOrInitOnCpu(PSUPDRVDEVEXT pDevExt, RTCPUID idCpu) 1260 1272 { 1261 int iCpuSet = 0;1262 uint16_t idApic = UINT16_MAX;1263 uint 32_t i = 0;1264 uint 64_t u64NanoTS= 0;1265 PSUPGLOBALINFOPAGE pGip = pDevExt->pGip;1273 PSUPGLOBALINFOPAGE pGip = pDevExt->pGip; 1274 int iCpuSet = 0; 1275 uint16_t idApic = UINT16_MAX; 1276 uint32_t i = 0; 1277 uint64_t u64NanoTS = 0; 1266 1278 1267 1279 AssertPtrReturnVoid(pGip); … … 1301 1313 ASMAtomicWriteS16(&pGip->aCPUs[i].iCpuSet, (int16_t)iCpuSet); 1302 1314 ASMAtomicWriteSize(&pGip->aCPUs[i].idCpu, idCpu); 1315 1316 pGip->aCPUs[i].iCpuGroup = 0; 1317 pGip->aCPUs[i].iCpuGroupMember = iCpuSet; 1318 #ifdef RT_OS_WINDOWS 1319 pGip->aCPUs[i].iCpuGroup = supdrvOSGipGetGroupFromCpu(pDevExt, idCpu, &pGip->aCPUs[i].iCpuGroupMember); 1320 #endif 1303 1321 1304 1322 /* … … 1683 1701 pCpu->i64TSCDelta = pGip->enmUseTscDelta > SUPGIPUSETSCDELTA_ZERO_CLAIMED ? INT64_MAX : 0; 1684 1702 1685 ASMAtomicWriteSize(&pCpu->enmState, SUPGIPCPUSTATE_INVALID); 1686 ASMAtomicWriteU32(&pCpu->idCpu, NIL_RTCPUID); 1687 ASMAtomicWriteS16(&pCpu->iCpuSet, -1); 1688 ASMAtomicWriteU16(&pCpu->idApic, UINT16_MAX); 1703 ASMAtomicWriteSize(&pCpu->enmState, SUPGIPCPUSTATE_INVALID); 1704 ASMAtomicWriteU32(&pCpu->idCpu, NIL_RTCPUID); 1705 ASMAtomicWriteS16(&pCpu->iCpuSet, -1); 1706 ASMAtomicWriteU16(&pCpu->iCpuGroup, 0); 1707 ASMAtomicWriteU16(&pCpu->iCpuGroupMember, UINT16_MAX); 1708 ASMAtomicWriteU16(&pCpu->idApic, UINT16_MAX); 1709 ASMAtomicWriteU32(&pCpu->iReservedForNumaNode, 0); 1689 1710 1690 1711 /* … … 1764 1785 pGip->cPresentCpus = RTMpGetPresentCount(); 1765 1786 pGip->cPossibleCpus = RTMpGetCount(); 1787 pGip->cPossibleCpuGroups = 1; 1766 1788 pGip->idCpuMax = RTMpGetMaxCpuId(); 1767 1789 for (i = 0; i < RT_ELEMENTS(pGip->aiCpuFromApicId); i++) … … 1769 1791 for (i = 0; i < RT_ELEMENTS(pGip->aiCpuFromCpuSetIdx); i++) 1770 1792 pGip->aiCpuFromCpuSetIdx[i] = UINT16_MAX; 1793 pGip->aiFirstCpuSetIdxFromCpuGroup[0] = 0; 1794 for (i = 1; i < RT_ELEMENTS(pGip->aiFirstCpuSetIdxFromCpuGroup); i++) 1795 pGip->aiFirstCpuSetIdxFromCpuGroup[i] = UINT16_MAX; 1796 #ifdef RT_OS_WINDOWS 1797 supdrvOSInitGipGroupTable(pDevExt, pGip); 1798 #endif 1771 1799 for (i = 0; i < cCpus; i++) 1772 1800 supdrvGipInitCpu(pGip, &pGip->aCPUs[i], u64NanoTS, 0 /*uCpuHz*/); … … 2394 2422 * run. 2395 2423 */ 2396 if (RT_UNLIKELY(iTick == 1)) 2424 if (RT_LIKELY(iTick != 1)) 2425 { /* likely*/ } 2426 else 2397 2427 { 2398 2428 iCpu = supdrvGipFindOrAllocCpuIndexForCpuId(pGip, idCpu); -
trunk/src/VBox/HostDrivers/Support/SUPDrvIOC.h
r62664 r64255 215 215 * - nothing. 216 216 */ 217 #define SUPDRV_IOC_VERSION 0x002 60000217 #define SUPDRV_IOC_VERSION 0x00270000 218 218 219 219 /** SUP_IOCTL_COOKIE. */ -
trunk/src/VBox/HostDrivers/Support/SUPDrvInternal.h
r62664 r64255 800 800 void VBOXCALL supdrvOSSessionHashTabRemoved(PSUPDRVDEVEXT pDevExt, PSUPDRVSESSION pSession, void *pvUser); 801 801 802 /** 803 * Called during GIP initialization to set up the group table and group count. 804 * 805 * This is currently only implemented on windows [lazy bird]. 806 * 807 * @param pDevExt The device globals. 808 * @param pGip The GIP which group table needs initialization. 809 * It's only partially initialized at this point. 810 */ 811 void VBOXCALL supdrvOSInitGipGroupTable(PSUPDRVDEVEXT pDevExt, PSUPGLOBALINFOPAGE pGip); 812 813 /** 814 * Gets the CPU group and member indexes for the given CPU ID. 815 * 816 * This is currently only implemented on windows [lazy bird]. 817 * 818 * @returns CPU group number. 819 * @param pDevExt The device globals. 820 * @param idCpu The ID of the CPU. 821 * @param piCpuGroupMember Where to return the group member number. 822 */ 823 uint16_t VBOXCALL supdrvOSGipGetGroupFromCpu(PSUPDRVDEVEXT pDevExt, RTCPUID idCpu, uint16_t *piCpuGroupMember); 824 802 825 void VBOXCALL supdrvOSObjInitCreator(PSUPDRVOBJ pObj, PSUPDRVSESSION pSession); 803 826 bool VBOXCALL supdrvOSObjCanAccess(PSUPDRVOBJ pObj, PSUPDRVSESSION pSession, const char *pszObjName, int *prc); -
trunk/src/VBox/HostDrivers/Support/testcase/tstGIP-2.cpp
r62490 r64255 131 131 SUPR3GipSetFlags(SUPGIP_FLAGS_TESTING_ENABLE, UINT32_MAX); 132 132 133 RTPrintf("tstGIP-2: cCpus=%d u32UpdateHz=%RU32 u32UpdateIntervalNS=%RU32 u64NanoTSLastUpdateHz=%RX64 u64CpuHz=%RU64 uCpuHzRef=%RU64 u32Mode=%d (%s) fTestMode=%RTbool u32Version=%#x\n", 133 RTPrintf("tstGIP-2: u32Mode=%d (%s) fTestMode=%RTbool u32Version=%#x fGetGipCpu=%#RX32\n", 134 g_pSUPGlobalInfoPage->u32Mode, 135 SUPGetGIPModeName(g_pSUPGlobalInfoPage), 136 fTestMode, 137 g_pSUPGlobalInfoPage->u32Version, 138 g_pSUPGlobalInfoPage->fGetGipCpu); 139 RTPrintf("tstGIP-2: cCpus=%d cPossibleCpus=%d cPossibleCpuGroups=%d cPresentCpus=%d cOnlineCpus=%d\n", 134 140 g_pSUPGlobalInfoPage->cCpus, 141 g_pSUPGlobalInfoPage->cPossibleCpus, 142 g_pSUPGlobalInfoPage->cPossibleCpuGroups, 143 g_pSUPGlobalInfoPage->cPresentCpus, 144 g_pSUPGlobalInfoPage->cOnlineCpus); 145 RTPrintf("tstGIP-2: u32UpdateHz=%RU32 u32UpdateIntervalNS=%RU32 u64NanoTSLastUpdateHz=%RX64 u64CpuHz=%RU64 uCpuHzRef=%RU64\n", 135 146 g_pSUPGlobalInfoPage->u32UpdateHz, 136 147 g_pSUPGlobalInfoPage->u32UpdateIntervalNS, 137 148 g_pSUPGlobalInfoPage->u64NanoTSLastUpdateHz, 138 149 g_pSUPGlobalInfoPage->u64CpuHz, 139 uCpuHzRef, 140 g_pSUPGlobalInfoPage->u32Mode, 141 SUPGetGIPModeName(g_pSUPGlobalInfoPage), 142 fTestMode, 143 g_pSUPGlobalInfoPage->u32Version); 150 uCpuHzRef); 151 144 152 RTPrintf(fHex 145 153 ? "tstGIP-2: it: u64NanoTS delta u64TSC UpIntTSC H TransId CpuHz %sTSC Interval History...\n" -
trunk/src/VBox/HostDrivers/Support/win/SUPDrv-win.cpp
r62677 r64255 359 359 #endif /* VBOXDRV_WITH_FAST_IO */ 360 360 361 /** Default ZERO value. */ 362 static ULONG g_fOptDefaultZero = 0; 363 /** Registry values. 364 * We wrap these in a struct to ensure they are followed by a little zero 365 * padding in order to limit the chance of trouble on unpatched systems. */ 366 struct 367 { 368 /** The ForceAsync registry value. */ 369 ULONG fOptForceAsyncTsc; 370 /** Padding. */ 371 uint64_t au64Padding[2]; 372 } g_Options = { FALSE, 0, 0 }; 373 /** Registry query table for RtlQueryRegistryValues. */ 374 static RTL_QUERY_REGISTRY_TABLE g_aRegValues[] = 375 { 376 { 377 /* .QueryRoutine = */ NULL, 378 /* .Flags = */ RTL_QUERY_REGISTRY_DIRECT | RTL_QUERY_REGISTRY_TYPECHECK, 379 /* .Name = */ L"ForceAsyncTsc", 380 /* .EntryContext = */ &g_Options.fOptForceAsyncTsc, 381 /* .DefaultType = */ (REG_DWORD << RTL_QUERY_REGISTRY_TYPECHECK_SHIFT) | REG_DWORD, 382 /* .DefaultData = */ &g_fOptDefaultZero, 383 /* .DefaultLength = */ sizeof(g_fOptDefaultZero), 384 }, 385 { NULL, 0, NULL, NULL, 0, NULL, 0 } /* terminator entry. */ 386 }; 387 388 /** Pointer to KeQueryMaximumGroupCount. */ 389 static PFNKEQUERYMAXIMUMGROUPCOUNT g_pfnKeQueryMaximumGroupCount = NULL; 390 /** Pointer to KeGetProcessorIndexFromNumber. */ 391 static PFNKEGETPROCESSORINDEXFROMNUMBER g_pfnKeGetProcessorIndexFromNumber = NULL; 392 /** Pointer to KeGetProcessorNumberFromIndex. */ 393 static PFNKEGETPROCESSORNUMBERFROMINDEX g_pfnKeGetProcessorNumberFromIndex = NULL; 394 361 395 #ifdef VBOX_WITH_HARDENING 362 396 /** Pointer to the stub device instance. */ … … 554 588 555 589 /* 590 * Query options first so any overflows on unpatched machines will do less 591 * harm (see MS11-011 / 2393802 / 2011-03-18). 592 * 593 * Unfortunately, pRegPath isn't documented as zero terminated, even if it 594 * quite likely always is, so we have to make a copy here. 595 */ 596 NTSTATUS rcNt; 597 PWSTR pwszCopy = (PWSTR)ExAllocatePoolWithTag(NonPagedPool, pRegPath->Length + sizeof(WCHAR), 'VBox'); 598 if (pwszCopy) 599 { 600 memcpy(pwszCopy, pRegPath->Buffer, pRegPath->Length); 601 pwszCopy[pRegPath->Length / sizeof(WCHAR)] = '\0'; 602 rcNt = RtlQueryRegistryValues(RTL_REGISTRY_ABSOLUTE | RTL_REGISTRY_OPTIONAL, pwszCopy, 603 g_aRegValues, NULL /*pvContext*/, NULL /*pvEnv*/); 604 ExFreePoolWithTag(pwszCopy, 'VBox'); 605 /* Probably safe to ignore rcNt here. */ 606 } 607 608 /* 609 * Resolve methods we want but isn't available everywhere. 610 */ 611 UNICODE_STRING RoutineName; 612 RtlInitUnicodeString(&RoutineName, L"KeQueryMaximumGroupCount"); 613 g_pfnKeQueryMaximumGroupCount = (PFNKEQUERYMAXIMUMGROUPCOUNT)MmGetSystemRoutineAddress(&RoutineName); 614 615 RtlInitUnicodeString(&RoutineName, L"KeGetProcessorIndexFromNumber"); 616 g_pfnKeGetProcessorIndexFromNumber = (PFNKEGETPROCESSORINDEXFROMNUMBER)MmGetSystemRoutineAddress(&RoutineName); 617 618 RtlInitUnicodeString(&RoutineName, L"KeGetProcessorNumberFromIndex"); 619 g_pfnKeGetProcessorNumberFromIndex = (PFNKEGETPROCESSORNUMBERFROMINDEX)MmGetSystemRoutineAddress(&RoutineName); 620 621 Assert( (g_pfnKeGetProcessorNumberFromIndex != NULL) == (g_pfnKeGetProcessorIndexFromNumber != NULL) 622 && (g_pfnKeGetProcessorNumberFromIndex != NULL) == (g_pfnKeQueryMaximumGroupCount != NULL)); /* all or nothing. */ 623 624 /* 556 625 * Initialize the runtime (IPRT). 557 626 */ 558 NTSTATUS rcNt;559 627 int vrc = RTR0Init(0); 560 628 if (RT_SUCCESS(vrc)) … … 1643 1711 1644 1712 1713 void VBOXCALL supdrvOSInitGipGroupTable(PSUPDRVDEVEXT pDevExt, PSUPGLOBALINFOPAGE pGip) 1714 { 1715 NOREF(pDevExt); 1716 1717 /* 1718 * The indexes are assigned in group order (see initterm-r0drv-nt.cpp). 1719 */ 1720 if ( g_pfnKeQueryMaximumGroupCount 1721 && g_pfnKeGetProcessorIndexFromNumber) 1722 { 1723 unsigned cGroups = g_pfnKeQueryMaximumGroupCount(); 1724 AssertStmt(cGroups > 0, cGroups = 1); 1725 AssertStmt(cGroups < RT_ELEMENTS(pGip->aiFirstCpuSetIdxFromCpuGroup), 1726 cGroups = RT_ELEMENTS(pGip->aiFirstCpuSetIdxFromCpuGroup)); 1727 pGip->cPossibleCpuGroups = cGroups; 1728 1729 KEPROCESSORINDEX idxCpuMin = 0; 1730 for (unsigned iGroup = 0; iGroup < cGroups; iGroup++) 1731 { 1732 PROCESSOR_NUMBER ProcNum; 1733 ProcNum.Group = (USHORT)iGroup; 1734 ProcNum.Number = 0; 1735 ProcNum.Reserved = 0; 1736 KEPROCESSORINDEX idxCpu = g_pfnKeGetProcessorIndexFromNumber(&ProcNum); 1737 Assert(idxCpu != INVALID_PROCESSOR_INDEX); 1738 Assert(idxCpu >= idxCpuMin); 1739 idxCpuMin = idxCpu; 1740 pGip->aiFirstCpuSetIdxFromCpuGroup[iGroup] = (uint16_t)idxCpu; 1741 } 1742 } 1743 else 1744 { 1745 Assert(!g_pfnKeQueryMaximumGroupCount); 1746 Assert(!g_pfnKeGetProcessorIndexFromNumber); 1747 1748 pGip->cPossibleCpuGroups = 1; 1749 pGip->aiFirstCpuSetIdxFromCpuGroup[0] = 0; 1750 } 1751 } 1752 1753 1754 uint16_t VBOXCALL supdrvOSGipGetGroupFromCpu(PSUPDRVDEVEXT pDevExt, RTCPUID idCpu, uint16_t *piCpuGroupMember) 1755 { 1756 NOREF(pDevExt); 1757 1758 /* 1759 * This is just a wrapper around KeGetProcessorNumberFromIndex. 1760 */ 1761 if (g_pfnKeGetProcessorNumberFromIndex) 1762 { 1763 PROCESSOR_NUMBER ProcNum = { UINT16_MAX, UINT8_MAX, 0 }; 1764 NTSTATUS rcNt = g_pfnKeGetProcessorNumberFromIndex(idCpu, &ProcNum); 1765 if (NT_SUCCESS(rcNt)) 1766 { 1767 Assert(ProcNum.Group < g_pfnKeQueryMaximumGroupCount()); 1768 *piCpuGroupMember = ProcNum.Number; 1769 return ProcNum.Group; 1770 } 1771 1772 AssertMsgFailed(("rcNt=%#x for idCpu=%u\n", rcNt, idCpu)); 1773 } 1774 1775 *piCpuGroupMember = 0; 1776 return idCpu; 1777 } 1778 1779 1645 1780 /** 1646 1781 * Initializes any OS specific object creator fields. … … 1680 1815 { 1681 1816 RT_NOREF1(pDevExt); 1682 return false;1817 return g_Options.fOptForceAsyncTsc != 0; 1683 1818 } 1684 1819
Note:
See TracChangeset
for help on using the changeset viewer.