Unify handling of GMX_ENABLE_GPU_TIMING and GMX_DISABLE_GPU_TIMING
[alexxy/gromacs.git] / src / gromacs / gpu_utils / gpu_utils.cpp
index fcfb1cc374306016ea3eca2ac325b9a24d5d50ae..2d8846caa334f827ad6c3ed6846b87694a0c4b17 100644 (file)
@@ -1,7 +1,8 @@
 /*
  * This file is part of the GROMACS molecular simulation package.
  *
- * Copyright (c) 2014,2015,2017,2018,2019,2020, by the GROMACS development team, led by
+ * Copyright (c) 2014,2015,2017,2018,2019, by the GROMACS development team.
+ * Copyright (c) 2020,2021, by the GROMACS development team, led by
  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
  * and including many others, as listed in the AUTHORS file in the
  * top-level source directory and at http://www.gromacs.org.
 
 #include "config.h"
 
-#include <cassert>
-
-#include "gromacs/hardware/gpu_hw_info.h"
 #include "gromacs/utility/arrayref.h"
-#include "gromacs/utility/smalloc.h"
+#include "gromacs/utility/enumerationhelpers.h"
 #include "gromacs/utility/stringutil.h"
 
 #ifdef _MSC_VER
 #    pragma warning(disable : 6237)
 #endif
 
-//! Constant used to help minimize preprocessed code
-static constexpr bool c_binarySupportsGpus = (GMX_GPU != GMX_GPU_NONE);
-
-bool canPerformGpuDetection()
-{
-    if (c_binarySupportsGpus && getenv("GMX_DISABLE_GPU_DETECTION") == nullptr)
-    {
-        return isGpuDetectionFunctional(nullptr);
-    }
-    else
-    {
-        return false;
-    }
-}
-
-#if GMX_GPU == GMX_GPU_NONE
-DeviceStatus gpu_info_get_stat(const gmx_gpu_info_t& /*unused*/, int /*unused*/)
-{
-    return DeviceStatus::Nonexistent;
-}
-#endif
-
-void free_gpu_info(const gmx_gpu_info_t* gpu_info)
+const char* enumValueToString(GpuApiCallBehavior enumValue)
 {
-    sfree(static_cast<void*>(gpu_info->deviceInfo)); // circumvent is_pod check in sfree
+    static constexpr gmx::EnumerationArray<GpuApiCallBehavior, const char*> s_gpuApiCallBehaviorNames = {
+        "Synchronous", "Asynchronous"
+    };
+    return s_gpuApiCallBehaviorNames[enumValue];
 }
 
-std::vector<int> getCompatibleGpus(const gmx_gpu_info_t& gpu_info)
-{
-    // Possible minor over-allocation here, but not important for anything
-    std::vector<int> compatibleGpus;
-    compatibleGpus.reserve(gpu_info.n_dev);
-    for (int i = 0; i < gpu_info.n_dev; i++)
-    {
-        assert(gpu_info.deviceInfo);
-        if (gpu_info_get_stat(gpu_info, i) == DeviceStatus::Compatible)
-        {
-            compatibleGpus.push_back(i);
-        }
-    }
-    return compatibleGpus;
-}
-
-const char* getGpuCompatibilityDescription(const gmx_gpu_info_t& gpu_info, int index)
-{
-    return (index >= gpu_info.n_dev ? c_deviceStateString[DeviceStatus::Nonexistent]
-                                    : c_deviceStateString[gpu_info_get_stat(gpu_info, index)]);
-}
-/*! \brief Help build a descriptive message in \c error if there are
- * \c errorReasons why nonbondeds on a GPU are not supported.
- *
- * \returns Whether the lack of errorReasons indicate there is support. */
-static bool addMessageIfNotSupported(gmx::ArrayRef<const std::string> errorReasons, std::string* error)
+bool decideGpuTimingsUsage()
 {
-    bool isSupported = errorReasons.empty();
-    if (!isSupported && error)
+    if (GMX_GPU_CUDA || GMX_GPU_SYCL)
     {
-        *error = "Nonbonded interactions cannot run on GPUs: ";
-        *error += joinStrings(errorReasons, "; ") + ".";
+        /* CUDA: timings are incorrect with multiple streams.
+         * This is the main reason why they are disabled by default.
+         * TODO: Consider turning on by default when we can detect nr of streams.
+         *
+         * SYCL: compilers and runtimes change rapidly, so we disable timings by default
+         * to avoid any possible overhead. */
+        return (getenv("GMX_ENABLE_GPU_TIMING") != nullptr);
     }
-    return isSupported;
-}
-
-bool buildSupportsNonbondedOnGpu(std::string* error)
-{
-    std::vector<std::string> errorReasons;
-    if (GMX_DOUBLE)
+    else if (GMX_GPU_OPENCL)
     {
-        errorReasons.emplace_back("double precision");
+        return (getenv("GMX_DISABLE_GPU_TIMING") == nullptr);
     }
-    if (!c_binarySupportsGpus)
+    else
     {
-        errorReasons.emplace_back("non-GPU build of GROMACS");
+        // CPU-only build
+        return false;
     }
-    return addMessageIfNotSupported(errorReasons, error);
 }