From ef8fefec28fd0a180d5f58ab4f88b675b4d999ea Mon Sep 17 00:00:00 2001 From: Jemale Lockett Date: Tue, 19 Nov 2024 23:20:10 +0000 Subject: [PATCH] fix: correct check for interrupt sent in tile debug sessions Resolves: NEO-12222 Signed-off-by: Jemale Lockett --- .../tools/source/debug/debug_session_imp.h | 1 + .../debug/linux/prelim/debug_session.cpp | 5 +- .../prelim/debug_session_fixtures_linux.h | 2 + .../linux/prelim/test_debug_api_linux.cpp | 71 +++++++++++++++++++ 4 files changed, 77 insertions(+), 2 deletions(-) diff --git a/level_zero/tools/source/debug/debug_session_imp.h b/level_zero/tools/source/debug/debug_session_imp.h index dc6f26e6fd..e333bdb513 100644 --- a/level_zero/tools/source/debug/debug_session_imp.h +++ b/level_zero/tools/source/debug/debug_session_imp.h @@ -52,6 +52,7 @@ struct DebugSessionImp : DebugSession { DebugSession *attachTileDebugSession(Device *device) override; void detachTileDebugSession(DebugSession *tileSession) override; bool areAllTileDebugSessionDetached() override; + bool isInterruptSent() { return interruptSent; } void setAttachMode(bool isRootAttach) override { if (isRootAttach) { diff --git a/level_zero/tools/source/debug/linux/prelim/debug_session.cpp b/level_zero/tools/source/debug/linux/prelim/debug_session.cpp index 07114194f1..ed7f49370f 100644 --- a/level_zero/tools/source/debug/linux/prelim/debug_session.cpp +++ b/level_zero/tools/source/debug/linux/prelim/debug_session.cpp @@ -971,7 +971,8 @@ uint64_t DebugSessionLinuxi915::getVmHandleFromClientAndlrcHandle(uint64_t clien void DebugSessionLinuxi915::handleAttentionEvent(prelim_drm_i915_debug_event_eu_attention *attention) { NEO::EngineClassInstance engineClassInstance = {attention->ci.engine_class, attention->ci.engine_instance}; auto tileIndex = DrmHelper::getEngineTileIndex(connectedDevice, engineClassInstance); - if (interruptSent && attention->base.seqno <= euControlInterruptSeqno[tileIndex]) { + auto tmpInterruptSent = tileSessionsEnabled ? tileSessions[tileIndex].first->isInterruptSent() : interruptSent.load(); + if (tmpInterruptSent && attention->base.seqno <= euControlInterruptSeqno[tileIndex]) { PRINT_DEBUGGER_INFO_LOG("Discarding EU ATTENTION event for interrupt request. Event seqno == %d <= %d == interrupt seqno\n", (uint32_t)attention->base.seqno, (uint32_t)euControlInterruptSeqno[tileIndex]); @@ -986,7 +987,7 @@ void DebugSessionLinuxi915::handleAttentionEvent(prelim_drm_i915_debug_event_eu_ std::vector threadsWithAttention; auto hwInfo = connectedDevice->getHwInfo(); auto &l0GfxCoreHelper = connectedDevice->getL0GfxCoreHelper(); - if (interruptSent) { + if (tmpInterruptSent) { std::unique_ptr bitmask; size_t bitmaskSize; auto attReadResult = threadControl({}, tileIndex, ThreadControlCmd::stopped, bitmask, bitmaskSize); diff --git a/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/debug_session_fixtures_linux.h b/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/debug_session_fixtures_linux.h index 81496b84af..34cc86ab1c 100644 --- a/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/debug_session_fixtures_linux.h +++ b/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/debug_session_fixtures_linux.h @@ -432,6 +432,7 @@ struct MockTileDebugSessionLinuxi915 : TileDebugSessionLinuxi915 { using DebugSessionImp::checkTriggerEventsForAttention; using DebugSessionImp::expectedAttentionEvents; using DebugSessionImp::interruptImp; + using DebugSessionImp::interruptSent; using DebugSessionImp::newlyStoppedThreads; using DebugSessionImp::resumeImp; using DebugSessionImp::sendInterrupts; @@ -440,6 +441,7 @@ struct MockTileDebugSessionLinuxi915 : TileDebugSessionLinuxi915 { using DebugSessionImp::triggerEvents; using DebugSessionLinuxi915::detached; using DebugSessionLinuxi915::ioctl; + using DebugSessionLinuxi915::pendingInterrupts; using DebugSessionLinuxi915::pushApiEvent; using TileDebugSessionLinuxi915::cleanRootSessionAfterDetach; using TileDebugSessionLinuxi915::getAllMemoryHandles; diff --git a/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/test_debug_api_linux.cpp b/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/test_debug_api_linux.cpp index 06a631677e..0cf14e8dbc 100644 --- a/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/test_debug_api_linux.cpp +++ b/level_zero/tools/test/unit_tests/sources/debug/linux/prelim/test_debug_api_linux.cpp @@ -8101,6 +8101,77 @@ TEST_F(DebugApiLinuxMultitileTest, givenApiThreadAndMultipleTilesWhenGettingDevi EXPECT_EQ(1u, deviceIndex); } +TEST_F(DebugApiLinuxMultitileTest, GivenMultitileDeviceAndInterruptSentForTileWhenHandlingAttentionEventThenEventIsNotProcessed) { + DebugManagerStateRestore restorer; + NEO::debugManager.flags.ExperimentalEnableTileAttach.set(1); + + zet_debug_config_t config = {}; + config.pid = 0x1234; + + auto sessionMock = std::make_unique(config, deviceImp, 10); + ASSERT_NE(nullptr, sessionMock); + sessionMock->clientHandle = MockDebugSessionLinuxi915::mockClientHandle; + sessionMock->createTileSessionsIfEnabled(); + EXPECT_TRUE(sessionMock->tileSessionsEnabled); + + MockTileDebugSessionLinuxi915 *tileSessions[2]; + tileSessions[0] = static_cast(sessionMock->tileSessions[0].first); + tileSessions[1] = static_cast(sessionMock->tileSessions[1].first); + + uint8_t data[sizeof(prelim_drm_i915_debug_event_eu_attention) + 128]; + std::unique_ptr bitmask; + size_t bitmaskSize = 0; + auto &hwInfo = neoDevice->getHardwareInfo(); + auto &l0GfxCoreHelper = neoDevice->getRootDeviceEnvironment().getHelper(); + + std::vector threads{ + {0, 0, 0, 0, 0}, + {0, 0, 0, 0, 1}, + {0, 0, 0, 0, 2}, + {0, 0, 0, 0, 3}, + {0, 0, 0, 0, 4}, + {0, 0, 0, 0, 5}, + {0, 0, 0, 0, 6}}; + + l0GfxCoreHelper.getAttentionBitmaskForSingleThreads(threads, hwInfo, bitmask, bitmaskSize); + + ze_device_thread_t thread = {0, 0, 0, UINT32_MAX}; + tileSessions[1]->pendingInterrupts.push_back(std::pair(thread, false)); + sessionMock->interruptSent = false; + tileSessions[1]->interruptSent = true; + sessionMock->euControlInterruptSeqno[1] = 3; + sessionMock->expectedAttentionEvents = 1; + tileSessions[0]->expectedAttentionEvents = 1; + tileSessions[1]->expectedAttentionEvents = 1; + + auto engineInfo = mockDrm->getEngineInfo(); + auto engineInstance = engineInfo->getEngineInstance(1, hwInfo.capabilityTable.defaultEngineType); + + prelim_drm_i915_debug_event_eu_attention attention = {}; + attention.base.type = PRELIM_DRM_I915_DEBUG_EVENT_EU_ATTENTION; + attention.base.flags = PRELIM_DRM_I915_DEBUG_EVENT_STATE_CHANGE; + attention.base.seqno = 2; + attention.base.size = sizeof(prelim_drm_i915_debug_event_eu_attention) + std::min(uint32_t(128), static_cast(bitmaskSize)); + attention.client_handle = MockDebugSessionLinuxi915::mockClientHandle; + attention.flags = 0; + attention.ci.engine_class = engineInstance->engineClass; + attention.ci.engine_instance = engineInstance->engineInstance; + attention.bitmask_size = std::min(uint32_t(128), static_cast(bitmaskSize)); + + memcpy(data, &attention, sizeof(prelim_drm_i915_debug_event_eu_attention)); + memcpy(ptrOffset(data, offsetof(prelim_drm_i915_debug_event_eu_attention, bitmask)), bitmask.get(), std::min(size_t(128), bitmaskSize)); + + sessionMock->handleEvent(reinterpret_cast(data)); + + EXPECT_EQ(0u, tileSessions[0]->newlyStoppedThreads.size()); + EXPECT_EQ(0u, tileSessions[1]->newlyStoppedThreads.size()); + EXPECT_EQ(1u, tileSessions[1]->pendingInterrupts.size()); + EXPECT_FALSE(tileSessions[1]->pendingInterrupts[0].second); + EXPECT_FALSE(tileSessions[1]->triggerEvents); + EXPECT_EQ(1u, sessionMock->expectedAttentionEvents); + EXPECT_EQ(1u, tileSessions[0]->expectedAttentionEvents); + EXPECT_EQ(1u, tileSessions[1]->expectedAttentionEvents); +} template struct DebugApiLinuxMultiDeviceVmBindFixture : public DebugApiLinuxMultiDeviceFixture, public MockDebugSessionLinuxi915Helper { void setUp() {