diff --git a/runtime/helpers/task_information.cpp b/runtime/helpers/task_information.cpp index e52aa24b22..83ea44d970 100644 --- a/runtime/helpers/task_information.cpp +++ b/runtime/helpers/task_information.cpp @@ -151,6 +151,14 @@ CompletionStamp &CommandComputeKernel::submit(uint32_t taskLevel, bool terminate IndirectHeap *dsh = nullptr; IndirectHeap *ioh = nullptr; + IndirectHeap::Type trackedHeaps[] = {IndirectHeap::SURFACE_STATE, IndirectHeap::INDIRECT_OBJECT, IndirectHeap::DYNAMIC_STATE, IndirectHeap::INSTRUCTION}; + + for (auto trackedHeap = 0u; trackedHeap < ARRAY_COUNT(trackedHeaps); trackedHeap++) { + if (commandQueue.getIndirectHeap(trackedHeaps[trackedHeap], 0).getUsed() > 0) { + commandQueue.releaseIndirectHeap(trackedHeaps[trackedHeap]); + } + } + if (executionModelKernel) { dsh = devQueue->getIndirectHeap(IndirectHeap::DYNAMIC_STATE); // In ExecutionModel IOH is the same as DSH to eliminate StateBaseAddress reprogramming for scheduler kernel and blocks. @@ -158,9 +166,6 @@ CompletionStamp &CommandComputeKernel::submit(uint32_t taskLevel, bool terminate memcpy_s(dsh->getSpace(0), dsh->getAvailableSpace(), ptrOffset(kernelOperation->dsh->getBase(), devQueue->colorCalcStateSize), kernelOperation->dsh->getUsed() - devQueue->colorCalcStateSize); dsh->getSpace(kernelOperation->dsh->getUsed() - devQueue->colorCalcStateSize); - - if (commandQueue.getIndirectHeap(IndirectHeap::SURFACE_STATE, 0).getUsed() > 0) - commandQueue.releaseIndirectHeap(IndirectHeap::SURFACE_STATE); } else { dsh = &commandQueue.getIndirectHeap(IndirectHeap::DYNAMIC_STATE, requestedDshSize); ioh = &commandQueue.getIndirectHeap(IndirectHeap::INDIRECT_OBJECT, requestedIohSize); diff --git a/unit_tests/command_queue/command_queue_hw_tests.cpp b/unit_tests/command_queue/command_queue_hw_tests.cpp index f681809a21..91991c2d74 100644 --- a/unit_tests/command_queue/command_queue_hw_tests.cpp +++ b/unit_tests/command_queue/command_queue_hw_tests.cpp @@ -348,6 +348,69 @@ HWTEST_F(CommandQueueHwTest, GivenNotCompleteUserEventPassedToEnqueueWhenEventIs mockCSR->getMemoryManager()->freeGraphicsMemory(printfSurface); mockCSR->getMemoryManager()->freeGraphicsMemory(constantSurface); } +typedef CommandQueueHwTest BlockedCommandQueueTest; +HWTEST_F(BlockedCommandQueueTest, givenCommandQueueWhichHasSomeUsedHeapsWhenBlockedCommandIsBeingSubmittedItReloadsThemToZeroToKeepProperOffsets) { + UserEvent userEvent(context); + MockKernelWithInternals mockKernelWithInternals(*pDevice); + auto mockKernel = mockKernelWithInternals.mockKernel; + + size_t offset = 0; + size_t size = 1; + + cl_event blockedEvent = &userEvent; + + auto &ish = pCmdQ->getIndirectHeap(IndirectHeap::INSTRUCTION, 4096u); + auto &ioh = pCmdQ->getIndirectHeap(IndirectHeap::INDIRECT_OBJECT, 4096u); + auto &dsh = pCmdQ->getIndirectHeap(IndirectHeap::DYNAMIC_STATE, 4096u); + auto &ssh = pCmdQ->getIndirectHeap(IndirectHeap::SURFACE_STATE, 4096u); + + ssh.getSpace(1); + ish.getSpace(1); + ioh.getSpace(1); + dsh.getSpace(1); + + auto ishBase = ish.getBase(); + auto iohBase = ioh.getBase(); + auto dshBase = dsh.getBase(); + auto sshBase = ssh.getBase(); + + pCmdQ->enqueueKernel(mockKernel, 1, &offset, &size, &size, 1, &blockedEvent, nullptr); + userEvent.setStatus(CL_COMPLETE); + + EXPECT_NE(ishBase, ish.getBase()); + EXPECT_NE(iohBase, ioh.getBase()); + EXPECT_NE(dshBase, dsh.getBase()); + EXPECT_NE(sshBase, ssh.getBase()); +} + +HWTEST_F(BlockedCommandQueueTest, givenCommandQueueWhichHasSomeUnusedHeapsWhenBlockedCommandIsBeingSubmittedThenThoseHeapsAreBeingUsed) { + UserEvent userEvent(context); + MockKernelWithInternals mockKernelWithInternals(*pDevice); + auto mockKernel = mockKernelWithInternals.mockKernel; + + size_t offset = 0; + size_t size = 1; + + cl_event blockedEvent = &userEvent; + + auto &ish = pCmdQ->getIndirectHeap(IndirectHeap::INSTRUCTION, 4096u); + auto &ioh = pCmdQ->getIndirectHeap(IndirectHeap::INDIRECT_OBJECT, 4096u); + auto &dsh = pCmdQ->getIndirectHeap(IndirectHeap::DYNAMIC_STATE, 4096u); + auto &ssh = pCmdQ->getIndirectHeap(IndirectHeap::SURFACE_STATE, 4096u); + + auto ishBase = ish.getBase(); + auto iohBase = ioh.getBase(); + auto dshBase = dsh.getBase(); + auto sshBase = ssh.getBase(); + + pCmdQ->enqueueKernel(mockKernel, 1, &offset, &size, &size, 1, &blockedEvent, nullptr); + userEvent.setStatus(CL_COMPLETE); + + EXPECT_EQ(ishBase, ish.getBase()); + EXPECT_EQ(iohBase, ioh.getBase()); + EXPECT_EQ(dshBase, dsh.getBase()); + EXPECT_EQ(sshBase, ssh.getBase()); +} typedef CommandQueueHwTest CommandQueueHwRefCountTest;