summaryrefslogtreecommitdiffstats
path: root/cmake
diff options
context:
space:
mode:
authorBernhard Guillon <Bernhard.Guillon@begu.org>2026-06-30 22:06:39 +0200
committerBernhard Guillon <Bernhard.Guillon@begu.org>2026-06-30 22:06:39 +0200
commit4470bda7f8f49bc8675889ef03ee4ef01f5a33cc (patch)
tree2adab17867add042625c6289137f1f2212212dda /cmake
parentf19db5021361f1cf5780d1d06ceea26b8bf392e6 (diff)
downloadcsharp-cmake-4470bda7f8f49bc8675889ef03ee4ef01f5a33cc.tar.gz
csharp-cmake-4470bda7f8f49bc8675889ef03ee4ef01f5a33cc.zip
Restore dotnet_finalize_targets with documentation explaining why deferred creation is needed
Diffstat (limited to 'cmake')
-rw-r--r--cmake/dotnet.cmake41
1 files changed, 41 insertions, 0 deletions
diff --git a/cmake/dotnet.cmake b/cmake/dotnet.cmake
index b4e15ea..8cf84fa 100644
--- a/cmake/dotnet.cmake
+++ b/cmake/dotnet.cmake
@@ -1,3 +1,41 @@
+# ============================================================================
+# dotnet.cmake - CMake functions for building .NET projects with Roslyn csc
+#
+# Provides add_dotnet_library, add_dotnet_executable, target_link_dotnet_libraries,
+# and dotnet_finalize_targets for building .NET assemblies using the Roslyn
+# compiler bundled with the .NET SDK.
+#
+# Usage pattern:
+#
+# add_dotnet_target(MyLib)
+# add_dotnet_library(MyLib SOURCES MyLib.cs)
+#
+# add_dotnet_target(MyApp)
+# add_dotnet_executable(MyApp MAIN Program SOURCES Program.cs)
+# target_link_dotnet_libraries(MyApp PRIVATE MyLib)
+#
+# dotnet_finalize_targets() # Must be called after all targets are defined
+#
+# WHY dotnet_finalize_targets()?
+# --------------------------------
+# CMake's native target_link_libraries works because the build system generator
+# (Ninja, Make, VS) handles dependency tracking at a lower level — it
+# automatically adds a linked library's output file as an input to the
+# dependent target's link step, so Ninja/Make know to rebuild when the
+# dependency changes.
+#
+# We use add_custom_command(OUTPUT ...) to compile .NET assemblies with csc.
+# For Ninja to rebuild a target when its dependency's .dll changes, that .dll
+# must appear in the DEPENDS list of the custom command. But DEPENDS is fixed
+# at creation time — we cannot append to it later.
+#
+# Since target_link_dotnet_libraries is called AFTER add_dotnet_library/
+# add_dotnet_executable, we don't know all dependencies when the custom
+# command is created. The solution: defer custom command creation to
+# dotnet_finalize_targets(), which runs after all linking is configured and
+# knows the full dependency graph.
+# ============================================================================
+
function(add_dotnet_library NAME)
set(multiValueArgs SOURCES REFERENCES)
@@ -125,6 +163,9 @@ function(target_link_dotnet_libraries TARGET)
endfunction()
+# Creates the actual custom commands and targets with full dependency knowledge.
+# Must be called after all add_dotnet_library/add_dotnet_executable and
+# target_link_dotnet_libraries calls.
function(dotnet_finalize_targets)
get_property(ALL_TARGETS GLOBAL PROPERTY DOTNET_TARGETS)
foreach(NAME IN LISTS ALL_TARGETS)