llvm.org GIT mirror llvm / bce877c
Revert r225048: It broke ObjC on AArch64. I've filed http://llvm.org/PR22100 to track this issue. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@225228 91177308-0d34-0410-b5e6-96231b3b80d8 Lang Hames 5 years ago
19 changed file(s) with 250 addition(s) and 306 deletion(s). Raw diff Collapse all Expand all
5959 /// hasDataInCodeSupport - Check whether this target implements data-in-code
6060 /// markers. If not, data region directives will be ignored.
6161 bool hasDataInCodeSupport() const { return HasDataInCodeSupport; }
62
63 /// doesSectionRequireSymbols - Check whether the given section requires that
64 /// all symbols (even temporaries) have symbol table entries.
65 virtual bool doesSectionRequireSymbols(const MCSection &Section) const {
66 return false;
67 }
6268
6369 /// @name Target Fixup Interfaces
6470 /// @{
1010 #define LLVM_MC_MCASSEMBLER_H
1111
1212 #include "llvm/ADT/DenseMap.h"
13 #include "llvm/ADT/DenseSet.h"
1413 #include "llvm/ADT/PointerIntPair.h"
1514 #include "llvm/ADT/SmallPtrSet.h"
1615 #include "llvm/ADT/SmallString.h"
880879 iplist Sections;
881880
882881 iplist Symbols;
883
884 DenseSet LocalsUsedInReloc;
885882
886883 /// The map of sections to their associated assembler backend data.
887884 //
982979 MCFragment &F, const MCFixup &Fixup);
983980
984981 public:
985 void addLocalUsedInReloc(const MCSymbol &Sym);
986 bool isLocalUsedInReloc(const MCSymbol &Sym) const;
987
988982 /// Compute the effective fragment size assuming it is laid out at the given
989983 /// \p SectionAddress and \p FragmentOffset.
990984 uint64_t computeFragmentSize(const MCAsmLayout &Layout,
6767 /// @name API
6868 /// @{
6969
70 virtual void RecordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
70 virtual void RecordRelocation(MachObjectWriter *Writer,
71 const MCAssembler &Asm,
7172 const MCAsmLayout &Layout,
7273 const MCFragment *Fragment,
73 const MCFixup &Fixup, MCValue Target,
74 const MCFixup &Fixup,
75 MCValue Target,
7476 uint64_t &FixedValue) = 0;
7577
7678 /// @}
9496 /// @name Relocation Data
9597 /// @{
9698
97 struct RelAndSymbol {
98 const MCSymbolData *Sym;
99 MachO::any_relocation_info MRE;
100 RelAndSymbol(const MCSymbolData *Sym, const MachO::any_relocation_info &MRE)
101 : Sym(Sym), MRE(MRE) {}
102 };
103
104 llvm::DenseMap *, std::vector> Relocations;
99 llvm::DenseMap*,
100 std::vector > Relocations;
105101 llvm::DenseMap IndirectSymBase;
106102
107103 /// @}
216212 // - Input errors, where something cannot be correctly encoded. 'as' allows
217213 // these through in many cases.
218214
219 // Add a relocation to be output in the object file. At the time this is
220 // called, the symbol indexes are not know, so if the relocation refers
221 // to a symbol it should be passed as \p RelSymbol so that it can be updated
222 // afterwards. If the relocation doesn't refer to a symbol, nullptr should be
223 // used.
224 void addRelocation(const MCSymbolData *RelSymbol, const MCSectionData *SD,
215 void addRelocation(const MCSectionData *SD,
225216 MachO::any_relocation_info &MRE) {
226 RelAndSymbol P(RelSymbol, MRE);
227 Relocations[SD].push_back(P);
217 Relocations[SD].push_back(MRE);
228218 }
229219
230220 void RecordScatteredRelocation(const MCAssembler &Asm,
240230 const MCFixup &Fixup, MCValue Target,
241231 uint64_t &FixedValue);
242232
243 void RecordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
233 void RecordRelocation(const MCAssembler &Asm, const MCAsmLayout &Layout,
244234 const MCFragment *Fragment, const MCFixup &Fixup,
245235 MCValue Target, bool &IsPCRel,
246236 uint64_t &FixedValue) override;
7575 /// post layout binding. The implementation is responsible for storing
7676 /// information about the relocation so that it can be emitted during
7777 /// WriteObject().
78 virtual void RecordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
78 virtual void RecordRelocation(const MCAssembler &Asm,
79 const MCAsmLayout &Layout,
7980 const MCFragment *Fragment,
8081 const MCFixup &Fixup, MCValue Target,
81 bool &IsPCRel, uint64_t &FixedValue) = 0;
82 bool &IsPCRel,
83 uint64_t &FixedValue) = 0;
8284
8385 /// \brief Check whether the difference (A - B) between two symbol
8486 /// references is fully resolved.
218218 const MCSymbolData *SD, uint64_t C,
219219 unsigned Type) const;
220220
221 void RecordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
221 void RecordRelocation(const MCAssembler &Asm, const MCAsmLayout &Layout,
222222 const MCFragment *Fragment, const MCFixup &Fixup,
223223 MCValue Target, bool &IsPCRel,
224224 uint64_t &FixedValue) override;
788788 return nullptr;
789789 }
790790
791 void ELFObjectWriter::RecordRelocation(MCAssembler &Asm,
791 void ELFObjectWriter::RecordRelocation(const MCAssembler &Asm,
792792 const MCAsmLayout &Layout,
793793 const MCFragment *Fragment,
794 const MCFixup &Fixup, MCValue Target,
795 bool &IsPCRel, uint64_t &FixedValue) {
794 const MCFixup &Fixup,
795 MCValue Target,
796 bool &IsPCRel,
797 uint64_t &FixedValue) {
796798 const MCSectionData *FixupSection = Fragment->getParent();
797799 uint64_t C = Target.getConstant();
798800 uint64_t FixupOffset = Layout.getFragmentOffset(Fragment) + Fixup.getOffset();
2626 // contain.
2727 // Sections holding 2 byte strings require symbols in order to be atomized.
2828 // There is no dedicated section for 4 byte strings.
29 if (SMO.getType() == MachO::S_CSTRING_LITERALS)
29 if (SMO.getKind().isMergeable1ByteCString())
30 return false;
31
32 if (SMO.getSegmentName() == "__TEXT" &&
33 SMO.getSectionName() == "__objc_classname" &&
34 SMO.getType() == MachO::S_CSTRING_LITERALS)
35 return false;
36
37 if (SMO.getSegmentName() == "__TEXT" &&
38 SMO.getSectionName() == "__objc_methname" &&
39 SMO.getType() == MachO::S_CSTRING_LITERALS)
40 return false;
41
42 if (SMO.getSegmentName() == "__TEXT" &&
43 SMO.getSectionName() == "__objc_methtype" &&
44 SMO.getType() == MachO::S_CSTRING_LITERALS)
3045 return false;
3146
3247 if (SMO.getSegmentName() == "__DATA" && SMO.getSectionName() == "__cfstring")
424424 return true;
425425 }
426426
427 void MCAssembler::addLocalUsedInReloc(const MCSymbol &Sym) {
428 assert(Sym.isTemporary());
429 LocalsUsedInReloc.insert(&Sym);
430 }
431
432 bool MCAssembler::isLocalUsedInReloc(const MCSymbol &Sym) const {
433 assert(Sym.isTemporary());
434 return LocalsUsedInReloc.count(&Sym);
435 }
436
437427 bool MCAssembler::isSymbolLinkerVisible(const MCSymbol &Symbol) const {
438428 // Non-temporary labels should always be visible to the linker.
439429 if (!Symbol.isTemporary())
443433 if (!Symbol.isInSection())
444434 return false;
445435
446 if (isLocalUsedInReloc(Symbol))
447 return true;
448
449 return false;
436 // Otherwise, check if the section requires symbols even for temporary labels.
437 return getBackend().doesSectionRequireSymbols(Symbol.getSection());
450438 }
451439
452440 const MCSymbolData *MCAssembler::getAtom(const MCSymbolData *SD) const {
447447 assert(OS.tell() - Start == Size);
448448 }
449449
450 void MachObjectWriter::RecordRelocation(MCAssembler &Asm,
450
451 void MachObjectWriter::RecordRelocation(const MCAssembler &Asm,
451452 const MCAsmLayout &Layout,
452453 const MCFragment *Fragment,
453 const MCFixup &Fixup, MCValue Target,
454 bool &IsPCRel, uint64_t &FixedValue) {
454 const MCFixup &Fixup,
455 MCValue Target,
456 bool &IsPCRel,
457 uint64_t &FixedValue) {
455458 TargetObjectWriter->RecordRelocation(this, Asm, Layout, Fragment, Fixup,
456459 Target, FixedValue);
457460 }
612615 ExternalSymbolData[i].SymbolData->setIndex(Index++);
613616 for (unsigned i = 0, e = UndefinedSymbolData.size(); i != e; ++i)
614617 UndefinedSymbolData[i].SymbolData->setIndex(Index++);
615
616 for (const MCSectionData &SD : Asm) {
617 std::vector &Relocs = Relocations[&SD];
618 for (RelAndSymbol &Rel : Relocs) {
619 if (!Rel.Sym)
620 continue;
621
622 // Set the Index and the IsExtern bit.
623 unsigned Index = Rel.Sym->getIndex();
624 assert(isInt<24>(Index));
625 if (IsLittleEndian)
626 Rel.MRE.r_word1 = (Rel.MRE.r_word1 & (-1 << 24)) | Index | (1 << 27);
627 else
628 Rel.MRE.r_word1 = (Rel.MRE.r_word1 & 0xff) | Index << 8 | (1 << 4);
629 }
630 }
631618 }
632619
633620 void MachObjectWriter::computeSectionAddresses(const MCAssembler &Asm,
674661 // Mark symbol difference expressions in variables (from .set or = directives)
675662 // as absolute.
676663 markAbsoluteVariableSymbols(Asm, Layout);
664
665 // Compute symbol table information and bind symbol indices.
666 ComputeSymbolTable(Asm, LocalSymbolData, ExternalSymbolData,
667 UndefinedSymbolData);
677668 }
678669
679670 bool MachObjectWriter::
757748
758749 void MachObjectWriter::WriteObject(MCAssembler &Asm,
759750 const MCAsmLayout &Layout) {
760 // Compute symbol table information and bind symbol indices.
761 ComputeSymbolTable(Asm, LocalSymbolData, ExternalSymbolData,
762 UndefinedSymbolData);
763
764751 unsigned NumSections = Asm.size();
765752 const MCAssembler::VersionMinInfoType &VersionInfo =
766753 Layout.getAssembler().getVersionMinInfo();
851838 uint64_t RelocTableEnd = SectionDataStart + SectionDataFileSize;
852839 for (MCAssembler::const_iterator it = Asm.begin(),
853840 ie = Asm.end(); it != ie; ++it) {
854 std::vector<RelAndSymbol> &Relocs = Relocations[it];
841 std::vector<MachO::any_relocation_info> &Relocs = Relocations[it];
855842 unsigned NumRelocs = Relocs.size();
856843 uint64_t SectionStart = SectionDataStart + getSectionAddress(it);
857844 WriteSection(Asm, Layout, *it, SectionStart, RelocTableEnd, NumRelocs);
945932 ie = Asm.end(); it != ie; ++it) {
946933 // Write the section relocation entries, in reverse order to match 'as'
947934 // (approximately, the exact algorithm is more complicated than this).
948 std::vector<RelAndSymbol> &Relocs = Relocations[it];
935 std::vector<MachO::any_relocation_info> &Relocs = Relocations[it];
949936 for (unsigned i = 0, e = Relocs.size(); i != e; ++i) {
950 Write32(Relocs[e - i - 1].MRE.r_word0);
951 Write32(Relocs[e - i - 1].MRE.r_word1);
937 Write32(Relocs[e - i - 1].r_word0);
938 Write32(Relocs[e - i - 1].r_word1);
952939 }
953940 }
954941
174174 const MCFragment &FB, bool InSet,
175175 bool IsPCRel) const override;
176176
177 void RecordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
177 void RecordRelocation(const MCAssembler &Asm, const MCAsmLayout &Layout,
178178 const MCFragment *Fragment, const MCFixup &Fixup,
179179 MCValue Target, bool &IsPCRel,
180180 uint64_t &FixedValue) override;
660660 InSet, IsPCRel);
661661 }
662662
663 void WinCOFFObjectWriter::RecordRelocation(
664 MCAssembler &Asm, const MCAsmLayout &Layout, const MCFragment *Fragment,
665 const MCFixup &Fixup, MCValue Target, bool &IsPCRel, uint64_t &FixedValue) {
663 void WinCOFFObjectWriter::RecordRelocation(const MCAssembler &Asm,
664 const MCAsmLayout &Layout,
665 const MCFragment *Fragment,
666 const MCFixup &Fixup,
667 MCValue Target,
668 bool &IsPCRel,
669 uint64_t &FixedValue) {
666670 assert(Target.getSymA() && "Relocation must reference a symbol!");
667671
668672 const MCSymbol &Symbol = Target.getSymA()->getSymbol();
316316 MachO::CPU_SUBTYPE_ARM64_ALL);
317317 }
318318
319 bool doesSectionRequireSymbols(const MCSection &Section) const override {
320 // Any section for which the linker breaks things into atoms needs to
321 // preserve symbols, including assembler local symbols, to identify
322 // those atoms. These sections are:
323 // Sections of type:
324 //
325 // S_CSTRING_LITERALS (e.g. __cstring)
326 // S_LITERAL_POINTERS (e.g. objc selector pointers)
327 // S_16BYTE_LITERALS, S_8BYTE_LITERALS, S_4BYTE_LITERALS
328 //
329 // Sections named:
330 //
331 // __TEXT,__eh_frame
332 // __TEXT,__ustring
333 // __DATA,__cfstring
334 // __DATA,__objc_classrefs
335 // __DATA,__objc_catlist
336 //
337 // FIXME: It would be better if the compiler used actual linker local
338 // symbols for each of these sections rather than preserving what
339 // are ostensibly assembler local symbols.
340 const MCSectionMachO &SMO = static_cast(Section);
341 return (SMO.getType() == MachO::S_CSTRING_LITERALS ||
342 SMO.getType() == MachO::S_4BYTE_LITERALS ||
343 SMO.getType() == MachO::S_8BYTE_LITERALS ||
344 SMO.getType() == MachO::S_16BYTE_LITERALS ||
345 SMO.getType() == MachO::S_LITERAL_POINTERS ||
346 (SMO.getSegmentName() == "__TEXT" &&
347 (SMO.getSectionName() == "__eh_frame" ||
348 SMO.getSectionName() == "__ustring")) ||
349 (SMO.getSegmentName() == "__DATA" &&
350 (SMO.getSectionName() == "__cfstring" ||
351 SMO.getSectionName() == "__objc_classrefs" ||
352 SMO.getSectionName() == "__objc_catlist")));
353 }
354
319355 /// \brief Generate the compact unwind encoding from the CFI directives.
320356 uint32_t generateCompactUnwindEncoding(
321357 ArrayRef Instrs) const override {
99 #include "MCTargetDesc/AArch64FixupKinds.h"
1010 #include "MCTargetDesc/AArch64MCTargetDesc.h"
1111 #include "llvm/ADT/Twine.h"
12 #include "llvm/MC/MCAsmInfo.h"
1312 #include "llvm/MC/MCAsmLayout.h"
1413 #include "llvm/MC/MCAssembler.h"
1514 #include "llvm/MC/MCContext.h"
3332 : MCMachObjectTargetWriter(true /* is64Bit */, CPUType, CPUSubtype,
3433 /*UseAggressiveSymbolFolding=*/true) {}
3534
36 void RecordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
35 void RecordRelocation(MachObjectWriter *Writer, const MCAssembler &Asm,
3736 const MCAsmLayout &Layout, const MCFragment *Fragment,
3837 const MCFixup &Fixup, MCValue Target,
3938 uint64_t &FixedValue) override;
113112 }
114113
115114 void AArch64MachObjectWriter::RecordRelocation(
116 MachObjectWriter *Writer, MCAssembler &Asm, const MCAsmLayout &Layout,
115 MachObjectWriter *Writer, const MCAssembler &Asm, const MCAsmLayout &Layout,
117116 const MCFragment *Fragment, const MCFixup &Fixup, MCValue Target,
118117 uint64_t &FixedValue) {
119118 unsigned IsPCRel = Writer->isFixupKindPCRel(Asm, Fixup.getKind());
123122 unsigned Log2Size = 0;
124123 int64_t Value = 0;
125124 unsigned Index = 0;
125 unsigned IsExtern = 0;
126126 unsigned Type = 0;
127127 unsigned Kind = Fixup.getKind();
128 const MCSymbolData *RelSymbol = nullptr;
129128
130129 FixupOffset += Fixup.getOffset();
131130
171170 // FIXME: Should this always be extern?
172171 // SymbolNum of 0 indicates the absolute section.
173172 Type = MachO::ARM64_RELOC_UNSIGNED;
173 Index = 0;
174174
175175 if (IsPCRel) {
176 IsExtern = 1;
176177 Asm.getContext().FatalError(Fixup.getLoc(),
177178 "PC relative absolute relocation!");
178179
196197 Layout.getSymbolOffset(&B_SD) ==
197198 Layout.getFragmentOffset(Fragment) + Fixup.getOffset()) {
198199 // SymB is the PC, so use a PC-rel pointer-to-GOT relocation.
200 Index = A_Base->getIndex();
201 IsExtern = 1;
199202 Type = MachO::ARM64_RELOC_POINTER_TO_GOT;
200203 IsPCRel = 1;
201204 MachO::any_relocation_info MRE;
202205 MRE.r_word0 = FixupOffset;
203 MRE.r_word1 = (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
204 Writer->addRelocation(A_Base, Fragment->getParent(), MRE);
206 MRE.r_word1 = ((Index << 0) | (IsPCRel << 24) | (Log2Size << 25) |
207 (IsExtern << 27) | (Type << 28));
208 Writer->addRelocation(Fragment->getParent(), MRE);
205209 return;
206210 } else if (Target.getSymA()->getKind() != MCSymbolRefExpr::VK_None ||
207211 Target.getSymB()->getKind() != MCSymbolRefExpr::VK_None)
247251 ? 0
248252 : Writer->getSymbolAddress(B_Base, Layout));
249253
254 Index = A_Base->getIndex();
255 IsExtern = 1;
250256 Type = MachO::ARM64_RELOC_UNSIGNED;
251257
252258 MachO::any_relocation_info MRE;
253259 MRE.r_word0 = FixupOffset;
254 MRE.r_word1 = (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
255 Writer->addRelocation(A_Base, Fragment->getParent(), MRE);
256
257 RelSymbol = B_Base;
260 MRE.r_word1 = ((Index << 0) | (IsPCRel << 24) | (Log2Size << 25) |
261 (IsExtern << 27) | (Type << 28));
262 Writer->addRelocation(Fragment->getParent(), MRE);
263
264 Index = B_Base->getIndex();
265 IsExtern = 1;
258266 Type = MachO::ARM64_RELOC_SUBTRACTOR;
259267 } else { // A + constant
260268 const MCSymbol *Symbol = &Target.getSymA()->getSymbol();
269 const MCSymbolData &SD = Asm.getSymbolData(*Symbol);
270 const MCSymbolData *Base = Asm.getAtom(&SD);
261271 const MCSectionMachO &Section = static_cast(
262272 Fragment->getParent()->getSection());
263
264 // Pointer-sized relocations can use a local relocation. Otherwise,
265 // we have to be in a debug info section.
266 bool CanUseLocalRelocation =
267 Section.hasAttribute(MachO::S_ATTR_DEBUG) || Log2Size == 3;
268
269 if (Symbol->isTemporary() && (Value || !CanUseLocalRelocation)) {
270 const MCSection &Sec = Symbol->getSection();
271 if (!Asm.getContext().getAsmInfo()->isSectionAtomizableBySymbols(Sec))
272 Asm.addLocalUsedInReloc(*Symbol);
273 }
274
275 const MCSymbolData &SD = Asm.getSymbolData(*Symbol);
276 const MCSymbolData *Base = Asm.getAtom(&SD);
277273
278274 // If the symbol is a variable and we weren't able to get a Base for it
279275 // (i.e., it's not in the symbol table associated with a section) resolve
313309 // sections, and for pointer-sized relocations (.quad), we allow section
314310 // relocations. It's code sections that run into trouble.
315311 if (Base) {
316 RelSymbol = Base;
312 Index = Base->getIndex();
313 IsExtern = 1;
317314
318315 // Add the local offset, if needed.
319316 if (Base != &SD)
320317 Value += Layout.getSymbolOffset(&SD) - Layout.getSymbolOffset(Base);
321318 } else if (Symbol->isInSection()) {
322 if (!CanUseLocalRelocation)
319 // Pointer-sized relocations can use a local relocation. Otherwise,
320 // we have to be in a debug info section.
321 if (!Section.hasAttribute(MachO::S_ATTR_DEBUG) && Log2Size != 3)
323322 Asm.getContext().FatalError(
324323 Fixup.getLoc(),
325324 "unsupported relocation of local symbol '" + Symbol->getName() +
329328 const MCSectionData &SymSD =
330329 Asm.getSectionData(SD.getSymbol().getSection());
331330 Index = SymSD.getOrdinal() + 1;
331 IsExtern = 0;
332332 Value += Writer->getSymbolAddress(&SD, Layout);
333333
334334 if (IsPCRel)
361361
362362 MachO::any_relocation_info MRE;
363363 MRE.r_word0 = FixupOffset;
364 MRE.r_word1 =
365 (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
366 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
364 MRE.r_word1 = ((Index << 0) | (IsPCRel << 24) | (Log2Size << 25) |
365 (IsExtern << 27) | (Type << 28));
366 Writer->addRelocation(Fragment->getParent(), MRE);
367367
368368 // Now set up the Addend relocation.
369369 Type = MachO::ARM64_RELOC_ADDEND;
370370 Index = Value;
371 RelSymbol = nullptr;
372371 IsPCRel = 0;
373372 Log2Size = 2;
373 IsExtern = 0;
374374
375375 // Put zero into the instruction itself. The addend is in the relocation.
376376 Value = 0;
382382 // struct relocation_info (8 bytes)
383383 MachO::any_relocation_info MRE;
384384 MRE.r_word0 = FixupOffset;
385 MRE.r_word1 =
386 (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
387 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
385 MRE.r_word1 = ((Index << 0) | (IsPCRel << 24) | (Log2Size << 25) |
386 (IsExtern << 27) | (Type << 28));
387 Writer->addRelocation(Fragment->getParent(), MRE);
388388 }
389389
390390 MCObjectWriter *llvm::createAArch64MachObjectWriter(raw_ostream &OS,
5353 : MCMachObjectTargetWriter(Is64Bit, CPUType, CPUSubtype,
5454 /*UseAggressiveSymbolFolding=*/true) {}
5555
56 void RecordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
57 const MCAsmLayout &Layout, const MCFragment *Fragment,
58 const MCFixup &Fixup, MCValue Target,
59 uint64_t &FixedValue) override;
56 void RecordRelocation(MachObjectWriter *Writer,
57 const MCAssembler &Asm, const MCAsmLayout &Layout,
58 const MCFragment *Fragment, const MCFixup &Fixup,
59 MCValue Target, uint64_t &FixedValue) override;
6060 };
6161 }
6262
231231 (IsPCRel << 30) |
232232 MachO::R_SCATTERED);
233233 MRE.r_word1 = Value2;
234 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
234 Writer->addRelocation(Fragment->getParent(), MRE);
235235 }
236236
237237 MachO::any_relocation_info MRE;
242242 (IsPCRel << 30) |
243243 MachO::R_SCATTERED);
244244 MRE.r_word1 = Value;
245 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
245 Writer->addRelocation(Fragment->getParent(), MRE);
246246 }
247247
248248 void ARMMachObjectWriter::RecordARMScatteredRelocation(MachObjectWriter *Writer,
296296 (IsPCRel << 30) |
297297 MachO::R_SCATTERED);
298298 MRE.r_word1 = Value2;
299 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
299 Writer->addRelocation(Fragment->getParent(), MRE);
300300 }
301301
302302 MachO::any_relocation_info MRE;
306306 (IsPCRel << 30) |
307307 MachO::R_SCATTERED);
308308 MRE.r_word1 = Value;
309 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
309 Writer->addRelocation(Fragment->getParent(), MRE);
310310 }
311311
312312 bool ARMMachObjectWriter::requiresExternRelocation(MachObjectWriter *Writer,
350350 }
351351
352352 void ARMMachObjectWriter::RecordRelocation(MachObjectWriter *Writer,
353 MCAssembler &Asm,
353 const MCAssembler &Asm,
354354 const MCAsmLayout &Layout,
355355 const MCFragment *Fragment,
356 const MCFixup &Fixup, MCValue Target,
356 const MCFixup &Fixup,
357 MCValue Target,
357358 uint64_t &FixedValue) {
358359 unsigned IsPCRel = Writer->isFixupKindPCRel(Asm, Fixup.getKind());
359360 unsigned Log2Size;
399400 // See .
400401 uint32_t FixupOffset = Layout.getFragmentOffset(Fragment)+Fixup.getOffset();
401402 unsigned Index = 0;
403 unsigned IsExtern = 0;
402404 unsigned Type = 0;
403 const MCSymbolData *RelSymbol = nullptr;
404405
405406 if (Target.isAbsolute()) { // constant
406407 // FIXME!
420421 // Check whether we need an external or internal relocation.
421422 if (requiresExternRelocation(Writer, Asm, *Fragment, RelocType, SD,
422423 FixedValue)) {
423 RelSymbol = SD;
424 IsExtern = 1;
425 Index = SD->getIndex();
424426
425427 // For external relocations, make sure to offset the fixup value to
426428 // compensate for the addend of the symbol address, if it was
444446 // struct relocation_info (8 bytes)
445447 MachO::any_relocation_info MRE;
446448 MRE.r_word0 = FixupOffset;
447 MRE.r_word1 =
448 (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
449 MRE.r_word1 = ((Index << 0) |
450 (IsPCRel << 24) |
451 (Log2Size << 25) |
452 (IsExtern << 27) |
453 (Type << 28));
449454
450455 // Even when it's not a scattered relocation, movw/movt always uses
451456 // a PAIR relocation.
470475 (Log2Size << 25) |
471476 (MachO::ARM_RELOC_PAIR << 28));
472477
473 Writer->addRelocation(nullptr, Fragment->getParent(), MREPair);
474 }
475
476 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
478 Writer->addRelocation(Fragment->getParent(), MREPair);
479 }
480
481 Writer->addRelocation(Fragment->getParent(), MRE);
477482 }
478483
479484 MCObjectWriter *llvm::createARMMachObjectWriter(raw_ostream &OS,
4040 : MCMachObjectTargetWriter(Is64Bit, CPUType, CPUSubtype,
4141 /*UseAggressiveSymbolFolding=*/Is64Bit) {}
4242
43 void RecordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
43 void RecordRelocation(MachObjectWriter *Writer, const MCAssembler &Asm,
4444 const MCAsmLayout &Layout, const MCFragment *Fragment,
4545 const MCFixup &Fixup, MCValue Target,
4646 uint64_t &FixedValue) override {
281281 MachO::any_relocation_info MRE;
282282 makeScatteredRelocationInfo(MRE, other_half, MachO::GENERIC_RELOC_PAIR,
283283 Log2Size, IsPCRel, Value2);
284 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
284 Writer->addRelocation(Fragment->getParent(), MRE);
285285 } else {
286286 // If the offset is more than 24-bits, it won't fit in a scattered
287287 // relocation offset field, so we fall back to using a non-scattered
295295 }
296296 MachO::any_relocation_info MRE;
297297 makeScatteredRelocationInfo(MRE, FixupOffset, Type, Log2Size, IsPCRel, Value);
298 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
298 Writer->addRelocation(Fragment->getParent(), MRE);
299299 return true;
300300 }
301301
330330 // See .
331331 const uint32_t FixupOffset = getFixupOffset(Layout, Fragment, Fixup);
332332 unsigned Index = 0;
333 unsigned IsExtern = 0;
333334 unsigned Type = RelocType;
334335
335 const MCSymbolData *RelSymbol = nullptr;
336336 if (Target.isAbsolute()) { // constant
337337 // SymbolNum of 0 indicates the absolute section.
338338 //
354354
355355 // Check whether we need an external or internal relocation.
356356 if (Writer->doesSymbolRequireExternRelocation(SD)) {
357 RelSymbol = SD;
357 IsExtern = 1;
358 Index = SD->getIndex();
358359 // For external relocations, make sure to offset the fixup value to
359360 // compensate for the addend of the symbol address, if it was
360361 // undefined. This occurs with weak definitions, for example.
373374
374375 // struct relocation_info (8 bytes)
375376 MachO::any_relocation_info MRE;
376 makeRelocationInfo(MRE, FixupOffset, Index, IsPCRel, Log2Size, false, Type);
377 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
377 makeRelocationInfo(MRE, FixupOffset, Index, IsPCRel, Log2Size, IsExtern,
378 Type);
379 Writer->addRelocation(Fragment->getParent(), MRE);
378380 }
379381
380382 MCObjectWriter *llvm::createPPCMachObjectWriter(raw_ostream &OS, bool Is64Bit,
2828 const MCAsmLayout &Layout) override {
2929 //XXX: Implement if necessary.
3030 }
31 void RecordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
31 void RecordRelocation(const MCAssembler &Asm, const MCAsmLayout &Layout,
3232 const MCFragment *Fragment, const MCFixup &Fixup,
3333 MCValue Target, bool &IsPCRel,
3434 uint64_t &FixedValue) override {
776776 MachO::CPU_TYPE_X86_64, Subtype);
777777 }
778778
779 bool doesSectionRequireSymbols(const MCSection &Section) const override {
780 // Temporary labels in the string literals sections require symbols. The
781 // issue is that the x86_64 relocation format does not allow symbol +
782 // offset, and so the linker does not have enough information to resolve the
783 // access to the appropriate atom unless an external relocation is used. For
784 // non-cstring sections, we expect the compiler to use a non-temporary label
785 // for anything that could have an addend pointing outside the symbol.
786 //
787 // See .
788 const MCSectionMachO &SMO = static_cast(Section);
789 return SMO.getType() == MachO::S_CSTRING_LITERALS;
790 }
791
779792 /// \brief Generate the compact unwind encoding for the CFI instructions.
780793 uint32_t generateCompactUnwindEncoding(
781794 ArrayRef Instrs) const override {
99 #include "MCTargetDesc/X86MCTargetDesc.h"
1010 #include "MCTargetDesc/X86FixupKinds.h"
1111 #include "llvm/ADT/Twine.h"
12 #include "llvm/MC/MCAsmInfo.h"
1312 #include "llvm/MC/MCAsmLayout.h"
1413 #include "llvm/MC/MCAssembler.h"
1514 #include "llvm/MC/MCContext.h"
4746 const MCFixup &Fixup,
4847 MCValue Target,
4948 uint64_t &FixedValue);
50 void RecordX86_64Relocation(MachObjectWriter *Writer, MCAssembler &Asm,
49 void RecordX86_64Relocation(MachObjectWriter *Writer,
50 const MCAssembler &Asm,
5151 const MCAsmLayout &Layout,
52 const MCFragment *Fragment, const MCFixup &Fixup,
53 MCValue Target, uint64_t &FixedValue);
54
52 const MCFragment *Fragment,
53 const MCFixup &Fixup,
54 MCValue Target,
55 uint64_t &FixedValue);
5556 public:
5657 X86MachObjectWriter(bool Is64Bit, uint32_t CPUType,
5758 uint32_t CPUSubtype)
5859 : MCMachObjectTargetWriter(Is64Bit, CPUType, CPUSubtype,
5960 /*UseAggressiveSymbolFolding=*/Is64Bit) {}
6061
61 void RecordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
62 const MCAsmLayout &Layout, const MCFragment *Fragment,
63 const MCFixup &Fixup, MCValue Target,
64 uint64_t &FixedValue) override {
62 void RecordRelocation(MachObjectWriter *Writer,
63 const MCAssembler &Asm, const MCAsmLayout &Layout,
64 const MCFragment *Fragment, const MCFixup &Fixup,
65 MCValue Target, uint64_t &FixedValue) override {
6566 if (Writer->is64Bit())
6667 RecordX86_64Relocation(Writer, Asm, Layout, Fragment, Fixup, Target,
6768 FixedValue);
9596 }
9697 }
9798
98 void X86MachObjectWriter::RecordX86_64Relocation(
99 MachObjectWriter *Writer, MCAssembler &Asm, const MCAsmLayout &Layout,
100 const MCFragment *Fragment, const MCFixup &Fixup, MCValue Target,
101 uint64_t &FixedValue) {
99 void X86MachObjectWriter::RecordX86_64Relocation(MachObjectWriter *Writer,
100 const MCAssembler &Asm,
101 const MCAsmLayout &Layout,
102 const MCFragment *Fragment,
103 const MCFixup &Fixup,
104 MCValue Target,
105 uint64_t &FixedValue) {
102106 unsigned IsPCRel = Writer->isFixupKindPCRel(Asm, Fixup.getKind());
103107 unsigned IsRIPRel = isFixupKindRIPRel(Fixup.getKind());
104108 unsigned Log2Size = getFixupKindLog2Size(Fixup.getKind());
112116 unsigned Index = 0;
113117 unsigned IsExtern = 0;
114118 unsigned Type = 0;
115 const MCSymbolData *RelSymbol = nullptr;
116119
117120 Value = Target.getConstant();
118121
128131 if (Target.isAbsolute()) { // constant
129132 // SymbolNum of 0 indicates the absolute section.
130133 Type = MachO::X86_64_RELOC_UNSIGNED;
134 Index = 0;
131135
132136 // FIXME: I believe this is broken, I don't think the linker can understand
133137 // it. I think it would require a local relocation, but I'm not sure if that
188192 Value -= Writer->getSymbolAddress(&B_SD, Layout) -
189193 (!B_Base ? 0 : Writer->getSymbolAddress(B_Base, Layout));
190194
191 if (!A_Base)
195 if (A_Base) {
196 Index = A_Base->getIndex();
197 IsExtern = 1;
198 } else {
192199 Index = A_SD.getFragment()->getParent()->getOrdinal() + 1;
200 IsExtern = 0;
201 }
193202 Type = MachO::X86_64_RELOC_UNSIGNED;
194203
195204 MachO::any_relocation_info MRE;
196205 MRE.r_word0 = FixupOffset;
197 MRE.r_word1 =
198 (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
199 Writer->addRelocation(A_Base, Fragment->getParent(), MRE);
200
201 if (B_Base)
202 RelSymbol = B_Base;
203 else
206 MRE.r_word1 = ((Index << 0) |
207 (IsPCRel << 24) |
208 (Log2Size << 25) |
209 (IsExtern << 27) |
210 (Type << 28));
211 Writer->addRelocation(Fragment->getParent(), MRE);
212
213 if (B_Base) {
214 Index = B_Base->getIndex();
215 IsExtern = 1;
216 } else {
204217 Index = B_SD.getFragment()->getParent()->getOrdinal() + 1;
218 IsExtern = 0;
219 }
205220 Type = MachO::X86_64_RELOC_SUBTRACTOR;
206221 } else {
207222 const MCSymbol *Symbol = &Target.getSymA()->getSymbol();
208 if (Symbol->isTemporary() && Value) {
209 const MCSection &Sec = Symbol->getSection();
210 if (!Asm.getContext().getAsmInfo()->isSectionAtomizableBySymbols(Sec))
211 Asm.addLocalUsedInReloc(*Symbol);
212 }
213223 const MCSymbolData &SD = Asm.getSymbolData(*Symbol);
214 RelSymbol = Asm.getAtom(&SD);
224 const MCSymbolData *Base = Asm.getAtom(&SD);
215225
216226 // Relocations inside debug sections always use local relocations when
217227 // possible. This seems to be done because the debugger doesn't fully
221231 const MCSectionMachO &Section = static_cast(
222232 Fragment->getParent()->getSection());
223233 if (Section.hasAttribute(MachO::S_ATTR_DEBUG))
224 RelSymbol = nullptr;
234 Base = nullptr;
225235 }
226236
227237 // x86_64 almost always uses external relocations, except when there is no
228238 // symbol to use as a base address (a local symbol with no preceding
229239 // non-local symbol).
230 if (RelSymbol) {
240 if (Base) {
241 Index = Base->getIndex();
242 IsExtern = 1;
243
231244 // Add the local offset, if needed.
232 if (RelSymbol != &SD)
233 Value +=
234 Layout.getSymbolOffset(&SD) - Layout.getSymbolOffset(RelSymbol);
245 if (Base != &SD)
246 Value += Layout.getSymbolOffset(&SD) - Layout.getSymbolOffset(Base);
235247 } else if (Symbol->isInSection() && !Symbol->isVariable()) {
236248 // The index is the section ordinal (1-based).
237249 Index = SD.getFragment()->getParent()->getOrdinal() + 1;
250 IsExtern = 0;
238251 Value += Writer->getSymbolAddress(&SD, Layout);
239252
240253 if (IsPCRel)
333346 // struct relocation_info (8 bytes)
334347 MachO::any_relocation_info MRE;
335348 MRE.r_word0 = FixupOffset;
336 MRE.r_word1 = (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) |
337 (IsExtern << 27) | (Type << 28);
338 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
349 MRE.r_word1 = ((Index << 0) |
350 (IsPCRel << 24) |
351 (Log2Size << 25) |
352 (IsExtern << 27) |
353 (Type << 28));
354 Writer->addRelocation(Fragment->getParent(), MRE);
339355 }
340356
341357 bool X86MachObjectWriter::RecordScatteredRelocation(MachObjectWriter *Writer,
407423 (IsPCRel << 30) |
408424 MachO::R_SCATTERED);
409425 MRE.r_word1 = Value2;
410 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
426 Writer->addRelocation(Fragment->getParent(), MRE);
411427 } else {
412428 // If the offset is more than 24-bits, it won't fit in a scattered
413429 // relocation offset field, so we fall back to using a non-scattered
429445 (IsPCRel << 30) |
430446 MachO::R_SCATTERED);
431447 MRE.r_word1 = Value;
432 Writer->addRelocation(nullptr, Fragment->getParent(), MRE);
448 Writer->addRelocation(Fragment->getParent(), MRE);
433449 return true;
434450 }
435451
450466
451467 // Get the symbol data.
452468 const MCSymbolData *SD_A = &Asm.getSymbolData(Target.getSymA()->getSymbol());
469 unsigned Index = SD_A->getIndex();
453470
454471 // We're only going to have a second symbol in pic mode and it'll be a
455472 // subtraction from the picbase. For 32-bit pic the addend is the difference
472489 // struct relocation_info (8 bytes)
473490 MachO::any_relocation_info MRE;
474491 MRE.r_word0 = Value;
475 MRE.r_word1 =
476 (IsPCRel << 24) | (Log2Size << 25) | (MachO::GENERIC_RELOC_TLV << 28);
477 Writer->addRelocation(SD_A, Fragment->getParent(), MRE);
492 MRE.r_word1 = ((Index << 0) |
493 (IsPCRel << 24) |
494 (Log2Size << 25) |
495 (1 << 27) | // r_extern
496 (MachO::GENERIC_RELOC_TLV << 28)); // r_type
497 Writer->addRelocation(Fragment->getParent(), MRE);
478498 }
479499
480500 void X86MachObjectWriter::RecordX86Relocation(MachObjectWriter *Writer,
525545 // See .
526546 uint32_t FixupOffset = Layout.getFragmentOffset(Fragment)+Fixup.getOffset();
527547 unsigned Index = 0;
548 unsigned IsExtern = 0;
528549 unsigned Type = 0;
529 const MCSymbolData *RelSymbol = nullptr;
530550
531551 if (Target.isAbsolute()) { // constant
532552 // SymbolNum of 0 indicates the absolute section.
547567
548568 // Check whether we need an external or internal relocation.
549569 if (Writer->doesSymbolRequireExternRelocation(SD)) {
550 RelSymbol = SD;
570 IsExtern = 1;
571 Index = SD->getIndex();
551572 // For external relocations, make sure to offset the fixup value to
552573 // compensate for the addend of the symbol address, if it was
553574 // undefined. This occurs with weak definitions, for example.
569590 // struct relocation_info (8 bytes)
570591 MachO::any_relocation_info MRE;
571592 MRE.r_word0 = FixupOffset;
572 MRE.r_word1 =
573 (Index << 0) | (IsPCRel << 24) | (Log2Size << 25) | (Type << 28);
574 Writer->addRelocation(RelSymbol, Fragment->getParent(), MRE);
593 MRE.r_word1 = ((Index << 0) |
594 (IsPCRel << 24) |
595 (Log2Size << 25) |
596 (IsExtern << 27) |
597 (Type << 28));
598 Writer->addRelocation(Fragment->getParent(), MRE);
575599 }
576600
577601 MCObjectWriter *llvm::createX86MachObjectWriter(raw_ostream &OS,
+0
-59
test/MC/MachO/AArch64/mergeable.s less more
None // RUN: llvm-mc -triple aarch64-apple-darwin14 %s -filetype=obj -o - | llvm-readobj -r --expand-relocs | FileCheck %s
1
2 // Test that we "S + K" produce a relocation with a symbol, but just S produces
3 // a relocation with the section.
4
5 .section __TEXT,__literal4,4byte_literals
6 L0:
7 .long 42
8
9 .section __TEXT,__cstring,cstring_literals
10 L1:
11 .asciz "42"
12
13 .section __DATA,__data
14 .quad L0
15 .quad L0 + 1
16 .quad L1
17 .quad L1 + 1
18
19 // CHECK: Relocations [
20 // CHECK-NEXT: Section __data {
21 // CHECK-NEXT: Relocation {
22 // CHECK-NEXT: Offset: 0x18
23 // CHECK-NEXT: PCRel: 0
24 // CHECK-NEXT: Length: 3
25 // CHECK-NEXT: Extern: 1
26 // CHECK-NEXT: Type: ARM64_RELOC_UNSIGNED (0)
27 // CHECK-NEXT: Symbol: L1
28 // CHECK-NEXT: Scattered: 0
29 // CHECK-NEXT: }
30 // CHECK-NEXT: Relocation {
31 // CHECK-NEXT: Offset: 0x10
32 // CHECK-NEXT: PCRel: 0
33 // CHECK-NEXT: Length: 3
34 // CHECK-NEXT: Extern: 0
35 // CHECK-NEXT: Type: ARM64_RELOC_UNSIGNED (0)
36 // CHECK-NEXT: Symbol: 0x3
37 // CHECK-NEXT: Scattered: 0
38 // CHECK-NEXT: }
39 // CHECK-NEXT: Relocation {
40 // CHECK-NEXT: Offset: 0x8
41 // CHECK-NEXT: PCRel: 0
42 // CHECK-NEXT: Length: 3
43 // CHECK-NEXT: Extern: 1
44 // CHECK-NEXT: Type: ARM64_RELOC_UNSIGNED (0)
45 // CHECK-NEXT: Symbol: L0
46 // CHECK-NEXT: Scattered: 0
47 // CHECK-NEXT: }
48 // CHECK-NEXT: Relocation {
49 // CHECK-NEXT: Offset: 0x0
50 // CHECK-NEXT: PCRel: 0
51 // CHECK-NEXT: Length: 3
52 // CHECK-NEXT: Extern: 0
53 // CHECK-NEXT: Type: ARM64_RELOC_UNSIGNED (0)
54 // CHECK-NEXT: Symbol: 0x2
55 // CHECK-NEXT: Scattered: 0
56 // CHECK-NEXT: }
57 // CHECK-NEXT: }
58 // CHECK-NEXT: ]
+0
-59
test/MC/MachO/x86_64-mergeable.s less more
None // RUN: llvm-mc -triple x86_64-apple-darwin14 %s -filetype=obj -o - | llvm-readobj -r --expand-relocs | FileCheck %s
1
2 // Test that we "S + K" produce a relocation with a symbol, but just S produces
3 // a relocation with the section.
4
5 .section __TEXT,__literal4,4byte_literals
6 L0:
7 .long 42
8
9 .section __TEXT,__cstring,cstring_literals
10 L1:
11 .asciz "42"
12
13 .section __DATA,__data
14 .quad L0
15 .quad L0 + 1
16 .quad L1
17 .quad L1 + 1
18
19 // CHECK: Relocations [
20 // CHECK-NEXT: Section __data {
21 // CHECK-NEXT: Relocation {
22 // CHECK-NEXT: Offset: 0x18
23 // CHECK-NEXT: PCRel: 0
24 // CHECK-NEXT: Length: 3
25 // CHECK-NEXT: Extern: 1
26 // CHECK-NEXT: Type: X86_64_RELOC_UNSIGNED (0)
27 // CHECK-NEXT: Symbol: L1
28 // CHECK-NEXT: Scattered: 0
29 // CHECK-NEXT: }
30 // CHECK-NEXT: Relocation {
31 // CHECK-NEXT: Offset: 0x10
32 // CHECK-NEXT: PCRel: 0
33 // CHECK-NEXT: Length: 3
34 // CHECK-NEXT: Extern: 0
35 // CHECK-NEXT: Type: X86_64_RELOC_UNSIGNED (0)
36 // CHECK-NEXT: Symbol: 0x3
37 // CHECK-NEXT: Scattered: 0
38 // CHECK-NEXT: }
39 // CHECK-NEXT: Relocation {
40 // CHECK-NEXT: Offset: 0x8
41 // CHECK-NEXT: PCRel: 0
42 // CHECK-NEXT: Length: 3
43 // CHECK-NEXT: Extern: 1
44 // CHECK-NEXT: Type: X86_64_RELOC_UNSIGNED (0)
45 // CHECK-NEXT: Symbol: L0
46 // CHECK-NEXT: Scattered: 0
47 // CHECK-NEXT: }
48 // CHECK-NEXT: Relocation {
49 // CHECK-NEXT: Offset: 0x0
50 // CHECK-NEXT: PCRel: 0
51 // CHECK-NEXT: Length: 3
52 // CHECK-NEXT: Extern: 0
53 // CHECK-NEXT: Type: X86_64_RELOC_UNSIGNED (0)
54 // CHECK-NEXT: Symbol: 0x2
55 // CHECK-NEXT: Scattered: 0
56 // CHECK-NEXT: }
57 // CHECK-NEXT: }
58 // CHECK-NEXT: ]
120120 //L39:
121121 //D39:
122122
123 .section foo, bar
124 .long L4 + 1
125 .long L35 + 1
126 .long L36 + 1
127 .long L37 + 1
128 .long L38 + 1
129123
130124 // CHECK: Symbols [
131125 // CHECK-NEXT: Symbol {