[clang] [llvm] [clang] Add cc1 --output-asm-variant= to set output syntax (PR #109360)

Fangrui Song via cfe-commits cfe-commits at lists.llvm.org
Thu Sep 19 19:00:17 PDT 2024


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

2fcaa549a824efeb56e807fcf750a56bf985296b (2010) added cc1as option
`-output-asm-variant` (untested) to set the output syntax.
`clang -cc1as -filetype asm -output-asm-variant 1` allows AT&T input and
Intel output.

This patch renames the cc1as option (to avoid collision with -o) and
makes it available for cc1 to set output syntax. This allows different
input & output syntax:

```
echo 'asm("mov $1, %eax");' | clang -xc - -S -o - -Xclang --output-asm-variant=1
```

Note: `AsmWriterFlavor` (with a misleading name), used to initialize
MCAsmInfo::AssemblerDialect, is primarily used for assembly input, not
for output.


>From 7be5f9edad29769ae5bf2a49e861afed0c984014 Mon Sep 17 00:00:00 2001
From: Fangrui Song <i at maskray.me>
Date: Thu, 19 Sep 2024 19:00:08 -0700
Subject: [PATCH] =?UTF-8?q?[=F0=9D=98=80=F0=9D=97=BD=F0=9D=97=BF]=20initia?=
 =?UTF-8?q?l=20version?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Created using spr 1.3.5-bogner
---
 clang/include/clang/Basic/CodeGenOptions.def  |  1 +
 clang/include/clang/Driver/Options.td         |  5 ++--
 clang/lib/CodeGen/BackendUtil.cpp             |  2 ++
 .../test/CodeGen/inline-asm-output-variant.c  | 26 +++++++++++++++++++
 clang/test/Misc/cc1as-output-asm-variant.c    |  8 ++++++
 llvm/include/llvm/MC/MCTargetOptions.h        |  2 ++
 llvm/lib/CodeGen/LLVMTargetMachine.cpp        |  4 ++-
 7 files changed, 45 insertions(+), 3 deletions(-)
 create mode 100644 clang/test/CodeGen/inline-asm-output-variant.c
 create mode 100644 clang/test/Misc/cc1as-output-asm-variant.c

diff --git a/clang/include/clang/Basic/CodeGenOptions.def b/clang/include/clang/Basic/CodeGenOptions.def
index b600198998d85b..2893377e5a38be 100644
--- a/clang/include/clang/Basic/CodeGenOptions.def
+++ b/clang/include/clang/Basic/CodeGenOptions.def
@@ -96,6 +96,7 @@ CODEGENOPT(EmulatedTLS       , 1, 0) ///< Set by default or -f[no-]emulated-tls.
 ENUM_CODEGENOPT(EmbedBitcode, EmbedBitcodeKind, 2, Embed_Off)
 /// Inline asm dialect, -masm=(att|intel)
 ENUM_CODEGENOPT(InlineAsmDialect, InlineAsmDialectKind, 1, IAD_ATT)
+CODEGENOPT(OutputAsmVariant, 2, 3) ///< Set the asm variant for output (3: unspecified).
 CODEGENOPT(ForbidGuardVariables , 1, 0) ///< Issue errors if C++ guard variables
                                         ///< are required.
 CODEGENOPT(FunctionSections  , 1, 0) ///< Set when -ffunction-sections is enabled.
diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td
index aa3ae92fb6ae78..2586782f3e3181 100644
--- a/clang/include/clang/Driver/Options.td
+++ b/clang/include/clang/Driver/Options.td
@@ -7209,6 +7209,9 @@ def fuse_ctor_homing: Flag<["-"], "fuse-ctor-homing">,
 def as_secure_log_file : Separate<["-"], "as-secure-log-file">,
   HelpText<"Emit .secure_log_unique directives to this filename.">,
   MarshallingInfoString<CodeGenOpts<"AsSecureLogFile">>;
+def output_asm_variant : Joined<["--"], "output-asm-variant=">,
+  HelpText<"Select the asm variant (integer) to use for output">,
+  MarshallingInfoInt<CodeGenOpts<"OutputAsmVariant">>;
 
 } // let Visibility = [CC1Option, CC1AsOption]
 
@@ -8303,8 +8306,6 @@ def filetype : Separate<["-"], "filetype">,
     HelpText<"Specify the output file type ('asm', 'null', or 'obj')">;
 
 // Transliterate Options
-def output_asm_variant : Separate<["-"], "output-asm-variant">,
-    HelpText<"Select the asm variant index to use for output">;
 def show_encoding : Flag<["-"], "show-encoding">,
     HelpText<"Show instruction encoding information in transliterate mode">;
 def show_inst : Flag<["-"], "show-inst">,
