/* * Copyright (C) 2017-2019 Intel Corporation * * SPDX-License-Identifier: MIT * */ #include "runtime/execution_environment/execution_environment.h" #include "runtime/memory_manager/os_agnostic_memory_manager.h" #include "runtime/program/kernel_info.h" #include "unit_tests/mocks/mock_execution_environment.h" #include "gtest/gtest.h" #include #include using namespace NEO; TEST(KernelInfo, NonCopyable) { EXPECT_FALSE(std::is_move_constructible::value); EXPECT_FALSE(std::is_copy_constructible::value); } TEST(KernelInfo, NonAssignable) { EXPECT_FALSE(std::is_move_assignable::value); EXPECT_FALSE(std::is_copy_assignable::value); } TEST(KernelInfo, defaultBehavior) { auto pKernelInfo = std::make_unique(); EXPECT_FALSE(pKernelInfo->usesSsh); EXPECT_FALSE(pKernelInfo->isValid); } TEST(KernelInfo, decodeConstantMemoryKernelArgument) { uint32_t argumentNumber = 0; auto pKernelInfo = std::make_unique(); SPatchStatelessConstantMemoryObjectKernelArgument arg; arg.Token = 0xa; arg.Size = 0x20; arg.ArgumentNumber = argumentNumber; arg.SurfaceStateHeapOffset = 0x30; arg.DataParamOffset = 0x40; arg.DataParamSize = 0x4; arg.LocationIndex = static_cast(-1); arg.LocationIndex2 = static_cast(-1); pKernelInfo->storeKernelArgument(&arg); EXPECT_TRUE(pKernelInfo->usesSsh); const auto &argInfo = pKernelInfo->kernelArgInfo[argumentNumber]; EXPECT_EQ(arg.SurfaceStateHeapOffset, argInfo.offsetHeap); EXPECT_FALSE(argInfo.isImage); const auto &patchInfo = pKernelInfo->patchInfo; EXPECT_EQ(1u, patchInfo.statelessGlobalMemObjKernelArgs.size()); } TEST(KernelInfo, decodeGlobalMemoryKernelArgument) { uint32_t argumentNumber = 1; auto pKernelInfo = std::make_unique(); SPatchStatelessGlobalMemoryObjectKernelArgument arg; arg.Token = 0xb; arg.Size = 0x30; arg.ArgumentNumber = argumentNumber; arg.SurfaceStateHeapOffset = 0x40; arg.DataParamOffset = 050; arg.DataParamSize = 0x8; arg.LocationIndex = static_cast(-1); arg.LocationIndex2 = static_cast(-1); pKernelInfo->storeKernelArgument(&arg); EXPECT_TRUE(pKernelInfo->usesSsh); const auto &argInfo = pKernelInfo->kernelArgInfo[argumentNumber]; EXPECT_EQ(arg.SurfaceStateHeapOffset, argInfo.offsetHeap); EXPECT_FALSE(argInfo.isImage); const auto &patchInfo = pKernelInfo->patchInfo; EXPECT_EQ(1u, patchInfo.statelessGlobalMemObjKernelArgs.size()); } TEST(KernelInfo, decodeImageKernelArgument) { uint32_t argumentNumber = 1; auto pKernelInfo = std::make_unique(); SPatchImageMemoryObjectKernelArgument arg; arg.Token = 0xc; arg.Size = 0x20; arg.ArgumentNumber = argumentNumber; arg.Type = 0x4; arg.Offset = 0x40; arg.LocationIndex = static_cast(-1); arg.LocationIndex2 = static_cast(-1); arg.Writeable = true; pKernelInfo->storeKernelArgument(&arg); EXPECT_TRUE(pKernelInfo->usesSsh); const auto &argInfo = pKernelInfo->kernelArgInfo[argumentNumber]; //EXPECT_EQ(???, argInfo.argSize); EXPECT_EQ(arg.Offset, argInfo.offsetHeap); EXPECT_TRUE(argInfo.isImage); EXPECT_EQ(static_cast(CL_KERNEL_ARG_ACCESS_READ_WRITE), argInfo.accessQualifier); //EXPECT_EQ(CL_KERNEL_ARG_ACCESS_READ_WRITE, argInfo.accessQualifier); //EXPECT_EQ(CL_KERNEL_ARG_ADDRESS_, argInfo.addressQualifier); //EXPECT_EQ(CL_KERNEL_ARG_TYPE_NONE, argInfo.typeQualifier); } TEST(KernelInfoTest, givenKernelInfoWhenCreateKernelAllocationThenCopyWholeKernelHeapToKernelAllocation) { KernelInfo kernelInfo; MockExecutionEnvironment executionEnvironment(*platformDevices); OsAgnosticMemoryManager memoryManager(executionEnvironment); SKernelBinaryHeaderCommon kernelHeader; const size_t heapSize = 0x40; char heap[heapSize]; kernelHeader.KernelHeapSize = heapSize; kernelInfo.heapInfo.pKernelHeader = &kernelHeader; kernelInfo.heapInfo.pKernelHeap = &heap; for (size_t i = 0; i < heapSize; i++) { heap[i] = static_cast(i); } auto retVal = kernelInfo.createKernelAllocation(&memoryManager); EXPECT_TRUE(retVal); auto allocation = kernelInfo.kernelAllocation; EXPECT_EQ(0, memcmp(allocation->getUnderlyingBuffer(), heap, heapSize)); EXPECT_EQ(heapSize, allocation->getUnderlyingBufferSize()); memoryManager.checkGpuUsageAndDestroyGraphicsAllocations(allocation); } class MyMemoryManager : public OsAgnosticMemoryManager { public: using OsAgnosticMemoryManager::OsAgnosticMemoryManager; GraphicsAllocation *allocate32BitGraphicsMemoryImpl(const AllocationData &allocationData) override { return nullptr; } }; TEST(KernelInfoTest, givenKernelInfoWhenCreateKernelAllocationAndCannotAllocateMemoryThenReturnsFalse) { KernelInfo kernelInfo; MockExecutionEnvironment executionEnvironment(*platformDevices); MyMemoryManager memoryManager(executionEnvironment); SKernelBinaryHeaderCommon kernelHeader; kernelInfo.heapInfo.pKernelHeader = &kernelHeader; auto retVal = kernelInfo.createKernelAllocation(&memoryManager); EXPECT_FALSE(retVal); } TEST(KernelInfo, decodeGlobalMemObjectKernelArgument) { uint32_t argumentNumber = 1; auto pKernelInfo = std::make_unique(); SPatchGlobalMemoryObjectKernelArgument arg; arg.Token = 0xb; arg.Size = 0x10; arg.ArgumentNumber = argumentNumber; arg.Offset = 0x40; arg.LocationIndex = static_cast(-1); arg.LocationIndex2 = static_cast(-1); pKernelInfo->storeKernelArgument(&arg); EXPECT_TRUE(pKernelInfo->usesSsh); const auto &argInfo = pKernelInfo->kernelArgInfo[argumentNumber]; EXPECT_EQ(arg.Offset, argInfo.offsetHeap); EXPECT_TRUE(argInfo.isBuffer); } TEST(KernelInfo, decodeSamplerKernelArgument) { uint32_t argumentNumber = 1; auto pKernelInfo = std::make_unique(); SPatchSamplerKernelArgument arg; arg.ArgumentNumber = argumentNumber; arg.Token = 0x10; arg.Size = 0x18; arg.LocationIndex = static_cast(-1); arg.LocationIndex2 = static_cast(-1); arg.Offset = 0x40; arg.Type = iOpenCL::SAMPLER_OBJECT_TEXTURE; pKernelInfo->usesSsh = true; pKernelInfo->storeKernelArgument(&arg); const auto &argInfo = pKernelInfo->kernelArgInfo[argumentNumber]; EXPECT_EQ(arg.Offset, argInfo.offsetHeap); EXPECT_FALSE(argInfo.isImage); EXPECT_TRUE(argInfo.isSampler); EXPECT_TRUE(pKernelInfo->usesSsh); } typedef KernelInfo KernelInfo_resolveKernelInfo; TEST(KernelInfo_resolveKernelInfo, basicArgument) { auto pKernelInfo = std::make_unique(); pKernelInfo->kernelArgInfo.resize(1); auto &kernelArgInfo = pKernelInfo->kernelArgInfo[0]; kernelArgInfo.accessQualifierStr = "read_only"; kernelArgInfo.addressQualifierStr = "__global"; kernelArgInfo.typeQualifierStr = "restrict"; auto retVal = pKernelInfo->resolveKernelInfo(); EXPECT_EQ(CL_SUCCESS, retVal); EXPECT_EQ(static_cast(CL_KERNEL_ARG_ACCESS_READ_ONLY), kernelArgInfo.accessQualifier); EXPECT_EQ(static_cast(CL_KERNEL_ARG_ADDRESS_GLOBAL), kernelArgInfo.addressQualifier); EXPECT_EQ(static_cast(CL_KERNEL_ARG_TYPE_RESTRICT), kernelArgInfo.typeQualifier); } TEST(KernelInfo_resolveKernelInfo, complexArgumentType) { auto pKernelInfo = std::make_unique(); pKernelInfo->kernelArgInfo.resize(1); auto &kernelArgInfo = pKernelInfo->kernelArgInfo[0]; kernelArgInfo.accessQualifierStr = "read_only"; kernelArgInfo.addressQualifierStr = "__global"; kernelArgInfo.typeQualifierStr = "restrict const"; auto retVal = pKernelInfo->resolveKernelInfo(); EXPECT_EQ(CL_SUCCESS, retVal); EXPECT_EQ(static_cast(CL_KERNEL_ARG_ACCESS_READ_ONLY), kernelArgInfo.accessQualifier); EXPECT_EQ(static_cast(CL_KERNEL_ARG_ADDRESS_GLOBAL), kernelArgInfo.addressQualifier); EXPECT_EQ(static_cast(CL_KERNEL_ARG_TYPE_RESTRICT | CL_KERNEL_ARG_TYPE_CONST), kernelArgInfo.typeQualifier); } TEST(KernelInfo, givenKernelInfoWhenStoreTransformableArgThenArgInfoIsTransformable) { uint32_t argumentNumber = 1; auto kernelInfo = std::make_unique(); SPatchImageMemoryObjectKernelArgument arg; arg.ArgumentNumber = argumentNumber; arg.Transformable = true; kernelInfo->storeKernelArgument(&arg); const auto &argInfo = kernelInfo->kernelArgInfo[argumentNumber]; EXPECT_TRUE(argInfo.isTransformable); } TEST(KernelInfo, givenKernelInfoWhenStoreNonTransformableArgThenArgInfoIsNotTransformable) { uint32_t argumentNumber = 1; auto kernelInfo = std::make_unique(); SPatchImageMemoryObjectKernelArgument arg; arg.ArgumentNumber = argumentNumber; arg.Transformable = false; kernelInfo->storeKernelArgument(&arg); const auto &argInfo = kernelInfo->kernelArgInfo[argumentNumber]; EXPECT_FALSE(argInfo.isTransformable); }