From bbb27cdb8ab947728e54af01ab9aa544745c6b83 Mon Sep 17 00:00:00 2001 From: Mateusz Hoppe Date: Tue, 6 Jul 2021 14:26:44 +0000 Subject: [PATCH] L0 Device slice id mapping Related-To: NEO-5640 Signed-off-by: Mateusz Hoppe --- level_zero/core/source/device/device_imp.cpp | 61 +++ level_zero/core/source/device/device_imp.h | 4 + .../unit_tests/sources/device/test_device.cpp | 440 ++++++++++++++++++ .../os_interface/linux/drm_tests.cpp | 20 + shared/source/helpers/CMakeLists.txt | 1 + shared/source/helpers/topology_map.h | 22 + shared/source/os_interface/linux/drm_neo.cpp | 4 + shared/source/os_interface/linux/drm_neo.h | 8 +- 8 files changed, 555 insertions(+), 5 deletions(-) create mode 100644 shared/source/helpers/topology_map.h diff --git a/level_zero/core/source/device/device_imp.cpp b/level_zero/core/source/device/device_imp.cpp index 5b9e2dfa82..9ac275469e 100644 --- a/level_zero/core/source/device/device_imp.cpp +++ b/level_zero/core/source/device/device_imp.cpp @@ -14,10 +14,12 @@ #include "shared/source/execution_environment/execution_environment.h" #include "shared/source/execution_environment/root_device_environment.h" #include "shared/source/gmm_helper/gmm_helper.h" +#include "shared/source/helpers/common_types.h" #include "shared/source/helpers/constants.h" #include "shared/source/helpers/engine_node_helper.h" #include "shared/source/helpers/hw_helper.h" #include "shared/source/helpers/string.h" +#include "shared/source/helpers/topology_map.h" #include "shared/source/kernel/grf_config.h" #include "shared/source/memory_manager/memory_manager.h" #include "shared/source/os_interface/hw_info_config.h" @@ -943,4 +945,63 @@ DebugSession *DeviceImp::createDebugSession(const zet_debug_config_t &config, ze return debugSession.get(); } +bool DeviceImp::toPhysicalSliceId(const NEO::TopologyMap &topologyMap, uint32_t &slice, uint32_t &deviceIndex) { + auto hwInfo = neoDevice->getRootDeviceEnvironment().getHardwareInfo(); + uint32_t subDeviceCount = NEO::HwHelper::getSubDevicesCount(hwInfo); + auto deviceBitfield = neoDevice->getDeviceBitfield(); + + if (topologyMap.size() == subDeviceCount && !isSubdevice) { + uint32_t sliceId = slice; + for (uint32_t i = 0; i < topologyMap.size(); i++) { + if (sliceId < topologyMap.at(i).sliceIndices.size()) { + slice = topologyMap.at(i).sliceIndices[sliceId]; + deviceIndex = i; + return true; + } + sliceId = sliceId - static_cast(topologyMap.at(i).sliceIndices.size()); + } + } else if (isSubdevice) { + UNRECOVERABLE_IF(!deviceBitfield.any()); + uint32_t subDeviceIndex = Math::log2(static_cast(deviceBitfield.to_ulong())); + + if (topologyMap.find(subDeviceIndex) != topologyMap.end()) { + if (slice < topologyMap.at(subDeviceIndex).sliceIndices.size()) { + deviceIndex = subDeviceIndex; + slice = topologyMap.at(subDeviceIndex).sliceIndices[slice]; + return true; + } + } + } + + return false; +} + +bool DeviceImp::toApiSliceId(const NEO::TopologyMap &topologyMap, uint32_t &slice, uint32_t deviceIndex) { + auto deviceBitfield = neoDevice->getDeviceBitfield(); + + if (isSubdevice) { + UNRECOVERABLE_IF(!deviceBitfield.any()); + deviceIndex = Math::log2(static_cast(deviceBitfield.to_ulong())); + } + + if (topologyMap.find(deviceIndex) != topologyMap.end()) { + uint32_t apiSliceId = 0; + if (!isSubdevice) { + for (uint32_t devId = 0; devId < deviceIndex; devId++) { + apiSliceId += static_cast(topologyMap.at(devId).sliceIndices.size()); + } + } + + for (uint32_t i = 0; i < topologyMap.at(deviceIndex).sliceIndices.size(); i++) { + if (static_cast(topologyMap.at(deviceIndex).sliceIndices[i]) == slice) { + apiSliceId += i; + slice = apiSliceId; + return true; + } + } + } + + return false; +} + } // namespace L0 diff --git a/level_zero/core/source/device/device_imp.h b/level_zero/core/source/device/device_imp.h index 51207bbe0e..25d09270ec 100644 --- a/level_zero/core/source/device/device_imp.h +++ b/level_zero/core/source/device/device_imp.h @@ -7,6 +7,7 @@ #pragma once +#include "shared/source/helpers/topology_map.h" #include "shared/source/utilities/spinlock.h" #include "level_zero/core/source/builtin/builtin_functions_lib.h" @@ -95,6 +96,9 @@ struct DeviceImp : public Device { NEO::Device *getActiveDevice() const; void getDeviceMemoryName(std::string &memoryName); + bool toPhysicalSliceId(const NEO::TopologyMap &topologyMap, uint32_t &slice, uint32_t &deviceIndex); + bool toApiSliceId(const NEO::TopologyMap &topologyMap, uint32_t &slice, uint32_t deviceIndex); + NEO::Device *neoDevice = nullptr; bool isSubdevice = false; void *execEnvironment = nullptr; diff --git a/level_zero/core/test/unit_tests/sources/device/test_device.cpp b/level_zero/core/test/unit_tests/sources/device/test_device.cpp index 243980fdfc..11d1e59f42 100644 --- a/level_zero/core/test/unit_tests/sources/device/test_device.cpp +++ b/level_zero/core/test/unit_tests/sources/device/test_device.cpp @@ -182,6 +182,191 @@ TEST(L0DeviceTest, givenDeviceWithoutAnyCompilerLibraryThenInvalidDependencyRetu Os::frontEndDllName = oldFclDllName; } +TEST(L0DeviceTest, givenFilledTopologyWhenGettingApiSliceThenCorrectSliceIdIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + uint32_t sliceId = hwInfo.gtSystemInfo.SliceCount - 1; + auto ret = deviceImp->toApiSliceId(map, sliceId, 0); + + EXPECT_EQ(hwInfo.gtSystemInfo.SliceCount - 1, sliceId); + EXPECT_TRUE(ret); + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 1; + } + map[0] = mapping; + + sliceId = 1; + ret = deviceImp->toApiSliceId(map, sliceId, 0); + + EXPECT_EQ(0u, sliceId); + EXPECT_TRUE(ret); +} + +TEST(L0DeviceTest, givenFilledTopologyForZeroSubDeviceWhenGettingApiSliceForHigherSubDevicesThenFalseIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 1; + } + map[0] = mapping; + + uint32_t sliceId = 1; + const uint32_t deviceIndex = 2; + auto ret = deviceImp->toApiSliceId(map, sliceId, deviceIndex); + EXPECT_FALSE(ret); +} + +TEST(L0DeviceTest, givenInvalidPhysicalSliceIdWhenGettingApiSliceIdThenFalseIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + uint32_t sliceId = hwInfo.gtSystemInfo.SliceCount + 1; + auto ret = deviceImp->toApiSliceId(map, sliceId, 0); + + EXPECT_FALSE(ret); +} + +TEST(L0DeviceTest, givenInvalidApiSliceIdWhenGettingPhysicalSliceIdThenFalseIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + uint32_t sliceId = hwInfo.gtSystemInfo.SliceCount + 1; + uint32_t deviceIndex = 0; + auto ret = deviceImp->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_FALSE(ret); +} + +TEST(L0DeviceTest, givenEmptyTopologyWhenGettingApiSliceIdThenFalseIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + uint32_t sliceId = hwInfo.gtSystemInfo.SliceCount - 1; + auto ret = deviceImp->toApiSliceId(map, sliceId, 0); + + EXPECT_FALSE(ret); +} + +TEST(L0DeviceTest, givenDeviceWithoutSubDevicesWhenGettingPhysicalSliceIdThenCorrectValuesAreReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 1; + } + map[0] = mapping; + + uint32_t sliceId = 0; + uint32_t deviceIndex = 10; + auto ret = deviceImp->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_TRUE(ret); + EXPECT_EQ(1u, sliceId); + EXPECT_EQ(0u, deviceIndex); +} + +TEST(L0DeviceTest, givenTopologyNotAvaialbleWhenGettingPhysicalSliceIdThenFalseIsReturned) { + NEO::MockCompilerEnableGuard mock(true); + std::unique_ptr driverHandle(new DriverHandleImp); + auto hwInfo = *NEO::defaultHwInfo; + + auto neoDevice = std::unique_ptr(NEO::MockDevice::createWithNewExecutionEnvironment(&hwInfo, 0)); + auto device = std::unique_ptr(Device::create(driverHandle.get(), neoDevice.release(), 1, false, nullptr)); + ASSERT_NE(nullptr, device); + + auto deviceImp = static_cast(device.get()); + + NEO::TopologyMap map; + TopologyMapping mapping; + + uint32_t sliceId = 0; + uint32_t deviceIndex = 10; + auto ret = deviceImp->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_FALSE(ret); +} + struct DeviceTest : public ::testing::Test { void SetUp() override { NEO::MockCompilerEnableGuard mock(true); @@ -1147,6 +1332,261 @@ TEST_F(MultipleDevicesTest, givenTwoSubDevicesFromTheSameRootDeviceThenCanAccess EXPECT_FALSE(canAccess); } +TEST_F(MultipleDevicesTest, givenTopologyForTwoSubdevicesWhenGettingApiSliceIdWithRootDeviceThenCorrectMappingIsUsedAndApiSliceIdsForSubdeviceReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto deviceImp0 = static_cast(device0); + auto hwInfo = device0->getHwInfo(); + + ze_device_properties_t deviceProperties = {}; + deviceImp0->getProperties(&deviceProperties); + + NEO::TopologyMap map; + TopologyMapping mapping; + + EXPECT_EQ(numSubDevices * hwInfo.gtSystemInfo.SliceCount, deviceProperties.numSlices); + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 10; + } + map[1] = mapping; + + uint32_t sliceId = 0; + auto ret = deviceImp0->toApiSliceId(map, sliceId, 0); + + EXPECT_TRUE(ret); + EXPECT_EQ(0u, sliceId); + + sliceId = 10; + ret = deviceImp0->toApiSliceId(map, sliceId, 1); + + EXPECT_TRUE(ret); + EXPECT_EQ(hwInfo.gtSystemInfo.SliceCount + 0u, sliceId); +} + +TEST_F(MultipleDevicesTest, givenTopologyForSingleSubdeviceWhenGettingApiSliceIdWithRootDeviceThenCorrectApiSliceIdsForFirstSubDeviceIsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto deviceImp0 = static_cast(device0); + auto hwInfo = device0->getHwInfo(); + + ze_device_properties_t deviceProperties = {}; + deviceImp0->getProperties(&deviceProperties); + + NEO::TopologyMap map; + TopologyMapping mapping; + + EXPECT_EQ(numSubDevices * hwInfo.gtSystemInfo.SliceCount, deviceProperties.numSlices); + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + uint32_t sliceId = 0; + auto ret = deviceImp0->toApiSliceId(map, sliceId, 0); + + EXPECT_TRUE(ret); + EXPECT_EQ(0u, sliceId); + + sliceId = 0; + ret = deviceImp0->toApiSliceId(map, sliceId, 1); + + EXPECT_FALSE(ret); +} + +TEST_F(MultipleDevicesTest, givenTopologyForTwoSubdevicesWhenGettingApiSliceIdWithSubDeviceThenCorrectSliceIdsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto hwInfo = device0->getHwInfo(); + + uint32_t subDeviceCount = numSubDevices; + std::vector subDevices0(subDeviceCount); + auto res = device0->getSubDevices(&subDeviceCount, subDevices0.data()); + + EXPECT_EQ(ZE_RESULT_SUCCESS, res); + + L0::Device *subDevice0 = Device::fromHandle(subDevices0[0]); + L0::Device *subDevice1 = Device::fromHandle(subDevices0[1]); + + L0::DeviceImp *subDeviceImp0 = static_cast(subDevice0); + L0::DeviceImp *subDeviceImp1 = static_cast(subDevice1); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 10; + } + map[1] = mapping; + + uint32_t sliceId = 0; + auto ret = subDeviceImp0->toApiSliceId(map, sliceId, 0); + + EXPECT_TRUE(ret); + EXPECT_EQ(0u, sliceId); + + sliceId = 10; + ret = subDeviceImp1->toApiSliceId(map, sliceId, 1); + + EXPECT_TRUE(ret); + EXPECT_EQ(0u, sliceId); +} + +TEST_F(MultipleDevicesTest, givenTopologyForTwoSubdevicesWhenGettingPhysicalSliceIdWithRootDeviceThenCorrectSliceIdAndDeviceIndexIsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto deviceImp0 = static_cast(device0); + auto hwInfo = device0->getHwInfo(); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i; + } + map[0] = mapping; + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 10; + } + map[1] = mapping; + + uint32_t sliceId = 0; + uint32_t deviceIndex = 100; + auto ret = deviceImp0->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_TRUE(ret); + EXPECT_EQ(0u, sliceId); + EXPECT_EQ(0u, deviceIndex); + + sliceId = hwInfo.gtSystemInfo.SliceCount; + deviceIndex = 200; + ret = deviceImp0->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_TRUE(ret); + EXPECT_EQ(10u, sliceId); + EXPECT_EQ(1u, deviceIndex); +} + +TEST_F(MultipleDevicesTest, givenTopologyForTwoSubdevicesWhenGettingPhysicalSliceIdWithSubDeviceThenCorrectSliceIdAndDeviceIndexIsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto hwInfo = device0->getHwInfo(); + + uint32_t subDeviceCount = numSubDevices; + std::vector subDevices0(subDeviceCount); + auto res = device0->getSubDevices(&subDeviceCount, subDevices0.data()); + + EXPECT_EQ(ZE_RESULT_SUCCESS, res); + + L0::Device *subDevice0 = Device::fromHandle(subDevices0[0]); + L0::Device *subDevice1 = Device::fromHandle(subDevices0[1]); + + L0::DeviceImp *subDeviceImp0 = static_cast(subDevice0); + L0::DeviceImp *subDeviceImp1 = static_cast(subDevice1); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 5; + } + map[0] = mapping; + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 10; + } + map[1] = mapping; + + uint32_t sliceId = 0; + uint32_t deviceIndex = 0; + auto ret = subDeviceImp0->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_TRUE(ret); + EXPECT_EQ(5u, sliceId); + EXPECT_EQ(0u, deviceIndex); + + sliceId = 0; + deviceIndex = 100; + ret = subDeviceImp1->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_TRUE(ret); + EXPECT_EQ(10u, sliceId); + EXPECT_EQ(1u, deviceIndex); +} + +TEST_F(MultipleDevicesTest, givenInvalidApiSliceIdWhenGettingPhysicalSliceIdThenFalseIsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto hwInfo = device0->getHwInfo(); + + uint32_t subDeviceCount = numSubDevices; + std::vector subDevices0(subDeviceCount); + auto res = device0->getSubDevices(&subDeviceCount, subDevices0.data()); + EXPECT_EQ(ZE_RESULT_SUCCESS, res); + + L0::Device *subDevice1 = Device::fromHandle(subDevices0[1]); + L0::DeviceImp *subDeviceImp1 = static_cast(subDevice1); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 5; + } + map[0] = mapping; + + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 10; + } + map[1] = mapping; + + uint32_t sliceId = hwInfo.gtSystemInfo.SliceCount; + uint32_t deviceIndex = 1; + auto ret = subDeviceImp1->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_FALSE(ret); +} + +TEST_F(MultipleDevicesTest, givenTopologyMapForSubdeviceZeroWhenGettingPhysicalSliceIdForSubdeviceOneThenFalseIsReturned) { + L0::Device *device0 = driverHandle->devices[0]; + auto hwInfo = device0->getHwInfo(); + + uint32_t subDeviceCount = numSubDevices; + std::vector subDevices0(subDeviceCount); + auto res = device0->getSubDevices(&subDeviceCount, subDevices0.data()); + EXPECT_EQ(ZE_RESULT_SUCCESS, res); + + L0::Device *subDevice1 = Device::fromHandle(subDevices0[1]); + L0::DeviceImp *subDeviceImp1 = static_cast(subDevice1); + + NEO::TopologyMap map; + TopologyMapping mapping; + + mapping.sliceIndices.resize(hwInfo.gtSystemInfo.SliceCount); + for (uint32_t i = 0; i < hwInfo.gtSystemInfo.SliceCount; i++) { + mapping.sliceIndices[i] = i + 5; + } + map[0] = mapping; + + uint32_t sliceId = 0; + uint32_t deviceIndex = 1; + auto ret = subDeviceImp1->toPhysicalSliceId(map, sliceId, deviceIndex); + + EXPECT_FALSE(ret); +} + struct MultipleDevicesDifferentLocalMemorySupportTest : public MultipleDevicesTest { void SetUp() override { MultipleDevicesTest::SetUp(); diff --git a/opencl/test/unit_test/os_interface/linux/drm_tests.cpp b/opencl/test/unit_test/os_interface/linux/drm_tests.cpp index f4c600f0b3..2bb12382c0 100644 --- a/opencl/test/unit_test/os_interface/linux/drm_tests.cpp +++ b/opencl/test/unit_test/os_interface/linux/drm_tests.cpp @@ -719,3 +719,23 @@ TEST(DrmQueryTest, GivenLessAvailableSubSlicesThanMaxSubSlicesWhenQueryingTopolo EXPECT_EQ(drm.storedSVal, topologyData.maxSliceCount); EXPECT_EQ(2, topologyData.maxSubSliceCount); } + +TEST(DrmQueryTest, givenDrmWhenGettingTopologyMapThenCorrectMapIsReturned) { + auto executionEnvironment = std::make_unique(); + executionEnvironment->prepareRootDeviceEnvironments(1); + + *executionEnvironment->rootDeviceEnvironments[0]->getMutableHardwareInfo() = *NEO::defaultHwInfo.get(); + DrmMock drmMock{*executionEnvironment->rootDeviceEnvironments[0]}; + + Drm::QueryTopologyData topologyData = {}; + + EXPECT_TRUE(drmMock.queryTopology(*executionEnvironment->rootDeviceEnvironments[0]->getHardwareInfo(), topologyData)); + + auto topologyMap = drmMock.getTopologyMap(); + + EXPECT_LE(1u, topologyMap.size()); + + for (uint32_t i = 0; i < topologyMap.size(); i++) { + EXPECT_EQ(drmMock.storedSVal, static_cast(topologyMap.at(i).sliceIndices.size())); + } +} \ No newline at end of file diff --git a/shared/source/helpers/CMakeLists.txt b/shared/source/helpers/CMakeLists.txt index 7817e82c30..438c9ef34a 100644 --- a/shared/source/helpers/CMakeLists.txt +++ b/shared/source/helpers/CMakeLists.txt @@ -106,6 +106,7 @@ set(NEO_CORE_HELPERS ${CMAKE_CURRENT_SOURCE_DIR}/timestamp_offsets.h ${CMAKE_CURRENT_SOURCE_DIR}/timestamp_packet.cpp ${CMAKE_CURRENT_SOURCE_DIR}/timestamp_packet.h + ${CMAKE_CURRENT_SOURCE_DIR}/topology_map.h ${CMAKE_CURRENT_SOURCE_DIR}/uint16_avx2.h ${CMAKE_CURRENT_SOURCE_DIR}/uint16_sse4.h ${CMAKE_CURRENT_SOURCE_DIR}/vec.h diff --git a/shared/source/helpers/topology_map.h b/shared/source/helpers/topology_map.h new file mode 100644 index 0000000000..343214e37c --- /dev/null +++ b/shared/source/helpers/topology_map.h @@ -0,0 +1,22 @@ +/* + * Copyright (C) 2021 Intel Corporation + * + * SPDX-License-Identifier: MIT + * + */ + +#pragma once + +#include +#include +#include + +namespace NEO { + +struct TopologyMapping { + std::vector sliceIndices; +}; + +using TopologyMap = std::unordered_map; + +} // namespace NEO diff --git a/shared/source/os_interface/linux/drm_neo.cpp b/shared/source/os_interface/linux/drm_neo.cpp index 17addcf0b2..0b1d99537f 100644 --- a/shared/source/os_interface/linux/drm_neo.cpp +++ b/shared/source/os_interface/linux/drm_neo.cpp @@ -729,6 +729,10 @@ const std::vector &Drm::getSliceMappings(uint32_t deviceIndex) { return topologyMap[deviceIndex].sliceIndices; } +const TopologyMap &Drm::getTopologyMap() { + return topologyMap; +} + int Drm::waitHandle(uint32_t waitHandle, int64_t timeout) { drm_i915_gem_wait wait = {}; wait.bo_handle = waitHandle; diff --git a/shared/source/os_interface/linux/drm_neo.h b/shared/source/os_interface/linux/drm_neo.h index a179355603..68c2f5ba7c 100644 --- a/shared/source/os_interface/linux/drm_neo.h +++ b/shared/source/os_interface/linux/drm_neo.h @@ -8,6 +8,7 @@ #pragma once #include "shared/source/gmm_helper/gmm_lib.h" #include "shared/source/helpers/basic_math.h" +#include "shared/source/helpers/topology_map.h" #include "shared/source/memory_manager/definitions/engine_limits.h" #include "shared/source/os_interface/driver_info.h" #include "shared/source/os_interface/linux/cache_info.h" @@ -225,14 +226,11 @@ class Drm : public DriverModel { bool getNewResourceBound() { return this->newResourceBound; }; const std::vector &getSliceMappings(uint32_t deviceIndex); + const TopologyMap &getTopologyMap(); static std::vector> discoverDevices(ExecutionEnvironment &executionEnvironment); protected: - struct TopologyMapping { - std::vector sliceIndices; - }; - Drm(std::unique_ptr hwDeviceIdIn, RootDeviceEnvironment &rootDeviceEnvironment); int getQueueSliceCount(drm_i915_gem_context_param_sseu *sseu); @@ -274,7 +272,7 @@ class Drm : public DriverModel { drm_i915_gem_context_param_sseu sseu{}; ADAPTER_BDF adapterBDF{}; - std::unordered_map topologyMap; + TopologyMap topologyMap; std::unordered_map> ioctlStatistics; std::array pagingFence;