diff options
Diffstat (limited to 'lib/CodeGen/TargetLoweringObjectFileImpl.cpp')
| -rw-r--r-- | lib/CodeGen/TargetLoweringObjectFileImpl.cpp | 229 | 
1 files changed, 179 insertions, 50 deletions
diff --git a/lib/CodeGen/TargetLoweringObjectFileImpl.cpp b/lib/CodeGen/TargetLoweringObjectFileImpl.cpp index eb2a28f574a5..34892680aceb 100644 --- a/lib/CodeGen/TargetLoweringObjectFileImpl.cpp +++ b/lib/CodeGen/TargetLoweringObjectFileImpl.cpp @@ -1,4 +1,4 @@ -//===-- llvm/CodeGen/TargetLoweringObjectFileImpl.cpp - Object File Info --===// +//===- llvm/CodeGen/TargetLoweringObjectFileImpl.cpp - Object File Info ---===//  //  //                     The LLVM Compiler Infrastructure  // @@ -12,36 +12,52 @@  //  //===----------------------------------------------------------------------===// -#include "llvm/CodeGen/TargetLoweringObjectFileImpl.h"  #include "llvm/ADT/SmallString.h" +#include "llvm/ADT/SmallVector.h"  #include "llvm/ADT/StringExtras.h" +#include "llvm/ADT/StringRef.h"  #include "llvm/ADT/Triple.h" +#include "llvm/CodeGen/MachineModuleInfo.h"  #include "llvm/CodeGen/MachineModuleInfoImpls.h" +#include "llvm/CodeGen/TargetLoweringObjectFileImpl.h" +#include "llvm/IR/Comdat.h"  #include "llvm/IR/Constants.h"  #include "llvm/IR/DataLayout.h"  #include "llvm/IR/DerivedTypes.h"  #include "llvm/IR/Function.h" +#include "llvm/IR/GlobalAlias.h" +#include "llvm/IR/GlobalObject.h" +#include "llvm/IR/GlobalValue.h"  #include "llvm/IR/GlobalVariable.h"  #include "llvm/IR/Mangler.h" +#include "llvm/IR/Metadata.h"  #include "llvm/IR/Module.h" +#include "llvm/IR/Type.h"  #include "llvm/MC/MCAsmInfo.h"  #include "llvm/MC/MCContext.h"  #include "llvm/MC/MCExpr.h"  #include "llvm/MC/MCSectionCOFF.h"  #include "llvm/MC/MCSectionELF.h"  #include "llvm/MC/MCSectionMachO.h" +#include "llvm/MC/MCSectionWasm.h"  #include "llvm/MC/MCStreamer.h" +#include "llvm/MC/MCSymbol.h"  #include "llvm/MC/MCSymbolELF.h"  #include "llvm/MC/MCValue.h" +#include "llvm/MC/SectionKind.h"  #include "llvm/ProfileData/InstrProf.h" +#include "llvm/Support/Casting.h" +#include "llvm/Support/CodeGen.h"  #include "llvm/Support/COFF.h"  #include "llvm/Support/Dwarf.h"  #include "llvm/Support/ELF.h"  #include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/MachO.h"  #include "llvm/Support/raw_ostream.h" -#include "llvm/Target/TargetLowering.h"  #include "llvm/Target/TargetMachine.h" -#include "llvm/Target/TargetSubtargetInfo.h" +#include <cassert> +#include <string> +  using namespace llvm;  using namespace dwarf; @@ -53,10 +69,10 @@ MCSymbol *TargetLoweringObjectFileELF::getCFIPersonalitySymbol(      const GlobalValue *GV, const TargetMachine &TM,      MachineModuleInfo *MMI) const {    unsigned Encoding = getPersonalityEncoding(); -  if ((Encoding & 0x80) == dwarf::DW_EH_PE_indirect) +  if ((Encoding & 0x80) == DW_EH_PE_indirect)      return getContext().getOrCreateSymbol(StringRef("DW.ref.") +                                            TM.getSymbol(GV)->getName()); -  if ((Encoding & 0x70) == dwarf::DW_EH_PE_absptr) +  if ((Encoding & 0x70) == DW_EH_PE_absptr)      return TM.getSymbol(GV);    report_fatal_error("We do not support this DWARF encoding yet!");  } @@ -86,8 +102,7 @@ void TargetLoweringObjectFileELF::emitPersonalityValue(  const MCExpr *TargetLoweringObjectFileELF::getTTypeGlobalReference(      const GlobalValue *GV, unsigned Encoding, const TargetMachine &TM,      MachineModuleInfo *MMI, MCStreamer &Streamer) const { - -  if (Encoding & dwarf::DW_EH_PE_indirect) { +  if (Encoding & DW_EH_PE_indirect) {      MachineModuleInfoELF &ELFMMI = MMI->getObjFileInfo<MachineModuleInfoELF>();      MCSymbol *SSym = getSymbolWithGlobalValueBase(GV, ".DW.stub", TM); @@ -102,7 +117,7 @@ const MCExpr *TargetLoweringObjectFileELF::getTTypeGlobalReference(      return TargetLoweringObjectFile::        getTTypeReference(MCSymbolRefExpr::create(SSym, getContext()), -                        Encoding & ~dwarf::DW_EH_PE_indirect, Streamer); +                        Encoding & ~DW_EH_PE_indirect, Streamer);    }    return TargetLoweringObjectFile::getTTypeGlobalReference(GV, Encoding, TM, @@ -117,8 +132,9 @@ getELFKindForNamedSection(StringRef Name, SectionKind K) {    // section(".eh_frame") gcc will produce:    //    //   .section   .eh_frame,"a",@progbits -   -  if (Name == getInstrProfCoverageSectionName(false)) + +  if (Name == getInstrProfSectionName(IPSK_covmap, Triple::ELF, +                                      /*AddSegmentInfo=*/false))      return SectionKind::getMetadata();    if (Name.empty() || Name[0] != '.') return K; @@ -149,7 +165,6 @@ getELFKindForNamedSection(StringRef Name, SectionKind K) {    return K;  } -  static unsigned getELFSectionType(StringRef Name, SectionKind K) {    // Use SHT_NOTE for section whose name starts with ".note" to allow    // emitting ELF notes from C variable declaration. @@ -211,6 +226,20 @@ static const Comdat *getELFComdat(const GlobalValue *GV) {    return C;  } +static const MCSymbolELF *getAssociatedSymbol(const GlobalObject *GO, +                                              const TargetMachine &TM) { +  MDNode *MD = GO->getMetadata(LLVMContext::MD_associated); +  if (!MD) +    return nullptr; + +  auto *VM = dyn_cast<ValueAsMetadata>(MD->getOperand(0)); +  if (!VM) +    report_fatal_error("MD_associated operand is not ValueAsMetadata"); + +  GlobalObject *OtherGO = dyn_cast<GlobalObject>(VM->getValue()); +  return OtherGO ? dyn_cast<MCSymbolELF>(TM.getSymbol(OtherGO)) : nullptr; +} +  MCSection *TargetLoweringObjectFileELF::getExplicitSectionGlobal(      const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const {    StringRef SectionName = GO->getSection(); @@ -224,9 +253,23 @@ MCSection *TargetLoweringObjectFileELF::getExplicitSectionGlobal(      Group = C->getName();      Flags |= ELF::SHF_GROUP;    } -  return getContext().getELFSection(SectionName, -                                    getELFSectionType(SectionName, Kind), Flags, -                                    /*EntrySize=*/0, Group); + +  // A section can have at most one associated section. Put each global with +  // MD_associated in a unique section. +  unsigned UniqueID = MCContext::GenericSectionID; +  const MCSymbolELF *AssociatedSymbol = getAssociatedSymbol(GO, TM); +  if (AssociatedSymbol) { +    UniqueID = NextUniqueID++; +    Flags |= ELF::SHF_LINK_ORDER; +  } + +  MCSectionELF *Section = getContext().getELFSection( +      SectionName, getELFSectionType(SectionName, Kind), Flags, +      /*EntrySize=*/0, Group, UniqueID, AssociatedSymbol); +  // Make sure that we did not get some other section with incompatible sh_link. +  // This should not be possible due to UniqueID code above. +  assert(Section->getAssociatedSymbol() == AssociatedSymbol); +  return Section;  }  /// Return the section prefix name used by options FunctionsSections and @@ -248,11 +291,10 @@ static StringRef getSectionPrefixForGlobal(SectionKind Kind) {    return ".data.rel.ro";  } -static MCSectionELF * -selectELFSectionForGlobal(MCContext &Ctx, const GlobalObject *GO, -                          SectionKind Kind, Mangler &Mang, -                          const TargetMachine &TM, bool EmitUniqueSection, -                          unsigned Flags, unsigned *NextUniqueID) { +static MCSectionELF *selectELFSectionForGlobal( +    MCContext &Ctx, const GlobalObject *GO, SectionKind Kind, Mangler &Mang, +    const TargetMachine &TM, bool EmitUniqueSection, unsigned Flags, +    unsigned *NextUniqueID, const MCSymbolELF *AssociatedSymbol) {    unsigned EntrySize = 0;    if (Kind.isMergeableCString()) {      if (Kind.isMergeable2ByteCString()) { @@ -319,7 +361,7 @@ selectELFSectionForGlobal(MCContext &Ctx, const GlobalObject *GO,    if (Kind.isExecuteOnly())      UniqueID = 0;    return Ctx.getELFSection(Name, getELFSectionType(Name, Kind), Flags, -                           EntrySize, Group, UniqueID); +                           EntrySize, Group, UniqueID, AssociatedSymbol);  }  MCSection *TargetLoweringObjectFileELF::SelectSectionForGlobal( @@ -337,8 +379,17 @@ MCSection *TargetLoweringObjectFileELF::SelectSectionForGlobal(    }    EmitUniqueSection |= GO->hasComdat(); -  return selectELFSectionForGlobal(getContext(), GO, Kind, getMangler(), TM, -                                   EmitUniqueSection, Flags, &NextUniqueID); +  const MCSymbolELF *AssociatedSymbol = getAssociatedSymbol(GO, TM); +  if (AssociatedSymbol) { +    EmitUniqueSection = true; +    Flags |= ELF::SHF_LINK_ORDER; +  } + +  MCSectionELF *Section = selectELFSectionForGlobal( +      getContext(), GO, Kind, getMangler(), TM, EmitUniqueSection, Flags, +      &NextUniqueID, AssociatedSymbol); +  assert(Section->getAssociatedSymbol() == AssociatedSymbol); +  return Section;  }  MCSection *TargetLoweringObjectFileELF::getSectionForJumpTable( @@ -351,8 +402,9 @@ MCSection *TargetLoweringObjectFileELF::getSectionForJumpTable(      return ReadOnlySection;    return selectELFSectionForGlobal(getContext(), &F, SectionKind::getReadOnly(), -                                   getMangler(), TM, EmitUniqueSection, ELF::SHF_ALLOC, -                                   &NextUniqueID); +                                   getMangler(), TM, EmitUniqueSection, +                                   ELF::SHF_ALLOC, &NextUniqueID, +                                   /* AssociatedSymbol */ nullptr);  }  bool TargetLoweringObjectFileELF::shouldPutJumpTableInFunctionSection( @@ -723,7 +775,7 @@ const MCExpr *TargetLoweringObjectFileMachO::getTTypeGlobalReference(      return TargetLoweringObjectFile::        getTTypeReference(MCSymbolRefExpr::create(SSym, getContext()), -                        Encoding & ~dwarf::DW_EH_PE_indirect, Streamer); +                        Encoding & ~DW_EH_PE_indirect, Streamer);    }    return TargetLoweringObjectFile::getTTypeGlobalReference(GV, Encoding, TM, @@ -1122,33 +1174,110 @@ MCSection *TargetLoweringObjectFileCOFF::getStaticDtorSection(  void TargetLoweringObjectFileCOFF::emitLinkerFlagsForGlobal(      raw_ostream &OS, const GlobalValue *GV) const { -  if (!GV->hasDLLExportStorageClass() || GV->isDeclaration()) -    return; +  emitLinkerFlagsForGlobalCOFF(OS, GV, getTargetTriple(), getMangler()); +} -  const Triple &TT = getTargetTriple(); +//===----------------------------------------------------------------------===// +//                                  Wasm +//===----------------------------------------------------------------------===// -  if (TT.isKnownWindowsMSVCEnvironment()) -    OS << " /EXPORT:"; -  else -    OS << " -export:"; - -  if (TT.isWindowsGNUEnvironment() || TT.isWindowsCygwinEnvironment()) { -    std::string Flag; -    raw_string_ostream FlagOS(Flag); -    getMangler().getNameWithPrefix(FlagOS, GV, false); -    FlagOS.flush(); -    if (Flag[0] == GV->getParent()->getDataLayout().getGlobalPrefix()) -      OS << Flag.substr(1); -    else -      OS << Flag; -  } else { -    getMangler().getNameWithPrefix(OS, GV, false); +static const Comdat *getWasmComdat(const GlobalValue *GV) { +  const Comdat *C = GV->getComdat(); +  if (!C) +    return nullptr; + +  if (C->getSelectionKind() != Comdat::Any) +    report_fatal_error("Wasm COMDATs only support SelectionKind::Any, '" + +                       C->getName() + "' cannot be lowered."); + +  return C; +} + +MCSection *TargetLoweringObjectFileWasm::getExplicitSectionGlobal( +    const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const { +  llvm_unreachable("getExplicitSectionGlobal not yet implemented"); +  return nullptr; +} + +static MCSectionWasm * +selectWasmSectionForGlobal(MCContext &Ctx, const GlobalObject *GO, +                           SectionKind Kind, Mangler &Mang, +                           const TargetMachine &TM, bool EmitUniqueSection, +                           unsigned Flags, unsigned *NextUniqueID) { +  StringRef Group = ""; +  if (getWasmComdat(GO)) +    llvm_unreachable("comdat not yet supported for wasm"); + +  bool UniqueSectionNames = TM.getUniqueSectionNames(); +  SmallString<128> Name = getSectionPrefixForGlobal(Kind); + +  if (const auto *F = dyn_cast<Function>(GO)) { +    const auto &OptionalPrefix = F->getSectionPrefix(); +    if (OptionalPrefix) +      Name += *OptionalPrefix;    } -  if (!GV->getValueType()->isFunctionTy()) { -    if (TT.isKnownWindowsMSVCEnvironment()) -      OS << ",DATA"; -    else -      OS << ",data"; +  if (EmitUniqueSection && UniqueSectionNames) { +    Name.push_back('.'); +    TM.getNameWithPrefix(Name, GO, Mang, true); +  } +  unsigned UniqueID = MCContext::GenericSectionID; +  if (EmitUniqueSection && !UniqueSectionNames) { +    UniqueID = *NextUniqueID; +    (*NextUniqueID)++;    } +  return Ctx.getWasmSection(Name, /*Type=*/0, Flags, +                            Group, UniqueID); +} + +MCSection *TargetLoweringObjectFileWasm::SelectSectionForGlobal( +    const GlobalObject *GO, SectionKind Kind, const TargetMachine &TM) const { + +  if (Kind.isCommon()) +    report_fatal_error("mergable sections not supported yet on wasm"); + +  // If we have -ffunction-section or -fdata-section then we should emit the +  // global value to a uniqued section specifically for it. +  bool EmitUniqueSection = false; +  if (Kind.isText()) +    EmitUniqueSection = TM.getFunctionSections(); +  else +    EmitUniqueSection = TM.getDataSections(); +  EmitUniqueSection |= GO->hasComdat(); + +  return selectWasmSectionForGlobal(getContext(), GO, Kind, getMangler(), TM, +                                    EmitUniqueSection, /*Flags=*/0, +                                    &NextUniqueID); +} + +bool TargetLoweringObjectFileWasm::shouldPutJumpTableInFunctionSection( +    bool UsesLabelDifference, const Function &F) const { +  // We can always create relative relocations, so use another section +  // that can be marked non-executable. +  return false; +} + +const MCExpr *TargetLoweringObjectFileWasm::lowerRelativeReference( +    const GlobalValue *LHS, const GlobalValue *RHS, +    const TargetMachine &TM) const { +  // We may only use a PLT-relative relocation to refer to unnamed_addr +  // functions. +  if (!LHS->hasGlobalUnnamedAddr() || !LHS->getValueType()->isFunctionTy()) +    return nullptr; + +  // Basic sanity checks. +  if (LHS->getType()->getPointerAddressSpace() != 0 || +      RHS->getType()->getPointerAddressSpace() != 0 || LHS->isThreadLocal() || +      RHS->isThreadLocal()) +    return nullptr; + +  return MCBinaryExpr::createSub( +      MCSymbolRefExpr::create(TM.getSymbol(LHS), MCSymbolRefExpr::VK_None, +                              getContext()), +      MCSymbolRefExpr::create(TM.getSymbol(RHS), getContext()), getContext()); +} + +void +TargetLoweringObjectFileWasm::InitializeWasm() { +  // TODO: Initialize StaticCtorSection and StaticDtorSection.  }  | 
