[clang] [llvm] [openmp] [openmp][WebAssembly] add support for wasm64 (PR #181669)

via cfe-commits cfe-commits at lists.llvm.org
Tue Jul 28 08:20:42 PDT 2026


https://github.com/arsnyder16 updated https://github.com/llvm/llvm-project/pull/181669

>From f56e99c0c4a1b878dbc4f55c300c18b76c49c5c4 Mon Sep 17 00:00:00 2001
From: Andrew Snyder <asnyder at minitab.com>
Date: Mon, 16 Feb 2026 09:02:43 -0500
Subject: [PATCH 1/5] [openmp][WebAssembly] add support for wasm64

---
 llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp     |  2 +-
 openmp/CMakeLists.txt                         |  2 +-
 openmp/cmake/modules/LibompUtils.cmake        |  4 ++++
 openmp/runtime/CMakeLists.txt                 | 19 ++++++++++++-------
 .../runtime/cmake/LibompGetArchitecture.cmake |  2 ++
 openmp/runtime/cmake/config-ix.cmake          |  2 +-
 openmp/runtime/src/kmp_gsupport.cpp           |  2 +-
 openmp/runtime/src/kmp_os.h                   | 11 ++++++-----
 openmp/runtime/src/kmp_platform.h             | 12 ++++++++----
 openmp/runtime/src/kmp_runtime.cpp            |  4 ++--
 openmp/runtime/src/z_Linux_asm.S              |  2 +-
 openmp/runtime/src/z_Linux_util.cpp           |  5 +++--
 12 files changed, 42 insertions(+), 25 deletions(-)

diff --git a/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp b/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp
index 464ec5b5a2ece..25285c5fefa31 100644
--- a/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp
+++ b/llvm/lib/Frontend/OpenMP/OMPIRBuilder.cpp
@@ -9285,7 +9285,7 @@ GlobalVariable *OpenMPIRBuilder::getOrCreateInternalVariable(
                                : M.getTargetTriple().isAMDGPU()
                                    ? 0
                                    : DL.getDefaultGlobalsAddressSpace();
-    auto Linkage = this->M.getTargetTriple().getArch() == Triple::wasm32
+    auto Linkage = this->M.getTargetTriple().isWasm()
                        ? GlobalValue::InternalLinkage
                        : GlobalValue::CommonLinkage;
     auto *GV = new GlobalVariable(M, Ty, /*IsConstant=*/false, Linkage,
diff --git a/openmp/CMakeLists.txt b/openmp/CMakeLists.txt
index 355c64d28d296..4b7e4dccfac0a 100644
--- a/openmp/CMakeLists.txt
+++ b/openmp/CMakeLists.txt
@@ -140,7 +140,7 @@ set(ENABLE_LIBOMPTARGET ON)
 # Since the device plugins are only supported on Linux anyway,
 # there is no point in trying to compile libomptarget on other OSes.
 # 32-bit systems are not supported either.
-if (APPLE OR WIN32 OR WASM OR NOT "cxx_std_17" IN_LIST CMAKE_CXX_COMPILE_FEATURES
+if (APPLE OR WIN32 OR WASM32 OR WASM64 OR NOT "cxx_std_17" IN_LIST CMAKE_CXX_COMPILE_FEATURES
     OR NOT CMAKE_SIZEOF_VOID_P EQUAL 8 OR "${CMAKE_SYSTEM_NAME}" MATCHES "AIX")
   set(ENABLE_LIBOMPTARGET OFF)
 endif()
diff --git a/openmp/cmake/modules/LibompUtils.cmake b/openmp/cmake/modules/LibompUtils.cmake
index a810881c2544e..1c60ffb242727 100644
--- a/openmp/cmake/modules/LibompUtils.cmake
+++ b/openmp/cmake/modules/LibompUtils.cmake
@@ -121,6 +121,10 @@ function(libomp_get_legal_arch return_arch_string)
     set(${return_arch_string} "SPARC" PARENT_SCOPE)
   elseif(${SPARCV9})
     set(${return_arch_string} "SPARCV9" PARENT_SCOPE)
+  elseif(${WASM32})
+    set(${return_arch_string} "WASM32" PARENT_SCOPE)
+  elseif(${WASM64})
+    set(${return_arch_string} "WASM64" PARENT_SCOPE)
   else()
     set(${return_arch_string} "${LIBOMP_ARCH}" PARENT_SCOPE)
     libomp_warning_say("libomp_get_legal_arch(): Warning: Unknown architecture: Using ${LIBOMP_ARCH}")
diff --git a/openmp/runtime/CMakeLists.txt b/openmp/runtime/CMakeLists.txt
index dc2f2be079bf3..58f8646c2d73d 100644
--- a/openmp/runtime/CMakeLists.txt
+++ b/openmp/runtime/CMakeLists.txt
@@ -24,7 +24,7 @@ if(${OPENMP_STANDALONE_BUILD})
   # If adding a new architecture, take a look at cmake/LibompGetArchitecture.cmake
   libomp_get_architecture(LIBOMP_DETECTED_ARCH)
   set(LIBOMP_ARCH ${LIBOMP_DETECTED_ARCH} CACHE STRING
-    "The architecture to build for (x86_64/i386/arm/ppc/ppc64/ppc64le/aarch64/aarch64_32/mic/mips/mips64/riscv64/loongarch64/ve/s390x/sparc/sparcv9/wasm32).")
+    "The architecture to build for (x86_64/i386/arm/ppc/ppc64/ppc64le/aarch64/aarch64_32/mic/mips/mips64/riscv64/loongarch64/ve/s390x/sparc/sparcv9/wasm32/wasm64).")
   # Should assertions be enabled?  They are on by default.
   set(LIBOMP_ENABLE_ASSERTIONS TRUE CACHE BOOL
     "enable assertions?")
@@ -69,8 +69,10 @@ else() # Part of LLVM build
     set(LIBOMP_ARCH sparcv9)
   elseif(LIBOMP_NATIVE_ARCH MATCHES "sparc")
     set(LIBOMP_ARCH sparc)
-  elseif(LIBOMP_NATIVE_ARCH MATCHES "wasm")
+  elseif(LIBOMP_NATIVE_ARCH MATCHES "wasm32")
     set(LIBOMP_ARCH wasm32)
+  elseif(LIBOMP_NATIVE_ARCH MATCHES "wasm64")
+    set(LIBOMP_ARCH wasm64)
   else()
     # last ditch effort
     libomp_get_architecture(LIBOMP_ARCH)
@@ -91,7 +93,7 @@ if(LIBOMP_ARCH STREQUAL "aarch64")
   endif()
 endif()
 
-libomp_check_variable(LIBOMP_ARCH 32e x86_64 32 i386 arm ppc ppc64 ppc64le aarch64 aarch64_32 aarch64_a64fx mic mips mips64 riscv64 loongarch64 ve s390x sparc sparcv9 wasm32)
+libomp_check_variable(LIBOMP_ARCH 32e x86_64 32 i386 arm ppc ppc64 ppc64le aarch64 aarch64_32 aarch64_a64fx mic mips mips64 riscv64 loongarch64 ve s390x sparc sparcv9 wasm32 wasm64)
 
 set(LIBOMP_LIB_TYPE normal CACHE STRING
   "Performance,Profiling,Stubs library (normal/profile/stubs)")
@@ -186,7 +188,8 @@ set(RISCV64 FALSE)
 set(LOONGARCH64 FALSE)
 set(VE FALSE)
 set(S390X FALSE)
-set(WASM FALSE)
+set(WASM32 FALSE)
+set(WASM64 FALSE)
 set(PPC FALSE)
 set(SPARC FALSE)
 set(SPARCV9 FALSE)
@@ -224,8 +227,10 @@ elseif("${LIBOMP_ARCH}" STREQUAL "ve") # VE architecture
     set(VE TRUE)
 elseif("${LIBOMP_ARCH}" STREQUAL "s390x") # S390x (Z) architecture
     set(S390X TRUE)
-elseif("${LIBOMP_ARCH}" STREQUAL "wasm32") # WebAssembly architecture
-    set(WASM TRUE)
+elseif("${LIBOMP_ARCH}" STREQUAL "wasm32") # WebAssembly 32 bit architecture
+    set(WASM32 TRUE)
+elseif("${LIBOMP_ARCH}" STREQUAL "wasm64") # WebAssembly 64 bit architecture
+    set(WASM64 TRUE)
 elseif("${LIBOMP_ARCH}" STREQUAL "sparc") # SPARC architecture
     set(SPARC TRUE)
 elseif("${LIBOMP_ARCH}" STREQUAL "sparcv9") # SPARC V9 architecture
@@ -334,7 +339,7 @@ endif()
 set(LIBOMP_ENABLE_SHARED TRUE CACHE BOOL
   "Shared library instead of static library?")
 
-if(WASM)
+if(WASM32 OR WASM64)
   libomp_warning_say("The WebAssembly build currently only supports static libraries; forcing LIBOMP_ENABLE_SHARED to false")
   set(LIBOMP_ENABLE_SHARED FALSE)
 endif()
diff --git a/openmp/runtime/cmake/LibompGetArchitecture.cmake b/openmp/runtime/cmake/LibompGetArchitecture.cmake
index 81aa700e3b6db..b69b129aa693f 100644
--- a/openmp/runtime/cmake/LibompGetArchitecture.cmake
+++ b/openmp/runtime/cmake/LibompGetArchitecture.cmake
@@ -59,6 +59,8 @@ function(libomp_get_architecture return_arch)
       #error ARCHITECTURE=s390x
     #elif defined(__wasm32__)
       #error ARCHITECTURE=wasm32
+    #elif defined(__wasm64__)
+      #error ARCHITECTURE=wasm64
     #elif defined(__sparcv9)
       #error ARCHITECTURE=sparcv9
     #elif defined(__sparc)
diff --git a/openmp/runtime/cmake/config-ix.cmake b/openmp/runtime/cmake/config-ix.cmake
index 150a0c3c7217b..fcd02c578465c 100644
--- a/openmp/runtime/cmake/config-ix.cmake
+++ b/openmp/runtime/cmake/config-ix.cmake
@@ -154,7 +154,7 @@ endif()
 # with either the Emscripten or wasi-threads flavor ends up using the pthreads
 # interface in a WebAssembly-compiled libc; CMake does not yet know how to
 # detect this.
-if (NOT WASM)
+if (NOT WASM32 AND NOT WASM64)
   find_package(Threads REQUIRED)
   if(WIN32)
     if(NOT CMAKE_USE_WIN32_THREADS_INIT)
diff --git a/openmp/runtime/src/kmp_gsupport.cpp b/openmp/runtime/src/kmp_gsupport.cpp
index 0d04045f7b165..be95e0f3de6e2 100644
--- a/openmp/runtime/src/kmp_gsupport.cpp
+++ b/openmp/runtime/src/kmp_gsupport.cpp
@@ -357,7 +357,7 @@ void KMP_EXPAND_NAME(KMP_API_NAME_GOMP_ORDERED_END)(void) {
 // They come in two flavors: 64-bit unsigned, and either 32-bit signed
 // (IA-32 architecture) or 64-bit signed (Intel(R) 64).
 
-#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM ||          \
+#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM32 ||        \
     KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC32
 #define KMP_DISPATCH_INIT __kmp_aux_dispatch_init_4
 #define KMP_DISPATCH_FINI_CHUNK __kmp_aux_dispatch_fini_chunk_4
diff --git a/openmp/runtime/src/kmp_os.h b/openmp/runtime/src/kmp_os.h
index e8ad2a6fdb78e..f74fec5a1f82e 100644
--- a/openmp/runtime/src/kmp_os.h
+++ b/openmp/runtime/src/kmp_os.h
@@ -178,18 +178,18 @@ typedef unsigned long long kmp_uint64;
 #define KMP_UINT64_SPEC "llu"
 #endif /* KMP_OS_UNIX */
 
-#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM ||          \
+#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM32 ||        \
     KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC32
 #define KMP_SIZE_T_SPEC KMP_UINT32_SPEC
 #elif KMP_ARCH_X86_64 || KMP_ARCH_PPC64 || KMP_ARCH_AARCH64 ||                 \
     KMP_ARCH_MIPS64 || KMP_ARCH_RISCV64 || KMP_ARCH_LOONGARCH64 ||             \
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_SPARC64
+    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_SPARC64 || KMP_ARCH_WASM64
 #define KMP_SIZE_T_SPEC KMP_UINT64_SPEC
 #else
 #error "Can't determine size_t printf format specifier."
 #endif
 
-#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_WASM || KMP_ARCH_PPC
+#if KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_WASM32 || KMP_ARCH_PPC
 #define KMP_SIZE_T_MAX (0xFFFFFFFF)
 #else
 #define KMP_SIZE_T_MAX (0xFFFFFFFFFFFFFFFF)
@@ -218,7 +218,8 @@ typedef kmp_uint32 kmp_uint;
 #define KMP_INT_MIN ((kmp_int32)0x80000000)
 
 // stdarg handling
-#if (KMP_ARCH_ARM || KMP_ARCH_X86_64 || KMP_ARCH_AARCH64 || KMP_ARCH_WASM) &&  \
+#if (KMP_ARCH_ARM || KMP_ARCH_X86_64 || KMP_ARCH_AARCH64 || KMP_ARCH_WASM32 || \
+     KMP_ARCH_WASM64) &&                                                       \
     (KMP_OS_FREEBSD || KMP_OS_NETBSD || KMP_OS_OPENBSD || KMP_OS_DRAGONFLY ||  \
      KMP_OS_LINUX || KMP_OS_WASI)
 typedef va_list *kmp_va_list;
@@ -1153,7 +1154,7 @@ extern kmp_real64 __kmp_xchg_real64(volatile kmp_real64 *p, kmp_real64 v);
   KMP_COMPARE_AND_STORE_REL64((volatile kmp_int64 *)(volatile void *)&(a),     \
                               (kmp_int64)(b), (kmp_int64)(c))
 
-#if KMP_ARCH_X86 || KMP_ARCH_MIPS || KMP_ARCH_WASM || KMP_ARCH_PPC
+#if KMP_ARCH_X86 || KMP_ARCH_MIPS || KMP_ARCH_WASM32 || KMP_ARCH_PPC
 // What about ARM?
 #define TCR_PTR(a) ((void *)TCR_4(a))
 #define TCW_PTR(a, b) TCW_4((a), (b))
diff --git a/openmp/runtime/src/kmp_platform.h b/openmp/runtime/src/kmp_platform.h
index 609b7c4688842..2d789e95f29bb 100644
--- a/openmp/runtime/src/kmp_platform.h
+++ b/openmp/runtime/src/kmp_platform.h
@@ -245,7 +245,11 @@
 #endif
 
 #if defined(__wasm32__)
-#define KMP_ARCH_WASM 1
+#define KMP_ARCH_WASM32 1
+#endif
+
+#if defined(__wasm64__)
+#define KMP_ARCH_WASM64 1
 #endif
 
 #define KMP_ARCH_PPC64                                                         \
@@ -279,7 +283,7 @@
 
 /* Specify 32 bit architectures here */
 #define KMP_32_BIT_ARCH                                                        \
-  (KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM ||           \
+  (KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_MIPS || KMP_ARCH_WASM32 ||         \
    KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC32)
 
 // Platforms which support Intel(R) Many Integrated Core Architecture
@@ -290,8 +294,8 @@
 #if (1 != KMP_ARCH_X86 + KMP_ARCH_X86_64 + KMP_ARCH_ARM + KMP_ARCH_PPC64 +     \
               KMP_ARCH_AARCH64 + KMP_ARCH_MIPS + KMP_ARCH_MIPS64 +             \
               KMP_ARCH_RISCV64 + KMP_ARCH_LOONGARCH64 + KMP_ARCH_VE +          \
-              KMP_ARCH_S390X + KMP_ARCH_WASM + KMP_ARCH_PPC +                  \
-              KMP_ARCH_AARCH64_32 + KMP_ARCH_SPARC)
+              KMP_ARCH_S390X + KMP_ARCH_WASM32 + KMP_ARCH_WASM64 +             \
+              KMP_ARCH_PPC + KMP_ARCH_AARCH64_32 + KMP_ARCH_SPARC)
 #error Unknown or unsupported architecture
 #endif
 
diff --git a/openmp/runtime/src/kmp_runtime.cpp b/openmp/runtime/src/kmp_runtime.cpp
index 3277a09c6497f..861c030db3fb1 100644
--- a/openmp/runtime/src/kmp_runtime.cpp
+++ b/openmp/runtime/src/kmp_runtime.cpp
@@ -8924,7 +8924,7 @@ __kmp_determine_reduction_method(
 
 #if KMP_ARCH_X86_64 || KMP_ARCH_PPC64 || KMP_ARCH_AARCH64 ||                   \
     KMP_ARCH_MIPS64 || KMP_ARCH_RISCV64 || KMP_ARCH_LOONGARCH64 ||             \
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM
+    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM64
 
 #if KMP_OS_LINUX || KMP_OS_DRAGONFLY || KMP_OS_FREEBSD || KMP_OS_NETBSD ||     \
     KMP_OS_OPENBSD || KMP_OS_WINDOWS || KMP_OS_DARWIN || KMP_OS_HAIKU ||       \
@@ -8956,7 +8956,7 @@ __kmp_determine_reduction_method(
        // KMP_OS_HURD || KMP_OS_SOLARIS || KMP_OS_WASI || KMP_OS_AIX
 
 #elif KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_AARCH || KMP_ARCH_MIPS ||       \
-    KMP_ARCH_WASM || KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC
+    KMP_ARCH_WASM32 || KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC
 
 #if KMP_OS_LINUX || KMP_OS_DRAGONFLY || KMP_OS_FREEBSD || KMP_OS_NETBSD ||     \
     KMP_OS_OPENBSD || KMP_OS_WINDOWS || KMP_OS_HAIKU || KMP_OS_HURD ||         \
diff --git a/openmp/runtime/src/z_Linux_asm.S b/openmp/runtime/src/z_Linux_asm.S
index 12fea67e000e8..bfc8aff325f2a 100644
--- a/openmp/runtime/src/z_Linux_asm.S
+++ b/openmp/runtime/src/z_Linux_asm.S
@@ -2512,7 +2512,7 @@ KMP_PREFIX_UNDERSCORE(__kmp_unnamed_critical_addr):
 #if KMP_OS_LINUX
 # if KMP_ARCH_ARM || KMP_ARCH_AARCH64
 .section .note.GNU-stack,"",%progbits
-# elif !KMP_ARCH_WASM
+# elif !KMP_ARCH_WASM32 && !KMP_ARCH_WASM64 
 .section .note.GNU-stack,"", at progbits
 # endif
 #endif
diff --git a/openmp/runtime/src/z_Linux_util.cpp b/openmp/runtime/src/z_Linux_util.cpp
index c7fe0642cea63..18ffedadee505 100644
--- a/openmp/runtime/src/z_Linux_util.cpp
+++ b/openmp/runtime/src/z_Linux_util.cpp
@@ -321,7 +321,8 @@ int __kmp_futex_determine_capable() {
 
 #endif // KMP_USE_FUTEX
 
-#if (KMP_ARCH_X86 || KMP_ARCH_X86_64 || KMP_ARCH_WASM) && (!KMP_ASM_INTRINS)
+#if (KMP_ARCH_X86 || KMP_ARCH_X86_64 || KMP_ARCH_WASM32 || KMP_ARCH_WASM64) && \
+    (!KMP_ASM_INTRINS)
 /* Only 32-bit "add-exchange" instruction on IA-32 architecture causes us to
    use compare_and_store for these routines */
 
@@ -381,7 +382,7 @@ kmp_uint32 __kmp_test_then_and32(volatile kmp_uint32 *p, kmp_uint32 d) {
   return old_value;
 }
 
-#if KMP_ARCH_X86 || KMP_ARCH_WASM
+#if KMP_ARCH_X86 || KMP_ARCH_WASM32
 kmp_int8 __kmp_test_then_add8(volatile kmp_int8 *p, kmp_int8 d) {
   kmp_int8 old_value, new_value;
 

>From 8d5304b51a977b81f63e47491114592b5ee9016f Mon Sep 17 00:00:00 2001
From: Andrew Snyder <asnyder at minitab.com>
Date: Tue, 28 Jul 2026 09:04:30 -0400
Subject: [PATCH 2/5] formatting

---
 openmp/runtime/src/kmp_os.h        | 3 ++-
 openmp/runtime/src/kmp_platform.h  | 5 +++--
 openmp/runtime/src/kmp_runtime.cpp | 6 +-----
 3 files changed, 6 insertions(+), 8 deletions(-)

diff --git a/openmp/runtime/src/kmp_os.h b/openmp/runtime/src/kmp_os.h
index c742e8272999f..be8c121e18736 100644
--- a/openmp/runtime/src/kmp_os.h
+++ b/openmp/runtime/src/kmp_os.h
@@ -183,7 +183,8 @@ typedef unsigned long long kmp_uint64;
 #define KMP_SIZE_T_SPEC KMP_UINT32_SPEC
 #elif KMP_ARCH_X86_64 || KMP_ARCH_PPC64 || KMP_ARCH_AARCH64 ||                 \
     KMP_ARCH_MIPS64 || KMP_ARCH_RISCV64 || KMP_ARCH_LOONGARCH64 ||             \
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_SPARC64 || KMP_ARCH_WASM64 || KMP_ARCH_ARM64EC
+    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_SPARC64 || KMP_ARCH_WASM64 ||    \
+    KMP_ARCH_ARM64EC
 #define KMP_SIZE_T_SPEC KMP_UINT64_SPEC
 #else
 #error "Can't determine size_t printf format specifier."
diff --git a/openmp/runtime/src/kmp_platform.h b/openmp/runtime/src/kmp_platform.h
index 6370047260681..3cafd90225614 100644
--- a/openmp/runtime/src/kmp_platform.h
+++ b/openmp/runtime/src/kmp_platform.h
@@ -298,8 +298,9 @@
 #if (1 != KMP_ARCH_X86 + KMP_ARCH_X86_64 + KMP_ARCH_ARM + KMP_ARCH_PPC64 +     \
               KMP_ARCH_AARCH64 + KMP_ARCH_MIPS + KMP_ARCH_MIPS64 +             \
               KMP_ARCH_RISCV64 + KMP_ARCH_LOONGARCH64 + KMP_ARCH_VE +          \
-              KMP_ARCH_S390X + KMP_ARCH_WASM32 + KMP_ARCH_WASM64 + KMP_ARCH_PPC +                  \
-              KMP_ARCH_AARCH64_32 + KMP_ARCH_SPARC + KMP_ARCH_ARM64EC)
+              KMP_ARCH_S390X + KMP_ARCH_WASM32 + KMP_ARCH_WASM64 +             \
+              KMP_ARCH_PPC + KMP_ARCH_AARCH64_32 + KMP_ARCH_SPARC +            \
+              KMP_ARCH_ARM64EC)
 #error Unknown or unsupported architecture
 #endif
 
diff --git a/openmp/runtime/src/kmp_runtime.cpp b/openmp/runtime/src/kmp_runtime.cpp
index b752991780678..8f7f5c8c7bfe5 100644
--- a/openmp/runtime/src/kmp_runtime.cpp
+++ b/openmp/runtime/src/kmp_runtime.cpp
@@ -8924,11 +8924,7 @@ __kmp_determine_reduction_method(
 
 #if KMP_ARCH_X86_64 || KMP_ARCH_PPC64 || KMP_ARCH_AARCH64 ||                   \
     KMP_ARCH_MIPS64 || KMP_ARCH_RISCV64 || KMP_ARCH_LOONGARCH64 ||             \
-<<<<<<< HEAD
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM64
-=======
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM || KMP_ARCH_ARM64EC
->>>>>>> origin/main
+    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM64 || KMP_ARCH_ARM64EC
 
 #if KMP_OS_LINUX || KMP_OS_DRAGONFLY || KMP_OS_FREEBSD || KMP_OS_NETBSD ||     \
     KMP_OS_OPENBSD || KMP_OS_WINDOWS || KMP_OS_DARWIN || KMP_OS_HAIKU ||       \

>From 1f22451463e5d5ca1317e91b79dce728c590a735 Mon Sep 17 00:00:00 2001
From: Andrew Snyder <asnyder at minitab.com>
Date: Tue, 28 Jul 2026 10:25:15 -0400
Subject: [PATCH 3/5] cleanup

---
 openmp/CMakeLists.txt              | 5 +++--
 openmp/runtime/CMakeLists.txt      | 4 ++++
 openmp/runtime/src/kmp_runtime.cpp | 5 +++--
 3 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/openmp/CMakeLists.txt b/openmp/CMakeLists.txt
index d5d4f79d4a6d4..f9a89859be7af 100644
--- a/openmp/CMakeLists.txt
+++ b/openmp/CMakeLists.txt
@@ -134,11 +134,12 @@ set(OPENMP_TEST_Fortran_FLAGS "${CMAKE_Fortran_FLAGS}" CACHE STRING
   "Additional compiler flags to use for testing Fortran programs (e.g. additional module search paths via -fintrinsic-modules-path )")
 
 set(ENABLE_LIBOMPTARGET ON)
-# Currently libomptarget cannot be compiled on Windows or MacOS X.
+# Currently libomptarget cannot be compiled on Windows, MacOS X, or WebAssembly.
 # Since the device plugins are only supported on Linux anyway,
 # there is no point in trying to compile libomptarget on other OSes.
 # 32-bit systems are not supported either.
-if (APPLE OR WIN32 OR WASM32 OR WASM64 OR NOT "cxx_std_17" IN_LIST CMAKE_CXX_COMPILE_FEATURES
+if (APPLE OR WIN32 OR "${CMAKE_SYSTEM_NAME}" MATCHES "^(Emscripten|WASI)$" OR
+    NOT "cxx_std_17" IN_LIST CMAKE_CXX_COMPILE_FEATURES
     OR NOT CMAKE_SIZEOF_VOID_P EQUAL 8 OR "${CMAKE_SYSTEM_NAME}" MATCHES "AIX")
   set(ENABLE_LIBOMPTARGET OFF)
 endif()
diff --git a/openmp/runtime/CMakeLists.txt b/openmp/runtime/CMakeLists.txt
index 61feef08c574d..0256bfaf4a892 100644
--- a/openmp/runtime/CMakeLists.txt
+++ b/openmp/runtime/CMakeLists.txt
@@ -140,12 +140,16 @@ set(LIBOMP_LDFLAGS "" CACHE STRING
 if("${CMAKE_SYSTEM_NAME}" MATCHES "AIX")
   set(LIBOMP_LIBFLAGS "-lperfstat" CACHE STRING
     "Appended user specified linked libs flags. (e.g., -lm)")
+  if("${LIBOMP_ARCH}" STREQUAL "ppc")
+    # PPC (32-bit) on AIX needs libcompiler_rt for __atomic_load_8, etc.
+    set(LIBOMP_LIBFLAGS "${LIBOMP_LIBFLAGS} -lcompiler_rt")
   endif()
 else()
   set(LIBOMP_LIBFLAGS "" CACHE STRING
     "Appended user specified linked libs flags. (e.g., -lm)")
 endif()
 
+if("${LIBOMP_ARCH}" STREQUAL "mips" OR "${LIBOMP_ARCH}" STREQUAL "mips64")
   set(LIBOMP_LIBFLAGS "${LIBOMP_LIBFLAGS} -latomic")
 endif()
 
diff --git a/openmp/runtime/src/kmp_runtime.cpp b/openmp/runtime/src/kmp_runtime.cpp
index 8f7f5c8c7bfe5..234a211bcfba3 100644
--- a/openmp/runtime/src/kmp_runtime.cpp
+++ b/openmp/runtime/src/kmp_runtime.cpp
@@ -8924,7 +8924,8 @@ __kmp_determine_reduction_method(
 
 #if KMP_ARCH_X86_64 || KMP_ARCH_PPC64 || KMP_ARCH_AARCH64 ||                   \
     KMP_ARCH_MIPS64 || KMP_ARCH_RISCV64 || KMP_ARCH_LOONGARCH64 ||             \
-    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM64 || KMP_ARCH_ARM64EC
+    KMP_ARCH_VE || KMP_ARCH_S390X || KMP_ARCH_WASM32 || KMP_ARCH_WASM64 ||     \
+    KMP_ARCH_ARM64EC
 
 #if KMP_OS_LINUX || KMP_OS_DRAGONFLY || KMP_OS_FREEBSD || KMP_OS_NETBSD ||     \
     KMP_OS_OPENBSD || KMP_OS_WINDOWS || KMP_OS_DARWIN || KMP_OS_HAIKU ||       \
@@ -8956,7 +8957,7 @@ __kmp_determine_reduction_method(
        // KMP_OS_HURD || KMP_OS_SOLARIS || KMP_OS_WASI || KMP_OS_AIX
 
 #elif KMP_ARCH_X86 || KMP_ARCH_ARM || KMP_ARCH_AARCH || KMP_ARCH_MIPS ||       \
-    KMP_ARCH_WASM32 || KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC
+    KMP_ARCH_PPC || KMP_ARCH_AARCH64_32 || KMP_ARCH_SPARC
 
 #if KMP_OS_LINUX || KMP_OS_DRAGONFLY || KMP_OS_FREEBSD || KMP_OS_NETBSD ||     \
     KMP_OS_OPENBSD || KMP_OS_WINDOWS || KMP_OS_HAIKU || KMP_OS_HURD ||         \

>From d57aad137058f122e8283cd329b4a6cb4721fd9d Mon Sep 17 00:00:00 2001
From: Andrew Snyder <asnyder at minitab.com>
Date: Tue, 28 Jul 2026 11:02:04 -0400
Subject: [PATCH 4/5] add a code gen test for wasm

---
 clang/test/OpenMP/wasm_codegen.c | 58 ++++++++++++++++++++++++++++++++
 1 file changed, 58 insertions(+)
 create mode 100644 clang/test/OpenMP/wasm_codegen.c

diff --git a/clang/test/OpenMP/wasm_codegen.c b/clang/test/OpenMP/wasm_codegen.c
new file mode 100644
index 0000000000000..0d40cd68fb710
--- /dev/null
+++ b/clang/test/OpenMP/wasm_codegen.c
@@ -0,0 +1,58 @@
+// REQUIRES: webassembly-registered-target
+// RUN: %clang_cc1 -triple wasm32-unknown-emscripten -fopenmp -fnoopenmp-use-tls -emit-llvm -o - %s | FileCheck %s --check-prefixes=CHECK,WASM32
+// RUN: %clang_cc1 -triple wasm64-unknown-emscripten -fopenmp -fnoopenmp-use-tls -emit-llvm -o - %s | FileCheck %s --check-prefixes=CHECK,WASM64
+// RUN: %clang_cc1 -triple wasm32-unknown-emscripten -fopenmp -fnoopenmp-use-tls -emit-obj -o %t.wasm32.o %s
+// RUN: %clang_cc1 -triple wasm64-unknown-emscripten -fopenmp -fnoopenmp-use-tls -emit-obj -o %t.wasm64.o %s
+
+// Exercise representative host OpenMP lowering for both WebAssembly pointer
+// models. WebAssembly does not support common linkage, so compiler-generated
+// locks and caches must have internal linkage.
+// CHECK-DAG: @.gomp_critical_user_.var = internal global [8 x i32] zeroinitializer
+// CHECK-DAG: @.gomp_critical_user_named.var = internal global [8 x i32] zeroinitializer
+// CHECK-DAG: @.gomp_critical_user_.reduction.var = internal global [8 x i32] zeroinitializer
+// CHECK-DAG: @threadprivate_var.cache. = internal global ptr null
+
+// The dependency record and size_t parameters must follow the target pointer
+// width rather than assuming wasm32.
+// WASM32-DAG: %struct.kmp_depend_info = type { i32, i32, i8 }
+// WASM64-DAG: %struct.kmp_depend_info = type { i64, i64, i8 }
+// WASM32-DAG: call ptr @__kmpc_omp_task_alloc({{.*}}i32 {{[0-9]+}}, i32 {{[0-9]+}}, ptr
+// WASM64-DAG: call ptr @__kmpc_omp_task_alloc({{.*}}i64 {{[0-9]+}}, i64 {{[0-9]+}}, ptr
+// WASM32-DAG: call ptr @__kmpc_threadprivate_cached({{.*}}i32 4, ptr @threadprivate_var.cache.)
+// WASM64-DAG: call ptr @__kmpc_threadprivate_cached({{.*}}i64 4, ptr @threadprivate_var.cache.)
+// WASM32-DAG: call i32 @__kmpc_reduce_nowait({{.*}}i32 4, ptr
+// WASM64-DAG: call i32 @__kmpc_reduce_nowait({{.*}}i64 8, ptr
+
+// CHECK-DAG: call void (ptr, i32, ptr, ...) @__kmpc_fork_call(
+// CHECK-DAG: call void @__kmpc_for_static_init_4(
+// CHECK-DAG: call i32 @__kmpc_omp_task_with_deps(
+// CHECK-DAG: call i32 @__kmpc_omp_taskwait(
+// CHECK-DAG: call void @__kmpc_critical(
+
+void critical_regions(void) {
+#pragma omp critical
+  {}
+
+#pragma omp critical(named)
+  {}
+}
+
+int threadprivate_var;
+#pragma omp threadprivate(threadprivate_var)
+
+int openmp_constructs(int *values, int count) {
+  int sum = 0;
+#pragma omp parallel for reduction(+ : sum)
+  for (int i = 0; i < count; ++i)
+    sum += values[i];
+
+#pragma omp task shared(values) depend(inout : values[0 : count])
+  values[0] = sum;
+
+#pragma omp taskwait
+
+#pragma omp critical(named)
+  threadprivate_var += sum;
+
+  return sum;
+}

>From 3e64bf4050c054842de5b4584971d93a0c7bf726 Mon Sep 17 00:00:00 2001
From: Andrew Snyder <asnyder at minitab.com>
Date: Tue, 28 Jul 2026 11:20:26 -0400
Subject: [PATCH 5/5] consistency

---
 openmp/cmake/modules/LibompUtils.cmake | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/openmp/cmake/modules/LibompUtils.cmake b/openmp/cmake/modules/LibompUtils.cmake
index 2a639bccc47b6..9dd80c28dcaf0 100644
--- a/openmp/cmake/modules/LibompUtils.cmake
+++ b/openmp/cmake/modules/LibompUtils.cmake
@@ -125,9 +125,9 @@ function(libomp_get_legal_arch return_arch_string)
     set(${return_arch_string} "SPARC" PARENT_SCOPE)
   elseif(SPARCV9)
     set(${return_arch_string} "SPARCV9" PARENT_SCOPE)
-  elseif(${WASM32})
+  elseif(WASM32)
     set(${return_arch_string} "WASM32" PARENT_SCOPE)
-  elseif(${WASM64})
+  elseif(WASM64)
     set(${return_arch_string} "WASM64" PARENT_SCOPE)
   else()
     set(${return_arch_string} "${LIBOMP_ARCH}" PARENT_SCOPE)



More information about the cfe-commits mailing list