mirror of
https://github.com/intel/compute-runtime.git
synced 2025-09-15 13:01:45 +08:00
Fix heap size programming.
- In various scenarios code was not programming the max heap size correctly - It was possible for SSH to overcome the limit - Size was programmed smaller then it really was, which resulted in smaller reuse, which led to SBA reprogramming which led to lower performance in ooq scenarios - This change fixes the heap size programming by always utilizing full allocation size and always limiting SSH at proper value Change-Id: Ib703d2b0709ed8227a293def3a454bf1bb516dfd
This commit is contained in:

committed by
sys_ocldev

parent
285ecbd9cb
commit
37c7e27276
2
Jenkinsfile
vendored
2
Jenkinsfile
vendored
@ -2,4 +2,4 @@
|
||||
neoDependenciesRev='733920-765'
|
||||
strategy='EQUAL'
|
||||
allowedF=47
|
||||
allowedCD=365
|
||||
allowedCD=364
|
||||
|
@ -237,34 +237,34 @@ IndirectHeap &CommandQueue::getIndirectHeap(IndirectHeap::Type heapType,
|
||||
}
|
||||
|
||||
if (!heapMemory) {
|
||||
// Heap should be at least minHeapSize unless we're requesting an empty heap
|
||||
size_t minHeapSize = 64 * KB;
|
||||
if (IndirectHeap::SURFACE_STATE == heapType) {
|
||||
minHeapSize -= MemoryConstants::pageSize;
|
||||
}
|
||||
|
||||
size_t reservedSize = 0;
|
||||
if (heapType == IndirectHeap::INSTRUCTION) {
|
||||
reservedSize = getInstructionHeapReservedBlockSize();
|
||||
}
|
||||
|
||||
auto finalHeapSize = defaultHeapSize;
|
||||
minRequiredSize += reservedSize;
|
||||
minRequiredSize = minRequiredSize ? std::max(minRequiredSize, minHeapSize) : 0;
|
||||
minRequiredSize = minRequiredSize > 0 ? alignUp(minRequiredSize, MemoryConstants::cacheLineSize) : 0;
|
||||
|
||||
const size_t heapAlignment = MemoryConstants::pageSize;
|
||||
heapMemory = memoryManager->obtainReusableAllocation(minRequiredSize).release();
|
||||
finalHeapSize = alignUp(std::max(finalHeapSize, minRequiredSize), MemoryConstants::pageSize);
|
||||
|
||||
heapMemory = memoryManager->obtainReusableAllocation(finalHeapSize).release();
|
||||
|
||||
if (!heapMemory) {
|
||||
heapMemory = memoryManager->allocateGraphicsMemory(minRequiredSize, heapAlignment);
|
||||
heapMemory = memoryManager->allocateGraphicsMemory(finalHeapSize, MemoryConstants::pageSize);
|
||||
} else {
|
||||
finalHeapSize = std::max(heapMemory->getUnderlyingBufferSize(), finalHeapSize);
|
||||
}
|
||||
|
||||
if (IndirectHeap::SURFACE_STATE == heapType) {
|
||||
DEBUG_BREAK_IF(minRequiredSize > maxSshSize);
|
||||
finalHeapSize = maxSshSize;
|
||||
}
|
||||
|
||||
if (heap) {
|
||||
heap->replaceBuffer(heapMemory->getUnderlyingBuffer(), minRequiredSize);
|
||||
heap->replaceBuffer(heapMemory->getUnderlyingBuffer(), finalHeapSize);
|
||||
heap->replaceGraphicsAllocation(heapMemory);
|
||||
} else {
|
||||
heap = new IndirectHeap(heapMemory);
|
||||
heap->overrideMaxSize(minRequiredSize);
|
||||
heap->overrideMaxSize(finalHeapSize);
|
||||
}
|
||||
|
||||
if (heapType == IndirectHeap::INSTRUCTION) {
|
||||
|
@ -24,10 +24,14 @@
|
||||
#include "runtime/command_stream/linear_stream.h"
|
||||
#include "runtime/helpers/aligned_memory.h"
|
||||
#include "runtime/helpers/ptr_math.h"
|
||||
#include "runtime/helpers/basic_math.h"
|
||||
|
||||
namespace OCLRT {
|
||||
class GraphicsAllocation;
|
||||
|
||||
constexpr size_t defaultHeapSize = 64 * KB;
|
||||
constexpr size_t maxSshSize = defaultHeapSize - MemoryConstants::pageSize;
|
||||
|
||||
class IndirectHeap : public LinearStream {
|
||||
typedef LinearStream BaseClass;
|
||||
|
||||
|
@ -434,7 +434,12 @@ TEST_P(CommandQueueIndirectHeapTest, getIndirectHeapCanRecycle) {
|
||||
|
||||
const auto &indirectHeap = cmdQ.getIndirectHeap(this->GetParam(), requiredSize);
|
||||
ASSERT_NE(nullptr, &indirectHeap);
|
||||
EXPECT_GE(indirectHeap.getMaxAvailableSpace(), requiredSize);
|
||||
if (this->GetParam() == IndirectHeap::SURFACE_STATE) {
|
||||
//no matter what SSH is always capped
|
||||
EXPECT_EQ(indirectHeap.getMaxAvailableSpace(), maxSshSize);
|
||||
} else {
|
||||
EXPECT_GE(indirectHeap.getMaxAvailableSpace(), requiredSize);
|
||||
}
|
||||
}
|
||||
|
||||
TEST_P(CommandQueueIndirectHeapTest, alignSizeToCacheLine) {
|
||||
@ -469,8 +474,13 @@ TEST_P(CommandQueueIndirectHeapTest, MemoryManagerWithReusableAllocationsWhenAsk
|
||||
|
||||
EXPECT_EQ(indirectHeap.getGraphicsAllocation(), allocation);
|
||||
|
||||
//make sure we are below 64 KB even though we reuse 128KB.
|
||||
EXPECT_LE(indirectHeap.getMaxAvailableSpace(), 64 * KB);
|
||||
//if we obtain heap from reusable pool, we need to keep the size of allocation
|
||||
//surface state heap is an exception, it is capped at ~60KB
|
||||
if (this->GetParam() == IndirectHeap::SURFACE_STATE) {
|
||||
EXPECT_EQ(indirectHeap.getMaxAvailableSpace(), 64 * KB - MemoryConstants::pageSize);
|
||||
} else {
|
||||
EXPECT_EQ(indirectHeap.getMaxAvailableSpace(), 128 * KB);
|
||||
}
|
||||
|
||||
EXPECT_TRUE(memoryManager->allocationsForReuse.peekIsEmpty());
|
||||
}
|
||||
|
@ -531,6 +531,54 @@ HWTEST_F(CommandStreamReceiverFlushTaskTests, stateBaseAddressShouldBeSentIfSize
|
||||
EXPECT_NE(cmdList.end(), stateBaseAddressItor);
|
||||
}
|
||||
|
||||
HWTEST_F(CommandStreamReceiverFlushTaskTests, givenDshHeapChangeWhenFlushTaskIsCalledThenSbaIsReloaded) {
|
||||
auto &commandStreamReceiver = pDevice->getUltCommandStreamReceiver<FamilyType>();
|
||||
configureCSRtoNonDirtyState<FamilyType>();
|
||||
|
||||
dsh.replaceBuffer(nullptr, 0);
|
||||
flushTask(commandStreamReceiver);
|
||||
|
||||
parseCommands<FamilyType>(commandStreamReceiver.commandStream, 0);
|
||||
auto stateBaseAddressItor = find<typename FamilyType::STATE_BASE_ADDRESS *>(cmdList.begin(), cmdList.end());
|
||||
EXPECT_NE(cmdList.end(), stateBaseAddressItor);
|
||||
}
|
||||
|
||||
HWTEST_F(CommandStreamReceiverFlushTaskTests, givenSshHeapChangeWhenFlushTaskIsCalledThenSbaIsReloaded) {
|
||||
auto &commandStreamReceiver = pDevice->getUltCommandStreamReceiver<FamilyType>();
|
||||
configureCSRtoNonDirtyState<FamilyType>();
|
||||
|
||||
ssh.replaceBuffer(nullptr, 0);
|
||||
flushTask(commandStreamReceiver);
|
||||
|
||||
parseCommands<FamilyType>(commandStreamReceiver.commandStream, 0);
|
||||
auto stateBaseAddressItor = find<typename FamilyType::STATE_BASE_ADDRESS *>(cmdList.begin(), cmdList.end());
|
||||
EXPECT_NE(cmdList.end(), stateBaseAddressItor);
|
||||
}
|
||||
|
||||
HWTEST_F(CommandStreamReceiverFlushTaskTests, givenIohHeapChangeWhenFlushTaskIsCalledThenSbaIsReloaded) {
|
||||
auto &commandStreamReceiver = pDevice->getUltCommandStreamReceiver<FamilyType>();
|
||||
configureCSRtoNonDirtyState<FamilyType>();
|
||||
|
||||
ioh.replaceBuffer(nullptr, 0);
|
||||
flushTask(commandStreamReceiver);
|
||||
|
||||
parseCommands<FamilyType>(commandStreamReceiver.commandStream, 0);
|
||||
auto stateBaseAddressItor = find<typename FamilyType::STATE_BASE_ADDRESS *>(cmdList.begin(), cmdList.end());
|
||||
EXPECT_NE(cmdList.end(), stateBaseAddressItor);
|
||||
}
|
||||
|
||||
HWTEST_F(CommandStreamReceiverFlushTaskTests, givenIshHeapChangeWhenFlushTaskIsCalledThenSbaIsReloaded) {
|
||||
auto &commandStreamReceiver = pDevice->getUltCommandStreamReceiver<FamilyType>();
|
||||
configureCSRtoNonDirtyState<FamilyType>();
|
||||
|
||||
ih.replaceBuffer(nullptr, 0);
|
||||
flushTask(commandStreamReceiver);
|
||||
|
||||
parseCommands<FamilyType>(commandStreamReceiver.commandStream, 0);
|
||||
auto stateBaseAddressItor = find<typename FamilyType::STATE_BASE_ADDRESS *>(cmdList.begin(), cmdList.end());
|
||||
EXPECT_NE(cmdList.end(), stateBaseAddressItor);
|
||||
}
|
||||
|
||||
HWTEST_F(CommandStreamReceiverFlushTaskTests, stateBaseAddressShouldNotBeSentIfTheSame) {
|
||||
auto &commandStreamReceiver = pDevice->getUltCommandStreamReceiver<FamilyType>();
|
||||
commandStreamReceiver.isPreambleSent = true;
|
||||
|
@ -467,7 +467,7 @@ TEST_F(InternalsEventTest, resizeCmdQueueHeapsWhenKernelOparationHeapsAreBigger)
|
||||
auto dsh = createFullHeap(requestedSize);
|
||||
auto ish = createFullHeap(requestedSize);
|
||||
auto ioh = createFullHeap(requestedSize);
|
||||
auto ssh = createFullHeap(requestedSize);
|
||||
auto ssh = createFullHeap(maxSshSize);
|
||||
|
||||
using UniqueIH = std::unique_ptr<IndirectHeap>;
|
||||
auto kernelOperation = new KernelOperation(std::unique_ptr<LinearStream>(cmdStream), UniqueIH(dsh),
|
||||
@ -482,7 +482,7 @@ TEST_F(InternalsEventTest, resizeCmdQueueHeapsWhenKernelOparationHeapsAreBigger)
|
||||
EXPECT_LT(cmdQueueDsh.getMaxAvailableSpace(), dsh->getMaxAvailableSpace());
|
||||
EXPECT_LT(cmdQueueIsh.getMaxAvailableSpace(), ish->getMaxAvailableSpace());
|
||||
EXPECT_LT(cmdQueueIoh.getMaxAvailableSpace(), ioh->getMaxAvailableSpace());
|
||||
EXPECT_LT(cmdQueueSsh.getMaxAvailableSpace(), ssh->getMaxAvailableSpace());
|
||||
EXPECT_EQ(cmdQueueSsh.getMaxAvailableSpace(), ssh->getMaxAvailableSpace());
|
||||
|
||||
cmdComputeKernel->submit(0, false);
|
||||
|
||||
|
Reference in New Issue
Block a user