diff --git a/clang/lib/Driver/ToolChains/Arch/AArch64.cpp b/clang/lib/Driver/ToolChains/Arch/AArch64.cpp --- a/clang/lib/Driver/ToolChains/Arch/AArch64.cpp +++ b/clang/lib/Driver/ToolChains/Arch/AArch64.cpp @@ -209,6 +209,22 @@ success = getAArch64MicroArchFeaturesFromMcpu( D, getAArch64TargetCPU(Args, Triple, A), Args, Features); + if (!success) + D.Diag(diag::err_drv_clang_unsupported) << A->getAsString(Args); + + // This matches GNU AArch64 assembler's behavior, which handles -Wa,-march + // after -march. And while only using the the value of last -march, it + // includes all the options passed via -Wa,-march. + success = true; + if ((A = Args.getLastArg(options::OPT_Wa_COMMA, options::OPT_Xassembler))) { + for (const Arg *A : + Args.filtered(options::OPT_Wa_COMMA, options::OPT_Xassembler)) + for (StringRef Value : A->getValues()) + if (Value.startswith("-march=")) + success = getAArch64ArchFeaturesFromMarch(D, Value.substr(7), Args, + Features); + } + if (!success) D.Diag(diag::err_drv_clang_unsupported) << A->getAsString(Args); diff --git a/clang/test/Driver/aarch64-target-as-march.s b/clang/test/Driver/aarch64-target-as-march.s new file mode 100644 --- /dev/null +++ b/clang/test/Driver/aarch64-target-as-march.s @@ -0,0 +1,8 @@ +/// These tests make sure that options passed to the assembler +/// via -Wa or -Xassembler are applied correctly to assembler inputs. + +/// The last -march wins, and is handled before -Wa,march. All the values of -Wa,march options are added. +// RUN: %clang --target=aarch64-linux-gnueabi -### -c -Wa,-march=armv8.1-a -march=armv8.2-a -Wa,-march=armv8.3-a -Wa,-march=armv8.4-a %s 2>&1 | \ +// RUN: FileCheck --check-prefix=TRIPLE-AARCH64 %s + +// TRIPLE-AARCH64: "-target-feature" "+v8.2a" "-target-feature" "+v8.1a" "-target-feature" "+v8.3a" "-target-feature" "+v8.4a"