[asm] Allow labels as operands in intel asm syntax
authorNico Weber <thakis@chromium.org>
Sun, 21 Nov 2021 03:04:26 +0000 (22:04 -0500)
committerNico Weber <thakis@chromium.org>
Mon, 22 Nov 2021 16:49:29 +0000 (11:49 -0500)
This makes a line in llvm/test/CodeGen/X86/asm-block-labels.ll pass
with `asm inteldialect` too.

I don't know if this is something one can hit in practice with inline
asm. The test is from 2007 (4646aa3e337aa) but in 2009 blockaddr was
introduced and e.g. `__asm__ __volatile__("brl %0" :: "X"(&&foo) : "memory");`
compiles to

    call void asm sideeffect "brl $0", "X,..."(i8* blockaddress(@func, %1))

nowadays (thanks to jrtc27 for that example!).

(6c4d255bf3d64 switched clang to blockaddress on an opt-in basis,
e4801f7844bb added docs for it, 31b132c0b781 added IR support.)

I half-heartedly tried to build clang 2.8 locally, but it didn't
just build. And 2.8 didn't have a prebuilt clang binary yet.

The motivation is to make EmitGCCInlineAsmStr() and EmitMSInlineAsmStr()
more alike, and maybe we should delete this code form EmitGCCInlineAsmStr()
instead. But since it's just 3 lines and it's reachable from LLVM IR,
let's do the safer thing for now.

Differential Revision: https://reviews.llvm.org/D114329

llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp
llvm/test/CodeGen/X86/asm-block-labels.ll

index ef1abc4..ea6da76 100644 (file)
@@ -281,6 +281,9 @@ static void EmitMSInlineAsmStr(const char *AsmStr, const MachineInstr *MI,
             MCSymbol *Sym = AP->GetBlockAddressSymbol(BA);
             Sym->print(OS, AP->MAI);
             MMI->getContext().registerInlineAsmLabel(Sym);
+          } else if (MI->getOperand(OpNo).isMBB()) {
+            const MCSymbol *Sym = MI->getOperand(OpNo).getMBB()->getSymbol();
+            Sym->print(OS, AP->MAI);
           } else if (InlineAsm::isMemKind(OpFlags)) {
             Error = AP->PrintAsmMemoryOperand(
                 MI, OpNo, Modifier[0] ? Modifier : nullptr, OS);
index 9352438..44bb751 100644 (file)
@@ -39,3 +39,12 @@ entry:
 return:                ; preds = %"LASM$foo"
        ret void
 }
+
+define void @quux() {
+entry:
+       call void asm sideeffect inteldialect "brl ${0:l}", "X,~{dirflag},~{fpsr},~{flags},~{memory}"( label %"LASM$foo" )
+       br label %"LASM$foo"
+
+"LASM$foo":            ; preds = %entry
+       ret void
+}