brintos

brintos / llvm-project-archived public Read only

0
0
Text · 5.4 KiB · 72cc79a Raw
176 lines · cpp
1//===- llvm/unittest/CodeGen/X86MCInstLowerTest.cpp2//-------------------------===//3//4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.5// See https://llvm.org/LICENSE.txt for license information.6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception7//8//===----------------------------------------------------------------------===//9 10#include "TestAsmPrinter.h"11#include "llvm/AsmParser/Parser.h"12#include "llvm/CodeGen/AsmPrinter.h"13#include "llvm/CodeGen/MachineModuleInfo.h"14#include "llvm/CodeGen/TargetLowering.h"15#include "llvm/CodeGen/TargetPassConfig.h"16#include "llvm/IR/LegacyPassManager.h"17#include "llvm/IR/MDBuilder.h"18#include "llvm/IR/Module.h"19#include "llvm/MC/MCStreamer.h"20#include "llvm/MC/TargetRegistry.h"21#include "llvm/Support/SourceMgr.h"22#include "llvm/Support/TargetSelect.h"23#include "llvm/Target/TargetLoweringObjectFile.h"24#include "llvm/Target/TargetMachine.h"25#include "gtest/gtest.h"26 27namespace llvm {28 29class X86MCInstLowerTest : public testing::Test {30protected:31  static void SetUpTestCase() {32    InitializeAllTargetMCs();33    InitializeAllTargetInfos();34    InitializeAllTargets();35    InitializeAllAsmPrinters();36  }37 38  // Function to setup codegen pipeline and returns the AsmPrinter.39  AsmPrinter *addPassesToEmitFile(llvm::legacy::PassManagerBase &PM,40                                  llvm::raw_pwrite_stream &Out,41                                  llvm::CodeGenFileType FileType,42                                  llvm::MachineModuleInfoWrapperPass *MMIWP) {43    TargetPassConfig *PassConfig = TM->createPassConfig(PM);44 45    PassConfig->setDisableVerify(true);46    PM.add(PassConfig);47    PM.add(MMIWP);48 49    if (PassConfig->addISelPasses())50      return nullptr;51 52    PassConfig->addMachinePasses();53    PassConfig->setInitialized();54 55    MC.reset(new MCContext(TM->getTargetTriple(), TM->getMCAsmInfo(),56                           TM->getMCRegisterInfo(), TM->getMCSubtargetInfo()));57    MC->setObjectFileInfo(TM->getObjFileLowering());58    TM->getObjFileLowering()->Initialize(*MC, *TM);59    MC->setObjectFileInfo(TM->getObjFileLowering());60 61    // Use a new MCContext for AsmPrinter for testing.62    // AsmPrinter.OutContext will be different from63    // MachineFunction's MCContext in MMIWP.64    Expected<std::unique_ptr<MCStreamer>> MCStreamerOrErr =65        TM->createMCStreamer(Out, nullptr, FileType, *MC);66 67    if (auto Err = MCStreamerOrErr.takeError())68      return nullptr;69 70    AsmPrinter *Printer =71        TM->getTarget().createAsmPrinter(*TM, std::move(*MCStreamerOrErr));72 73    if (!Printer)74      return nullptr;75 76    PM.add(Printer);77 78    return Printer;79  }80 81  void SetUp() override {82    // Module to compile.83    const char *FooStr = R""""(84        @G = external global i3285 86        define i32 @foo() {87          %1 = load i32, i32* @G; load the global variable88          %2 = call i32 @f()89          %3 = mul i32 %1, %290          ret i32 %391        }92 93        declare i32 @f() #094      )"""";95    StringRef AssemblyF(FooStr);96 97    // Get target triple for X86_6498    Triple TargetTriple("x86_64--");99    std::string Error;100    const Target *T = TargetRegistry::lookupTarget("", TargetTriple, Error);101    // Skip the test if target is not built.102    if (!T)103      GTEST_SKIP();104 105    // Get TargetMachine.106    // Use Reloc::Model::PIC_ and CodeModel::Model::Large107    // to get GOT during codegen as MO_ExternalSymbol.108    TargetOptions Options;109    TM = std::unique_ptr<TargetMachine>(T->createTargetMachine(110        TargetTriple, "", "", Options, Reloc::Model::PIC_,111        CodeModel::Model::Large, CodeGenOptLevel::Default));112    if (!TM)113      GTEST_SKIP();114 115    SMDiagnostic SMError;116 117    // Parse the module.118    M = parseAssemblyString(AssemblyF, SMError, Context);119    if (!M)120      report_fatal_error(SMError.getMessage());121    M->setDataLayout(TM->createDataLayout());122 123    // Get llvm::Function from M124    Foo = M->getFunction("foo");125    if (!Foo)126      report_fatal_error("foo?");127 128    // Prepare the MCContext for codegen M.129    // MachineFunction for Foo will have this MCContext.130    MCFoo.reset(new MCContext(TargetTriple, TM->getMCAsmInfo(),131                              TM->getMCRegisterInfo(),132                              TM->getMCSubtargetInfo()));133    MCFoo->setObjectFileInfo(TM->getObjFileLowering());134    TM->getObjFileLowering()->Initialize(*MCFoo, *TM);135    MCFoo->setObjectFileInfo(TM->getObjFileLowering());136  }137 138  LLVMContext Context;139  std::unique_ptr<TargetMachine> TM;140  std::unique_ptr<Module> M;141 142  std::unique_ptr<MCContext> MC;143  std::unique_ptr<MCContext> MCFoo;144 145  Function *Foo;146  std::unique_ptr<MachineFunction> MFFoo;147};148 149TEST_F(X86MCInstLowerTest, moExternalSymbol_MCSYMBOL) {150 151  MachineModuleInfoWrapperPass *MMIWP =152      new MachineModuleInfoWrapperPass(TM.get(), &*MCFoo);153 154  SmallString<1024> Buf;155  llvm::raw_svector_ostream OS(Buf);156  legacy::PassManager PassMgrF;157 158  AsmPrinter *Printer =159      addPassesToEmitFile(PassMgrF, OS, CodeGenFileType::AssemblyFile, MMIWP);160  PassMgrF.run(*M);161 162  // Check GOT MCSymbol is from Printer.OutContext.163  MCSymbol *GOTPrinterPtr =164      Printer->OutContext.lookupSymbol("_GLOBAL_OFFSET_TABLE_");165 166  // Check GOT MCSymbol is NOT from MachineFunction's MCContext.167  MCSymbol *GOTMFCtxPtr =168      MMIWP->getMMI().getMachineFunction(*Foo)->getContext().lookupSymbol(169          "_GLOBAL_OFFSET_TABLE_");170 171  EXPECT_NE(GOTPrinterPtr, nullptr);172  EXPECT_EQ(GOTMFCtxPtr, nullptr);173}174 175} // end namespace llvm176