[7/n] Unified Shared Memory.

- Add basic allocation support for shared allocations
- Add kernel support for shared allocations.

Related-To: NEO-3148

Change-Id: Ie0523acc3a444eef6a5aeb6a56a041280df6a02e
Signed-off-by: Mrozek, Michal <michal.mrozek@intel.com>
This commit is contained in:
Mrozek, Michal
2019-06-18 07:22:38 +02:00
committed by sys_ocldev
parent 57f88ee197
commit 3a75c4fb71
7 changed files with 70 additions and 2 deletions

View File

@@ -15,6 +15,9 @@ uint32_t UnifiedMemoryControls::generateMask() {
if (this->indirectDeviceAllocationsAllowed) {
resourceMask |= InternalMemoryType::DEVICE_UNIFIED_MEMORY;
}
if (this->indirectSharedAllocationsAllowed) {
resourceMask |= InternalMemoryType::SHARED_UNIFIED_MEMORY;
}
return resourceMask;
}

View File

@@ -13,10 +13,12 @@ enum InternalMemoryType : uint32_t {
SVM = 0b1,
DEVICE_UNIFIED_MEMORY = 0b10,
HOST_UNIFIED_MEMORY = 0b100,
SHARED_UNIFIED_MEMORY = 0b1000
};
struct UnifiedMemoryControls {
uint32_t generateMask();
bool indirectDeviceAllocationsAllowed = false;
bool indirectHostAllocationsAllowed = false;
bool indirectSharedAllocationsAllowed = false;
};

View File

@@ -14,6 +14,7 @@
TEST(UnifiedMemoryTests, givenInternalMemoryTypesThenAllHaveOnlyOneBitSet) {
EXPECT_EQ(1u, std::bitset<32>(InternalMemoryType::DEVICE_UNIFIED_MEMORY).count());
EXPECT_EQ(1u, std::bitset<32>(InternalMemoryType::HOST_UNIFIED_MEMORY).count());
EXPECT_EQ(1u, std::bitset<32>(InternalMemoryType::SHARED_UNIFIED_MEMORY).count());
EXPECT_EQ(1u, std::bitset<32>(InternalMemoryType::SVM).count());
}
@@ -29,4 +30,8 @@ TEST(UnifiedMemoryTests, givenUnifiedMemoryControlsWhenDedicatedFieldsAreSetThen
controls.indirectDeviceAllocationsAllowed = false;
EXPECT_EQ(InternalMemoryType::HOST_UNIFIED_MEMORY, controls.generateMask());
controls.indirectHostAllocationsAllowed = false;
controls.indirectSharedAllocationsAllowed = true;
EXPECT_EQ(InternalMemoryType::SHARED_UNIFIED_MEMORY, controls.generateMask());
}

View File

@@ -3988,7 +3988,8 @@ cl_int CL_API_CALL clSetKernelExecInfo(cl_kernel kernel,
switch (paramName) {
case CL_KERNEL_EXEC_INFO_INDIRECT_DEVICE_ACCESS_INTEL:
case CL_KERNEL_EXEC_INFO_INDIRECT_HOST_ACCESS_INTEL: {
case CL_KERNEL_EXEC_INFO_INDIRECT_HOST_ACCESS_INTEL:
case CL_KERNEL_EXEC_INFO_INDIRECT_SHARED_ACCESS_INTEL: {
auto propertyValue = *reinterpret_cast<const cl_bool *>(paramValue);
pKernel->setUnifiedMemoryProperty(paramName, propertyValue);
} break;

View File

@@ -950,6 +950,10 @@ void Kernel::setUnifiedMemoryProperty(cl_kernel_exec_info infoType, bool infoVal
this->unifiedMemoryControls.indirectHostAllocationsAllowed = infoValue;
return;
}
if (infoType == CL_KERNEL_EXEC_INFO_INDIRECT_SHARED_ACCESS_INTEL) {
this->unifiedMemoryControls.indirectSharedAllocationsAllowed = infoValue;
return;
}
}
void Kernel::setUnifiedMemoryExecInfo(GraphicsAllocation *unifiedMemoryAllocation) {
@@ -1015,7 +1019,8 @@ void Kernel::makeResident(CommandStreamReceiver &commandStreamReceiver) {
gtpinNotifyMakeResident(this, &commandStreamReceiver);
if (unifiedMemoryControls.indirectDeviceAllocationsAllowed ||
unifiedMemoryControls.indirectHostAllocationsAllowed) {
unifiedMemoryControls.indirectHostAllocationsAllowed ||
unifiedMemoryControls.indirectSharedAllocationsAllowed) {
this->getContext().getSVMAllocsManager()->makeInternalAllocationsResident(commandStreamReceiver, unifiedMemoryControls.generateMask());
}
}

View File

@@ -1660,6 +1660,26 @@ HWTEST_F(KernelResidencyTest, givenKernelUsingIndirectHostMemoryWhenMakeResident
svmAllocationsManager->freeSVMAlloc(unifiedHostMemoryAllocation);
}
HWTEST_F(KernelResidencyTest, givenKernelUsingIndirectSharedMemoryWhenMakeResidentIsCalledThenOnlySharedAllocationsAreMadeResident) {
MockKernelWithInternals mockKernel(*this->pDevice);
auto &commandStreamReceiver = this->pDevice->getUltCommandStreamReceiver<FamilyType>();
auto svmAllocationsManager = mockKernel.mockContext->getSVMAllocsManager();
auto unifiedSharedMemoryAllocation = svmAllocationsManager->createUnifiedMemoryAllocation(4096u, SVMAllocsManager::UnifiedMemoryProperties(InternalMemoryType::SHARED_UNIFIED_MEMORY));
auto unifiedHostMemoryAllocation = svmAllocationsManager->createUnifiedMemoryAllocation(4096u, SVMAllocsManager::UnifiedMemoryProperties(InternalMemoryType::HOST_UNIFIED_MEMORY));
mockKernel.mockKernel->makeResident(this->pDevice->getCommandStreamReceiver());
EXPECT_EQ(0u, commandStreamReceiver.getResidencyAllocations().size());
mockKernel.mockKernel->setUnifiedMemoryProperty(CL_KERNEL_EXEC_INFO_INDIRECT_SHARED_ACCESS_INTEL, true);
mockKernel.mockKernel->makeResident(this->pDevice->getCommandStreamReceiver());
EXPECT_EQ(1u, commandStreamReceiver.getResidencyAllocations().size());
EXPECT_EQ(commandStreamReceiver.getResidencyAllocations()[0]->getGpuAddress(), castToUint64(unifiedSharedMemoryAllocation));
svmAllocationsManager->freeSVMAlloc(unifiedSharedMemoryAllocation);
svmAllocationsManager->freeSVMAlloc(unifiedHostMemoryAllocation);
}
HWTEST_F(KernelResidencyTest, givenKernelWhenSetKernelExecInfoWithUnifiedMemoryIsCalledThenAllocationIsStoredWithinKernel) {
MockKernelWithInternals mockKernel(*this->pDevice);
auto &commandStreamReceiver = this->pDevice->getUltCommandStreamReceiver<FamilyType>();
@@ -1706,6 +1726,7 @@ HWTEST_F(KernelResidencyTest, givenKernelWhenclSetKernelExecInfoWithUnifiedMemor
svmAllocationsManager->freeSVMAlloc(unifiedMemoryAllocation);
svmAllocationsManager->freeSVMAlloc(unifiedMemoryAllocation2);
}
HWTEST_F(KernelResidencyTest, givenKernelWhenclSetKernelExecInfoWithUnifiedMemoryDevicePropertyIsCalledThenKernelControlIsChanged) {
MockKernelWithInternals mockKernel(*this->pDevice);
cl_bool enableIndirectDeviceAccess = CL_TRUE;
@@ -1730,6 +1751,18 @@ HWTEST_F(KernelResidencyTest, givenKernelWhenclSetKernelExecInfoWithUnifiedMemor
EXPECT_FALSE(mockKernel.mockKernel->unifiedMemoryControls.indirectHostAllocationsAllowed);
}
HWTEST_F(KernelResidencyTest, givenKernelWhenclSetKernelExecInfoWithUnifiedMemorySharedPropertyIsCalledThenKernelControlIsChanged) {
MockKernelWithInternals mockKernel(*this->pDevice);
cl_bool enableIndirectSharedAccess = CL_TRUE;
auto status = clSetKernelExecInfo(mockKernel.mockKernel, CL_KERNEL_EXEC_INFO_INDIRECT_SHARED_ACCESS_INTEL, sizeof(cl_bool), &enableIndirectSharedAccess);
EXPECT_EQ(CL_SUCCESS, status);
EXPECT_TRUE(mockKernel.mockKernel->unifiedMemoryControls.indirectSharedAllocationsAllowed);
enableIndirectSharedAccess = CL_FALSE;
status = clSetKernelExecInfo(mockKernel.mockKernel, CL_KERNEL_EXEC_INFO_INDIRECT_SHARED_ACCESS_INTEL, sizeof(cl_bool), &enableIndirectSharedAccess);
EXPECT_EQ(CL_SUCCESS, status);
EXPECT_FALSE(mockKernel.mockKernel->unifiedMemoryControls.indirectSharedAllocationsAllowed);
}
TEST(KernelImageDetectionTests, givenKernelWithImagesOnlyWhenItIsAskedIfItHasImagesOnlyThenTrueIsReturned) {
auto pKernelInfo = std::make_unique<KernelInfo>();
pKernelInfo->kernelArgInfo.resize(3);

View File

@@ -179,6 +179,25 @@ TEST_F(SVMMemoryAllocatorTest, whenHostAllocationIsCreatedThenItIsStoredWithProp
svmManager->freeSVMAlloc(ptr);
}
TEST_F(SVMMemoryAllocatorTest, whenSharedAllocationIsCreatedThenItIsStoredWithProperTypeInAllocationMap) {
SVMAllocsManager::UnifiedMemoryProperties unifiedMemoryProperties;
unifiedMemoryProperties.memoryType = InternalMemoryType::SHARED_UNIFIED_MEMORY;
auto allocationSize = 4096u;
auto ptr = svmManager->createUnifiedMemoryAllocation(4096u, unifiedMemoryProperties);
EXPECT_NE(nullptr, ptr);
auto allocation = svmManager->getSVMAlloc(ptr);
EXPECT_EQ(nullptr, allocation->cpuAllocation);
EXPECT_NE(nullptr, allocation->gpuAllocation);
EXPECT_EQ(InternalMemoryType::SHARED_UNIFIED_MEMORY, allocation->memoryType);
EXPECT_EQ(allocationSize, allocation->size);
EXPECT_EQ(alignUp(allocationSize, MemoryConstants::pageSize64k), allocation->gpuAllocation->getUnderlyingBufferSize());
EXPECT_EQ(GraphicsAllocation::AllocationType::BUFFER_HOST_MEMORY, allocation->gpuAllocation->getAllocationType());
EXPECT_NE(allocation->gpuAllocation->getMemoryPool(), MemoryPool::LocalMemory);
EXPECT_NE(nullptr, allocation->gpuAllocation->getUnderlyingBuffer());
svmManager->freeSVMAlloc(ptr);
}
TEST(SvmAllocationPropertiesTests, givenDifferentMemFlagsWhenGettingSvmAllocationPropertiesThenPropertiesAreCorrectlySet) {
SVMAllocsManager::SvmAllocationProperties allocationProperties = MemObjHelper::getSvmAllocationProperties(0);
EXPECT_FALSE(allocationProperties.coherent);