From 5172877bbddc4e718e4bee57369c820d82f9a784 Mon Sep 17 00:00:00 2001 From: Joseph Huber Date: Thu, 16 Feb 2023 14:50:56 -0600 Subject: [PATCH] [Libomptarget] Check errors when synchronizing the async queue Summary: Currently when we synchronize the asynchronous queue for the plugins, we ignore the return value. This is problematic because we will continue on like nothing happened if the kernel fails. Fixes https://github.com/llvm/llvm-project/issues/60814 Reviewed By: jdoerfert Differential Revision: https://reviews.llvm.org/D144191 --- openmp/libomptarget/include/omptarget.h | 5 +++-- openmp/libomptarget/src/interface.cpp | 5 ++++- openmp/libomptarget/src/omptarget.cpp | 6 ++++-- openmp/libomptarget/src/private.h | 6 +++++- 4 files changed, 16 insertions(+), 6 deletions(-) diff --git a/openmp/libomptarget/include/omptarget.h b/openmp/libomptarget/include/omptarget.h index 9df9e22..dd577e4 100644 --- a/openmp/libomptarget/include/omptarget.h +++ b/openmp/libomptarget/include/omptarget.h @@ -17,6 +17,7 @@ #include #include #include +#include #include #include #include @@ -247,8 +248,8 @@ public: /// functions will be executed once and unregistered afterwards. /// /// \returns true if there is no pending asynchronous operations, false - /// otherwise. - bool isDone(); + /// otherwise. We return a null value in the case of an error from the plugin. + std::optional isDone(); /// Add a new post-processing function to be executed after synchronization. /// diff --git a/openmp/libomptarget/src/interface.cpp b/openmp/libomptarget/src/interface.cpp index beea0c2..45f4999 100644 --- a/openmp/libomptarget/src/interface.cpp +++ b/openmp/libomptarget/src/interface.cpp @@ -412,9 +412,12 @@ EXTERN void __tgt_target_nowait_query(void **AsyncHandle) { if (QueryCounter.isAboveThreshold()) AsyncInfo->SyncType = AsyncInfoTy::SyncTy::BLOCKING; + auto DoneOrErr = AsyncInfo->isDone(); + if (!DoneOrErr) + FATAL_MESSAGE0(1, "Error while querying the async queue for completion.\n"); // If there are device operations still pending, return immediately without // deallocating the handle and increase the current thread query count. - if (!AsyncInfo->isDone()) { + if (!*DoneOrErr) { QueryCounter.increment(); return; } diff --git a/openmp/libomptarget/src/omptarget.cpp b/openmp/libomptarget/src/omptarget.cpp index b0d10df..da91a9a 100644 --- a/openmp/libomptarget/src/omptarget.cpp +++ b/openmp/libomptarget/src/omptarget.cpp @@ -51,8 +51,10 @@ void *&AsyncInfoTy::getVoidPtrLocation() { return BufferLocations.back(); } -bool AsyncInfoTy::isDone() { - synchronize(); +std::optional AsyncInfoTy::isDone() { + if (synchronize() == OFFLOAD_FAIL) + return std::nullopt; + // The async info operations are completed when the internal queue is empty. return isQueueEmpty(); } diff --git a/openmp/libomptarget/src/private.h b/openmp/libomptarget/src/private.h index 9f15619..fe55355 100644 --- a/openmp/libomptarget/src/private.h +++ b/openmp/libomptarget/src/private.h @@ -250,9 +250,13 @@ public: if (AsyncInfo == &LocalAsyncInfo) return; + auto DoneOrErr = AsyncInfo->isDone(); + if (!DoneOrErr) + FATAL_MESSAGE0(1, + "Error while querying the async queue for completion.\n"); // If the are device operations still pending, return immediately without // deallocating the handle. - if (!AsyncInfo->isDone()) + if (!*DoneOrErr) return; // Delete the handle and unset it from the OpenMP task data. -- 2.7.4