Author: Nikita Popov Date: 2024-05-16T09:56:07+09:00 New Revision: fa750f09be6966de7423ddce1af7d1eaf817182c
URL: https://github.com/llvm/llvm-project/commit/fa750f09be6966de7423ddce1af7d1eaf817182c DIFF: https://github.com/llvm/llvm-project/commit/fa750f09be6966de7423ddce1af7d1eaf817182c.diff LOG: Revert "[MC] Remove UseAssemblerInfoForParsing" This reverts commit 03c53c69a367008da689f0d2940e2197eb4a955c. This causes very large compile-time regressions in some cases, e.g. sqlite3 at O0 regresses by 5%. Added: Modified: clang/tools/driver/cc1as_main.cpp llvm/include/llvm/MC/MCStreamer.h llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp llvm/lib/MC/MCObjectStreamer.cpp llvm/lib/MC/MCStreamer.cpp llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp llvm/test/MC/AsmParser/assembler-expressions-inlineasm.ll llvm/tools/llvm-mc/llvm-mc.cpp llvm/tools/llvm-ml/llvm-ml.cpp Removed: ################################################################################ diff --git a/clang/tools/driver/cc1as_main.cpp b/clang/tools/driver/cc1as_main.cpp index 4eb753a7297a9..86afe22fac24c 100644 --- a/clang/tools/driver/cc1as_main.cpp +++ b/clang/tools/driver/cc1as_main.cpp @@ -576,6 +576,9 @@ static bool ExecuteAssemblerImpl(AssemblerInvocation &Opts, Str.get()->emitZeros(1); } + // Assembly to object compilation should leverage assembly info. + Str->setUseAssemblerInfoForParsing(true); + bool Failed = false; std::unique_ptr<MCAsmParser> Parser( diff --git a/llvm/include/llvm/MC/MCStreamer.h b/llvm/include/llvm/MC/MCStreamer.h index 50986e6bde886..69867620e1bf8 100644 --- a/llvm/include/llvm/MC/MCStreamer.h +++ b/llvm/include/llvm/MC/MCStreamer.h @@ -245,6 +245,8 @@ class MCStreamer { /// requires. unsigned NextWinCFIID = 0; + bool UseAssemblerInfoForParsing; + /// Is the assembler allowed to insert padding automatically? For /// correctness reasons, we sometimes need to ensure instructions aren't /// separated in unexpected ways. At the moment, this feature is only @@ -294,10 +296,11 @@ class MCStreamer { MCContext &getContext() const { return Context; } - // MCObjectStreamer has an MCAssembler and allows more expression folding at - // parse time. virtual MCAssembler *getAssemblerPtr() { return nullptr; } + void setUseAssemblerInfoForParsing(bool v) { UseAssemblerInfoForParsing = v; } + bool getUseAssemblerInfoForParsing() { return UseAssemblerInfoForParsing; } + MCTargetStreamer *getTargetStreamer() { return TargetStreamer.get(); } diff --git a/llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp b/llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp index 08e3c208ba4d3..d0ef3e5a19391 100644 --- a/llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp +++ b/llvm/lib/CodeGen/AsmPrinter/AsmPrinterInlineAsm.cpp @@ -102,6 +102,9 @@ void AsmPrinter::emitInlineAsm(StringRef Str, const MCSubtargetInfo &STI, std::unique_ptr<MCAsmParser> Parser( createMCAsmParser(SrcMgr, OutContext, *OutStreamer, *MAI, BufNum)); + // Do not use assembler-level information for parsing inline assembly. + OutStreamer->setUseAssemblerInfoForParsing(false); + // We create a new MCInstrInfo here since we might be at the module level // and not have a MachineFunction to initialize the TargetInstrInfo from and // we only need MCInstrInfo for asm parsing. We create one unconditionally diff --git a/llvm/lib/MC/MCObjectStreamer.cpp b/llvm/lib/MC/MCObjectStreamer.cpp index a9003a164b306..d2da5d0d3f90f 100644 --- a/llvm/lib/MC/MCObjectStreamer.cpp +++ b/llvm/lib/MC/MCObjectStreamer.cpp @@ -40,7 +40,14 @@ MCObjectStreamer::MCObjectStreamer(MCContext &Context, MCObjectStreamer::~MCObjectStreamer() = default; -MCAssembler *MCObjectStreamer::getAssemblerPtr() { return Assembler.get(); } +// AssemblerPtr is used for evaluation of expressions and causes +// diff erence between asm and object outputs. Return nullptr to in +// inline asm mode to limit divergence to assembly inputs. +MCAssembler *MCObjectStreamer::getAssemblerPtr() { + if (getUseAssemblerInfoForParsing()) + return Assembler.get(); + return nullptr; +} void MCObjectStreamer::addPendingLabel(MCSymbol* S) { MCSection *CurSection = getCurrentSectionOnly(); diff --git a/llvm/lib/MC/MCStreamer.cpp b/llvm/lib/MC/MCStreamer.cpp index 199d865ea3496..176d55aa890be 100644 --- a/llvm/lib/MC/MCStreamer.cpp +++ b/llvm/lib/MC/MCStreamer.cpp @@ -93,7 +93,7 @@ void MCTargetStreamer::emitAssignment(MCSymbol *Symbol, const MCExpr *Value) {} MCStreamer::MCStreamer(MCContext &Ctx) : Context(Ctx), CurrentWinFrameInfo(nullptr), - CurrentProcWinFrameInfoStartIndex(0) { + CurrentProcWinFrameInfoStartIndex(0), UseAssemblerInfoForParsing(false) { SectionStack.push_back(std::pair<MCSectionSubPair, MCSectionSubPair>()); } diff --git a/llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp b/llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp index bd48a5f80c828..b7388ed9e85a8 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp +++ b/llvm/lib/Target/AMDGPU/AMDGPUAsmPrinter.cpp @@ -517,9 +517,12 @@ bool AMDGPUAsmPrinter::runOnMachineFunction(MachineFunction &MF) { DumpCodeInstEmitter = nullptr; if (STM.dumpCode()) { - // For -dumpcode, get the assembler out of the streamer. This only works - // with -filetype=obj. + // For -dumpcode, get the assembler out of the streamer, even if it does + // not really want to let us have it. This only works with -filetype=obj. + bool SaveFlag = OutStreamer->getUseAssemblerInfoForParsing(); + OutStreamer->setUseAssemblerInfoForParsing(true); MCAssembler *Assembler = OutStreamer->getAssemblerPtr(); + OutStreamer->setUseAssemblerInfoForParsing(SaveFlag); if (Assembler) DumpCodeInstEmitter = Assembler->getEmitterPtr(); } diff --git a/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp b/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp index ad01580860448..2ebe5bdc47715 100644 --- a/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp +++ b/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp @@ -114,9 +114,12 @@ void SPIRVAsmPrinter::emitEndOfAsmFile(Module &M) { // Bound is an approximation that accounts for the maximum used register // number and number of generated OpLabels unsigned Bound = 2 * (ST->getBound() + 1) + NLabels; + bool FlagToRestore = OutStreamer->getUseAssemblerInfoForParsing(); + OutStreamer->setUseAssemblerInfoForParsing(true); if (MCAssembler *Asm = OutStreamer->getAssemblerPtr()) Asm->setBuildVersion(static_cast<MachO::PlatformType>(0), Major, Minor, Bound, VersionTuple(Major, Minor, 0, Bound)); + OutStreamer->setUseAssemblerInfoForParsing(FlagToRestore); } void SPIRVAsmPrinter::emitFunctionHeader() { diff --git a/llvm/test/MC/AsmParser/assembler-expressions-inlineasm.ll b/llvm/test/MC/AsmParser/assembler-expressions-inlineasm.ll index 9d9a38f5b5a54..35f110f37e2fb 100644 --- a/llvm/test/MC/AsmParser/assembler-expressions-inlineasm.ll +++ b/llvm/test/MC/AsmParser/assembler-expressions-inlineasm.ll @@ -1,16 +1,12 @@ -; RUN: not llc -mtriple=x86_64 %s -o /dev/null 2>&1 | FileCheck %s -; RUN: llc -mtriple=x86_64 -no-integrated-as < %s | FileCheck %s --check-prefix=GAS -; RUN: llc -mtriple=x86_64 -filetype=obj %s -o - | llvm-objdump -d - | FileCheck %s --check-prefix=DISASM +; RUN: not llc -mtriple x86_64-unknown-linux-gnu -o %t.s -filetype=asm %s 2>&1 | FileCheck %s +; RUN: not llc -mtriple x86_64-unknown-linux-gnu -o %t.o -filetype=obj %s 2>&1 | FileCheck %s -; GAS: nop; .if . - foo==1; nop;.endif +; Assembler-aware expression evaluation should be disabled in inline +; assembly to prevent diff erences in behavior between object and +; assembly output. -; CHECK: <inline asm>:1:17: error: expected absolute expression -; DISASM: <main>: -; DISASM-NEXT: nop -; DISASM-NEXT: nop -; DISASM-NEXT: xorl %eax, %eax -; DISASM-NEXT: retq +; CHECK: <inline asm>:1:17: error: expected absolute expression define i32 @main() local_unnamed_addr { tail call void asm sideeffect "foo: nop; .if . - foo==1; nop;.endif", "~{dirflag},~{fpsr},~{flags}"() diff --git a/llvm/tools/llvm-mc/llvm-mc.cpp b/llvm/tools/llvm-mc/llvm-mc.cpp index 506e4f22ef8f5..807071a7b9a16 100644 --- a/llvm/tools/llvm-mc/llvm-mc.cpp +++ b/llvm/tools/llvm-mc/llvm-mc.cpp @@ -569,6 +569,9 @@ int main(int argc, char **argv) { Str->initSections(true, *STI); } + // Use Assembler information for parsing. + Str->setUseAssemblerInfoForParsing(true); + int Res = 1; bool disassemble = false; switch (Action) { diff --git a/llvm/tools/llvm-ml/llvm-ml.cpp b/llvm/tools/llvm-ml/llvm-ml.cpp index f1f39af059aa4..1cac576f54e77 100644 --- a/llvm/tools/llvm-ml/llvm-ml.cpp +++ b/llvm/tools/llvm-ml/llvm-ml.cpp @@ -428,6 +428,9 @@ int llvm_ml_main(int Argc, char **Argv, const llvm::ToolContext &) { Str->emitAssignment(Feat00Sym, MCConstantExpr::create(Feat00Flags, Ctx)); } + // Use Assembler information for parsing. + Str->setUseAssemblerInfoForParsing(true); + int Res = 1; if (InputArgs.hasArg(OPT_as_lex)) { // -as-lex; Lex only, and output a stream of tokens _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits