From d57b9acbd8416ff3c51665f55f37e4c1da331df9 Mon Sep 17 00:00:00 2001 From: Mikael Simberg Date: Tue, 7 Mar 2023 11:34:48 +0100 Subject: [PATCH] Add more verbose message when default thread pool doesn't have any threads assigned to it --- .../include/pika/affinity/affinity_data.hpp | 5 ++++ .../src/detail_partitioner.cpp | 25 ++++++++++++++++--- 2 files changed, 27 insertions(+), 3 deletions(-) diff --git a/libs/pika/affinity/include/pika/affinity/affinity_data.hpp b/libs/pika/affinity/include/pika/affinity/affinity_data.hpp index 9c2d311cb..05dc5c8ad 100644 --- a/libs/pika/affinity/include/pika/affinity/affinity_data.hpp +++ b/libs/pika/affinity/include/pika/affinity/affinity_data.hpp @@ -50,6 +50,11 @@ namespace pika::detail { return num_threads_; } + bool using_process_mask() const noexcept + { + return use_process_mask_; + } + threads::detail::mask_cref_type get_pu_mask( threads::detail::topology const& topo, std::size_t num_thread) const; diff --git a/libs/pika/resource_partitioner/src/detail_partitioner.cpp b/libs/pika/resource_partitioner/src/detail_partitioner.cpp index b0aebc150..71e6a512b 100644 --- a/libs/pika/resource_partitioner/src/detail_partitioner.cpp +++ b/libs/pika/resource_partitioner/src/detail_partitioner.cpp @@ -391,10 +391,29 @@ namespace pika::resource::detail { if (get_pool_data(l, get_default_pool_name()).num_threads_ == 0) { l.unlock(); + + std::string process_mask_message = affinity_data_.using_process_mask() ? + fmt::format("pika is using a process mask: {}.", + pika::threads::detail::to_string(get_topology().get_cpubind_mask())) : + "pika is not using a process mask."; + auto omp_proc_bind = std::getenv("OMP_PROC_BIND"); + std::string omp_proc_bind_message = omp_proc_bind ? + fmt::format("OMP_PROC_BIND is currently set to \"{}\".", omp_proc_bind) : + "OMP_PROC_BIND is currently unset."; throw_runtime_error("partitioner::setup_pools", - "Default pool " + get_default_pool_name() + - " has no threads assigned. Please rerun with --pika:threads=X and check the " - "pool thread assignment"); + fmt::format( + "The default pool (\"{}\") has no threads assigned. Make sure that the pika " + "runtime is started with enough threads for all thread pools. This can be " + "caused by the pika runtime being configured to use additional thread pools " + "(e.g. for MPI) but starting the runtime with too few threads, leaving no " + "threads for the default pool. It can also be caused by OpenMP using thread " + "pinning (through OMP_PROC_BIND) and OpenMP changing the process mask before " + "pika can read the mask. pika is currently configured to use {} thread{} and " + "{} thread pool{}. {} {}", + get_default_pool_name(), get_num_threads(), get_num_threads() != 1 ? "s" : "", + get_num_pools(), get_num_pools() != 1 ? "s" : "", process_mask_message, + omp_proc_bind_message)); + // TODO: Explain most common failure modes? } // Check whether any of the pools defined up to now are empty