mirror of
https://github.com/intel/compute-runtime.git
synced 2025-12-19 06:24:51 +08:00
feature: support for context group on Windows
Related-To: NEO-14289 Signed-off-by: Mateusz Hoppe <mateusz.hoppe@intel.com>
This commit is contained in:
committed by
Compute-Runtime-Automation
parent
0ef032bb28
commit
98fcaf4ceb
@@ -105,6 +105,9 @@ class OsContext : public ReferenceTrackedObject<OsContext> {
|
||||
void setContextGroupCount(uint32_t contextGroupCount) {
|
||||
this->contextGroupCount = contextGroupCount;
|
||||
}
|
||||
uint32_t getContextGroupCount() {
|
||||
return contextGroupCount;
|
||||
}
|
||||
bool isPartOfContextGroup() const {
|
||||
return contextGroupCount > 0;
|
||||
}
|
||||
|
||||
@@ -56,7 +56,7 @@ bool OsContextWin::initializeContext(bool allocateInterrupt) {
|
||||
void OsContextWin::reInitializeContext() {
|
||||
NEO::EnvironmentVariableReader envReader;
|
||||
bool disableContextCreationFlag = envReader.getSetting("NEO_L0_SYSMAN_NO_CONTEXT_MODE", false);
|
||||
if (!disableContextCreationFlag) {
|
||||
if (!disableContextCreationFlag && !isPartOfContextGroup()) {
|
||||
if (contextInitialized && (false == this->wddm.skipResourceCleanup())) {
|
||||
wddm.getWddmInterface()->destroyHwQueue(hardwareQueue.handle);
|
||||
wddm.destroyContext(wddmContextHandle);
|
||||
@@ -111,7 +111,11 @@ OsContextWin::~OsContextWin() {
|
||||
if (residencyController.getMonitoredFence().fenceHandle != hardwareQueue.progressFenceHandle) {
|
||||
wddm.getWddmInterface()->destroyMonitorFence(residencyController.getMonitoredFence().fenceHandle);
|
||||
}
|
||||
wddm.destroyContext(wddmContextHandle);
|
||||
|
||||
if (!isPartOfContextGroup() ||
|
||||
(isPartOfContextGroup() && getPrimaryContext() == nullptr)) {
|
||||
wddm.destroyContext(wddmContextHandle);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -208,4 +208,5 @@ inline void propagateData(ADAPTER_INFO_KMD &adapterInfo) {
|
||||
base.WaTable = adapterInfo.WaTable;
|
||||
base.GfxPlatform = adapterInfo.GfxPlatform;
|
||||
}
|
||||
struct CREATEHWQUEUE_PVTDATA {}; // NOLINT(readability-identifier-naming)
|
||||
#endif
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (C) 2021-2024 Intel Corporation
|
||||
* Copyright (C) 2021-2025 Intel Corporation
|
||||
*
|
||||
* SPDX-License-Identifier: MIT
|
||||
*
|
||||
@@ -21,4 +21,9 @@ CREATECONTEXT_PVTDATA initPrivateData(OsContextWin &osContext) {
|
||||
return privateData;
|
||||
}
|
||||
|
||||
CREATEHWQUEUE_PVTDATA initHwQueuePrivateData(OsContextWin &osContext) {
|
||||
CREATEHWQUEUE_PVTDATA privateData = {};
|
||||
return privateData;
|
||||
}
|
||||
|
||||
} // namespace NEO
|
||||
|
||||
@@ -1011,6 +1011,11 @@ bool Wddm::setLowPriorityContextParam(D3DKMT_HANDLE contextHandle) {
|
||||
}
|
||||
|
||||
bool Wddm::createContext(OsContextWin &osContext) {
|
||||
if (osContext.isPartOfContextGroup() && osContext.getPrimaryContext() != nullptr && wddmInterface->hwQueuesSupported()) {
|
||||
osContext.setWddmContextHandle(static_cast<const OsContextWin *>(osContext.getPrimaryContext())->getWddmContextHandle());
|
||||
return true;
|
||||
}
|
||||
|
||||
NTSTATUS status = STATUS_UNSUCCESSFUL;
|
||||
D3DKMT_CREATECONTEXTVIRTUAL createContext = {};
|
||||
|
||||
|
||||
@@ -47,6 +47,7 @@ enum class HeapIndex : uint32_t;
|
||||
unsigned int readEnablePreemptionRegKey();
|
||||
bool isShutdownInProgress();
|
||||
CREATECONTEXT_PVTDATA initPrivateData(OsContextWin &osContext);
|
||||
CREATEHWQUEUE_PVTDATA initHwQueuePrivateData(OsContextWin &osContext);
|
||||
|
||||
class Wddm : public DriverModel {
|
||||
public:
|
||||
|
||||
@@ -105,11 +105,18 @@ bool NEO::WddmInterface20::createFenceForDirectSubmission(MonitoredFence &monito
|
||||
|
||||
bool WddmInterface23::createHwQueue(OsContextWin &osContext) {
|
||||
D3DKMT_CREATEHWQUEUE createHwQueue = {};
|
||||
CREATEHWQUEUE_PVTDATA hwQueuePrivateData = {};
|
||||
|
||||
if (!wddm.getGdi()->setupHwQueueProcAddresses()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (osContext.isPartOfContextGroup()) {
|
||||
hwQueuePrivateData = initHwQueuePrivateData(osContext);
|
||||
createHwQueue.pPrivateDriverData = &hwQueuePrivateData;
|
||||
createHwQueue.PrivateDriverDataSize = sizeof(hwQueuePrivateData);
|
||||
}
|
||||
|
||||
createHwQueue.hHwContext = osContext.getWddmContextHandle();
|
||||
if (osContext.getPreemptionMode() >= PreemptionMode::MidBatch) {
|
||||
createHwQueue.Flags.DisableGpuTimeout = wddm.getEnablePreemptionRegValue();
|
||||
|
||||
@@ -601,6 +601,7 @@ NTSTATUS __stdcall mockD3DKMTSetAllocationPriority(IN CONST D3DKMT_SETALLOCATION
|
||||
}
|
||||
|
||||
static D3DKMT_CREATEHWQUEUE createHwQueueData{};
|
||||
static CREATEHWQUEUE_PVTDATA createHwQueuePrivateData{};
|
||||
|
||||
NTSTATUS __stdcall mockD3DKMTCreateHwQueue(IN OUT D3DKMT_CREATEHWQUEUE *createHwQueue) {
|
||||
createHwQueue->hHwQueueProgressFence = 1;
|
||||
@@ -608,6 +609,11 @@ NTSTATUS __stdcall mockD3DKMTCreateHwQueue(IN OUT D3DKMT_CREATEHWQUEUE *createHw
|
||||
createHwQueue->HwQueueProgressFenceGPUVirtualAddress = 3;
|
||||
createHwQueue->hHwQueue = 4;
|
||||
createHwQueueData = *createHwQueue;
|
||||
|
||||
if (createHwQueue->PrivateDriverDataSize == sizeof(CREATEHWQUEUE_PVTDATA) && createHwQueue->pPrivateDriverData) {
|
||||
createHwQueuePrivateData = *((CREATEHWQUEUE_PVTDATA *)createHwQueue->pPrivateDriverData);
|
||||
createHwQueueData.pPrivateDriverData = &createHwQueuePrivateData;
|
||||
}
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -615,6 +621,8 @@ static D3DKMT_DESTROYHWQUEUE destroyHwQueueData{};
|
||||
|
||||
NTSTATUS __stdcall mockD3DKMTDestroyHwQueue(IN CONST D3DKMT_DESTROYHWQUEUE *destroyHwQueue) {
|
||||
destroyHwQueueData = *destroyHwQueue;
|
||||
createHwQueueData.pPrivateDriverData = nullptr;
|
||||
createHwQueueData.PrivateDriverDataSize = 0;
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
@@ -246,3 +246,63 @@ TEST_F(Wddm23TestsWithoutWddmInit, givenFailureOnGdiInitializationWhenCreatingHw
|
||||
EXPECT_EQ(1u, wddmMockInterface->createHwQueueCalled);
|
||||
EXPECT_FALSE(wddmMockInterface->createHwQueueResult);
|
||||
}
|
||||
|
||||
TEST_F(Wddm23TestsWithoutWddmInit, givenContextGroupWhenContextFromContextGroupCreatedThenItHasPrimaryContextHandle) {
|
||||
if (defaultHwInfo->capabilityTable.defaultEngineType != aub_stream::EngineType::ENGINE_CCS) {
|
||||
GTEST_SKIP();
|
||||
}
|
||||
|
||||
DebugManagerStateRestore retore;
|
||||
debugManager.flags.ContextGroupSize.set(4);
|
||||
|
||||
wddmMockInterface = static_cast<WddmMockInterface23 *>(wddm->wddmInterface.release());
|
||||
wddm->init();
|
||||
wddm->wddmInterface.reset(wddmMockInterface);
|
||||
|
||||
EngineTypeUsage engineUsage = {};
|
||||
engineUsage.first = aub_stream::EngineType::ENGINE_CCS;
|
||||
engineUsage.second = EngineUsage::regular;
|
||||
|
||||
osContext = std::make_unique<OsContextWin>(*wddm, 0, 0u,
|
||||
EngineDescriptorHelper::getDefaultDescriptor(engineUsage));
|
||||
EXPECT_TRUE(osContext->ensureContextInitialized(false));
|
||||
EXPECT_EQ(1u, wddmMockInterface->createHwQueueCalled);
|
||||
|
||||
auto osContext2 = std::make_unique<OsContextWin>(*wddm, 0, 1u,
|
||||
EngineDescriptorHelper::getDefaultDescriptor(engineUsage));
|
||||
osContext2->setPrimaryContext(osContext.get());
|
||||
|
||||
EXPECT_TRUE(osContext2->ensureContextInitialized(false));
|
||||
EXPECT_EQ(osContext->getWddmContextHandle(), osContext2->getWddmContextHandle());
|
||||
EXPECT_EQ(getCreateHwQueueData()->hHwContext, osContext->getWddmContextHandle());
|
||||
}
|
||||
|
||||
TEST_F(Wddm23TestsWithoutWddmInit, givenContextGroupWhenContextFromContextGroupDestroyedThenPrimaryContextHandleIsDestroyedOnce) {
|
||||
if (defaultHwInfo->capabilityTable.defaultEngineType != aub_stream::EngineType::ENGINE_CCS) {
|
||||
GTEST_SKIP();
|
||||
}
|
||||
|
||||
DebugManagerStateRestore retore;
|
||||
debugManager.flags.ContextGroupSize.set(4);
|
||||
|
||||
wddmMockInterface = static_cast<WddmMockInterface23 *>(wddm->wddmInterface.release());
|
||||
wddm->init();
|
||||
wddm->wddmInterface.reset(wddmMockInterface);
|
||||
|
||||
{
|
||||
EngineTypeUsage engineUsage = {};
|
||||
engineUsage.first = aub_stream::EngineType::ENGINE_CCS;
|
||||
engineUsage.second = EngineUsage::regular;
|
||||
|
||||
osContext = std::make_unique<OsContextWin>(*wddm, 0, 0u,
|
||||
EngineDescriptorHelper::getDefaultDescriptor(engineUsage));
|
||||
EXPECT_TRUE(osContext->ensureContextInitialized(false));
|
||||
|
||||
auto osContext2 = std::make_unique<OsContextWin>(*wddm, 0, 1u,
|
||||
EngineDescriptorHelper::getDefaultDescriptor(engineUsage));
|
||||
osContext2->setPrimaryContext(osContext.get());
|
||||
EXPECT_TRUE(osContext2->ensureContextInitialized(false));
|
||||
}
|
||||
|
||||
EXPECT_EQ(1u, wddm->destroyContextResult.called);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user