From f7facbbbf9d3c0239dfd1be2c9fc7dcc13013a44 Mon Sep 17 00:00:00 2001 From: "Zhang, Winston" Date: Tue, 30 Sep 2025 12:00:03 -0700 Subject: [PATCH 1/2] [UR][L0] Added safety checks to prevent double urProgramRelease Users used to be able to call urProgramRelease on the same module, but with these changes, that would no longer be possible. Signed-off-by: Zhang, Winston --- .../source/adapters/level_zero/program.cpp | 49 +++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/unified-runtime/source/adapters/level_zero/program.cpp b/unified-runtime/source/adapters/level_zero/program.cpp index 6b8fa9fff2db2..136175a61031c 100644 --- a/unified-runtime/source/adapters/level_zero/program.cpp +++ b/unified-runtime/source/adapters/level_zero/program.cpp @@ -565,6 +565,55 @@ ur_result_t urProgramRetain( ur_result_t urProgramRelease( /// [in] handle for the Program to release ur_program_handle_t Program) { + if (!Program) + return UR_RESULT_ERROR_INVALID_NULL_HANDLE; + + // Detect double-release by attempting to safely access program members + // and catching any access violations that indicate freed memory + try { + // First, try to access the RefCount to see if it's valid + uint32_t currentRefCount = Program->RefCount.getCount(); + + if (currentRefCount == 0) { + // This is a double-release - RefCount should never be 0 when + // urProgramRelease is called + return UR_RESULT_ERROR_INVALID_PROGRAM; + } + + if (Program->resourcesReleased) { + // Resources already released, this is a double-release attempt + return UR_RESULT_ERROR_INVALID_PROGRAM; + } + + if (!Program->Context) { + // Check if the program has a valid context + return UR_RESULT_ERROR_INVALID_PROGRAM; + } + + if (!Program->AssociatedDevices.empty()) { + for (const auto &Device : Program->AssociatedDevices) { + if (Device && Device->ZeDevice) { + ze_module_handle_t zeModuleHandle = + Program->getZeModuleHandle(Device->ZeDevice); + + // Validate that the retrieved module handle is valid + // A null module handle in certain states could indicate corruption or + // double-release + if (!zeModuleHandle) { + return UR_RESULT_ERROR_INVALID_PROGRAM; + } + } + } + } + + } catch (...) { + // If we can't safely access the program members, it's likely + // corrupted/freed This catches the case where urProgramRelease is called on + // the same module twice + return UR_RESULT_ERROR_INVALID_PROGRAM; + } + + // Perform the actual release if (!Program->RefCount.release()) return UR_RESULT_SUCCESS; From 9353e43549979805ebf2428ea313c651d3e4e2bc Mon Sep 17 00:00:00 2001 From: "Zhang, Winston" Date: Tue, 30 Sep 2025 13:14:11 -0700 Subject: [PATCH 2/2] fixed incorrect catch Signed-off-by: Zhang, Winston --- .../source/adapters/level_zero/program.cpp | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/unified-runtime/source/adapters/level_zero/program.cpp b/unified-runtime/source/adapters/level_zero/program.cpp index 136175a61031c..b77a972541877 100644 --- a/unified-runtime/source/adapters/level_zero/program.cpp +++ b/unified-runtime/source/adapters/level_zero/program.cpp @@ -590,22 +590,6 @@ ur_result_t urProgramRelease( return UR_RESULT_ERROR_INVALID_PROGRAM; } - if (!Program->AssociatedDevices.empty()) { - for (const auto &Device : Program->AssociatedDevices) { - if (Device && Device->ZeDevice) { - ze_module_handle_t zeModuleHandle = - Program->getZeModuleHandle(Device->ZeDevice); - - // Validate that the retrieved module handle is valid - // A null module handle in certain states could indicate corruption or - // double-release - if (!zeModuleHandle) { - return UR_RESULT_ERROR_INVALID_PROGRAM; - } - } - } - } - } catch (...) { // If we can't safely access the program members, it's likely // corrupted/freed This catches the case where urProgramRelease is called on