diff options
20 files changed, 470 insertions, 297 deletions
diff --git a/include/llvm/CodeGen/MachineModuleInfo.h b/include/llvm/CodeGen/MachineModuleInfo.h index 556ba7f..8eeac9f 100644 --- a/include/llvm/CodeGen/MachineModuleInfo.h +++ b/include/llvm/CodeGen/MachineModuleInfo.h @@ -50,6 +50,7 @@ namespace llvm { //===----------------------------------------------------------------------===// // Forward declarations. class Constant; +class MCSymbol; class MDNode; class GlobalVariable; class MachineBasicBlock; @@ -66,6 +67,12 @@ class StructType; class MachineModuleInfoImpl { public: virtual ~MachineModuleInfoImpl(); + + typedef std::vector<std::pair<MCSymbol*, MCSymbol*> > + SymbolListTy; +protected: + static SymbolListTy + GetSortedStubs(const DenseMap<MCSymbol*, MCSymbol*> &Map); }; diff --git a/include/llvm/CodeGen/MachineModuleInfoImpls.h b/include/llvm/CodeGen/MachineModuleInfoImpls.h index 6679990..89b8207 100644 --- a/include/llvm/CodeGen/MachineModuleInfoImpls.h +++ b/include/llvm/CodeGen/MachineModuleInfoImpls.h @@ -19,7 +19,7 @@ namespace llvm { class MCSymbol; - + /// MachineModuleInfoMachO - This is a MachineModuleInfoImpl implementation /// for MachO targets. class MachineModuleInfoMachO : public MachineModuleInfoImpl { @@ -54,10 +54,8 @@ namespace llvm { assert(Sym && "Key cannot be null"); return HiddenGVStubs[Sym]; } - + /// Accessor methods to return the set of stubs in sorted order. - typedef std::vector<std::pair<MCSymbol*, MCSymbol*> > SymbolListTy; - SymbolListTy GetFnStubList() const { return GetSortedStubs(FnStubs); } @@ -67,12 +65,31 @@ namespace llvm { SymbolListTy GetHiddenGVStubList() const { return GetSortedStubs(HiddenGVStubs); } - - private: - static SymbolListTy - GetSortedStubs(const DenseMap<MCSymbol*, MCSymbol*> &Map); }; - + + /// MachineModuleInfoELF - This is a MachineModuleInfoImpl implementation + /// for ELF targets. + class MachineModuleInfoELF : public MachineModuleInfoImpl { + /// GVStubs - These stubs are used to materialize global addresses in PIC + /// mode. + DenseMap<MCSymbol*, MCSymbol*> GVStubs; + + virtual void Anchor(); // Out of line virtual method. + public: + MachineModuleInfoELF(const MachineModuleInfo &) {} + + MCSymbol *&getGVStubEntry(MCSymbol *Sym) { + assert(Sym && "Key cannot be null"); + return GVStubs[Sym]; + } + + /// Accessor methods to return the set of stubs in sorted order. + + SymbolListTy GetGVStubList() const { + return GetSortedStubs(GVStubs); + } + }; + } // end namespace llvm #endif diff --git a/include/llvm/Support/Dwarf.h b/include/llvm/Support/Dwarf.h index bfccc52..5f591d4 100644 --- a/include/llvm/Support/Dwarf.h +++ b/include/llvm/Support/Dwarf.h @@ -580,7 +580,6 @@ const char *MacinfoString(unsigned Encoding); /// CallFrameString - Return the string for the specified call frame instruction /// encodings. const char *CallFrameString(unsigned Encoding); - } // End of namespace dwarf } // End of namespace llvm diff --git a/include/llvm/Target/TargetLoweringObjectFile.h b/include/llvm/Target/TargetLoweringObjectFile.h index d3e5cf2..a2f8c75 100644 --- a/include/llvm/Target/TargetLoweringObjectFile.h +++ b/include/llvm/Target/TargetLoweringObjectFile.h @@ -25,6 +25,7 @@ namespace llvm { class MCExpr; class MCSection; class MCSectionMachO; + class MCSymbol; class MCContext; class GlobalValue; class TargetMachine; @@ -175,23 +176,22 @@ public: return 0; } - /// getSymbolForDwarfGlobalReference - Return an MCExpr to use for a - /// pc-relative reference to the specified global variable from exception - /// handling information. In addition to the symbol, this returns - /// by-reference: - /// - /// IsIndirect - True if the returned symbol is actually a stub that contains - /// the address of the symbol, false if the symbol is the global itself. - /// - /// IsPCRel - True if the symbol reference is already pc-relative, false if - /// the caller needs to subtract off the address of the reference from the - /// symbol. + /// getSymbolForDwarfGlobalReference - Return an MCExpr to use for a reference + /// to the specified global variable from exception handling information. /// virtual const MCExpr * getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const; - + MachineModuleInfo *MMI, unsigned Encoding) const; + + virtual const MCExpr * + getSymbolForDwarfReference(const MCSymbol *Sym, MachineModuleInfo *MMI, + unsigned Encoding) const; + + virtual unsigned getPersonalityEncoding() const; + virtual unsigned getLSDAEncoding() const; + virtual unsigned getFDEEncoding() const; + virtual unsigned getTTypeEncoding() const; + protected: virtual const MCSection * SelectSectionForGlobal(const GlobalValue *GV, SectionKind Kind, @@ -231,7 +231,9 @@ public: ~TargetLoweringObjectFileELF(); virtual void Initialize(MCContext &Ctx, const TargetMachine &TM); - + + const MCSection *getDataRelSection() const { return DataRelSection; } + /// getSectionForConstant - Given a constant with the SectionKind, return a /// section that it should be placed in. virtual const MCSection *getSectionForConstant(SectionKind Kind) const; @@ -244,6 +246,13 @@ public: virtual const MCSection * SelectSectionForGlobal(const GlobalValue *GV, SectionKind Kind, Mangler *Mang, const TargetMachine &TM) const; + + /// getSymbolForDwarfGlobalReference - Return an MCExpr to use for a reference + /// to the specified global variable from exception handling information. + /// + virtual const MCExpr * + getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, + MachineModuleInfo *MMI, unsigned Encoding) const; }; @@ -330,8 +339,7 @@ public: /// defaults to returning a stub reference. virtual const MCExpr * getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const; + MachineModuleInfo *MMI, unsigned Encoding) const; }; diff --git a/include/llvm/Target/TargetMachine.h b/include/llvm/Target/TargetMachine.h index 63e28ac..c496e11 100644 --- a/include/llvm/Target/TargetMachine.h +++ b/include/llvm/Target/TargetMachine.h @@ -68,15 +68,6 @@ namespace CodeGenOpt { }; } -// Specify if we should encode the LSDA pointer in the FDE as 4- or 8-bytes. -namespace DwarfLSDAEncoding { - enum Encoding { - Default, - FourByte, - EightByte - }; -} - //===----------------------------------------------------------------------===// /// /// TargetMachine - Primary interface to the complete machine description for @@ -179,20 +170,6 @@ public: /// is false. static void setAsmVerbosityDefault(bool); - /// getLSDAEncoding - Returns the LSDA pointer encoding. The choices are - /// 4-byte, 8-byte, and target default. The CIE is hard-coded to indicate that - /// the LSDA pointer in the FDE section is an "sdata4", and should be encoded - /// as a 4-byte pointer by default. However, some systems may require a - /// different size due to bugs or other conditions. We will default to a - /// 4-byte encoding unless the system tells us otherwise. - /// - /// FIXME: This call-back isn't good! We should be using the correct encoding - /// regardless of the system. However, there are some systems which have bugs - /// that prevent this from occuring. - virtual DwarfLSDAEncoding::Encoding getLSDAEncoding() const { - return DwarfLSDAEncoding::Default; - } - /// CodeGenFileType - These enums are meant to be passed into /// addPassesToEmitFile to indicate what type of file to emit, and returned by /// it to indicate what type of file could actually be made. diff --git a/lib/CodeGen/AsmPrinter/DwarfException.cpp b/lib/CodeGen/AsmPrinter/DwarfException.cpp index 22b1b1c..e3f06a3 100644 --- a/lib/CodeGen/AsmPrinter/DwarfException.cpp +++ b/lib/CodeGen/AsmPrinter/DwarfException.cpp @@ -50,26 +50,6 @@ DwarfException::~DwarfException() { delete ExceptionTimer; } -/// SizeOfEncodedValue - Return the size of the encoding in bytes. -unsigned DwarfException::SizeOfEncodedValue(unsigned Encoding) { - if (Encoding == dwarf::DW_EH_PE_omit) - return 0; - - switch (Encoding & 0x07) { - case dwarf::DW_EH_PE_absptr: - return TD->getPointerSize(); - case dwarf::DW_EH_PE_udata2: - return 2; - case dwarf::DW_EH_PE_udata4: - return 4; - case dwarf::DW_EH_PE_udata8: - return 8; - } - - assert(0 && "Invalid encoded value."); - return 0; -} - /// CreateLabelDiff - Emit a label and subtract it from the expression we /// already have. This is equivalent to emitting "foo - .", but we have to emit /// the label for "." directly. @@ -100,7 +80,7 @@ void DwarfException::EmitCIE(const Function *PersonalityFn, unsigned Index) { TD->getPointerSize() : -TD->getPointerSize(); const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); - + // Begin eh frame section. Asm->OutStreamer.SwitchSection(TLOF.getEHFrameSection()); @@ -128,30 +108,16 @@ void DwarfException::EmitCIE(const Function *PersonalityFn, unsigned Index) { // The personality presence indicates that language specific information will // show up in the eh frame. Find out how we are supposed to lower the // personality function reference: - const MCExpr *PersonalityRef = 0; - bool IsPersonalityIndirect = false, IsPersonalityPCRel = false; - if (PersonalityFn) { - // FIXME: HANDLE STATIC CODEGEN MODEL HERE. - - // In non-static mode, ask the object file how to represent this reference. - PersonalityRef = - TLOF.getSymbolForDwarfGlobalReference(PersonalityFn, Asm->Mang, - Asm->MMI, - IsPersonalityIndirect, - IsPersonalityPCRel); - } - - unsigned PerEncoding = dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4; - if (IsPersonalityIndirect) - PerEncoding |= dwarf::DW_EH_PE_indirect; - unsigned LSDAEncoding = dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4; - unsigned FDEEncoding = dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4; + + unsigned LSDAEncoding = TLOF.getLSDAEncoding(); + unsigned FDEEncoding = TLOF.getFDEEncoding(); + unsigned PerEncoding = TLOF.getPersonalityEncoding(); char Augmentation[6] = { 0 }; unsigned AugmentationSize = 0; char *APtr = Augmentation + 1; - if (PersonalityRef) { + if (PersonalityFn) { // There is a personality function. *APtr++ = 'P'; AugmentationSize += 1 + SizeOfEncodedValue(PerEncoding); @@ -182,19 +148,16 @@ void DwarfException::EmitCIE(const Function *PersonalityFn, unsigned Index) { EOL("CIE Return Address Column"); EmitULEB128(AugmentationSize, "Augmentation Size"); - EmitEncodingByte(PerEncoding, "Personality"); // If there is a personality, we need to indicate the function's location. - if (PersonalityRef) { - if (!IsPersonalityPCRel) - PersonalityRef = CreateLabelDiff(PersonalityRef, "personalityref_addr", - Index); - - O << MAI->getData32bitsDirective() << *PersonalityRef; + if (PersonalityFn) { + EmitEncodingByte(PerEncoding, "Personality"); + EmitReference(PersonalityFn, PerEncoding); EOL("Personality"); - - EmitEncodingByte(LSDAEncoding, "LSDA"); - EmitEncodingByte(FDEEncoding, "FDE"); + if (UsesLSDA[Index]) + EmitEncodingByte(LSDAEncoding, "LSDA"); + if (FDEEncoding != dwarf::DW_EH_PE_absptr) + EmitEncodingByte(FDEEncoding, "FDE"); } // Indicate locations of general callee saved registers in frame. @@ -216,8 +179,12 @@ void DwarfException::EmitFDE(const FunctionEHFrameInfo &EHFrameInfo) { "Should not emit 'available externally' functions at all"); const Function *TheFunc = EHFrameInfo.function; + const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); - Asm->OutStreamer.SwitchSection(Asm->getObjFileLowering().getEHFrameSection()); + unsigned LSDAEncoding = TLOF.getLSDAEncoding(); + unsigned FDEEncoding = TLOF.getFDEEncoding(); + + Asm->OutStreamer.SwitchSection(TLOF.getEHFrameSection()); // Externally visible entry into the functions eh frame info. If the // corresponding function is static, this should not be externally visible. @@ -255,7 +222,8 @@ void DwarfException::EmitFDE(const FunctionEHFrameInfo &EHFrameInfo) { // EH frame header. EmitDifference("eh_frame_end", EHFrameInfo.Number, - "eh_frame_begin", EHFrameInfo.Number, true); + "eh_frame_begin", EHFrameInfo.Number, + true); EOL("Length of Frame Information Entry"); EmitLabel("eh_frame_begin", EHFrameInfo.Number); @@ -266,33 +234,23 @@ void DwarfException::EmitFDE(const FunctionEHFrameInfo &EHFrameInfo) { EOL("FDE CIE offset"); - EmitReference("eh_func_begin", EHFrameInfo.Number, true, true); + EmitReference("eh_func_begin", EHFrameInfo.Number, FDEEncoding); EOL("FDE initial location"); EmitDifference("eh_func_end", EHFrameInfo.Number, - "eh_func_begin", EHFrameInfo.Number, true); + "eh_func_begin", EHFrameInfo.Number, + SizeOfEncodedValue(FDEEncoding) == 4); EOL("FDE address range"); // If there is a personality and landing pads then point to the language // specific data area in the exception table. if (MMI->getPersonalities()[0] != NULL) { + unsigned Size = SizeOfEncodedValue(LSDAEncoding); - if (Asm->TM.getLSDAEncoding() != DwarfLSDAEncoding::EightByte) { - EmitULEB128(4, "Augmentation size"); - - if (EHFrameInfo.hasLandingPads) - EmitReference("exception", EHFrameInfo.Number, true, true); - else - Asm->OutStreamer.EmitIntValue(0, 4/*size*/, 0/*addrspace*/); - } else { - EmitULEB128(TD->getPointerSize(), "Augmentation size"); - - if (EHFrameInfo.hasLandingPads) { - EmitReference("exception", EHFrameInfo.Number, true, false); - } else { - Asm->OutStreamer.EmitIntValue(0, TD->getPointerSize(), - 0/*addrspace*/); - } - } + EmitULEB128(Size, "Augmentation size"); + if (EHFrameInfo.hasLandingPads) + EmitReference("exception", EHFrameInfo.Number, LSDAEncoding); + else + Asm->OutStreamer.EmitIntValue(0, Size/*size*/, 0/*addrspace*/); EOL("Language Specific Data Area"); } else { @@ -694,13 +652,13 @@ void DwarfException::EmitExceptionTable() { // Type infos. const MCSection *LSDASection = Asm->getObjFileLowering().getLSDASection(); - unsigned TTypeFormat; + unsigned TTypeEncoding; unsigned TypeFormatSize; if (!HaveTTData) { // For SjLj exceptions, if there is no TypeInfo, then we just explicitly say // that we're omitting that bit. - TTypeFormat = dwarf::DW_EH_PE_omit; + TTypeEncoding = dwarf::DW_EH_PE_omit; TypeFormatSize = SizeOfEncodedValue(dwarf::DW_EH_PE_absptr); } else { // Okay, we have actual filters or typeinfos to emit. As such, we need to @@ -730,14 +688,8 @@ void DwarfException::EmitExceptionTable() { // somewhere. This predicate should be moved to a shared location that is // in target-independent code. // - if (LSDASection->getKind().isWriteable() || - Asm->TM.getRelocationModel() == Reloc::Static) - TTypeFormat = dwarf::DW_EH_PE_absptr; - else - TTypeFormat = dwarf::DW_EH_PE_indirect | dwarf::DW_EH_PE_pcrel | - dwarf::DW_EH_PE_sdata4; - - TypeFormatSize = SizeOfEncodedValue(TTypeFormat); + TTypeEncoding = Asm->getObjFileLowering().getTTypeEncoding(); + TypeFormatSize = SizeOfEncodedValue(TTypeEncoding); } // Begin the exception table. @@ -788,7 +740,7 @@ void DwarfException::EmitExceptionTable() { // Emit the header. EmitEncodingByte(dwarf::DW_EH_PE_omit, "@LPStart"); - EmitEncodingByte(TTypeFormat, "@TType"); + EmitEncodingByte(TTypeEncoding, "@TType"); if (HaveTTData) EmitULEB128(TyOffset, "@TType base offset"); @@ -911,12 +863,12 @@ void DwarfException::EmitExceptionTable() { for (std::vector<GlobalVariable *>::const_reverse_iterator I = TypeInfos.rbegin(), E = TypeInfos.rend(); I != E; ++I) { const GlobalVariable *GV = *I; - PrintRelDirective(); if (GV) { - O << *Asm->GetGlobalValueSymbol(GV); + EmitReference(GV, TTypeEncoding); EOL("TypeInfo"); } else { + PrintRelDirective(); O << "0x0"; EOL(""); } diff --git a/lib/CodeGen/AsmPrinter/DwarfException.h b/lib/CodeGen/AsmPrinter/DwarfException.h index 6177d26..3db1a00 100644 --- a/lib/CodeGen/AsmPrinter/DwarfException.h +++ b/lib/CodeGen/AsmPrinter/DwarfException.h @@ -76,9 +76,6 @@ class DwarfException : public DwarfPrinter { /// ExceptionTimer - Timer for the Dwarf exception writer. Timer *ExceptionTimer; - /// SizeOfEncodedValue - Return the size of the encoding in bytes. - unsigned SizeOfEncodedValue(unsigned Encoding); - /// EmitCIE - Emit a Common Information Entry (CIE). This holds information /// that is shared among many Frame Description Entries. There is at least /// one CIE in every non-empty .debug_frame section. diff --git a/lib/CodeGen/AsmPrinter/DwarfPrinter.cpp b/lib/CodeGen/AsmPrinter/DwarfPrinter.cpp index 4de0b74..1299d04 100644 --- a/lib/CodeGen/AsmPrinter/DwarfPrinter.cpp +++ b/lib/CodeGen/AsmPrinter/DwarfPrinter.cpp @@ -8,7 +8,7 @@ //===----------------------------------------------------------------------===// // // Emit general DWARF directives. -// +// //===----------------------------------------------------------------------===// #include "DwarfPrinter.h" @@ -18,13 +18,17 @@ #include "llvm/CodeGen/MachineFunction.h" #include "llvm/CodeGen/MachineModuleInfo.h" #include "llvm/MC/MCAsmInfo.h" +#include "llvm/MC/MCContext.h" +#include "llvm/MC/MCExpr.h" #include "llvm/MC/MCStreamer.h" #include "llvm/MC/MCSymbol.h" #include "llvm/Target/TargetData.h" #include "llvm/Target/TargetFrameInfo.h" +#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Target/TargetRegisterInfo.h" #include "llvm/Support/Dwarf.h" #include "llvm/Support/ErrorHandling.h" +#include "llvm/ADT/SmallString.h" using namespace llvm; DwarfPrinter::DwarfPrinter(raw_ostream &OS, AsmPrinter *A, const MCAsmInfo *T, @@ -33,6 +37,26 @@ DwarfPrinter::DwarfPrinter(raw_ostream &OS, AsmPrinter *A, const MCAsmInfo *T, RI(Asm->TM.getRegisterInfo()), M(NULL), MF(NULL), MMI(NULL), SubprogramCount(0), Flavor(flavor), SetCounter(1) {} +/// SizeOfEncodedValue - Return the size of the encoding in bytes. +unsigned DwarfPrinter::SizeOfEncodedValue(unsigned Encoding) const { + if (Encoding == dwarf::DW_EH_PE_omit) + return 0; + + switch (Encoding & 0x07) { + case dwarf::DW_EH_PE_absptr: + return TD->getPointerSize(); + case dwarf::DW_EH_PE_udata2: + return 2; + case dwarf::DW_EH_PE_udata4: + return 4; + case dwarf::DW_EH_PE_udata8: + return 8; + } + + assert(0 && "Invalid encoded value."); + return 0; +} + void DwarfPrinter::PrintRelDirective(bool Force32Bit, bool isInSection) const { if (isInSection && MAI->getDwarfSectionOffsetDirective()) O << MAI->getDwarfSectionOffsetDirective(); @@ -42,6 +66,14 @@ void DwarfPrinter::PrintRelDirective(bool Force32Bit, bool isInSection) const { O << MAI->getData64bitsDirective(); } +void DwarfPrinter::PrintRelDirective(unsigned Encoding) const { + unsigned Size = SizeOfEncodedValue(Encoding); + assert((Size == 4 || Size == 8) && "Do not support other types or rels!"); + + O << (Size == 4 ? + MAI->getData32bitsDirective() : MAI->getData64bitsDirective()); +} + /// EOL - Print a newline character to asm stream. If a comment is present /// then it will be printed first. Comments should not contain '\n'. void DwarfPrinter::EOL(const Twine &Comment) const { @@ -195,6 +227,31 @@ void DwarfPrinter::EmitReference(const MCSymbol *Sym, bool IsPCRelative, if (IsPCRelative) O << "-" << MAI->getPCSymbol(); } +void DwarfPrinter::EmitReference(const char *Tag, unsigned Number, + unsigned Encoding) const { + SmallString<64> Name; + raw_svector_ostream(Name) << MAI->getPrivateGlobalPrefix() + << Tag << Number; + + MCSymbol *Sym = Asm->OutContext.GetOrCreateSymbol(Name.str()); + EmitReference(Sym, Encoding); +} + +void DwarfPrinter::EmitReference(const MCSymbol *Sym, unsigned Encoding) const { + const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); + + PrintRelDirective(Encoding); + O << *TLOF.getSymbolForDwarfReference(Sym, Asm->MMI, Encoding);; +} + +void DwarfPrinter::EmitReference(const GlobalValue *GV, unsigned Encoding)const { + const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); + + PrintRelDirective(Encoding); + O << *TLOF.getSymbolForDwarfGlobalReference(GV, Asm->Mang, + Asm->MMI, Encoding);; +} + /// EmitDifference - Emit the difference between two labels. If this assembler /// supports .set, we emit a .set of a temporary and then use it in the .word. void DwarfPrinter::EmitDifference(const char *TagHi, unsigned NumberHi, diff --git a/lib/CodeGen/AsmPrinter/DwarfPrinter.h b/lib/CodeGen/AsmPrinter/DwarfPrinter.h index 69d9c27..73de398 100644 --- a/lib/CodeGen/AsmPrinter/DwarfPrinter.h +++ b/lib/CodeGen/AsmPrinter/DwarfPrinter.h @@ -28,6 +28,7 @@ class Module; class MCAsmInfo; class TargetData; class TargetRegisterInfo; +class GlobalValue; class MCSymbol; class Twine; @@ -85,6 +86,10 @@ public: const MCAsmInfo *getMCAsmInfo() const { return MAI; } const TargetData *getTargetData() const { return TD; } + /// SizeOfEncodedValue - Return the size of the encoding in bytes. + unsigned SizeOfEncodedValue(unsigned Encoding) const; + + void PrintRelDirective(unsigned Encoding) const; void PrintRelDirective(bool Force32Bit = false, bool isInSection = false) const; @@ -140,6 +145,10 @@ public: void EmitReference(const MCSymbol *Sym, bool IsPCRelative = false, bool Force32Bit = false) const; + void EmitReference(const char *Tag, unsigned Number, unsigned Encoding) const; + void EmitReference(const MCSymbol *Sym, unsigned Encoding) const; + void EmitReference(const GlobalValue *GV, unsigned Encoding) const; + /// EmitDifference - Emit the difference between two labels. void EmitDifference(const DWLabel &LabelHi, const DWLabel &LabelLo, bool IsSmall = false) { diff --git a/lib/CodeGen/MachineModuleInfoImpls.cpp b/lib/CodeGen/MachineModuleInfoImpls.cpp index 8378906..39d2c75 100644 --- a/lib/CodeGen/MachineModuleInfoImpls.cpp +++ b/lib/CodeGen/MachineModuleInfoImpls.cpp @@ -22,7 +22,7 @@ using namespace llvm; // Out of line virtual method. void MachineModuleInfoMachO::Anchor() {} - +void MachineModuleInfoELF::Anchor() {} static int SortSymbolPair(const void *LHS, const void *RHS) { const MCSymbol *LHSS = @@ -34,10 +34,11 @@ static int SortSymbolPair(const void *LHS, const void *RHS) { /// GetSortedStubs - Return the entries from a DenseMap in a deterministic /// sorted orer. -MachineModuleInfoMachO::SymbolListTy -MachineModuleInfoMachO::GetSortedStubs(const DenseMap<MCSymbol*, - MCSymbol*> &Map) { - MachineModuleInfoMachO::SymbolListTy List(Map.begin(), Map.end()); +MachineModuleInfoImpl::SymbolListTy +MachineModuleInfoImpl::GetSortedStubs(const DenseMap<MCSymbol*, + MCSymbol*> &Map) { + MachineModuleInfoImpl::SymbolListTy List(Map.begin(), Map.end()); + if (!List.empty()) qsort(&List[0], List.size(), sizeof(List[0]), SortSymbolPair); return List; diff --git a/lib/Target/PowerPC/PPCTargetMachine.cpp b/lib/Target/PowerPC/PPCTargetMachine.cpp index 22eecd4..cac6962 100644 --- a/lib/Target/PowerPC/PPCTargetMachine.cpp +++ b/lib/Target/PowerPC/PPCTargetMachine.cpp @@ -115,32 +115,3 @@ bool PPCTargetMachine::addCodeEmitter(PassManagerBase &PM, return false; } - -/// getLSDAEncoding - Returns the LSDA pointer encoding. The choices are 4-byte, -/// 8-byte, and target default. The CIE is hard-coded to indicate that the LSDA -/// pointer in the FDE section is an "sdata4", and should be encoded as a 4-byte -/// pointer by default. However, some systems may require a different size due -/// to bugs or other conditions. We will default to a 4-byte encoding unless the -/// system tells us otherwise. -/// -/// The issue is when the CIE says their is an LSDA. That mandates that every -/// FDE have an LSDA slot. But if the function does not need an LSDA. There -/// needs to be some way to signify there is none. The LSDA is encoded as -/// pc-rel. But you don't look for some magic value after adding the pc. You -/// have to look for a zero before adding the pc. The problem is that the size -/// of the zero to look for depends on the encoding. The unwinder bug in SL is -/// that it always checks for a pointer-size zero. So on x86_64 it looks for 8 -/// bytes of zero. If you have an LSDA, it works fine since the 8-bytes are -/// non-zero so it goes ahead and then reads the value based on the encoding. -/// But if you use sdata4 and there is no LSDA, then the test for zero gives a -/// false negative and the unwinder thinks there is an LSDA. -/// -/// FIXME: This call-back isn't good! We should be using the correct encoding -/// regardless of the system. However, there are some systems which have bugs -/// that prevent this from occuring. -DwarfLSDAEncoding::Encoding PPCTargetMachine::getLSDAEncoding() const { - if (Subtarget.isDarwin() && Subtarget.getDarwinVers() != 10) - return DwarfLSDAEncoding::Default; - - return DwarfLSDAEncoding::EightByte; -} diff --git a/lib/Target/PowerPC/PPCTargetMachine.h b/lib/Target/PowerPC/PPCTargetMachine.h index a654435..ac9ae2b 100644 --- a/lib/Target/PowerPC/PPCTargetMachine.h +++ b/lib/Target/PowerPC/PPCTargetMachine.h @@ -57,18 +57,6 @@ public: return InstrItins; } - /// getLSDAEncoding - Returns the LSDA pointer encoding. The choices are - /// 4-byte, 8-byte, and target default. The CIE is hard-coded to indicate that - /// the LSDA pointer in the FDE section is an "sdata4", and should be encoded - /// as a 4-byte pointer by default. However, some systems may require a - /// different size due to bugs or other conditions. We will default to a - /// 4-byte encoding unless the system tells us otherwise. - /// - /// FIXME: This call-back isn't good! We should be using the correct encoding - /// regardless of the system. However, there are some systems which have bugs - /// that prevent this from occuring. - virtual DwarfLSDAEncoding::Encoding getLSDAEncoding() const; - // Pass Pipeline Configuration virtual bool addInstSelector(PassManagerBase &PM, CodeGenOpt::Level OptLevel); virtual bool addPreEmitPass(PassManagerBase &PM, CodeGenOpt::Level OptLevel); diff --git a/lib/Target/TargetLoweringObjectFile.cpp b/lib/Target/TargetLoweringObjectFile.cpp index a231ebc..88a978a 100644 --- a/lib/Target/TargetLoweringObjectFile.cpp +++ b/lib/Target/TargetLoweringObjectFile.cpp @@ -17,6 +17,7 @@ #include "llvm/DerivedTypes.h" #include "llvm/Function.h" #include "llvm/GlobalVariable.h" +#include "llvm/CodeGen/MachineModuleInfoImpls.h" #include "llvm/MC/MCContext.h" #include "llvm/MC/MCExpr.h" #include "llvm/MC/MCSectionMachO.h" @@ -26,6 +27,7 @@ #include "llvm/Target/TargetData.h" #include "llvm/Target/TargetMachine.h" #include "llvm/Target/TargetOptions.h" +#include "llvm/Support/Dwarf.h" #include "llvm/Support/ErrorHandling.h" #include "llvm/Support/raw_ostream.h" #include "llvm/ADT/SmallString.h" @@ -289,32 +291,56 @@ TargetLoweringObjectFile::getSectionForConstant(SectionKind Kind) const { } /// getSymbolForDwarfGlobalReference - Return an MCExpr to use for a -/// pc-relative reference to the specified global variable from exception -/// handling information. In addition to the symbol, this returns -/// by-reference: -/// -/// IsIndirect - True if the returned symbol is actually a stub that contains -/// the address of the symbol, false if the symbol is the global itself. -/// -/// IsPCRel - True if the symbol reference is already pc-relative, false if -/// the caller needs to subtract off the address of the reference from the -/// symbol. -/// +/// reference to the specified global variable from exception +/// handling information. const MCExpr *TargetLoweringObjectFile:: getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const { - // The generic implementation of this just returns a direct reference to the - // symbol. - IsIndirect = false; - IsPCRel = false; - + MachineModuleInfo *MMI, unsigned Encoding) const { // FIXME: Use GetGlobalValueSymbol. SmallString<128> Name; Mang->getNameWithPrefix(Name, GV, false); - return MCSymbolRefExpr::Create(Name.str(), getContext()); + const MCSymbol *Sym = getContext().GetOrCreateSymbol(Name.str()); + + return getSymbolForDwarfReference(Sym, MMI, Encoding); +} + +const MCExpr *TargetLoweringObjectFile:: +getSymbolForDwarfReference(const MCSymbol *Sym, MachineModuleInfo *MMI, + unsigned Encoding) const { + const MCExpr *Res = MCSymbolRefExpr::Create(Sym, getContext()); + + switch (Encoding & 0xF0) { + default: + llvm_report_error("Do not support this DWARF encoding yet!"); + break; + case dwarf::DW_EH_PE_absptr: + // Do nothing special + break; + case dwarf::DW_EH_PE_pcrel: + // FIXME: PCSymbol + const MCExpr *PC = MCSymbolRefExpr::Create(".", getContext()); + Res = MCBinaryExpr::CreateSub(Res, PC, getContext()); + break; + } + + return Res; +} + +unsigned TargetLoweringObjectFile::getPersonalityEncoding() const { + return dwarf::DW_EH_PE_absptr; +} + +unsigned TargetLoweringObjectFile::getLSDAEncoding() const { + return dwarf::DW_EH_PE_absptr; +} + +unsigned TargetLoweringObjectFile::getFDEEncoding() const { + return dwarf::DW_EH_PE_absptr; } +unsigned TargetLoweringObjectFile::getTTypeEncoding() const { + return dwarf::DW_EH_PE_absptr; +} //===----------------------------------------------------------------------===// // ELF @@ -671,6 +697,35 @@ getSectionForConstant(SectionKind Kind) const { return DataRelROSection; } +const MCExpr *TargetLoweringObjectFileELF:: +getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, + MachineModuleInfo *MMI, unsigned Encoding) const { + + if (Encoding & dwarf::DW_EH_PE_indirect) { + MachineModuleInfoELF &ELFMMI = MMI->getObjFileInfo<MachineModuleInfoELF>(); + + SmallString<128> Name; + Mang->getNameWithPrefix(Name, GV, true); + + // Add information about the stub reference to ELFMMI so that the stub + // gets emitted by the asmprinter. + MCSymbol *Sym = getContext().GetOrCreateSymbol(Name.str()); + MCSymbol *&StubSym = ELFMMI.getGVStubEntry(Sym); + if (StubSym == 0) { + Name.clear(); + Mang->getNameWithPrefix(Name, GV, false); + StubSym = getContext().GetOrCreateSymbol(Name.str()); + } + + return TargetLoweringObjectFile:: + getSymbolForDwarfReference(Sym, MMI, + Encoding & ~dwarf::DW_EH_PE_indirect); + } + + return TargetLoweringObjectFile:: + getSymbolForDwarfGlobalReference(GV, Mang, MMI, Encoding); +} + //===----------------------------------------------------------------------===// // MachO //===----------------------------------------------------------------------===// @@ -987,16 +1042,22 @@ shouldEmitUsedDirectiveFor(const GlobalValue *GV, Mangler *Mang) const { const MCExpr *TargetLoweringObjectFileMachO:: getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const { + MachineModuleInfo *MMI, unsigned Encoding) const { // The mach-o version of this method defaults to returning a stub reference. - IsIndirect = true; - IsPCRel = false; - - SmallString<128> Name; - Mang->getNameWithPrefix(Name, GV, true); - Name += "$non_lazy_ptr"; - return MCSymbolRefExpr::Create(Name.str(), getContext()); + + if (Encoding & dwarf::DW_EH_PE_indirect) { + SmallString<128> Name; + Mang->getNameWithPrefix(Name, GV, true); + Name += "$non_lazy_ptr"; + MCSymbol *Sym = getContext().GetOrCreateSymbol(Name.str()); + + return TargetLoweringObjectFile:: + getSymbolForDwarfReference(Sym, MMI, + Encoding & ~dwarf::DW_EH_PE_indirect); + } + + return TargetLoweringObjectFile:: + getSymbolForDwarfGlobalReference(GV, Mang, MMI, Encoding); } diff --git a/lib/Target/X86/AsmPrinter/X86AsmPrinter.cpp b/lib/Target/X86/AsmPrinter/X86AsmPrinter.cpp index dfcee79..704c013 100644 --- a/lib/Target/X86/AsmPrinter/X86AsmPrinter.cpp +++ b/lib/Target/X86/AsmPrinter/X86AsmPrinter.cpp @@ -603,6 +603,28 @@ void X86AsmPrinter::EmitEndOfAsmFile(Module &M) { } } } + + if (Subtarget->isTargetELF()) { + TargetLoweringObjectFileELF &TLOFELF = + static_cast<TargetLoweringObjectFileELF &>(getObjFileLowering()); + + MachineModuleInfoELF &MMIELF = MMI->getObjFileInfo<MachineModuleInfoELF>(); + + // Output stubs for external and common global variables. + MachineModuleInfoELF::SymbolListTy Stubs = MMIELF.GetGVStubList(); + if (!Stubs.empty()) { + OutStreamer.SwitchSection(TLOFELF.getDataRelSection()); + const TargetData *TD = TM.getTargetData(); + + for (unsigned i = 0, e = Stubs.size(); i != e; ++i) + O << *Stubs[i].first << ":\n" + << (TD->getPointerSize() == 8 ? + MAI->getData64bitsDirective() : MAI->getData32bitsDirective()) + << *Stubs[i].second << '\n'; + + Stubs.clear(); + } + } } diff --git a/lib/Target/X86/X86ISelLowering.cpp b/lib/Target/X86/X86ISelLowering.cpp index a80f2f8..9974d8c 100644 --- a/lib/Target/X86/X86ISelLowering.cpp +++ b/lib/Target/X86/X86ISelLowering.cpp @@ -75,13 +75,14 @@ static TargetLoweringObjectFile *createTLOF(X86TargetMachine &TM) { return new X8664_MachoTargetObjectFile(); return new X8632_MachoTargetObjectFile(); case X86Subtarget::isELF: - return new TargetLoweringObjectFileELF(); + if (TM.getSubtarget<X86Subtarget>().is64Bit()) + return new X8664_ELFTargetObjectFile(TM); + return new X8632_ELFTargetObjectFile(TM); case X86Subtarget::isMingw: case X86Subtarget::isCygwin: case X86Subtarget::isWindows: return new TargetLoweringObjectFileCOFF(); } - } X86TargetLowering::X86TargetLowering(X86TargetMachine &TM) diff --git a/lib/Target/X86/X86TargetMachine.cpp b/lib/Target/X86/X86TargetMachine.cpp index b507871..7802f98 100644 --- a/lib/Target/X86/X86TargetMachine.cpp +++ b/lib/Target/X86/X86TargetMachine.cpp @@ -199,32 +199,3 @@ void X86TargetMachine::setCodeModelForJIT() { else setCodeModel(CodeModel::Small); } - -/// getLSDAEncoding - Returns the LSDA pointer encoding. The choices are 4-byte, -/// 8-byte, and target default. The CIE is hard-coded to indicate that the LSDA -/// pointer in the FDE section is an "sdata4", and should be encoded as a 4-byte -/// pointer by default. However, some systems may require a different size due -/// to bugs or other conditions. We will default to a 4-byte encoding unless the -/// system tells us otherwise. -/// -/// The issue is when the CIE says their is an LSDA. That mandates that every -/// FDE have an LSDA slot. But if the function does not need an LSDA. There -/// needs to be some way to signify there is none. The LSDA is encoded as -/// pc-rel. But you don't look for some magic value after adding the pc. You -/// have to look for a zero before adding the pc. The problem is that the size -/// of the zero to look for depends on the encoding. The unwinder bug in SL is -/// that it always checks for a pointer-size zero. So on x86_64 it looks for 8 -/// bytes of zero. If you have an LSDA, it works fine since the 8-bytes are -/// non-zero so it goes ahead and then reads the value based on the encoding. -/// But if you use sdata4 and there is no LSDA, then the test for zero gives a -/// false negative and the unwinder thinks there is an LSDA. -/// -/// FIXME: This call-back isn't good! We should be using the correct encoding -/// regardless of the system. However, there are some systems which have bugs -/// that prevent this from occuring. -DwarfLSDAEncoding::Encoding X86TargetMachine::getLSDAEncoding() const { - if (Subtarget.isTargetDarwin() && Subtarget.getDarwinVers() != 10) - return DwarfLSDAEncoding::Default; - - return DwarfLSDAEncoding::EightByte; -} diff --git a/lib/Target/X86/X86TargetMachine.h b/lib/Target/X86/X86TargetMachine.h index eee29be..2bb5454 100644 --- a/lib/Target/X86/X86TargetMachine.h +++ b/lib/Target/X86/X86TargetMachine.h @@ -62,18 +62,6 @@ public: return Subtarget.isTargetELF() ? &ELFWriterInfo : 0; } - /// getLSDAEncoding - Returns the LSDA pointer encoding. The choices are - /// 4-byte, 8-byte, and target default. The CIE is hard-coded to indicate that - /// the LSDA pointer in the FDE section is an "sdata4", and should be encoded - /// as a 4-byte pointer by default. However, some systems may require a - /// different size due to bugs or other conditions. We will default to a - /// 4-byte encoding unless the system tells us otherwise. - /// - /// FIXME: This call-back isn't good! We should be using the correct encoding - /// regardless of the system. However, there are some systems which have bugs - /// that prevent this from occuring. - virtual DwarfLSDAEncoding::Encoding getLSDAEncoding() const; - // Set up the pass pipeline. virtual bool addInstSelector(PassManagerBase &PM, CodeGenOpt::Level OptLevel); virtual bool addPreRegAlloc(PassManagerBase &PM, CodeGenOpt::Level OptLevel); diff --git a/lib/Target/X86/X86TargetObjectFile.cpp b/lib/Target/X86/X86TargetObjectFile.cpp index b8cef7d..be01b5f 100644 --- a/lib/Target/X86/X86TargetObjectFile.cpp +++ b/lib/Target/X86/X86TargetObjectFile.cpp @@ -7,61 +7,177 @@ // //===----------------------------------------------------------------------===// -#include "X86TargetObjectFile.h" #include "X86MCTargetExpr.h" +#include "X86TargetObjectFile.h" +#include "X86TargetMachine.h" #include "llvm/CodeGen/MachineModuleInfoImpls.h" #include "llvm/MC/MCContext.h" #include "llvm/Target/Mangler.h" #include "llvm/ADT/SmallString.h" +#include "llvm/Support/Dwarf.h" using namespace llvm; +using namespace dwarf; const MCExpr *X8632_MachoTargetObjectFile:: getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const { + MachineModuleInfo *MMI, unsigned Encoding) const { // The mach-o version of this method defaults to returning a stub reference. - IsIndirect = true; - IsPCRel = false; - - - MachineModuleInfoMachO &MachOMMI = - MMI->getObjFileInfo<MachineModuleInfoMachO>(); - - // FIXME: Use GetSymbolWithGlobalValueBase. - SmallString<128> Name; - Mang->getNameWithPrefix(Name, GV, true); - Name += "$non_lazy_ptr"; - - // Add information about the stub reference to MachOMMI so that the stub gets - // emitted by the asmprinter. - MCSymbol *Sym = getContext().GetOrCreateSymbol(Name.str()); - MCSymbol *&StubSym = MachOMMI.getGVStubEntry(Sym); - if (StubSym == 0) { - Name.clear(); - Mang->getNameWithPrefix(Name, GV, false); - StubSym = getContext().GetOrCreateSymbol(Name.str()); + + if (Encoding & DW_EH_PE_indirect) { + MachineModuleInfoMachO &MachOMMI = + MMI->getObjFileInfo<MachineModuleInfoMachO>(); + + SmallString<128> Name; + Mang->getNameWithPrefix(Name, GV, true); + Name += "$non_lazy_ptr"; + + // Add information about the stub reference to MachOMMI so that the stub + // gets emitted by the asmprinter. + MCSymbol *Sym = getContext().GetOrCreateSymbol(Name.str()); + MCSymbol *&StubSym = MachOMMI.getGVStubEntry(Sym); + if (StubSym == 0) { + Name.clear(); + Mang->getNameWithPrefix(Name, GV, false); + StubSym = getContext().GetOrCreateSymbol(Name.str()); + } + + return TargetLoweringObjectFile:: + getSymbolForDwarfReference(Sym, MMI, + Encoding & ~dwarf::DW_EH_PE_indirect); } - - return MCSymbolRefExpr::Create(Sym, getContext()); + + return TargetLoweringObjectFileMachO:: + getSymbolForDwarfGlobalReference(GV, Mang, MMI, Encoding); } const MCExpr *X8664_MachoTargetObjectFile:: getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const { - + MachineModuleInfo *MMI, unsigned Encoding) const { + // On Darwin/X86-64, we can reference dwarf symbols with foo@GOTPCREL+4, which // is an indirect pc-relative reference. - IsIndirect = true; - IsPCRel = true; - - // FIXME: Use GetSymbolWithGlobalValueBase. - SmallString<128> Name; - Mang->getNameWithPrefix(Name, GV, false); + if ((Encoding & DW_EH_PE_indirect) && + (Encoding & DW_EH_PE_pcrel)) { + SmallString<128> Name; + Mang->getNameWithPrefix(Name, GV, false); const MCSymbol *Sym = getContext().CreateSymbol(Name); const MCExpr *Res = X86MCTargetExpr::Create(Sym, X86MCTargetExpr::GOTPCREL, getContext()); const MCExpr *Four = MCConstantExpr::Create(4, getContext()); return MCBinaryExpr::CreateAdd(Res, Four, getContext()); + } + + return TargetLoweringObjectFileMachO:: + getSymbolForDwarfGlobalReference(GV, Mang, MMI, Encoding); +} + +unsigned X8632_ELFTargetObjectFile::getPersonalityEncoding() const { + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; + else + return DW_EH_PE_absptr; +} + +unsigned X8632_ELFTargetObjectFile::getLSDAEncoding() const { + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; + else + return DW_EH_PE_absptr; +} + +unsigned X8632_ELFTargetObjectFile::getFDEEncoding() const { + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; + else + return DW_EH_PE_absptr; +} + +unsigned X8632_ELFTargetObjectFile::getTTypeEncoding() const { + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; + else + return DW_EH_PE_absptr; } +unsigned X8664_ELFTargetObjectFile::getPersonalityEncoding() const { + CodeModel::Model Model = TM.getCodeModel(); + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_indirect | DW_EH_PE_pcrel | (Model == CodeModel::Small || + Model == CodeModel::Medium ? + DW_EH_PE_sdata4 : DW_EH_PE_sdata8); + + if (Model == CodeModel::Small || Model == CodeModel::Medium) + return DW_EH_PE_udata4; + + return DW_EH_PE_absptr; +} + +unsigned X8664_ELFTargetObjectFile::getLSDAEncoding() const { + CodeModel::Model Model = TM.getCodeModel(); + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_pcrel | (Model == CodeModel::Small ? + DW_EH_PE_sdata4 : DW_EH_PE_sdata8); + + if (Model == CodeModel::Small) + return DW_EH_PE_udata4; + + return DW_EH_PE_absptr; +} + +unsigned X8664_ELFTargetObjectFile::getFDEEncoding() const { + CodeModel::Model Model = TM.getCodeModel(); + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_pcrel | (Model == CodeModel::Small || + Model == CodeModel::Medium ? + DW_EH_PE_sdata4 : DW_EH_PE_sdata8); + + if (Model == CodeModel::Small || Model == CodeModel::Medium) + return DW_EH_PE_udata4; + + return DW_EH_PE_absptr; +} + +unsigned X8664_ELFTargetObjectFile::getTTypeEncoding() const { + CodeModel::Model Model = TM.getCodeModel(); + if (TM.getRelocationModel() == Reloc::PIC_) + return DW_EH_PE_indirect | DW_EH_PE_pcrel | (Model == CodeModel::Small || + Model == CodeModel::Medium ? + DW_EH_PE_sdata4 : DW_EH_PE_sdata8); + + if (Model == CodeModel::Small) + return DW_EH_PE_udata4; + + return DW_EH_PE_absptr; +} + +unsigned X8632_MachoTargetObjectFile::getPersonalityEncoding() const { + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8632_MachoTargetObjectFile::getLSDAEncoding() const { + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8632_MachoTargetObjectFile::getFDEEncoding() const { + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8632_MachoTargetObjectFile::getTTypeEncoding() const { + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8664_MachoTargetObjectFile::getPersonalityEncoding() const { + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8664_MachoTargetObjectFile::getLSDAEncoding() const { + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8664_MachoTargetObjectFile::getFDEEncoding() const { + return DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} + +unsigned X8664_MachoTargetObjectFile::getTTypeEncoding() const { + return DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4; +} diff --git a/lib/Target/X86/X86TargetObjectFile.h b/lib/Target/X86/X86TargetObjectFile.h index 377a93b..0b5dec1 100644 --- a/lib/Target/X86/X86TargetObjectFile.h +++ b/lib/Target/X86/X86TargetObjectFile.h @@ -10,21 +10,26 @@ #ifndef LLVM_TARGET_X86_TARGETOBJECTFILE_H #define LLVM_TARGET_X86_TARGETOBJECTFILE_H +#include "llvm/Target/TargetMachine.h" #include "llvm/Target/TargetLoweringObjectFile.h" namespace llvm { - + class X86TargetMachine; + /// X8632_MachoTargetObjectFile - This TLOF implementation is used for /// Darwin/x86-32. class X8632_MachoTargetObjectFile : public TargetLoweringObjectFileMachO { public: - + virtual const MCExpr * getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const; + MachineModuleInfo *MMI, unsigned Encoding) const; + virtual unsigned getPersonalityEncoding() const; + virtual unsigned getLSDAEncoding() const; + virtual unsigned getFDEEncoding() const; + virtual unsigned getTTypeEncoding() const; }; - + /// X8664_MachoTargetObjectFile - This TLOF implementation is used for /// Darwin/x86-64. class X8664_MachoTargetObjectFile : public TargetLoweringObjectFileMachO { @@ -32,9 +37,35 @@ namespace llvm { virtual const MCExpr * getSymbolForDwarfGlobalReference(const GlobalValue *GV, Mangler *Mang, - MachineModuleInfo *MMI, - bool &IsIndirect, bool &IsPCRel) const; + MachineModuleInfo *MMI, unsigned Encoding) const; + virtual unsigned getPersonalityEncoding() const; + virtual unsigned getLSDAEncoding() const; + virtual unsigned getFDEEncoding() const; + virtual unsigned getTTypeEncoding() const; + }; + + class X8632_ELFTargetObjectFile : public TargetLoweringObjectFileELF { + const X86TargetMachine &TM; + public: + X8632_ELFTargetObjectFile(const X86TargetMachine &tm) + :TM(tm) { }; + virtual unsigned getPersonalityEncoding() const; + virtual unsigned getLSDAEncoding() const; + virtual unsigned getFDEEncoding() const; + virtual unsigned getTTypeEncoding() const; }; + + class X8664_ELFTargetObjectFile : public TargetLoweringObjectFileELF { + const X86TargetMachine &TM; + public: + X8664_ELFTargetObjectFile(const X86TargetMachine &tm) + :TM(tm) { }; + virtual unsigned getPersonalityEncoding() const; + virtual unsigned getLSDAEncoding() const; + virtual unsigned getFDEEncoding() const; + virtual unsigned getTTypeEncoding() const; + }; + } // end namespace llvm #endif diff --git a/test/CodeGen/Generic/2007-05-05-Personality.ll b/test/CodeGen/Generic/2007-05-05-Personality.ll index 2749326..c92783e 100644 --- a/test/CodeGen/Generic/2007-05-05-Personality.ll +++ b/test/CodeGen/Generic/2007-05-05-Personality.ll @@ -1,4 +1,4 @@ -; RUN: llc < %s -mtriple=i686-pc-linux-gnu -enable-eh -o - | grep zPLR +; RUN: llc < %s -mtriple=i686-pc-linux-gnu -enable-eh -o - | grep zPL @error = external global i8 ; <i8*> [#uses=2] |