[22/n] Internal 4GB allocator.

- Finalize Instruction Heap removal.

Change-Id: Idd7df94a228238a5157c3251180fc3c8d3a189df
This commit is contained in:
Mrozek, Michal
2018-03-29 07:31:09 +02:00
parent 2be5934096
commit 7f3c4d3d70
12 changed files with 2 additions and 170 deletions

View File

@ -217,11 +217,6 @@ uint32_t CommandQueue::getTaskLevelFromWaitList(uint32_t taskLevel,
return taskLevel; return taskLevel;
} }
size_t CommandQueue::getInstructionHeapReservedBlockSize() const {
return alignUp(device->getCommandStreamReceiver().getInstructionHeapCmdStreamReceiverReservedSize(),
MemoryConstants::cacheLineSize);
}
IndirectHeap &CommandQueue::getIndirectHeap(IndirectHeap::Type heapType, IndirectHeap &CommandQueue::getIndirectHeap(IndirectHeap::Type heapType,
size_t minRequiredSize) { size_t minRequiredSize) {
DEBUG_BREAK_IF(static_cast<uint32_t>(heapType) >= ARRAY_COUNT(indirectHeap)); DEBUG_BREAK_IF(static_cast<uint32_t>(heapType) >= ARRAY_COUNT(indirectHeap));
@ -243,10 +238,6 @@ IndirectHeap &CommandQueue::getIndirectHeap(IndirectHeap::Type heapType,
if (!heapMemory) { if (!heapMemory) {
size_t reservedSize = 0; size_t reservedSize = 0;
auto finalHeapSize = defaultHeapSize; auto finalHeapSize = defaultHeapSize;
if (heapType == IndirectHeap::INSTRUCTION) {
finalHeapSize = optimalInstructionHeapSize;
reservedSize = getInstructionHeapReservedBlockSize();
}
minRequiredSize += reservedSize; minRequiredSize += reservedSize;
@ -274,11 +265,6 @@ IndirectHeap &CommandQueue::getIndirectHeap(IndirectHeap::Type heapType,
heap = new IndirectHeap(heapMemory); heap = new IndirectHeap(heapMemory);
heap->overrideMaxSize(finalHeapSize); heap->overrideMaxSize(finalHeapSize);
} }
if (heapType == IndirectHeap::INSTRUCTION) {
device->getCommandStreamReceiver().initializeInstructionHeapCmdStreamReceiverReservedBlock(*heap);
heap->align(MemoryConstants::cacheLineSize);
}
} }
return *heap; return *heap;

View File

@ -333,7 +333,6 @@ class CommandQueue : public BaseObject<_cl_command_queue> {
Context *getContextPtr() { return context; } Context *getContextPtr() { return context; }
LinearStream &getCS(size_t minRequiredSize = 1024u); LinearStream &getCS(size_t minRequiredSize = 1024u);
size_t getInstructionHeapReservedBlockSize() const;
IndirectHeap &getIndirectHeap(IndirectHeap::Type heapType, IndirectHeap &getIndirectHeap(IndirectHeap::Type heapType,
size_t minRequiredSize = 0u); size_t minRequiredSize = 0u);

View File

@ -219,14 +219,6 @@ void CommandStreamReceiver::setRequiredScratchSize(uint32_t newRequiredScratchSi
} }
} }
size_t CommandStreamReceiver::getInstructionHeapCmdStreamReceiverReservedSize() const {
return PreemptionHelper::getInstructionHeapSipKernelReservedSize(*memoryManager->device);
}
void CommandStreamReceiver::initializeInstructionHeapCmdStreamReceiverReservedBlock(LinearStream &ih) const {
return PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(ih, *memoryManager->device);
}
GraphicsAllocation *CommandStreamReceiver::allocateDebugSurface(size_t size) { GraphicsAllocation *CommandStreamReceiver::allocateDebugSurface(size_t size) {
UNRECOVERABLE_IF(debugSurface != nullptr); UNRECOVERABLE_IF(debugSurface != nullptr);
debugSurface = memoryManager->allocateGraphicsMemory(size); debugSurface = memoryManager->allocateGraphicsMemory(size);

View File

@ -116,12 +116,6 @@ class CommandStreamReceiver {
virtual void waitForTaskCountWithKmdNotifyFallback(uint32_t taskCountToWait, FlushStamp flushStampToWait, bool useQuickKmdSleep) = 0; virtual void waitForTaskCountWithKmdNotifyFallback(uint32_t taskCountToWait, FlushStamp flushStampToWait, bool useQuickKmdSleep) = 0;
MOCKABLE_VIRTUAL bool waitForCompletionWithTimeout(bool enableTimeout, int64_t timeoutMicroseconds, uint32_t taskCountToWait); MOCKABLE_VIRTUAL bool waitForCompletionWithTimeout(bool enableTimeout, int64_t timeoutMicroseconds, uint32_t taskCountToWait);
// returns size of block that needs to be reserved at the beginning of each instruction heap for CommandStreamReceiver
MOCKABLE_VIRTUAL size_t getInstructionHeapCmdStreamReceiverReservedSize() const;
// allows CommandStreamReceiver to prepopulate reserved block in instruction heap
MOCKABLE_VIRTUAL void initializeInstructionHeapCmdStreamReceiverReservedBlock(LinearStream &ih) const;
void setSamplerCacheFlushRequired(SamplerCacheFlushState value) { this->samplerCacheFlushRequired = value; } void setSamplerCacheFlushRequired(SamplerCacheFlushState value) { this->samplerCacheFlushRequired = value; }
// Collect patch info data // Collect patch info data

View File

@ -104,29 +104,6 @@ void PreemptionHelper::adjustDefaultPreemptionMode(RuntimeCapabilityTable &devic
} }
} }
size_t PreemptionHelper::getInstructionHeapSipKernelReservedSize(Device &device) {
if (device.getPreemptionMode() != PreemptionMode::MidThread) {
return 0;
}
return BuiltIns::getInstance().getSipKernel(SipKernelType::Csr, device).getBinarySize();
}
void PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, Device &device) {
if (device.getPreemptionMode() != PreemptionMode::MidThread) {
return;
}
const SipKernel &sip = BuiltIns::getInstance().getSipKernel(SipKernelType::Csr, device);
size_t sipSize = sip.getBinarySize();
UNRECOVERABLE_IF(sipSize > ih.getAvailableSpace());
UNRECOVERABLE_IF(0 != ih.getUsed());
void *blockForSip = ih.getSpace(sipSize);
UNRECOVERABLE_IF(nullptr == blockForSip);
auto err = memcpy_s(blockForSip, sipSize, sip.getBinary(), sipSize);
UNRECOVERABLE_IF(err != 0);
}
PreemptionMode PreemptionHelper::getDefaultPreemptionMode(const HardwareInfo &hwInfo) { PreemptionMode PreemptionHelper::getDefaultPreemptionMode(const HardwareInfo &hwInfo) {
return DebugManager.flags.ForcePreemptionMode.get() == -1 return DebugManager.flags.ForcePreemptionMode.get() == -1
? hwInfo.capabilityTable.defaultPreemptionMode ? hwInfo.capabilityTable.defaultPreemptionMode

View File

@ -41,9 +41,6 @@ class PreemptionHelper {
static bool allowMidThreadPreemption(Kernel *kernel, Device &device); static bool allowMidThreadPreemption(Kernel *kernel, Device &device);
static void adjustDefaultPreemptionMode(RuntimeCapabilityTable &deviceCapabilities, bool allowMidThread, bool allowThreadGroup, bool allowMidBatch); static void adjustDefaultPreemptionMode(RuntimeCapabilityTable &deviceCapabilities, bool allowMidThread, bool allowThreadGroup, bool allowMidBatch);
static size_t getInstructionHeapSipKernelReservedSize(Device &device);
static void initializeInstructionHeapSipKernelReservedBlock(LinearStream &ih, Device &device);
template <typename GfxFamily> template <typename GfxFamily>
static size_t getRequiredPreambleSize(const Device &device); static size_t getRequiredPreambleSize(const Device &device);

View File

@ -30,7 +30,6 @@ namespace OCLRT {
class GraphicsAllocation; class GraphicsAllocation;
constexpr size_t defaultHeapSize = 64 * KB; constexpr size_t defaultHeapSize = 64 * KB;
constexpr size_t optimalInstructionHeapSize = 512 * KB;
constexpr size_t maxSshSize = defaultHeapSize - MemoryConstants::pageSize; constexpr size_t maxSshSize = defaultHeapSize - MemoryConstants::pageSize;
class IndirectHeap : public LinearStream { class IndirectHeap : public LinearStream {
@ -41,7 +40,6 @@ class IndirectHeap : public LinearStream {
DYNAMIC_STATE = 0, DYNAMIC_STATE = 0,
GENERAL_STATE, GENERAL_STATE,
INDIRECT_OBJECT, INDIRECT_OBJECT,
INSTRUCTION,
SURFACE_STATE, SURFACE_STATE,
NUM_TYPES NUM_TYPES
}; };

View File

@ -421,8 +421,6 @@ TEST_P(CommandQueueIndirectHeapTest, IndirectHeapContainsAtLeast64KB) {
auto &indirectHeap = cmdQ.getIndirectHeap(this->GetParam(), sizeof(uint32_t)); auto &indirectHeap = cmdQ.getIndirectHeap(this->GetParam(), sizeof(uint32_t));
if (this->GetParam() == IndirectHeap::SURFACE_STATE) { if (this->GetParam() == IndirectHeap::SURFACE_STATE) {
EXPECT_EQ(64 * KB - MemoryConstants::pageSize, indirectHeap.getAvailableSpace()); EXPECT_EQ(64 * KB - MemoryConstants::pageSize, indirectHeap.getAvailableSpace());
} else if (this->GetParam() == IndirectHeap::INSTRUCTION) {
EXPECT_EQ(optimalInstructionHeapSize, indirectHeap.getAvailableSpace());
} else { } else {
EXPECT_EQ(64 * KB, indirectHeap.getAvailableSpace()); EXPECT_EQ(64 * KB, indirectHeap.getAvailableSpace());
} }
@ -478,9 +476,6 @@ TEST_P(CommandQueueIndirectHeapTest, MemoryManagerWithReusableAllocationsWhenAsk
auto memoryManager = pDevice->getMemoryManager(); auto memoryManager = pDevice->getMemoryManager();
auto allocationSize = defaultHeapSize * 2; auto allocationSize = defaultHeapSize * 2;
if (this->GetParam() == IndirectHeap::INSTRUCTION) {
allocationSize = optimalInstructionHeapSize * 2;
}
auto allocation = memoryManager->allocateGraphicsMemory(allocationSize); auto allocation = memoryManager->allocateGraphicsMemory(allocationSize);
memoryManager->storeAllocation(std::unique_ptr<GraphicsAllocation>(allocation), REUSABLE_ALLOCATION); memoryManager->storeAllocation(std::unique_ptr<GraphicsAllocation>(allocation), REUSABLE_ALLOCATION);
@ -627,7 +622,6 @@ INSTANTIATE_TEST_CASE_P(
IndirectHeap::DYNAMIC_STATE, IndirectHeap::DYNAMIC_STATE,
IndirectHeap::GENERAL_STATE, IndirectHeap::GENERAL_STATE,
IndirectHeap::INDIRECT_OBJECT, IndirectHeap::INDIRECT_OBJECT,
IndirectHeap::INSTRUCTION,
IndirectHeap::SURFACE_STATE)); IndirectHeap::SURFACE_STATE));
typedef Test<DeviceFixture> CommandQueueCSTest; typedef Test<DeviceFixture> CommandQueueCSTest;
@ -733,40 +727,6 @@ HWTEST_F(WaitForQueueCompletionTests, whenFinishIsCalledThenCallWaitWithoutQuick
EXPECT_FALSE(cmdQ->requestedUseQuickKmdSleep); EXPECT_FALSE(cmdQ->requestedUseQuickKmdSleep);
} }
constexpr char sipPattern[] = {2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 39, 41};
static_assert(false == isAligned<MemoryConstants::cacheLineSize>(sizeof(sipPattern)),
"Will be checking for automatic cacheline alignment, so pattern length must not be a multiple of cacheline");
constexpr size_t alignedPatternSize = alignUp(sizeof(sipPattern), MemoryConstants::cacheLineSize);
TEST(CommandQueueGetIndirectHeap, whenNewInstructionHeapIsBeingCreatedThenCommandStreamReceiverCanReserveAMemoryBlockAtItsBegining) {
auto mockDevice = std::unique_ptr<MockDevice>(MockDevice::create<MockDevice>(nullptr));
MockCommandStreamReceiver *csr = new MockCommandStreamReceiver;
mockDevice->resetCommandStreamReceiver(csr);
csr->instructionHeapReserveredData.assign(sipPattern, sipPattern + sizeof(sipPattern));
MockCommandQueue cmdQ{nullptr, mockDevice.get(), nullptr};
IndirectHeap &heap = cmdQ.getIndirectHeap(OCLRT::IndirectHeap::INSTRUCTION, 8192);
EXPECT_LE(8192U, heap.getAvailableSpace());
EXPECT_EQ(alignedPatternSize, heap.getUsed());
ASSERT_LE(sizeof(sipPattern), heap.getMaxAvailableSpace());
char *reservedBlock = reinterpret_cast<char *>(heap.getCpuBase());
auto dataFoundInReservedBlock = ArrayRef<char>(reservedBlock, sizeof(sipPattern));
auto expectedData = ArrayRef<char>(csr->instructionHeapReserveredData);
EXPECT_THAT(dataFoundInReservedBlock, testing::ContainerEq(expectedData));
}
TEST(CommandQueueGetIndirectHeap, whenCheckingForCsrInstructionHeapReservedBlockSizeThenCachelineAlignmentIsExpected) {
auto mockDevice = std::unique_ptr<MockDevice>(MockDevice::create<MockDevice>(nullptr));
MockCommandStreamReceiver *csr = new MockCommandStreamReceiver;
mockDevice->resetCommandStreamReceiver(csr);
csr->instructionHeapReserveredData.assign(sipPattern, sipPattern + sizeof(sipPattern));
MockCommandQueue cmdQ{nullptr, mockDevice.get(), nullptr};
EXPECT_GE(alignedPatternSize, csr->getInstructionHeapCmdStreamReceiverReservedSize());
EXPECT_EQ(alignedPatternSize, cmdQ.getInstructionHeapReservedBlockSize());
}
TEST(CommandQueue, givenEnqueueAcquireSharedObjectsWhenNoObjectsThenReturnSuccess) { TEST(CommandQueue, givenEnqueueAcquireSharedObjectsWhenNoObjectsThenReturnSuccess) {
MockContext context; MockContext context;
CommandQueue cmdQ(&context, nullptr, 0); CommandQueue cmdQ(&context, nullptr, 0);

View File

@ -2763,6 +2763,7 @@ HWTEST_F(CommandStreamReceiverFlushTaskTests, givenCsrInBatchingModeWhenSusbsequ
dispatchFlags); dispatchFlags);
EXPECT_EQ(expectedUsed + additionalSize, mockCsr->peekTotalMemoryUsed()); EXPECT_EQ(expectedUsed + additionalSize, mockCsr->peekTotalMemoryUsed());
mockCsr->flushBatchedSubmissions();
} }
struct MockedMemoryManager : public OsAgnosticMemoryManager { struct MockedMemoryManager : public OsAgnosticMemoryManager {

View File

@ -260,36 +260,4 @@ TEST_F(CommandStreamReceiverTest, givenForced32BitAddressingWhenDebugSurfaceIsAl
HWTEST_F(CommandStreamReceiverTest, givenDefaultCommandStreamReceiverThenDefaultDispatchingPolicyIsImmediateSubmission) { HWTEST_F(CommandStreamReceiverTest, givenDefaultCommandStreamReceiverThenDefaultDispatchingPolicyIsImmediateSubmission) {
auto &csr = pDevice->getUltCommandStreamReceiver<FamilyType>(); auto &csr = pDevice->getUltCommandStreamReceiver<FamilyType>();
EXPECT_EQ(CommandStreamReceiver::DispatchMode::ImmediateDispatch, csr.dispatchMode); EXPECT_EQ(CommandStreamReceiver::DispatchMode::ImmediateDispatch, csr.dispatchMode);
} }
TEST(CommandStreamReceiver, cmdStreamReceiverReservedBlockInInstructionHeapIsBasedOnPreemptionHelper) {
auto mockDevice = std::unique_ptr<MockDevice>(MockDevice::create<MockDevice>(nullptr));
mockDevice->setPreemptionMode(PreemptionMode::MidThread);
{
MockBuiltins mockBuiltins;
mockBuiltins.overrideGlobalBuiltins();
{
auto sipOverride = std::unique_ptr<OCLRT::SipKernel>(new OCLRT::SipKernel(OCLRT::SipKernelType::Csr, getSipProgramWithCustomBinary()));
mockBuiltins.overrideSipKernel(std::move(sipOverride));
}
size_t reservedSize = mockDevice->getCommandStreamReceiver().getInstructionHeapCmdStreamReceiverReservedSize();
size_t expectedSize = OCLRT::PreemptionHelper::getInstructionHeapSipKernelReservedSize(*mockDevice);
EXPECT_NE(0U, expectedSize);
EXPECT_EQ(expectedSize, reservedSize);
ASSERT_LE(expectedSize, reservedSize);
StackVec<char, 4096> cmdStreamIhBuffer;
cmdStreamIhBuffer.resize(reservedSize);
LinearStream cmdStreamReceiverInstrucionHeap{cmdStreamIhBuffer.begin(), cmdStreamIhBuffer.size()};
mockDevice->getCommandStreamReceiver().initializeInstructionHeapCmdStreamReceiverReservedBlock(cmdStreamReceiverInstrucionHeap);
StackVec<char, 4096> preemptionHelperIhBuffer;
preemptionHelperIhBuffer.resize(expectedSize);
LinearStream preemptionHelperInstrucionHeap{preemptionHelperIhBuffer.begin(), preemptionHelperIhBuffer.size()};
PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(preemptionHelperInstrucionHeap, *mockDevice);
cmdStreamIhBuffer.resize(expectedSize);
EXPECT_THAT(preemptionHelperIhBuffer, testing::ContainerEq(cmdStreamIhBuffer));
}
}

View File

@ -236,25 +236,6 @@ class MockCommandStreamReceiver : public CommandStreamReceiver {
} }
void setOSInterface(OSInterface *osInterface); void setOSInterface(OSInterface *osInterface);
size_t getInstructionHeapCmdStreamReceiverReservedSize() const override {
if (instructionHeapReserveredData.size() == 0) {
return CommandStreamReceiver::getInstructionHeapCmdStreamReceiverReservedSize();
}
return instructionHeapReserveredData.size();
}
void initializeInstructionHeapCmdStreamReceiverReservedBlock(LinearStream &ih) const override {
if (instructionHeapReserveredData.size() == 0) {
CommandStreamReceiver::initializeInstructionHeapCmdStreamReceiverReservedBlock(ih);
return;
}
void *block = ih.getSpace(instructionHeapReserveredData.size());
memcpy_s(block, instructionHeapReserveredData.size(),
instructionHeapReserveredData.data(), instructionHeapReserveredData.size());
}
}; };
#if defined(__clang__) #if defined(__clang__)

View File

@ -313,27 +313,6 @@ TEST(PreemptionTest, defaultMode) {
EXPECT_EQ(-1, preemptionModeFromDebugManager); EXPECT_EQ(-1, preemptionModeFromDebugManager);
} }
TEST(PreemptionTest, whenPreemptionModeIsNotMidThreadThenInstructionHeapSipKernelReservedSizeIsEmpty) {
char buffer[4096];
LinearStream instructionHeap(buffer, sizeof(buffer));
auto mockDevice = std::unique_ptr<MockDevice>(MockDevice::create<MockDevice>(nullptr));
mockDevice->setPreemptionMode(PreemptionMode::Disabled);
EXPECT_EQ(0U, PreemptionHelper::getInstructionHeapSipKernelReservedSize(*mockDevice));
PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(instructionHeap, *mockDevice);
ASSERT_EQ(0U, instructionHeap.getUsed());
mockDevice->setPreemptionMode(PreemptionMode::MidBatch);
EXPECT_EQ(0U, PreemptionHelper::getInstructionHeapSipKernelReservedSize(*mockDevice));
PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(instructionHeap, *mockDevice);
ASSERT_EQ(0U, instructionHeap.getUsed());
mockDevice->setPreemptionMode(PreemptionMode::ThreadGroup);
EXPECT_EQ(0U, PreemptionHelper::getInstructionHeapSipKernelReservedSize(*mockDevice));
PreemptionHelper::initializeInstructionHeapSipKernelReservedBlock(instructionHeap, *mockDevice);
ASSERT_EQ(0U, instructionHeap.getUsed());
}
struct PreemptionHwTest : ::testing::Test, ::testing::WithParamInterface<PreemptionMode> { struct PreemptionHwTest : ::testing::Test, ::testing::WithParamInterface<PreemptionMode> {
}; };