https://github.com/jhuber6 updated 
https://github.com/llvm/llvm-project/pull/200212

>From 152e1f50d9b6a1d513658072c5bdd7b70a7f92db Mon Sep 17 00:00:00 2001
From: Joseph Huber <[email protected]>
Date: Thu, 28 May 2026 10:55:53 -0500
Subject: [PATCH 1/4] [Clang] Support multilibs on Windows

Summary:
This was pushed to a follow-up, and I think the previous has lingered
long enough to expand this to Windows. the per-target runtime directory
this uses is default-off, but nothing stops us from just providing this.
The interest in this is for ROCm builds on Windows to be able to provide
asan / debug builds the same way on Linux.
---
 clang/lib/Driver/ToolChains/MSVC.cpp          | 14 ++++
 .../Inputs/multilib_msvc_tree/bin/.keep       |  0
 .../include/x86_64-pc-windows-msvc/.keep      |  0
 .../x86_64-pc-windows-msvc/debug/.keep        |  0
 .../x86_64-pc-windows-msvc/noexcept/.keep     |  0
 .../x86_64-pc-windows-msvc/release/.keep      |  0
 clang/test/Driver/msvc-multilib.yaml          | 81 +++++++++++++++++++
 7 files changed, 95 insertions(+)
 create mode 100644 clang/test/Driver/Inputs/multilib_msvc_tree/bin/.keep
 create mode 100644 
clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/.keep
 create mode 100644 
clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/debug/.keep
 create mode 100644 
clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/noexcept/.keep
 create mode 100644 
clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/release/.keep
 create mode 100644 clang/test/Driver/msvc-multilib.yaml

