[clang] [test] Improve driver option coverage (PR #192861)

Fangrui Song via cfe-commits cfe-commits at lists.llvm.org
Sun Apr 19 11:22:46 PDT 2026


https://github.com/MaskRay created https://github.com/llvm/llvm-project/pull/192861

Split the Linux GNU-linker assertions into a dedicated file and extend
them with previously-untested passthrough flags handled by
gnutools::Linker::ConstructJob: -s, -u sym, -rdynamic (-export-dynamic),
-Wl,-z keyword pairs.

LoongArch on Linux previously had no test for -X / --no-relax, which are
emitted by Gnu.cpp for LoongArch and RISC-V.

>From d95188bea7fb5f44b84cfebb8207c3d6b1a73809 Mon Sep 17 00:00:00 2001
From: Fangrui Song <i at maskray.me>
Date: Sun, 19 Apr 2026 10:43:51 -0700
Subject: [PATCH] [test] Improve driver option coverage

Split the Linux GNU-linker assertions into a dedicated file and extend
them with previously-untested passthrough flags handled by
gnutools::Linker::ConstructJob: -s, -u sym, -rdynamic (-export-dynamic),
-Wl,-z keyword pairs.

LoongArch on Linux previously had no test for -X / --no-relax, which are
emitted by Gnu.cpp for LoongArch and RISC-V.
---
 clang/test/Driver/Xlinker-args.c        |  7 +------
 clang/test/Driver/freebsd.c             |  7 +++++++
 clang/test/Driver/linux-ld-args.c       | 25 +++++++++++++++++++++++++
 clang/test/Driver/linux-ld.c            | 14 +++++++-------
 clang/test/Driver/loongarch-toolchain.c |  9 +++++++++
 5 files changed, 49 insertions(+), 13 deletions(-)
 create mode 100644 clang/test/Driver/linux-ld-args.c

diff --git a/clang/test/Driver/Xlinker-args.c b/clang/test/Driver/Xlinker-args.c
index 87f98a0cdbd83..632ae748d8eae 100644
--- a/clang/test/Driver/Xlinker-args.c
+++ b/clang/test/Driver/Xlinker-args.c
@@ -6,11 +6,7 @@
 // RUN:   -Wl,two,--no-demangle,three -Xlinker four -z five -r %s 2> %t
 // RUN: FileCheck -check-prefix=DARWIN < %t %s
 
-/// -T is reordered to the last to make sure -L takes precedence.
-// RUN: %clang -target x86_64-pc-linux-gnu -### \
-// RUN:   -e _start -T a.lds -t -Xlinker one -Xlinker --no-demangle \
-// RUN:   -Wl,two,--no-demangle,three -Xlinker four -z five -r %s 2> %t
-// RUN: FileCheck -check-prefix=LINUX < %t %s
+/// Linux/GNU forwarding lives in linux-ld-args.c.
 
 /// Check that --no-demangle gets forwarded to the mingw linker
 // RUN: %clang -target x86_64-w64-mingw32 -### \
@@ -23,7 +19,6 @@
 
 // DARWIN-NOT: --no-demangle
 // DARWIN: "one" "two" "three" "four" "-z" "five" "-r"
-// LINUX: "--no-demangle" "-e" "_start" "one" "two" "three" "four" "-z" "five" "-r" {{.*}} "-T" "a.lds" "-t"
 // MINGW: "--no-demangle"
 // AIX: "-b" "one" "-b" "two"
 
diff --git a/clang/test/Driver/freebsd.c b/clang/test/Driver/freebsd.c
index 94db63278bfe9..77310bed4c30f 100644
--- a/clang/test/Driver/freebsd.c
+++ b/clang/test/Driver/freebsd.c
@@ -219,3 +219,10 @@
 // RUN: %clang --target=riscv64-unknown-freebsd -mno-relax -### %s 2>&1 \
 // RUN:   | FileCheck -check-prefix=RISCV64-FLAGS %s
 // RISCV64-FLAGS: "-X" "--no-relax"
+
+/// -rdynamic becomes -export-dynamic; -s, -t, and -T are forwarded.
+// RUN: %clang --target=x86_64-unknown-freebsd -rdynamic -s -t -T a.lds -### %s \
+// RUN:   2>&1 | FileCheck --check-prefix=PASS %s
+// PASS:      "--eh-frame-hdr"
+// PASS-SAME: "-export-dynamic"
+// PASS-SAME: "-s" "-t" "-T" "a.lds"
diff --git a/clang/test/Driver/linux-ld-args.c b/clang/test/Driver/linux-ld-args.c
new file mode 100644
index 0000000000000..e047d6ce009e9
--- /dev/null
+++ b/clang/test/Driver/linux-ld-args.c
@@ -0,0 +1,25 @@
+/// Tests that gnutools::Linker::ConstructJob forwards user command-line options
+/// to the ld invocation. Sysroot-dependent toolchain discovery and
+/// crt*/library-path selection live in linux-ld.c.
+
+/// Mixed -Xlinker, -Wl, and standalone forwarding. -T is reordered to the end
+/// so that earlier -L paths take precedence.
+// RUN: %clang --target=x86_64-linux-gnu -### \
+// RUN:   -e _start -T a.lds -t -Xlinker one -Xlinker --no-demangle \
+// RUN:   -Wl,two,--no-demangle,three -Xlinker four -z five -r %s 2>&1 | \
+// RUN:   FileCheck --check-prefix=MIXED %s
+// MIXED: "--no-demangle" "-e" "_start" "one" "two" "three" "four" "-z" "five" "-r" {{.*}} "-T" "a.lds" "-t"
+
+/// Passthrough flags. -rdynamic becomes -export-dynamic; -Wl,-z keyword pairs
+/// are forwarded as separate "-z" KEYWORD tokens.
+// RUN: %clang --target=x86_64-linux-gnu -### \
+// RUN:   -s -u my_sym -rdynamic -Wl,-z,relro,-z,now %s 2>&1 | \
+// RUN:   FileCheck --check-prefix=PASS %s
+// PASS:      "-s"
+// PASS-SAME: "-export-dynamic"
+// PASS-SAME: "-u" "my_sym"
+// PASS-SAME: "-z" "relro" "-z" "now"
+
+/// -nopie is OpenBSD-specific.
+// RUN: not %clang -### --target=x86_64-unknown-linux-gnu %s -nopie 2>&1 | FileCheck %s --check-prefix=CHECK-NOPIE
+// CHECK-NOPIE: error: unsupported option '-nopie' for target 'x86_64-unknown-linux-gnu'
diff --git a/clang/test/Driver/linux-ld.c b/clang/test/Driver/linux-ld.c
index 2c9d3a6ec3f90..8de1988d606cf 100644
--- a/clang/test/Driver/linux-ld.c
+++ b/clang/test/Driver/linux-ld.c
@@ -1,7 +1,11 @@
 // UNSUPPORTED: system-windows
-// General tests that ld invocations on Linux targets sane. Note that we use
-// sysroot to make these tests independent of the host system.
-//
+/// Tests for Linux toolchain discovery and start/end-file selection in
+/// gnutools::Linker::ConstructJob: crt*.o selection, -L search paths, multilib,
+/// -m elf_* per triple, --hash-style per target, -lgcc chains, and per-triple
+/// --dynamic-linker. Every RUN uses a sysroot tree so results are host-
+/// independent. Pure driver->linker argument forwarding without sysroot
+/// dependencies lives in linux-ld-args.c.
+
 // RUN: %clang -### -Werror %s -no-pie 2>&1 \
 // RUN:     --target=i386-unknown-linux -rtlib=platform --unwindlib=platform \
 // RUN:     --sysroot=%S/Inputs/basic_linux_tree \
@@ -1820,7 +1824,3 @@
 // CHECK-OE-AARCH64: "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed" "-lc" "-lgcc" "--as-needed" "-lgcc_s" "--no-as-needed"
 // CHECK-OE-AARCH64: "[[SYSROOT]]/usr/lib64/aarch64-oe-linux/6.3.0{{/|\\\\}}crtend.o"
 // CHECK-OE-AARCH64: "[[SYSROOT]]/usr/lib64/aarch64-oe-linux/6.3.0/../../../lib64{{/|\\\\}}crtn.o"
-
-/// -nopie is OpenBSD-specific.
-// RUN: not %clang -### --target=x86_64-unknown-linux-gnu %s -nopie 2>&1 | FileCheck %s --check-prefix=CHECK-NOPIE
-// CHECK-NOPIE: error: unsupported option '-nopie' for target 'x86_64-unknown-linux-gnu'
diff --git a/clang/test/Driver/loongarch-toolchain.c b/clang/test/Driver/loongarch-toolchain.c
index cfd53152b7e6e..54a2519e0a70d 100644
--- a/clang/test/Driver/loongarch-toolchain.c
+++ b/clang/test/Driver/loongarch-toolchain.c
@@ -25,3 +25,12 @@
 // LA64-SAME: {{^}} "-L{{.*}}/Inputs/multilib_loongarch_linux_sdk/sysroot/usr{{/|\\\\}}lib64"
 // LA64-SAME: {{^}} "-L{{.*}}/Inputs/multilib_loongarch_linux_sdk/lib/gcc/loongarch64-unknown-linux-gnu/12.1.0/../../../../loongarch64-unknown-linux-gnu/lib"
 // LA64-SAME: {{^}} "-L{{.*}}/Inputs/multilib_loongarch_linux_sdk/sysroot/usr/lib"
+
+/// -X is always passed on LoongArch; --no-relax only with -mno-relax.
+// RUN: %clang --target=loongarch64-unknown-linux-gnu -### %s 2>&1 | \
+// RUN:   FileCheck --check-prefix=LA64-RELAX %s
+// RUN: %clang --target=loongarch64-unknown-linux-gnu -mno-relax -### %s 2>&1 | \
+// RUN:   FileCheck --check-prefix=LA64-NORELAX %s
+// LA64-RELAX:     "-X"
+// LA64-RELAX-NOT: "--no-relax"
+// LA64-NORELAX:   "-X" "--no-relax"



More information about the cfe-commits mailing list