diff --git a/runtime/built_ins/built_ins.cpp b/runtime/built_ins/built_ins.cpp index 9037b7aaa0..602ae623f3 100644 --- a/runtime/built_ins/built_ins.cpp +++ b/runtime/built_ins/built_ins.cpp @@ -111,7 +111,7 @@ SchedulerKernel &BuiltIns::getSchedulerKernel(Context &context) { return *static_cast(schedulerBuiltIn.pKernel); } -const SipKernel &BuiltIns::getSipKernel(SipKernelType type, const Device &device) { +const SipKernel &BuiltIns::getSipKernel(SipKernelType type, Device &device) { uint32_t kernelId = static_cast(type); UNRECOVERABLE_IF(kernelId >= static_cast(SipKernelType::COUNT)); auto &sipBuiltIn = this->sipKernels[kernelId]; @@ -135,6 +135,8 @@ const SipKernel &BuiltIns::getSipKernel(SipKernelType type, const Device &device DEBUG_BREAK_IF(retVal != CL_SUCCESS); UNRECOVERABLE_IF(program == nullptr); + program->setDevice(&device); + retVal = program->processGenBinary(); DEBUG_BREAK_IF(retVal != CL_SUCCESS); diff --git a/runtime/built_ins/built_ins.h b/runtime/built_ins/built_ins.h index 25fbef37cf..411ad9b2de 100644 --- a/runtime/built_ins/built_ins.h +++ b/runtime/built_ins/built_ins.h @@ -196,7 +196,7 @@ class BuiltIns { SchedulerKernel &getSchedulerKernel(Context &context); - MOCKABLE_VIRTUAL const SipKernel &getSipKernel(SipKernelType type, const Device &device); + MOCKABLE_VIRTUAL const SipKernel &getSipKernel(SipKernelType type, Device &device); BuiltinsLib &getBuiltinsLib() { DEBUG_BREAK_IF(!builtinsLib.get()); diff --git a/runtime/built_ins/sip.cpp b/runtime/built_ins/sip.cpp index 388ad9b051..23925089a9 100644 --- a/runtime/built_ins/sip.cpp +++ b/runtime/built_ins/sip.cpp @@ -26,6 +26,7 @@ #include "runtime/program/program.h" #include "runtime/helpers/debug_helpers.h" #include "runtime/helpers/string.h" +#include "runtime/memory_manager/graphics_allocation.h" namespace OCLRT { @@ -78,6 +79,11 @@ SipKernel::SipKernel(SipKernelType type, Program *sipProgram) : type(type) { program.reset(sipProgram); } + +GraphicsAllocation *SipKernel::getSipAllocation() const { + return program->getKernelInfo(size_t{0})->getGraphicsAllocation(); +} + const char *SipKernel::getBinary() const { auto kernelInfo = program->getKernelInfo(size_t{0}); return reinterpret_cast(ptrOffset(kernelInfo->heapInfo.pKernelHeap, kernelInfo->systemKernelOffset)); diff --git a/runtime/built_ins/sip.h b/runtime/built_ins/sip.h index e15e50e563..8b127dc07f 100644 --- a/runtime/built_ins/sip.h +++ b/runtime/built_ins/sip.h @@ -29,6 +29,7 @@ namespace OCLRT { class Device; class Program; +class GraphicsAllocation; enum class SipKernelType : std::uint32_t { Csr = 0, @@ -57,6 +58,8 @@ class SipKernel { return type; } + GraphicsAllocation *getSipAllocation() const; + protected: SipKernelType type = SipKernelType::COUNT; std::unique_ptr program; diff --git a/runtime/command_stream/preemption.cpp b/runtime/command_stream/preemption.cpp index e1e26b5d9b..8eeb0e3a2e 100644 --- a/runtime/command_stream/preemption.cpp +++ b/runtime/command_stream/preemption.cpp @@ -104,7 +104,7 @@ void PreemptionHelper::adjustDefaultPreemptionMode(RuntimeCapabilityTable &devic } } -size_t PreemptionHelper::getInstructionHeapSipKernelReservedSize(const Device &device) { +size_t PreemptionHelper::getInstructionHeapSipKernelReservedSize(Device &device) { if (device.getPreemptionMode() != PreemptionMode::MidThread) { return 0; } @@ -112,7 +112,7 @@ size_t PreemptionHelper::getInstructionHeapSipKernelReservedSize(const Device &d return BuiltIns::getInstance().getSipKernel(SipKernelType::Csr, device).getBinarySize(); } -void PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, const Device &device) { +void PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, Device &device) { if (device.getPreemptionMode() != PreemptionMode::MidThread) { return; } @@ -128,7 +128,7 @@ void PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(LinearStr } // verify that SIP CSR kernel resides at the begining of the InstructionHeap -bool PreemptionHelper::isValidInstructionHeapForMidThreadPreemption(const LinearStream &ih, const Device &device) { +bool PreemptionHelper::isValidInstructionHeapForMidThreadPreemption(const LinearStream &ih, Device &device) { const SipKernel &sip = BuiltIns::getInstance().getSipKernel(SipKernelType::Csr, device); if (ih.getUsed() < sip.getBinarySize()) { return false; diff --git a/runtime/command_stream/preemption.h b/runtime/command_stream/preemption.h index 89104df9b3..4d20676635 100644 --- a/runtime/command_stream/preemption.h +++ b/runtime/command_stream/preemption.h @@ -41,9 +41,9 @@ class PreemptionHelper { static bool allowMidThreadPreemption(Kernel *kernel, Device &device); static void adjustDefaultPreemptionMode(RuntimeCapabilityTable &deviceCapabilities, bool allowMidThread, bool allowThreadGroup, bool allowMidBatch); - static size_t getInstructionHeapSipKernelReservedSize(const Device &device); - static void initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, const Device &device); - static bool isValidInstructionHeapForMidThreadPreemption(const LinearStream &ih, const Device &device); + static size_t getInstructionHeapSipKernelReservedSize(Device &device); + static void initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, Device &device); + static bool isValidInstructionHeapForMidThreadPreemption(const LinearStream &ih, Device &device); template static size_t getRequiredPreambleSize(const Device &device); @@ -56,7 +56,7 @@ class PreemptionHelper { template static void programCmdStream(LinearStream &cmdStream, PreemptionMode newPreemptionMode, PreemptionMode oldPreemptionMode, - GraphicsAllocation *preemptionCsr, const LinearStream &ih, const Device &device); + GraphicsAllocation *preemptionCsr, const LinearStream &ih, Device &device); template static size_t getPreemptionWaCsSize(const Device &device); diff --git a/runtime/command_stream/preemption.inl b/runtime/command_stream/preemption.inl index 614941401d..2a075269d8 100644 --- a/runtime/command_stream/preemption.inl +++ b/runtime/command_stream/preemption.inl @@ -95,7 +95,7 @@ template void PreemptionHelper::programCmdStream(LinearStream &cmdStream, PreemptionMode newPreemptionMode, PreemptionMode oldPreemptionMode, GraphicsAllocation *preemptionCsr, - const LinearStream &ih, const Device &device) { + const LinearStream &ih, Device &device) { if (oldPreemptionMode == newPreemptionMode) { DEBUG_BREAK_IF((newPreemptionMode == PreemptionMode::MidThread) && (false == isValidInstructionHeapForMidThreadPreemption(ih, device))); return; diff --git a/runtime/gen8/preemption.cpp b/runtime/gen8/preemption.cpp index e5624cd5c6..69c657633f 100644 --- a/runtime/gen8/preemption.cpp +++ b/runtime/gen8/preemption.cpp @@ -41,7 +41,7 @@ struct PreemptionConfig { template <> void PreemptionHelper::programCmdStream(LinearStream &cmdStream, PreemptionMode newPreemptionMode, PreemptionMode oldPreemptionMode, - GraphicsAllocation *preemptionCsr, const LinearStream &ih, const Device &device) { + GraphicsAllocation *preemptionCsr, const LinearStream &ih, Device &device) { if (newPreemptionMode == oldPreemptionMode) { return; } diff --git a/runtime/gen9/preemption.cpp b/runtime/gen9/preemption.cpp index aa2c34d58c..810c0851e7 100644 --- a/runtime/gen9/preemption.cpp +++ b/runtime/gen9/preemption.cpp @@ -46,7 +46,7 @@ struct PreemptionConfig { template void PreemptionHelper::programCmdStream(LinearStream &cmdStream, PreemptionMode newPreemptionMode, PreemptionMode oldPreemptionMode, GraphicsAllocation *preemptionCsr, - const LinearStream &ih, const Device &device); + const LinearStream &ih, Device &device); template void PreemptionHelper::programPreamble(LinearStream &preambleCmdStream, const Device &device, const GraphicsAllocation *preemptionCsr); template size_t PreemptionHelper::getRequiredPreambleSize(const Device &device); template size_t PreemptionHelper::getRequiredCmdStreamSize(PreemptionMode newPreemptionMode, PreemptionMode oldPreemptionMode); diff --git a/runtime/program/process_gen_binary.cpp b/runtime/program/process_gen_binary.cpp index 7ecb9b6077..06e5a59758 100644 --- a/runtime/program/process_gen_binary.cpp +++ b/runtime/program/process_gen_binary.cpp @@ -807,6 +807,8 @@ cl_int Program::parsePatchList(KernelInfo &kernelInfo) { } } + DEBUG_BREAK_IF(kernelInfo.heapInfo.pKernelHeader->KernelHeapSize && !this->pDevice); + return retVal; } diff --git a/runtime/program/program.h b/runtime/program/program.h index e8d73039c0..fbc86e1e56 100644 --- a/runtime/program/program.h +++ b/runtime/program/program.h @@ -165,6 +165,8 @@ class Program : public BaseObject<_cl_program> { return *pDevice; } + void setDevice(Device *device) { this->pDevice = device; } + cl_uint getNumDevices() const { return 1; } diff --git a/unit_tests/built_ins/built_in_tests.cpp b/unit_tests/built_ins/built_in_tests.cpp index 0a094f7eb5..f53fed8a73 100644 --- a/unit_tests/built_ins/built_in_tests.cpp +++ b/unit_tests/built_ins/built_in_tests.cpp @@ -1500,3 +1500,9 @@ TEST_F(BuiltInTests, getSipKernelReturnsProgramCreatedOutOfIsaAcquiredFromCompil EXPECT_EQ(SipKernelType::Csr, mockCompilerInterface.requestedSipKernel); p->release(); } + +TEST_F(BuiltInTests, givenSipKernelWhenItIsCreatedThenItHasGraphicsAllocationForKernel) { + const SipKernel &sipKern = BuiltIns::getInstance().getSipKernel(SipKernelType::Csr, *pContext->getDevice(0)); + auto sipAllocation = sipKern.getSipAllocation(); + EXPECT_NE(nullptr, sipAllocation); +} \ No newline at end of file diff --git a/unit_tests/device/device_caps_tests.cpp b/unit_tests/device/device_caps_tests.cpp index 9320c077b4..af85707a4f 100644 --- a/unit_tests/device/device_caps_tests.cpp +++ b/unit_tests/device/device_caps_tests.cpp @@ -256,16 +256,18 @@ TEST(Device_GetCaps, givenDeviceWithMidThreadPreemptionWhenDeviceIsCreatedThenSi { BuiltIns::shutDown(); - MockBuiltins mockBuiltins; - EXPECT_EQ(nullptr, mockBuiltins.peekCurrentInstance()); - mockBuiltins.overrideGlobalBuiltins(); - EXPECT_EQ(&mockBuiltins, mockBuiltins.peekCurrentInstance()); - EXPECT_FALSE(mockBuiltins.getSipKernelCalled); + std::unique_ptr mockBuiltins(new MockBuiltins); + EXPECT_EQ(nullptr, mockBuiltins->peekCurrentInstance()); + mockBuiltins->overrideGlobalBuiltins(); + EXPECT_EQ(mockBuiltins.get(), mockBuiltins->peekCurrentInstance()); + EXPECT_FALSE(mockBuiltins->getSipKernelCalled); DebugManager.flags.ForcePreemptionMode.set((int32_t)PreemptionMode::MidThread); auto device = std::unique_ptr(DeviceHelper<>::create(platformDevices[0])); - EXPECT_TRUE(mockBuiltins.getSipKernelCalled); - mockBuiltins.restoreGlobalBuiltins(); + EXPECT_TRUE(mockBuiltins->getSipKernelCalled); + mockBuiltins->restoreGlobalBuiltins(); + //make sure to release builtins prior to device as they use device + mockBuiltins.reset(); } } diff --git a/unit_tests/mocks/mock_builtins.h b/unit_tests/mocks/mock_builtins.h index 820696a6c5..ad33103e01 100644 --- a/unit_tests/mocks/mock_builtins.h +++ b/unit_tests/mocks/mock_builtins.h @@ -52,7 +52,7 @@ class MockBuiltins : public OCLRT::BuiltIns { return BuiltIns::pInstance; } - const OCLRT::SipKernel &getSipKernel(OCLRT::SipKernelType type, const OCLRT::Device &device) override { + const OCLRT::SipKernel &getSipKernel(OCLRT::SipKernelType type, OCLRT::Device &device) override { if (sipKernelsOverride.find(type) != sipKernelsOverride.end()) { return *sipKernelsOverride[type]; } diff --git a/unit_tests/mocks/mock_program.h b/unit_tests/mocks/mock_program.h index 2aa3004033..f11caf08e2 100644 --- a/unit_tests/mocks/mock_program.h +++ b/unit_tests/mocks/mock_program.h @@ -106,6 +106,8 @@ class MockProgram : public Program { allowNonUniform = allow; } + Device *getDevicePtr() { return this->pDevice; } + bool contextSet = false; }; diff --git a/unit_tests/program/program_tests.cpp b/unit_tests/program/program_tests.cpp index 0cba5f5636..7c1b8966b6 100644 --- a/unit_tests/program/program_tests.cpp +++ b/unit_tests/program/program_tests.cpp @@ -2919,3 +2919,13 @@ TEST_F(ProgramTests, givenSeparateBlockKernelsWhenSubgroupKernelWithChildKernelT EXPECT_EQ(1u, program.getBlockKernelManager()->getCount()); EXPECT_EQ(0, strcmp("subgroup_kernel_dispatch_0", program.getBlockKernelManager()->getBlockKernelInfo(0)->name.c_str())); } + +TEST(SimpleProgramTests, givenDefaultProgramWhenSetDeviceIsCalledThenDeviceIsSet) { + MockProgram pProgram(nullptr, false); + EXPECT_EQ(nullptr, pProgram.getDevicePtr()); + auto dummyDevice = (Device *)0x1337; + pProgram.SetDevice(dummyDevice); + EXPECT_EQ(dummyDevice, pProgram.getDevicePtr()); + pProgram.SetDevice(nullptr); + EXPECT_EQ(nullptr, pProgram.getDevicePtr()); +}