diff --git a/clang/lib/Driver/ToolChains/MSVC.cpp 
b/clang/lib/Driver/ToolChains/MSVC.cpp
index f0cb01058e9c9..d7486ddeef09e 100644
--- a/clang/lib/Driver/ToolChains/MSVC.cpp
+++ b/clang/lib/Driver/ToolChains/MSVC.cpp
@@ -523,6 +523,8 @@ MSVCToolChain::MSVCToolChain(const Driver &D, const 
llvm::Triple &Triple,
       llvm::findVCToolChainViaSetupConfig(getVFS(), VCToolsVersion,
                                           VCToolChainPath, VSLayout) ||
       llvm::findVCToolChainViaRegistry(VCToolChainPath, VSLayout);
+
+  loadMultilibsFromYAML(Args, D);
 }
 
 Tool *MSVCToolChain::buildLinker() const {
@@ -767,6 +769,18 @@ void MSVCToolChain::AddClangSystemIncludeArgs(const 
ArgList &DriverArgs,
   if (DriverArgs.hasArg(options::OPT_nostdlibinc))
     return;
 
+  // Add multilib variant include paths in priority order.
+  for (const Multilib &M : getOrderedMultilibs()) {
+    if (M.isDefault())
+      continue;
+    if (std::optional<std::string> StdlibIncDir = getStdlibIncludePath()) {
+      SmallString<128> Dir(*StdlibIncDir);
+      llvm::sys::path::append(Dir, M.includeSuffix());
+      if (getDriver().getVFS().exists(Dir))
+        addSystemInclude(DriverArgs, CC1Args, Dir);
+    }
+  }
+
   // Honor %INCLUDE% and %EXTERNAL_INCLUDE%. It should have essential search
   // paths set by vcvarsall.bat. Skip if the user expressly set any of the
   // Windows SDK or VC Tools options.
diff --git a/clang/test/Driver/Inputs/multilib_msvc_tree/bin/.keep 
b/clang/test/Driver/Inputs/multilib_msvc_tree/bin/.keep
new file mode 100644
index 0000000000000..e69de29bb2d1d
diff --git 
a/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/.keep
 
b/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/.keep
new file mode 100644
index 0000000000000..e69de29bb2d1d
diff --git 
a/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/debug/.keep
 
b/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/debug/.keep
new file mode 100644
index 0000000000000..e69de29bb2d1d
diff --git 
a/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/noexcept/.keep
 
b/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/noexcept/.keep
new file mode 100644
index 0000000000000..e69de29bb2d1d
diff --git 
a/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/release/.keep
 
b/clang/test/Driver/Inputs/multilib_msvc_tree/include/x86_64-pc-windows-msvc/release/.keep
new file mode 100644
index 0000000000000..e69de29bb2d1d
diff --git a/clang/test/Driver/msvc-multilib.yaml 
b/clang/test/Driver/msvc-multilib.yaml
new file mode 100644
index 0000000000000..34ac47149b19b
--- /dev/null
+++ b/clang/test/Driver/msvc-multilib.yaml
@@ -0,0 +1,81 @@
+# Basic selection where -fmultilib-flag=debug selects the debug variant.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes -x c %s -### -o 
/dev/null 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc -fmultilib-flag=debug \
+# RUN:     -ccc-install-dir %S/Inputs/multilib_msvc_tree/bin \
+# RUN:   | FileCheck --check-prefix=CHECK-DEBUG %s
+# CHECK-DEBUG:      "-cc1" "-triple" "x86_64-pc-windows-msvc
+# CHECK-DEBUG:      "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
+
+# Default behavior where no variant path is prepended.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes -x c %s -### -o 
/dev/null 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc \
+# RUN:     -ccc-install-dir %S/Inputs/multilib_msvc_tree/bin \
+# RUN:   | FileCheck --check-prefix=CHECK-DEFAULT %s
+# CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
+# CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/release"
+# CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/noexcept"
+
+# Multiple matches stacking on top of each-other.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes -x c %s -### -o 
/dev/null 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc -fmultilib-flag=debug 
-fno-exceptions \
+# RUN:     -ccc-install-dir %S/Inputs/multilib_msvc_tree/bin \
+# RUN:   | FileCheck --check-prefix=CHECK-LAYERED %s
+# CHECK-LAYERED:      "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/noexcept"
+# CHECK-LAYERED-SAME: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
+
+# Lists selected variant directories.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes 
-print-multi-directory 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc -fmultilib-flag=debug \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-DIR %s
+# CHECK-PRINT-DIR: debug
+
+# Lists all non-default variants with flags.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes -print-multi-lib 
2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc \
+# RUN:   | FileCheck --check-prefix=CHECK-PRINT-LIB %s
+# CHECK-PRINT-LIB: debug;@fmultilib-flag=debug
+# CHECK-PRINT-LIB: release;@fmultilib-flag=release
+# CHECK-PRINT-LIB: noexcept;@fno-exceptions
+
+# Error emitted when custom flag value is invalid.
+# RUN: not %clang --multi-lib-config=%s -no-canonical-prefixes -x c %s -### -o 
/dev/null 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc -fmultilib-flag=nonexistent \
+# RUN:   | FileCheck --check-prefix=CHECK-NOMATCH %s
+# CHECK-NOMATCH: error: unsupported option '-fmultilib-flag=nonexistent'
+
+# Check exclusivity so that only one of debug/release selected.
+# RUN: %clang --multi-lib-config=%s -no-canonical-prefixes 
-print-multi-directory 2>&1 \
+# RUN:     --target=x86_64-pc-windows-msvc -fmultilib-flag=release \
+# RUN:   | FileCheck --check-prefix=CHECK-EXCLUSIVE %s
+# CHECK-EXCLUSIVE:     release
+# CHECK-EXCLUSIVE-NOT: debug
+
+---
+MultilibVersion: 1.0
+
+Groups:
+- Name: build-type
+  Type: Exclusive
+
+Variants:
+- Dir: .
+  Flags: []
+- Dir: debug
+  Flags: [-fmultilib-flag=debug]
+  Group: build-type
+- Dir: release
+  Flags: [-fmultilib-flag=release]
+  Group: build-type
+- Dir: noexcept
+  Flags: [-fno-exceptions]
+
+Mappings: []
+
+Flags:
+- Name: build-type
+  Values:
+  - Name: none
+  - Name: debug
+  - Name: release
+  Default: none
+...

>From 9e19ef87982d6223c55377e7fa45c00666dfb62a Mon Sep 17 00:00:00 2001
From: Joseph Huber <[email protected]>
Date: Thu, 28 May 2026 12:15:02 -0500
Subject: [PATCH 2/4] Fix lib paths

---
 clang/lib/Driver/ToolChains/MSVC.cpp | 4 ++++
 clang/test/Driver/msvc-multilib.yaml | 6 ++++++
 2 files changed, 10 insertions(+)

diff --git a/clang/lib/Driver/ToolChains/MSVC.cpp 
b/clang/lib/Driver/ToolChains/MSVC.cpp
index d7486ddeef09e..7fb95ebc013c1 100644
--- a/clang/lib/Driver/ToolChains/MSVC.cpp
+++ b/clang/lib/Driver/ToolChains/MSVC.cpp
@@ -205,6 +205,10 @@ void visualstudio::Linker::ConstructJob(Compilation &C, 
const JobAction &JA,
     if (TC.getVFS().exists(LibPath))
       CmdArgs.push_back(Args.MakeArgString("-libpath:" + LibPath));
   }
+  for (const auto &LibPath : TC.getFilePaths()) {
+    if (LibPath.length() > 0)
+      CmdArgs.push_back(Args.MakeArgString("-libpath:" + LibPath));
+  }
   auto CRTPath = TC.getCompilerRTPath();
   if (TC.getVFS().exists(CRTPath))
     CmdArgs.push_back(Args.MakeArgString("-libpath:" + CRTPath));
diff --git a/clang/test/Driver/msvc-multilib.yaml 
b/clang/test/Driver/msvc-multilib.yaml
index 34ac47149b19b..b650393003fd0 100644
--- a/clang/test/Driver/msvc-multilib.yaml
+++ b/clang/test/Driver/msvc-multilib.yaml
@@ -5,12 +5,16 @@
 # RUN:   | FileCheck --check-prefix=CHECK-DEBUG %s
 # CHECK-DEBUG:      "-cc1" "-triple" "x86_64-pc-windows-msvc
 # CHECK-DEBUG:      "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
+# CHECK-DEBUG:      "-libpath:{{[^"]*}}/debug"
 
 # Default behavior where no variant path is prepended.
 # RUN: %clang --multi-lib-config=%s -no-canonical-prefixes -x c %s -### -o 
/dev/null 2>&1 \
 # RUN:     --target=x86_64-pc-windows-msvc \
 # RUN:     -ccc-install-dir %S/Inputs/multilib_msvc_tree/bin \
 # RUN:   | FileCheck --check-prefix=CHECK-DEFAULT %s
+# CHECK-DEFAULT-NOT: "-libpath:{{[^"]*}}/debug"
+# CHECK-DEFAULT-NOT: "-libpath:{{[^"]*}}/release"
+# CHECK-DEFAULT-NOT: "-libpath:{{[^"]*}}/noexcept"
 # CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
 # CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/release"
 # CHECK-DEFAULT-NOT: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/noexcept"
@@ -22,6 +26,8 @@
 # RUN:   | FileCheck --check-prefix=CHECK-LAYERED %s
 # CHECK-LAYERED:      "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/noexcept"
 # CHECK-LAYERED-SAME: "-internal-isystem" 
"{{[^"]*}}{{[/\\]}}x86_64-pc-windows-msvc/debug"
+# CHECK-LAYERED:      "-libpath:{{[^"]*}}/noexcept"
+# CHECK-LAYERED-SAME: "-libpath:{{[^"]*}}/debug"
 
 # Lists selected variant directories.
 # RUN: %clang --multi-lib-config=%s -no-canonical-prefixes 
