LLVM  14.0.0git
MCMachObjectWriter.h
Go to the documentation of this file.
1 //===- llvm/MC/MCMachObjectWriter.h - Mach Object Writer --------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef LLVM_MC_MCMACHOBJECTWRITER_H
10 #define LLVM_MC_MCMACHOBJECTWRITER_H
11 
12 #include "llvm/ADT/DenseMap.h"
13 #include "llvm/ADT/StringRef.h"
15 #include "llvm/MC/MCExpr.h"
16 #include "llvm/MC/MCObjectWriter.h"
17 #include "llvm/MC/MCSection.h"
20 #include <cstdint>
21 #include <memory>
22 #include <string>
23 #include <vector>
24 
25 namespace llvm {
26 
27 class MachObjectWriter;
28 
30  const unsigned Is64Bit : 1;
31  const uint32_t CPUType;
32 protected:
34 public:
36 
37 protected:
38  MCMachObjectTargetWriter(bool Is64Bit_, uint32_t CPUType_,
39  uint32_t CPUSubtype_);
40 
43  }
44 
45 public:
46  virtual ~MCMachObjectTargetWriter();
47 
48  Triple::ObjectFormatType getFormat() const override { return Triple::MachO; }
49  static bool classof(const MCObjectTargetWriter *W) {
50  return W->getFormat() == Triple::MachO;
51  }
52 
53  /// \name Lifetime Management
54  /// @{
55 
56  virtual void reset() {}
57 
58  /// @}
59 
60  /// \name Accessors
61  /// @{
62 
63  bool is64Bit() const { return Is64Bit; }
64  uint32_t getCPUType() const { return CPUType; }
65  uint32_t getCPUSubtype() const { return CPUSubtype; }
67  return LocalDifference_RIT;
68  }
69 
70  /// @}
71 
72  /// \name API
73  /// @{
74 
75  virtual void recordRelocation(MachObjectWriter *Writer, MCAssembler &Asm,
76  const MCAsmLayout &Layout,
77  const MCFragment *Fragment,
78  const MCFixup &Fixup, MCValue Target,
79  uint64_t &FixedValue) = 0;
80 
81  /// @}
82 };
83 
85  /// Helper struct for containing some precomputed information on symbols.
86  struct MachSymbolData {
87  const MCSymbol *Symbol;
88  uint64_t StringIndex;
89  uint8_t SectionIndex;
90 
91  // Support lexicographic sorting.
92  bool operator<(const MachSymbolData &RHS) const;
93  };
94 
95  /// The target specific Mach-O writer instance.
96  std::unique_ptr<MCMachObjectTargetWriter> TargetObjectWriter;
97 
98  /// \name Relocation Data
99  /// @{
100 
101  struct RelAndSymbol {
102  const MCSymbol *Sym;
104  RelAndSymbol(const MCSymbol *Sym, const MachO::any_relocation_info &MRE)
105  : Sym(Sym), MRE(MRE) {}
106  };
107 
110 
111  SectionAddrMap SectionAddress;
112 
113  /// @}
114  /// \name Symbol Table Data
115  /// @{
116 
117  StringTableBuilder StringTable;
118  std::vector<MachSymbolData> LocalSymbolData;
119  std::vector<MachSymbolData> ExternalSymbolData;
120  std::vector<MachSymbolData> UndefinedSymbolData;
121 
122  /// @}
123 
124  MachSymbolData *findSymbolData(const MCSymbol &Sym);
125 
126  void writeWithPadding(StringRef Str, uint64_t Size);
127 
128 public:
129  MachObjectWriter(std::unique_ptr<MCMachObjectTargetWriter> MOTW,
130  raw_pwrite_stream &OS, bool IsLittleEndian)
131  : TargetObjectWriter(std::move(MOTW)),
132  StringTable(TargetObjectWriter->is64Bit() ? StringTableBuilder::MachO64
133  : StringTableBuilder::MachO),
134  W(OS, IsLittleEndian ? support::little : support::big) {}
135 
137 
138  const MCSymbol &findAliasedSymbol(const MCSymbol &Sym) const;
139 
140  /// \name Lifetime management Methods
141  /// @{
142 
143  void reset() override;
144 
145  /// @}
146 
147  /// \name Utility Methods
148  /// @{
149 
150  bool isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind);
151 
152  SectionAddrMap &getSectionAddressMap() { return SectionAddress; }
153 
154  uint64_t getSectionAddress(const MCSection *Sec) const {
155  return SectionAddress.lookup(Sec);
156  }
157  uint64_t getSymbolAddress(const MCSymbol &S, const MCAsmLayout &Layout) const;
158 
159  uint64_t getFragmentAddress(const MCFragment *Fragment,
160  const MCAsmLayout &Layout) const;
161 
162  uint64_t getPaddingSize(const MCSection *SD, const MCAsmLayout &Layout) const;
163 
165 
166  /// @}
167 
168  /// \name Target Writer Proxy Accessors
169  /// @{
170 
171  bool is64Bit() const { return TargetObjectWriter->is64Bit(); }
172  bool isX86_64() const {
173  uint32_t CPUType = TargetObjectWriter->getCPUType();
175  }
176 
177  /// @}
178 
179  void writeHeader(MachO::HeaderFileType Type, unsigned NumLoadCommands,
180  unsigned LoadCommandsSize, bool SubsectionsViaSymbols);
181 
182  /// Write a segment load command.
183  ///
184  /// \param NumSections The number of sections in this segment.
185  /// \param SectionDataSize The total size of the sections.
186  void writeSegmentLoadCommand(StringRef Name, unsigned NumSections,
187  uint64_t VMAddr, uint64_t VMSize,
188  uint64_t SectionDataStartOffset,
189  uint64_t SectionDataSize, uint32_t MaxProt,
190  uint32_t InitProt);
191 
192  void writeSection(const MCAsmLayout &Layout, const MCSection &Sec,
193  uint64_t VMAddr, uint64_t FileOffset, unsigned Flags,
194  uint64_t RelocationsStart, unsigned NumRelocations);
195 
196  void writeSymtabLoadCommand(uint32_t SymbolOffset, uint32_t NumSymbols,
197  uint32_t StringTableOffset,
198  uint32_t StringTableSize);
199 
201  uint32_t FirstLocalSymbol, uint32_t NumLocalSymbols,
202  uint32_t FirstExternalSymbol, uint32_t NumExternalSymbols,
203  uint32_t FirstUndefinedSymbol, uint32_t NumUndefinedSymbols,
204  uint32_t IndirectSymbolOffset, uint32_t NumIndirectSymbols);
205 
206  void writeNlist(MachSymbolData &MSD, const MCAsmLayout &Layout);
207 
209  uint32_t DataSize);
210 
211  void writeLinkerOptionsLoadCommand(const std::vector<std::string> &Options);
212 
213  // FIXME: We really need to improve the relocation validation. Basically, we
214  // want to implement a separate computation which evaluates the relocation
215  // entry as the linker would, and verifies that the resultant fixup value is
216  // exactly what the encoder wanted. This will catch several classes of
217  // problems:
218  //
219  // - Relocation entry bugs, the two algorithms are unlikely to have the same
220  // exact bug.
221  //
222  // - Relaxation issues, where we forget to relax something.
223  //
224  // - Input errors, where something cannot be correctly encoded. 'as' allows
225  // these through in many cases.
226 
227  // Add a relocation to be output in the object file. At the time this is
228  // called, the symbol indexes are not know, so if the relocation refers
229  // to a symbol it should be passed as \p RelSymbol so that it can be updated
230  // afterwards. If the relocation doesn't refer to a symbol, nullptr should be
231  // used.
232  void addRelocation(const MCSymbol *RelSymbol, const MCSection *Sec,
234  RelAndSymbol P(RelSymbol, MRE);
235  Relocations[Sec].push_back(P);
236  }
237 
238  void recordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout,
239  const MCFragment *Fragment, const MCFixup &Fixup,
240  MCValue Target, uint64_t &FixedValue) override;
241 
243 
244  /// Compute the symbol table data.
246  std::vector<MachSymbolData> &LocalSymbolData,
247  std::vector<MachSymbolData> &ExternalSymbolData,
248  std::vector<MachSymbolData> &UndefinedSymbolData);
249 
251  const MCAsmLayout &Layout);
252 
254  const MCAsmLayout &Layout) override;
255 
257  const MCSymbol &A,
258  const MCSymbol &B,
259  bool InSet) const override;
260 
262  const MCSymbol &SymA,
263  const MCFragment &FB, bool InSet,
264  bool IsPCRel) const override;
265 
266  uint64_t writeObject(MCAssembler &Asm, const MCAsmLayout &Layout) override;
267 };
268 
269 /// Construct a new Mach-O writer instance.
270 ///
271 /// This routine takes ownership of the target writer subclass.
272 ///
273 /// \param MOTW - The target specific Mach-O writer subclass.
274 /// \param OS - The stream to write to.
275 /// \returns The constructed object writer.
276 std::unique_ptr<MCObjectWriter>
277 createMachObjectWriter(std::unique_ptr<MCMachObjectTargetWriter> MOTW,
278  raw_pwrite_stream &OS, bool IsLittleEndian);
279 
280 } // end namespace llvm
281 
282 #endif // LLVM_MC_MCMACHOBJECTWRITER_H
llvm::Check::Size
@ Size
Definition: FileCheck.h:73
llvm::MachObjectWriter::writeNlist
void writeNlist(MachSymbolData &MSD, const MCAsmLayout &Layout)
Definition: MachObjectWriter.cpp:338
llvm
---------------------— PointerInfo ------------------------------------—
Definition: AllocatorList.h:23
llvm::MachO::any_relocation_info
Definition: MachO.h:975
llvm::MCSymbol
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
Definition: MCSymbol.h:41
llvm::MachObjectWriter::writeLinkeditLoadCommand
void writeLinkeditLoadCommand(uint32_t Type, uint32_t DataOffset, uint32_t DataSize)
Definition: MachObjectWriter.cpp:407
llvm::DenseMapBase::lookup
ValueT lookup(const_arg_type_t< KeyT > Val) const
lookup - Return the entry for the specified key, or a default constructed value if no such entry exis...
Definition: DenseMap.h:197
StringRef.h
P
This currently compiles esp xmm0 movsd esp eax eax esp ret We should use not the dag combiner This is because dagcombine2 needs to be able to see through the X86ISD::Wrapper which DAGCombine can t really do The code for turning x load into a single vector load is target independent and should be moved to the dag combiner The code for turning x load into a vector load can only handle a direct load from a global or a direct load from the stack It should be generalized to handle any load from P
Definition: README-SSE.txt:411
llvm::Target
Target - Wrapper for Target specific information.
Definition: TargetRegistry.h:137
llvm::RISCVFenceField::W
@ W
Definition: RISCVBaseInfo.h:181
llvm::MCMachObjectTargetWriter::MCMachObjectTargetWriter
MCMachObjectTargetWriter(bool Is64Bit_, uint32_t CPUType_, uint32_t CPUSubtype_)
Definition: MCMachObjectTargetWriter.cpp:13
llvm::MCMachObjectTargetWriter::getCPUType
uint32_t getCPUType() const
Definition: MCMachObjectWriter.h:64
llvm::Type
The instances of the Type class are immutable: once they are created, they are never changed.
Definition: Type.h:45
DenseMap.h
llvm::MachObjectWriter::doesSymbolRequireExternRelocation
bool doesSymbolRequireExternRelocation(const MCSymbol &S)
Definition: MachObjectWriter.cpp:55
llvm::MachO::CPUType
CPUType
Definition: MachO.h:1418
llvm::support::endian::Writer
Adapter to write values to a stream in a particular byte order.
Definition: EndianStream.h:52
llvm::MCMachObjectTargetWriter::reset
virtual void reset()
Definition: MCMachObjectWriter.h:56
llvm::MachObjectWriter::writeObject
uint64_t writeObject(MCAssembler &Asm, const MCAsmLayout &Layout) override
Write the object file and returns the number of bytes written.
Definition: MachObjectWriter.cpp:754
llvm::MachO::CPU_TYPE_X86_64
@ CPU_TYPE_X86_64
Definition: MachO.h:1422
llvm::MachObjectWriter::computeSectionAddresses
void computeSectionAddresses(const MCAssembler &Asm, const MCAsmLayout &Layout)
Definition: MachObjectWriter.cpp:642
llvm::MCFragment
Definition: MCFragment.h:31
StringTableBuilder.h
llvm::MCObjectTargetWriter
Base class for classes that define behaviour that is specific to both the target and the object forma...
Definition: MCObjectWriter.h:112
llvm::support::little
@ little
Definition: Endian.h:27
llvm::MachObjectWriter
Definition: MCMachObjectWriter.h:84
llvm::MachObjectWriter::MachObjectWriter
MachObjectWriter(std::unique_ptr< MCMachObjectTargetWriter > MOTW, raw_pwrite_stream &OS, bool IsLittleEndian)
Definition: MCMachObjectWriter.h:129
B
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
Options
const char LLVMTargetMachineRef LLVMPassBuilderOptionsRef Options
Definition: PassBuilderBindings.cpp:48
llvm::MCMachObjectTargetWriter::~MCMachObjectTargetWriter
virtual ~MCMachObjectTargetWriter()
llvm::MachObjectWriter::isFixupKindPCRel
bool isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind)
Definition: MachObjectWriter.cpp:74
llvm::MCMachObjectTargetWriter::setLocalDifferenceRelocationType
void setLocalDifferenceRelocationType(unsigned Type)
Definition: MCMachObjectWriter.h:41
llvm::MachObjectWriter::getSectionAddressMap
SectionAddrMap & getSectionAddressMap()
Definition: MCMachObjectWriter.h:152
llvm::lltok::Kind
Kind
Definition: LLToken.h:18
llvm::MachO::HeaderFileType
HeaderFileType
Definition: MachO.h:40
llvm::createMachObjectWriter
std::unique_ptr< MCObjectWriter > createMachObjectWriter(std::unique_ptr< MCMachObjectTargetWriter > MOTW, raw_pwrite_stream &OS, bool IsLittleEndian)
Construct a new Mach-O writer instance.
Definition: MachObjectWriter.cpp:1048
llvm::MachObjectWriter::executePostLayoutBinding
void executePostLayoutBinding(MCAssembler &Asm, const MCAsmLayout &Layout) override
Perform any late binding of symbols (for example, to assign symbol indices for use when generating re...
Definition: MachObjectWriter.cpp:657
llvm::MachObjectWriter::getPaddingSize
uint64_t getPaddingSize(const MCSection *SD, const MCAsmLayout &Layout) const
Definition: MachObjectWriter.cpp:120
llvm::MachObjectWriter::isSymbolRefDifferenceFullyResolvedImpl
bool isSymbolRefDifferenceFullyResolvedImpl(const MCAssembler &Asm, const MCSymbol &A, const MCSymbol &B, bool InSet) const override
Definition: MachObjectWriter.cpp:665
llvm::MCAssembler
Definition: MCAssembler.h:60
llvm::MachObjectWriter::is64Bit
bool is64Bit() const
Definition: MCMachObjectWriter.h:171
llvm::MachObjectWriter::getFragmentAddress
uint64_t getFragmentAddress(const MCFragment *Fragment, const MCAsmLayout &Layout) const
Definition: MachObjectWriter.cpp:81
llvm::raw_pwrite_stream
An abstract base class for streams implementations that also support a pwrite operation.
Definition: raw_ostream.h:415
llvm::MCMachObjectTargetWriter::recordRelocation
virtual void recordRelocation(MachObjectWriter *Writer, MCAssembler &Asm, const MCAsmLayout &Layout, const MCFragment *Fragment, const MCFixup &Fixup, MCValue Target, uint64_t &FixedValue)=0
llvm::MachObjectWriter::writeLinkerOptionsLoadCommand
void writeLinkerOptionsLoadCommand(const std::vector< std::string > &Options)
Definition: MachObjectWriter.cpp:430
llvm::DenseMap
Definition: DenseMap.h:714
llvm::operator<
bool operator<(int64_t V1, const APSInt &V2)
Definition: APSInt.h:338
llvm::MachObjectWriter::writeHeader
void writeHeader(MachO::HeaderFileType Type, unsigned NumLoadCommands, unsigned LoadCommandsSize, bool SubsectionsViaSymbols)
Definition: MachObjectWriter.cpp:133
llvm::MCMachObjectTargetWriter
Definition: MCMachObjectWriter.h:29
llvm::MCMachObjectTargetWriter::classof
static bool classof(const MCObjectTargetWriter *W)
Definition: MCMachObjectWriter.h:49
llvm::MachObjectWriter::writeDysymtabLoadCommand
void writeDysymtabLoadCommand(uint32_t FirstLocalSymbol, uint32_t NumLocalSymbols, uint32_t FirstExternalSymbol, uint32_t NumExternalSymbols, uint32_t FirstUndefinedSymbol, uint32_t NumUndefinedSymbols, uint32_t IndirectSymbolOffset, uint32_t NumIndirectSymbols)
Definition: MachObjectWriter.cpp:278
llvm::MCMachObjectTargetWriter::getFormat
Triple::ObjectFormatType getFormat() const override
Definition: MCMachObjectWriter.h:48
llvm::MachObjectWriter::writeSymtabLoadCommand
void writeSymtabLoadCommand(uint32_t SymbolOffset, uint32_t NumSymbols, uint32_t StringTableOffset, uint32_t StringTableSize)
Definition: MachObjectWriter.cpp:259
llvm::move
OutputIt move(R &&Range, OutputIt Out)
Provide wrappers to std::move which take ranges instead of having to pass begin/end explicitly.
Definition: STLExtras.h:1605
MCSection.h
llvm::StringRef
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:58
uint32_t
llvm::MCMachObjectTargetWriter::getCPUSubtype
uint32_t getCPUSubtype() const
Definition: MCMachObjectWriter.h:65
llvm::MCObjectWriter
Defines the object file and target independent interfaces used by the assembler backend to write nati...
Definition: MCObjectWriter.h:33
llvm::MCSection
Instances of this class represent a uniqued identifier for a section in the current translation unit.
Definition: MCSection.h:39
S
add sub stmia L5 ldr r0 bl L_printf $stub Instead of a and a wouldn t it be better to do three moves *Return an aggregate type is even return S
Definition: README.txt:210
llvm::MachObjectWriter::getSymbolAddress
uint64_t getSymbolAddress(const MCSymbol &S, const MCAsmLayout &Layout) const
Definition: MachObjectWriter.cpp:87
llvm::Triple::ObjectFormatType
ObjectFormatType
Definition: Triple.h:231
llvm::MCMachObjectTargetWriter::LocalDifference_RIT
unsigned LocalDifference_RIT
Definition: MCMachObjectWriter.h:35
MCObjectWriter.h
llvm::MCMachObjectTargetWriter::CPUSubtype
uint32_t CPUSubtype
Definition: MCMachObjectWriter.h:33
llvm::GraphProgram::Name
Name
Definition: GraphWriter.h:52
std
Definition: BitVector.h:838
EndianStream.h
llvm::MCAsmLayout
Encapsulates the layout of an assembly file at a particular point in time.
Definition: MCAsmLayout.h:28
llvm::Triple::MachO
@ MachO
Definition: Triple.h:237
llvm::StringTableBuilder
Utility for building string tables with deduplicated suffixes.
Definition: StringTableBuilder.h:23
llvm::MachObjectWriter::reset
void reset() override
lifetime management
Definition: MachObjectWriter.cpp:45
llvm::MachObjectWriter::addRelocation
void addRelocation(const MCSymbol *RelSymbol, const MCSection *Sec, MachO::any_relocation_info &MRE)
Definition: MCMachObjectWriter.h:232
llvm::MachObjectWriter::W
support::endian::Writer W
Definition: MCMachObjectWriter.h:136
llvm::ARMBuildAttrs::Symbol
@ Symbol
Definition: ARMBuildAttributes.h:79
llvm::MachObjectWriter::findAliasedSymbol
const MCSymbol & findAliasedSymbol(const MCSymbol &Sym) const
Definition: MachObjectWriter.cpp:326
llvm::MachObjectWriter::getSectionAddress
uint64_t getSectionAddress(const MCSection *Sec) const
Definition: MCMachObjectWriter.h:154
support
Reimplement select in terms of SEL *We would really like to support but we need to prove that the add doesn t need to overflow between the two bit chunks *Implement pre post increment support(e.g. PR935) *Implement smarter const ant generation for binops with large immediates. A few ARMv6T2 ops should be pattern matched
Definition: README.txt:10
llvm::MachObjectWriter::computeSymbolTable
void computeSymbolTable(MCAssembler &Asm, std::vector< MachSymbolData > &LocalSymbolData, std::vector< MachSymbolData > &ExternalSymbolData, std::vector< MachSymbolData > &UndefinedSymbolData)
Compute the symbol table data.
Definition: MachObjectWriter.cpp:541
llvm::MachObjectWriter::recordRelocation
void recordRelocation(MCAssembler &Asm, const MCAsmLayout &Layout, const MCFragment *Fragment, const MCFixup &Fixup, MCValue Target, uint64_t &FixedValue) override
Record a relocation entry.
Definition: MachObjectWriter.cpp:462
llvm::HexStyle::Asm
@ Asm
0ffh
Definition: MCInstPrinter.h:34
llvm::MCValue
This represents an "assembler immediate".
Definition: MCValue.h:37
MachO.h
llvm::MachObjectWriter::isX86_64
bool isX86_64() const
Definition: MCMachObjectWriter.h:172
MCExpr.h
llvm::MCFixup
Encode information on a single operation to perform on a byte sequence (e.g., an encoded instruction)...
Definition: MCFixup.h:71
llvm::MachObjectWriter::writeSegmentLoadCommand
void writeSegmentLoadCommand(StringRef Name, unsigned NumSections, uint64_t VMAddr, uint64_t VMSize, uint64_t SectionDataStartOffset, uint64_t SectionDataSize, uint32_t MaxProt, uint32_t InitProt)
Write a segment load command.
Definition: MachObjectWriter.cpp:174
llvm::MachObjectWriter::writeSection
void writeSection(const MCAsmLayout &Layout, const MCSection &Sec, uint64_t VMAddr, uint64_t FileOffset, unsigned Flags, uint64_t RelocationsStart, unsigned NumRelocations)
Definition: MachObjectWriter.cpp:214
llvm::MCMachObjectTargetWriter::getLocalDifferenceRelocationType
unsigned getLocalDifferenceRelocationType() const
Definition: MCMachObjectWriter.h:66
llvm::support::big
@ big
Definition: Endian.h:27
llvm::MachObjectWriter::bindIndirectSymbols
void bindIndirectSymbols(MCAssembler &Asm)
Definition: MachObjectWriter.cpp:477
llvm::MCMachObjectTargetWriter::is64Bit
bool is64Bit() const
Definition: MCMachObjectWriter.h:63