diff --git a/clang/lib/CodeGen/BackendUtil.cpp b/clang/lib/CodeGen/BackendUtil.cpp
index fa49763e312f13..916c92adb89309 100644
--- a/clang/lib/CodeGen/BackendUtil.cpp
+++ b/clang/lib/CodeGen/BackendUtil.cpp
@@ -509,6 +509,8 @@ static bool initTargetOptions(DiagnosticsEngine &Diags,
   Options.MCOptions.X86RelaxRelocations = CodeGenOpts.X86RelaxRelocations;
   Options.MCOptions.CompressDebugSections =
       CodeGenOpts.getCompressDebugSections();
+  if (CodeGenOpts.OutputAsmVariant != 3) // 3 (default): not specified
+    Options.MCOptions.OutputAsmVariant = CodeGenOpts.OutputAsmVariant;
   Options.MCOptions.ABIName = TargetOpts.ABI;
   for (const auto &Entry : HSOpts.UserEntries)
     if (!Entry.IsFramework &&
diff --git a/clang/test/CodeGen/inline-asm-output-variant.c b/clang/test/CodeGen/inline-asm-output-variant.c
new file mode 100644
index 00000000000000..5fc5c1cc09b016
--- /dev/null
+++ b/clang/test/CodeGen/inline-asm-output-variant.c
@@ -0,0 +1,26 @@
+// REQUIRES: x86-registered-target
+/// AT&T input
+// RUN: %clang_cc1 -triple x86_64 -S --output-asm-variant=0 %s -o - | FileCheck --check-prefix=ATT %s
+// RUN: %clang_cc1 -triple x86_64 -S --output-asm-variant=1 %s -o - | FileCheck --check-prefix=INTEL %s
+
+/// Intel input
+// RUN: %clang_cc1 -triple x86_64 -S -D INTEL -mllvm -x86-asm-syntax=intel -inline-asm=intel %s -o - | FileCheck --check-prefix=ATT %s
+// RUN: %clang_cc1 -triple x86_64 -S -D INTEL -mllvm -x86-asm-syntax=intel -inline-asm=intel --output-asm-variant=1 %s -o - | FileCheck --check-prefix=INTEL %s
+
+// ATT: movl $1, %eax
+// ATT: movl $2, %eax
+
+// INTEL: mov eax, 1
+// INTEL: mov eax, 2
+
+#ifdef INTEL
+asm("mov eax, 1");
+void foo() {
+  asm("mov eax, 2");
+}
+#else
+asm("mov $1, %eax");
+void foo() {
+  asm("mov $2, %eax");
+}
+#endif
diff --git a/clang/test/Misc/cc1as-output-asm-variant.c b/clang/test/Misc/cc1as-output-asm-variant.c
new file mode 100644
index 00000000000000..c287c62fc95e4d
--- /dev/null
+++ b/clang/test/Misc/cc1as-output-asm-variant.c
@@ -0,0 +1,8 @@
+// REQUIRES: x86-registered-target
+// RUN: %clang -cc1as -triple x86_64 %s -o - | FileCheck %s --check-prefix=ATT
+// RUN: %clang -cc1as -triple x86_64 %s --output-asm-variant=1 -o - | FileCheck %s --check-prefix=INTEL
+
+// ATT: movl $1, %eax
+// INTEL: mov eax, 1
+
+mov $1, %eax
diff --git a/llvm/include/llvm/MC/MCTargetOptions.h b/llvm/include/llvm/MC/MCTargetOptions.h
index 2e2025c2e7b2c8..7b0d81faf73d2d 100644
--- a/llvm/include/llvm/MC/MCTargetOptions.h
+++ b/llvm/include/llvm/MC/MCTargetOptions.h
@@ -72,6 +72,8 @@ class MCTargetOptions {
 
   bool X86Sse2Avx = false;
 
+  std::optional<unsigned> OutputAsmVariant;
+
   EmitDwarfUnwindType EmitDwarfUnwind;
 
   int DwarfVersion = 0;
diff --git a/llvm/lib/CodeGen/LLVMTargetMachine.cpp b/llvm/lib/CodeGen/LLVMTargetMachine.cpp
index d0dfafeaef561f..71d2e6491bc25d 100644
--- a/llvm/lib/CodeGen/LLVMTargetMachine.cpp
+++ b/llvm/lib/CodeGen/LLVMTargetMachine.cpp
@@ -160,7 +160,9 @@ Expected<std::unique_ptr<MCStreamer>> LLVMTargetMachine::createMCStreamer(
   switch (FileType) {
   case CodeGenFileType::AssemblyFile: {
     MCInstPrinter *InstPrinter = getTarget().createMCInstPrinter(
-        getTargetTriple(), MAI.getAssemblerDialect(), MAI, MII, MRI);
+        getTargetTriple(),
+        Options.MCOptions.OutputAsmVariant.value_or(MAI.getAssemblerDialect()),
+        MAI, MII, MRI);
 
     // Create a code emitter if asked to show the encoding.
     std::unique_ptr<MCCodeEmitter> MCE;



More information about the cfe-commits mailing list