-print-multi-directory 2>&1 \

>From b04ce0b79c68077e81c8ed2ca9d4b5edbe24f06e Mon Sep 17 00:00:00 2001
From: Joseph Huber <[email protected]>
Date: Thu, 28 May 2026 13:40:23 -0500
Subject: [PATCH 3/4] Commnets

---
 clang/docs/Multilib.rst                         | 3 ++-
 clang/docs/ReleaseNotes.rst                     | 3 +++
 clang/test/Driver/print-multi-selection-flags.c | 3 +++
 3 files changed, 8 insertions(+), 1 deletion(-)

diff --git a/clang/docs/Multilib.rst b/clang/docs/Multilib.rst
index d36b73dce68cd..06c43e720ab87 100644
--- a/clang/docs/Multilib.rst
+++ b/clang/docs/Multilib.rst
@@ -48,7 +48,8 @@ EXPERIMENTAL Multilib via configuration file
 ============================================
 
 Some Clang toolchains support loading multilib configuration from a
-``multilib.yaml`` configuration file.
+``multilib.yaml`` configuration file. This is currently supported on Linux,
+Windows, and Baremetal toolchains.
 
 A ``multilib.yaml`` configuration file specifies which multilib variants are
 available, their relative location, what compilation options were used to build
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 11cce36a0906c..50ea2b8fdbc2d 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -314,6 +314,9 @@ Non-comprehensive list of changes in this release
 
 - Updated support for Unicode from 15.1 to 18.0.
 
