[Openmp-commits] [flang] [llvm] [openmp] [flang][runtimes] Rebuild Fortran modules when dependency modules change (PR #203549)

Eugene Epshteyn via Openmp-commits openmp-commits at lists.llvm.org
Fri Jun 12 10:48:08 PDT 2026


https://github.com/eugeneepshteyn updated https://github.com/llvm/llvm-project/pull/203549

>From 4bc3506afd2cead5d5e58846a0bb5c930dc4a2da Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Fri, 12 Jun 2026 10:23:58 -0400
Subject: [PATCH 1/5] [flang][runtimes] Rebuild Fortran modules when dependency
 modules change

With the Fortran intrinsic module generation moving to flang-rt, any time
someone changes some key modules, a buildbot or a build starts failing until
someone remembers to do a full rebuild. This change is trying to set
dependencies for some key modules to avoid this problem.
---
 flang-rt/lib/runtime/CMakeLists.txt | 8 ++++++++
 openmp/module/CMakeLists.txt        | 5 +++++
 2 files changed, 13 insertions(+)

diff --git a/flang-rt/lib/runtime/CMakeLists.txt b/flang-rt/lib/runtime/CMakeLists.txt
index a956cda31b52d..e0a871c8521ea 100644
--- a/flang-rt/lib/runtime/CMakeLists.txt
+++ b/flang-rt/lib/runtime/CMakeLists.txt
@@ -298,6 +298,14 @@ if (FLANG_RT_FORTRAN_MODULES)
   flang_module_target(flang_rt.mod.intrinsics PUBLIC)
   add_module_barrier(flang_rt.mod.intrinsics.barrier flang_rt.mod.intrinsics)
 
+  set(intrinsic_module_files
+    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/__fortran_builtins.mod"
+    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/__cuda_builtins.mod"
+  )
+  set_property(SOURCE ${module_sources}
+    APPEND PROPERTY OBJECT_DEPENDS "${intrinsic_module_files}"
+  )
+
   # The modules themselves
   add_flangrt_library(flang_rt.mod OBJECT
     ${module_sources}
diff --git a/openmp/module/CMakeLists.txt b/openmp/module/CMakeLists.txt
index c4b9554bdffa4..5cb9c3453f1f5 100644
--- a/openmp/module/CMakeLists.txt
+++ b/openmp/module/CMakeLists.txt
@@ -11,6 +11,11 @@
 configure_file(omp_lib.F90.var "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90" @ONLY)
 configure_file(omp_lib.h.var "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/omp_lib.h" @ONLY)
 
+set_property(SOURCE "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90"
+  APPEND PROPERTY OBJECT_DEPENDS
+    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/iso_c_binding.mod"
+)
+
 # One compilation step creates both, omp_lib.mod and omp_lib_kinds.mod. Only
 # these files are used, the object file itself can be discarded.
 # TODO: Adding it to libomp ($<TARGET_OBJECTS:libomp-mod>) would allow implementing Fortran API in Fortran

>From 73b9df52c0cad4c5db0248565cd6ed7e38ebec96 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Fri, 12 Jun 2026 10:55:29 -0400
Subject: [PATCH 2/5] The original fix only worked for incremental builds that
 already build flang-rt. AI suggested using module stamps for more generic
 fix.

---
 flang-rt/lib/runtime/CMakeLists.txt | 12 ++++++++----
 openmp/module/CMakeLists.txt        | 17 +++++++++++++----
 2 files changed, 21 insertions(+), 8 deletions(-)

diff --git a/flang-rt/lib/runtime/CMakeLists.txt b/flang-rt/lib/runtime/CMakeLists.txt
index e0a871c8521ea..356dfed33eef3 100644
--- a/flang-rt/lib/runtime/CMakeLists.txt
+++ b/flang-rt/lib/runtime/CMakeLists.txt
@@ -298,12 +298,16 @@ if (FLANG_RT_FORTRAN_MODULES)
   flang_module_target(flang_rt.mod.intrinsics PUBLIC)
   add_module_barrier(flang_rt.mod.intrinsics.barrier flang_rt.mod.intrinsics)
 
-  set(intrinsic_module_files
-    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/__fortran_builtins.mod"
-    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/__cuda_builtins.mod"
+  set(intrinsic_module_stamp
+    "${CMAKE_CURRENT_BINARY_DIR}/flang_rt.mod.intrinsics.stamp"
+  )
+  add_custom_command(OUTPUT "${intrinsic_module_stamp}"
+    COMMAND "${CMAKE_COMMAND}" -E touch "${intrinsic_module_stamp}"
+    DEPENDS "$<TARGET_OBJECTS:flang_rt.mod.intrinsics>"
+    VERBATIM
   )
   set_property(SOURCE ${module_sources}
-    APPEND PROPERTY OBJECT_DEPENDS "${intrinsic_module_files}"
+    APPEND PROPERTY OBJECT_DEPENDS "${intrinsic_module_stamp}"
   )
 
   # The modules themselves
diff --git a/openmp/module/CMakeLists.txt b/openmp/module/CMakeLists.txt
index 5cb9c3453f1f5..b593c2d044aa3 100644
--- a/openmp/module/CMakeLists.txt
+++ b/openmp/module/CMakeLists.txt
@@ -11,10 +11,19 @@
 configure_file(omp_lib.F90.var "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90" @ONLY)
 configure_file(omp_lib.h.var "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/omp_lib.h" @ONLY)
 
-set_property(SOURCE "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90"
-  APPEND PROPERTY OBJECT_DEPENDS
-    "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/iso_c_binding.mod"
-)
+if ("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
+  set(flang_rt_module_stamp
+    "${CMAKE_CURRENT_BINARY_DIR}/flang_rt.mod.stamp"
+  )
+  add_custom_command(OUTPUT "${flang_rt_module_stamp}"
+    COMMAND "${CMAKE_COMMAND}" -E touch "${flang_rt_module_stamp}"
+    DEPENDS ${RUNTIMES_FORTRAN_BUILD_DEPS}
+    VERBATIM
+  )
+  set_property(SOURCE "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90"
+    APPEND PROPERTY OBJECT_DEPENDS "${flang_rt_module_stamp}"
+  )
+endif ()
 
 # One compilation step creates both, omp_lib.mod and omp_lib_kinds.mod. Only
 # these files are used, the object file itself can be discarded.

>From b831576442d573fe0927ed64154882177bf23c96 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Fri, 12 Jun 2026 11:15:53 -0400
Subject: [PATCH 3/5] The new CI error is different from the original stale
 .mod failure. In run 27423676117, check-flang-rt tried to execute the
 runtimes bootstrap placeholder:

  /home/gha/.../build/./bin/flang: Permission denied

Make the top-level per-runtime check targets, including check-flang-rt, depend
on the real just-built flang executable before entering the external runtimes
build.

Also tightened the module dependency fix:

  - llvm-project/llvm/runtimes/CMakeLists.txt: adds check-${runtime_name} targets to the test dependency list so check-flang-rt
    gets the existing flang dependency.

  - llvm-project/flang-rt/lib/runtime/CMakeLists.txt: adds a real flang_rt.mod.stamp produced from flang_rt.mod object files.
  - llvm-project/openmp/module/CMakeLists.txt: makes omp_lib.F90 depend on that stamp.
---
 flang-rt/lib/runtime/CMakeLists.txt | 13 +++++++++++++
 llvm/runtimes/CMakeLists.txt        | 13 ++++++++++++-
 openmp/module/CMakeLists.txt        |  7 +------
 3 files changed, 26 insertions(+), 7 deletions(-)

diff --git a/flang-rt/lib/runtime/CMakeLists.txt b/flang-rt/lib/runtime/CMakeLists.txt
index 356dfed33eef3..8d9c795a616c3 100644
--- a/flang-rt/lib/runtime/CMakeLists.txt
+++ b/flang-rt/lib/runtime/CMakeLists.txt
@@ -318,6 +318,19 @@ if (FLANG_RT_FORTRAN_MODULES)
   flang_module_target(flang_rt.mod PUBLIC)
   add_module_barrier(flang-rt-mod flang_rt.mod)
 
+  set(flang_rt_module_stamp
+    "${CMAKE_CURRENT_BINARY_DIR}/flang_rt.mod.stamp"
+  )
+  add_custom_command(OUTPUT "${flang_rt_module_stamp}"
+    COMMAND "${CMAKE_COMMAND}" -E touch "${flang_rt_module_stamp}"
+    DEPENDS "$<TARGET_OBJECTS:flang_rt.mod>"
+    VERBATIM
+  )
+  add_custom_target(flang-rt-mod-stamp
+    DEPENDS "${flang_rt_module_stamp}"
+  )
+  add_dependencies(flang-rt-mod flang-rt-mod-stamp)
+
   if (RUNTIMES_FORTRAN_MODULES)
     set(_mod_install_dest "${RUNTIMES_INSTALL_RESOURCE_MOD_PATH}/..")
     cmake_path(NORMAL_PATH _mod_install_dest)
diff --git a/llvm/runtimes/CMakeLists.txt b/llvm/runtimes/CMakeLists.txt
index bbc91a709c553..9631d377d216c 100644
--- a/llvm/runtimes/CMakeLists.txt
+++ b/llvm/runtimes/CMakeLists.txt
@@ -663,7 +663,12 @@ if(build_runtimes)
       CMAKE_ARGS ${extra_cmake_args}
       PREFIXES ${prefixes}
       EXTRA_ARGS ${extra_args})
-    set(test_targets check-runtimes)
+    if(LLVM_INCLUDE_TESTS)
+      list(APPEND test_targets check-runtimes)
+      foreach(runtime_name ${RUNTIME_NAMES})
+        list(APPEND test_targets check-${runtime_name})
+      endforeach()
+    endif()
   else()
     if("default" IN_LIST LLVM_RUNTIME_TARGETS)
       runtime_default_target(
@@ -671,6 +676,12 @@ if(build_runtimes)
         CMAKE_ARGS ${extra_cmake_args}
         PREFIXES ${prefixes}
         EXTRA_ARGS ${extra_args})
+      if(LLVM_INCLUDE_TESTS)
+        list(APPEND test_targets check-runtimes)
+        foreach(runtime_name ${RUNTIME_NAMES})
+          list(APPEND test_targets check-${runtime_name})
+        endforeach()
+      endif()
       list(REMOVE_ITEM LLVM_RUNTIME_TARGETS "default")
     else()
       add_custom_target(runtimes)
diff --git a/openmp/module/CMakeLists.txt b/openmp/module/CMakeLists.txt
index b593c2d044aa3..7dac82ea712ef 100644
--- a/openmp/module/CMakeLists.txt
+++ b/openmp/module/CMakeLists.txt
@@ -13,12 +13,7 @@ configure_file(omp_lib.h.var "${RUNTIMES_OUTPUT_RESOURCE_MOD_DIR}/omp_lib.h" @ON
 
 if ("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
   set(flang_rt_module_stamp
-    "${CMAKE_CURRENT_BINARY_DIR}/flang_rt.mod.stamp"
-  )
-  add_custom_command(OUTPUT "${flang_rt_module_stamp}"
-    COMMAND "${CMAKE_COMMAND}" -E touch "${flang_rt_module_stamp}"
-    DEPENDS ${RUNTIMES_FORTRAN_BUILD_DEPS}
-    VERBATIM
+    "${CMAKE_BINARY_DIR}/flang-rt/lib/runtime/flang_rt.mod.stamp"
   )
   set_property(SOURCE "${CMAKE_CURRENT_BINARY_DIR}/omp_lib.F90"
     APPEND PROPERTY OBJECT_DEPENDS "${flang_rt_module_stamp}"

>From d1366d0402a42d003955bf92c4d979fc58f843a4 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Fri, 12 Jun 2026 12:01:17 -0400
Subject: [PATCH 4/5] The prior fix added check-flang-rt to the generic runtime
 test_targets path, which made it inherit the full LLVM lit/tool dependency
 set. Replaced that with a small helper that adds only flang to
 check-flang-rt.

Verified graph after reconfigure:

runtimes/check-flang-rt now depends only on:

  runtimes/CMakeFiles/check-flang-rt
  bin/flang
  runtimes/runtimes-configure

runtimes/check-openmp and runtimes/openmp no longer pick up bin/flang
from this change.

One caveat: bin/flang itself is still necessary for check-flang-rt, because
the external runtimes build compiles flang-rt Fortran module sources. If the
CI time is dominated by building flang and its MLIR/Flang libraries, that
part is unavoidable without using a prebuilt flang.
---
 llvm/runtimes/CMakeLists.txt | 25 +++++++++++++++----------
 1 file changed, 15 insertions(+), 10 deletions(-)

diff --git a/llvm/runtimes/CMakeLists.txt b/llvm/runtimes/CMakeLists.txt
index 9631d377d216c..76267fd6cf4df 100644
--- a/llvm/runtimes/CMakeLists.txt
+++ b/llvm/runtimes/CMakeLists.txt
@@ -134,6 +134,16 @@ function(add_flang_mod_deps build_target)
   endif()
 endfunction()
 
+function(add_flang_target_deps)
+  if(TARGET flang)
+    foreach(tgt IN LISTS ARGN)
+      if(TARGET ${tgt})
+        add_dependencies(${tgt} flang)
+      endif()
+    endforeach()
+  endif()
+endfunction()
+
 function(builtin_default_target compiler_rt_path)
   cmake_parse_arguments(ARG "" "" "DEPENDS" ${ARGN})
 
@@ -663,11 +673,9 @@ if(build_runtimes)
       CMAKE_ARGS ${extra_cmake_args}
       PREFIXES ${prefixes}
       EXTRA_ARGS ${extra_args})
-    if(LLVM_INCLUDE_TESTS)
-      list(APPEND test_targets check-runtimes)
-      foreach(runtime_name ${RUNTIME_NAMES})
-        list(APPEND test_targets check-${runtime_name})
-      endforeach()
+    set(test_targets check-runtimes)
+    if("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
+      add_flang_target_deps(check-flang-rt)
     endif()
   else()
     if("default" IN_LIST LLVM_RUNTIME_TARGETS)
@@ -676,11 +684,8 @@ if(build_runtimes)
         CMAKE_ARGS ${extra_cmake_args}
         PREFIXES ${prefixes}
         EXTRA_ARGS ${extra_args})
-      if(LLVM_INCLUDE_TESTS)
-        list(APPEND test_targets check-runtimes)
-        foreach(runtime_name ${RUNTIME_NAMES})
-          list(APPEND test_targets check-${runtime_name})
-        endforeach()
+      if("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
+        add_flang_target_deps(check-flang-rt)
       endif()
       list(REMOVE_ITEM LLVM_RUNTIME_TARGETS "default")
     else()

>From dc9503651b85f3ae4f72bf23d2fd2b5cea9c6bb0 Mon Sep 17 00:00:00 2001
From: Eugene Epshteyn <eepshteyn at nvidia.com>
Date: Fri, 12 Jun 2026 13:45:30 -0400
Subject: [PATCH 5/5] The slow CI run was caused by the latest commit touching
 llvm/runtimes/CMakeLists.txt. .ci/compute_projects.py classifies that as an
 llvm change, which expanded Linux CI to:

  check-bolt check-clang check-clang-tools check-cross-project check-flang check-lld check-lldb check-llvm check-mlir check-
polly

Removed that workaround from the cumulative patch and moved the needed
check-flang-rt -> flang dependency into llvm-project/flang/test/CMakeLists.txt.
It uses a deferred CMake edge because check-flang-rt is created later by
llvm/runtimes.

Current cumulative diff against origin/main is only:

flang-rt/lib/runtime/CMakeLists.txt
flang/test/CMakeLists.txt
openmp/module/CMakeLists.txt

CI selector for that final patch is back to the narrow set:

projects_to_build='clang;flang;lld;llvm'
project_check_targets='check-flang'
runtimes_to_build='flang-rt;openmp'
runtimes_check_targets='check-flang-rt openmp'

Important: a normal follow-up commit will still touch
llvm/runtimes/CMakeLists.txt because it reverts the previous workaround,
so that one CI run would still be broad.
---
 flang/test/CMakeLists.txt    |  9 +++++++++
 llvm/runtimes/CMakeLists.txt | 16 ----------------
 2 files changed, 9 insertions(+), 16 deletions(-)

diff --git a/flang/test/CMakeLists.txt b/flang/test/CMakeLists.txt
index 0e26711e76467..f36975b03b62d 100644
--- a/flang/test/CMakeLists.txt
+++ b/flang/test/CMakeLists.txt
@@ -124,6 +124,15 @@ if ("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES AND NOT FLANG_STANDALONE_BUILD)
   # Flang tests need runtimes module files (flang-rt-mod, libomp-mod, etc.).
   add_custom_target(flang-rt-test-deps)
   list(APPEND FLANG_TEST_DEPENDS flang-rt-test-deps)
+
+  function(add_flang_rt_check_target_dependency)
+    if (TARGET check-flang-rt AND TARGET flang)
+      add_dependencies(check-flang-rt flang)
+    endif ()
+  endfunction()
+  # check-flang-rt is created later by llvm/runtimes, so defer this edge.
+  cmake_language(DEFER DIRECTORY "${LLVM_MAIN_SRC_DIR}"
+    CALL add_flang_rt_check_target_dependency)
 endif ()
 
 add_custom_target(flang-test-depends DEPENDS ${FLANG_TEST_DEPENDS})
diff --git a/llvm/runtimes/CMakeLists.txt b/llvm/runtimes/CMakeLists.txt
index 76267fd6cf4df..bbc91a709c553 100644
--- a/llvm/runtimes/CMakeLists.txt
+++ b/llvm/runtimes/CMakeLists.txt
@@ -134,16 +134,6 @@ function(add_flang_mod_deps build_target)
   endif()
 endfunction()
 
-function(add_flang_target_deps)
-  if(TARGET flang)
-    foreach(tgt IN LISTS ARGN)
-      if(TARGET ${tgt})
-        add_dependencies(${tgt} flang)
-      endif()
-    endforeach()
-  endif()
-endfunction()
-
 function(builtin_default_target compiler_rt_path)
   cmake_parse_arguments(ARG "" "" "DEPENDS" ${ARGN})
 
@@ -674,9 +664,6 @@ if(build_runtimes)
       PREFIXES ${prefixes}
       EXTRA_ARGS ${extra_args})
     set(test_targets check-runtimes)
-    if("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
-      add_flang_target_deps(check-flang-rt)
-    endif()
   else()
     if("default" IN_LIST LLVM_RUNTIME_TARGETS)
       runtime_default_target(
@@ -684,9 +671,6 @@ if(build_runtimes)
         CMAKE_ARGS ${extra_cmake_args}
         PREFIXES ${prefixes}
         EXTRA_ARGS ${extra_args})
-      if("flang-rt" IN_LIST LLVM_ENABLE_RUNTIMES)
-        add_flang_target_deps(check-flang-rt)
-      endif()
       list(REMOVE_ITEM LLVM_RUNTIME_TARGETS "default")
     else()
       add_custom_target(runtimes)



More information about the Openmp-commits mailing list