[Openmp-commits] [openmp] 5adc7dd - [OpenMP] Ignore teams ICV setters in restricted contexts (#194428)
via Openmp-commits
openmp-commits at lists.llvm.org
Tue Jun 9 09:31:22 PDT 2026
Author: Sairudra More
Date: 2026-06-09T11:31:17-05:00
New Revision: 5adc7ddc15cdb39d0f2f8e1daa8ca21aaa374d3a
URL: https://github.com/llvm/llvm-project/commit/5adc7ddc15cdb39d0f2f8e1daa8ca21aaa374d3a
DIFF: https://github.com/llvm/llvm-project/commit/5adc7ddc15cdb39d0f2f8e1daa8ca21aaa374d3a.diff
LOG: [OpenMP] Ignore teams ICV setters in restricted contexts (#194428)
This patch prevents `omp_set_num_teams()` and
`omp_set_teams_thread_limit()` from updating teams-related ICVs when
called from restricted runtime contexts.
The non-implicit parallel-region case follows the OpenMP 5.1
restriction. The active `teams`-region case is handled defensively
because these ICVs are device-scoped and updating them during an active
`teams` region can affect later teams execution.
The calls now warn and return without updating the ICVs.
Fixes #194426.
Added:
openmp/runtime/test/api/omp_nteams_api_restriction.c
Modified:
openmp/runtime/src/i18n/en_US.txt
openmp/runtime/src/kmp_ftn_entry.h
Removed:
################################################################################
diff --git a/openmp/runtime/src/i18n/en_US.txt b/openmp/runtime/src/i18n/en_US.txt
index 08e837d3dea11..b3699df6db65d 100644
--- a/openmp/runtime/src/i18n/en_US.txt
+++ b/openmp/runtime/src/i18n/en_US.txt
@@ -482,6 +482,8 @@ AffHWSubsetIgnoringAttr "KMP_HW_SUBSET: ignoring %1$s attribute. This machi
TargetMemNotAvailable "Target memory not available, will use default allocator."
AffIgnoringNonHybrid "%1$s ignored: This machine is not a hybrid architecutre. Using \"%2$s\" instead."
AffIgnoringNotAvailable "%1$s ignored: %2$s is not available. Using \"%3$s\" instead."
+SetNumTeamsInParOrTeamsRegion "%1$s() called inside a parallel or teams region; call ignored."
+SetTeamsThreadLimitInParOrTeamsRegion "%1$s() called inside a parallel or teams region; call ignored."
# --------------------------------------------------------------------------------------------------
-*- HINTS -*-
diff --git a/openmp/runtime/src/kmp_ftn_entry.h b/openmp/runtime/src/kmp_ftn_entry.h
index dc57a6a74668e..1c8e568b78407 100644
--- a/openmp/runtime/src/kmp_ftn_entry.h
+++ b/openmp/runtime/src/kmp_ftn_entry.h
@@ -1636,9 +1636,23 @@ void FTN_STDCALL FTN_SET_NUM_TEAMS(int KMP_DEREF num_teams) {
if (!__kmp_init_serial) {
__kmp_serial_initialize();
}
+ kmp_info_t *th = __kmp_entry_thread();
+ // OpenMP 5.1, Section 3.4.3: omp_set_num_teams may not be called from
+ // within a parallel region other than the implicit parallel region.
+ // Also guard against calls from within a teams region: nteams-var is a
+ // device-scoped ICV and concurrent modification from multiple team initial
+ // threads may race.
+ // t_level counts both active and serialized parallel levels (0 at the
+ // implicit top-level parallel region), so this catches all non-implicit
+ // parallel regions.
+ if (th->th.th_teams_microtask || th->th.th_team->t.t_level > 0) {
+ KMP_WARNING(SetNumTeamsInParOrTeamsRegion, "omp_set_num_teams");
+ return;
+ }
__kmp_set_num_teams(KMP_DEREF num_teams);
#endif
}
+
int FTN_STDCALL FTN_GET_MAX_TEAMS(void) {
#ifdef KMP_STUB
return 1;
@@ -1657,9 +1671,24 @@ void FTN_STDCALL FTN_SET_TEAMS_THREAD_LIMIT(int KMP_DEREF limit) {
if (!__kmp_init_serial) {
__kmp_serial_initialize();
}
+ kmp_info_t *th = __kmp_entry_thread();
+ // OpenMP 5.1, Section 3.4.5: omp_set_teams_thread_limit may not be called
+ // from within a parallel region other than the implicit parallel region.
+ // Also guard against calls from within a teams region:
+ // teams-thread-limit-var is a device-scoped ICV and concurrent modification
+ // from multiple team initial threads may race.
+ // t_level counts both active and serialized parallel levels (0 at the
+ // implicit top-level parallel region), so this catches all non-implicit
+ // parallel regions.
+ if (th->th.th_teams_microtask || th->th.th_team->t.t_level > 0) {
+ KMP_WARNING(SetTeamsThreadLimitInParOrTeamsRegion,
+ "omp_set_teams_thread_limit");
+ return;
+ }
__kmp_set_teams_thread_limit(KMP_DEREF limit);
#endif
}
+
int FTN_STDCALL FTN_GET_TEAMS_THREAD_LIMIT(void) {
#ifdef KMP_STUB
return 1;
diff --git a/openmp/runtime/test/api/omp_nteams_api_restriction.c b/openmp/runtime/test/api/omp_nteams_api_restriction.c
new file mode 100644
index 0000000000000..71821e7e8745f
--- /dev/null
+++ b/openmp/runtime/test/api/omp_nteams_api_restriction.c
@@ -0,0 +1,71 @@
+// RUN: %libomp-compile-and-run 2>&1 | FileCheck %s
+// Verify that omp_set_num_teams() and omp_set_teams_thread_limit() are
+// ignored when called from within a parallel or teams region.
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <omp.h>
+
+int main(int argc, char **argv) {
+ int err = 0;
+
+ // Set initial values outside any region.
+ omp_set_num_teams(5);
+ omp_set_teams_thread_limit(7);
+
+ if (omp_get_max_teams() != 5) {
+ fprintf(stderr, "error: nteams-var not set correctly\n");
+ exit(1);
+ }
+ if (omp_get_teams_thread_limit() != 7) {
+ fprintf(stderr, "error: teams-thread-limit-var not set correctly\n");
+ exit(1);
+ }
+
+ // Call from inside a teams region -- should be ignored.
+ // Use num_teams(1) to ensure exactly one team and deterministic warning
+ // count.
+#pragma omp teams num_teams(1)
+ {
+ omp_set_num_teams(99);
+ omp_set_teams_thread_limit(99);
+ }
+
+ if (omp_get_max_teams() != 5) {
+ fprintf(stderr, "error: nteams-var modified inside teams region\n");
+ err++;
+ }
+ if (omp_get_teams_thread_limit() != 7) {
+ fprintf(stderr, "error: teams-thread-limit-var modified inside teams "
+ "region\n");
+ err++;
+ }
+
+ // Call from inside a parallel region -- should be ignored.
+#pragma omp parallel num_threads(1)
+ {
+ omp_set_num_teams(99);
+ omp_set_teams_thread_limit(99);
+ }
+
+ if (omp_get_max_teams() != 5) {
+ fprintf(stderr, "error: nteams-var modified inside parallel region\n");
+ err++;
+ }
+ if (omp_get_teams_thread_limit() != 7) {
+ fprintf(stderr, "error: teams-thread-limit-var modified inside parallel "
+ "region\n");
+ err++;
+ }
+
+ if (err == 0) {
+ printf("passed\n");
+ }
+ return err;
+}
+
+// CHECK: OMP: Warning{{.*}}omp_set_num_teams{{.*}}call ignored
+// CHECK: OMP: Warning{{.*}}omp_set_teams_thread_limit{{.*}}call ignored
+// CHECK: OMP: Warning{{.*}}omp_set_num_teams{{.*}}call ignored
+// CHECK: OMP: Warning{{.*}}omp_set_teams_thread_limit{{.*}}call ignored
+// CHECK: passed
More information about the Openmp-commits
mailing list