+- Linux and Windows toolchains now support Clang multilib support
+  ``-fmultilib-flag=``.
+
 New Compiler Flags
 ------------------
 - New option ``-fms-anonymous-structs`` / ``-fno-ms-anonymous-structs`` added
diff --git a/clang/test/Driver/print-multi-selection-flags.c 
b/clang/test/Driver/print-multi-selection-flags.c
index 64efddad878c5..ba7b325892f9c 100644
--- a/clang/test/Driver/print-multi-selection-flags.c
+++ b/clang/test/Driver/print-multi-selection-flags.c
@@ -1,6 +1,9 @@
 // RUN: %clang -multi-lib-config=%S/Inputs/multilib/empty.yaml 
-print-multi-flags-experimental --target=aarch64-linux -fc++-abi=itanium 
-fsanitize=address | FileCheck --check-prefix=CHECK-LINUX %s
 // CHECK-LINUX: --target=aarch64-unknown-linux
 
+// RUN: %clang -multi-lib-config=%S/Inputs/multilib/empty.yaml 
-print-multi-flags-experimental --target=x86_64-pc-windows-msvc 
-fc++-abi=itanium -fsanitize=address | FileCheck --check-prefix=CHECK-WINDOWS %s
+// CHECK-WINDOWS: --target=x86_64-pc-windows-msvc
+
 // RUN: %clang -multi-lib-config=%S/Inputs/multilib/empty.yaml 
-print-multi-flags-experimental --target=aarch64-fuchsia -fsanitize=hwaddress | 
FileCheck --check-prefix=CHECK-FUCHSIA %s
 // CHECK-FUCHSIA: --target=aarch64-unknown-fuchsia
 

>From e5e90f4c8a602733214dc979df59bf5a4a624e55 Mon Sep 17 00:00:00 2001
From: Joseph Huber <[email protected]>
Date: Mon, 8 Jun 2026 09:25:42 -0500
Subject: [PATCH 4/4] Update ReleaseNotes.rst

---
 clang/docs/ReleaseNotes.rst | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 50ea2b8fdbc2d..b740160a9d948 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -314,7 +314,7 @@ Non-comprehensive list of changes in this release
 
 - Updated support for Unicode from 15.1 to 18.0.
 
-- Linux and Windows toolchains now support Clang multilib support
+- Linux and Windows toolchains now support Clang multilib using
   ``-fmultilib-flag=``.
 
 New Compiler Flags

_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to