]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - include/lld/Core/DefinedAtom.h
Vendor import of lld trunk r233088:
[FreeBSD/FreeBSD.git] / include / lld / Core / DefinedAtom.h
1 //===- Core/DefinedAtom.h - An Atom with content --------------------------===//
2 //
3 //                             The LLVM Linker
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 #ifndef LLD_CORE_DEFINED_ATOM_H
11 #define LLD_CORE_DEFINED_ATOM_H
12
13 #include "lld/Core/Atom.h"
14 #include "lld/Core/LLVM.h"
15
16 namespace lld {
17 class File;
18 class Reference;
19
20 /// \brief The fundamental unit of linking.
21 ///
22 /// A C function or global variable is an atom.  An atom has content and
23 /// attributes. The content of a function atom is the instructions that
24 /// implement the function.  The content of a global variable atom is its
25 /// initial bytes.
26 ///
27 /// Here are some example attribute sets for common atoms. If a particular
28 /// attribute is not listed, the default values are:  definition=regular,
29 /// sectionChoice=basedOnContent, scope=translationUnit, merge=no,
30 /// deadStrip=normal, interposable=no
31 ///
32 ///  C function:  void foo() {} <br>
33 ///    name=foo, type=code, perm=r_x, scope=global
34 ///
35 ///  C static function:  staic void func() {} <br>
36 ///    name=func, type=code, perm=r_x
37 ///
38 ///  C global variable:  int count = 1; <br>
39 ///    name=count, type=data, perm=rw_, scope=global
40 ///
41 ///  C tentative definition:  int bar; <br>
42 ///    name=bar, type=zerofill, perm=rw_, scope=global,
43 ///    merge=asTentative, interposable=yesAndRuntimeWeak
44 ///
45 ///  Uninitialized C static variable:  static int stuff; <br>
46 ///    name=stuff, type=zerofill, perm=rw_
47 ///
48 ///  Weak C function:  __attribute__((weak)) void foo() {} <br>
49 ///    name=foo, type=code, perm=r_x, scope=global, merge=asWeak
50 ///
51 ///  Hidden C function:  __attribute__((visibility("hidden"))) void foo() {}<br>
52 ///    name=foo, type=code, perm=r_x, scope=linkageUnit
53 ///
54 ///  No-dead-strip function:  __attribute__((used)) void foo() {} <br>
55 ///    name=foo, type=code, perm=r_x, scope=global, deadStrip=never
56 ///
57 ///  Non-inlined C++ inline method:  inline void Foo::doit() {} <br>
58 ///    name=_ZN3Foo4doitEv, type=code, perm=r_x, scope=global,
59 ///    mergeDupes=asWeak
60 ///
61 ///  Non-inlined C++ inline method whose address is taken:
62 ///     inline void Foo::doit() {} <br>
63 ///    name=_ZN3Foo4doitEv, type=code, perm=r_x, scope=global,
64 ///    mergeDupes=asAddressedWeak
65 ///
66 ///  literal c-string:  "hello" <br>
67 ///    name="" type=cstring, perm=r__, scope=linkageUnit
68 ///
69 ///  literal double:  1.234 <br>
70 ///    name="" type=literal8, perm=r__, scope=linkageUnit
71 ///
72 ///  constant:  { 1,2,3 } <br>
73 ///    name="" type=constant, perm=r__, scope=linkageUnit
74 ///
75 ///  Pointer to initializer function:  <br>
76 ///    name="" type=initializer, perm=rw_l,
77 ///    sectionChoice=customRequired
78 ///
79 ///  C function place in custom section:  __attribute__((section("__foo")))
80 ///                                       void foo() {} <br>
81 ///    name=foo, type=code, perm=r_x, scope=global,
82 ///    sectionChoice=customRequired, customSectionName=__foo
83 ///
84 class DefinedAtom : public Atom {
85 public:
86   enum Interposable {
87     interposeNo,            // linker can directly bind uses of this atom
88     interposeYes,           // linker must indirect (through GOT) uses
89     interposeYesAndRuntimeWeak // must indirect and mark symbol weak in final
90                                // linked image
91   };
92
93   enum Merge {
94     mergeNo,                // Another atom with same name is error
95     mergeAsTentative,       // Is ANSI C tentative definition, can be coalesced
96     mergeAsWeak,            // Is C++ inline definition that was not inlined,
97                             // but address was not taken, so atom can be hidden
98                             // by linker
99     mergeAsWeakAndAddressUsed, // Is C++ definition inline definition whose
100                                // address was taken.
101     mergeSameNameAndSize,   // Another atom with different size is error
102     mergeByLargestSection,  // Choose an atom whose section is the largest.
103     mergeByContent,         // Merge with other constants with same content.
104   };
105
106   enum ContentType {
107     typeUnknown,            // for use with definitionUndefined
108     typeCode,               // executable code
109     typeResolver,           // function which returns address of target
110     typeBranchIsland,       // linker created for large binaries
111     typeBranchShim,         // linker created to switch thumb mode
112     typeStub,               // linker created for calling external function
113     typeStubHelper,         // linker created for initial stub binding
114     typeConstant,           // a read-only constant
115     typeCString,            // a zero terminated UTF8 C string
116     typeUTF16String,        // a zero terminated UTF16 string
117     typeCFI,                // a FDE or CIE from dwarf unwind info
118     typeLSDA,               // extra unwinding info
119     typeLiteral4,           // a four-btye read-only constant
120     typeLiteral8,           // an eight-btye read-only constant
121     typeLiteral16,          // a sixteen-btye read-only constant
122     typeData,               // read-write data
123     typeDataFast,           // allow data to be quickly accessed
124     typeZeroFill,           // zero-fill data
125     typeZeroFillFast,       // allow zero-fill data to be quicky accessed
126     typeConstData,          // read-only data after dynamic linker is done
127     typeObjC1Class,         // ObjC1 class [Darwin]
128     typeLazyPointer,        // pointer through which a stub jumps
129     typeLazyDylibPointer,   // pointer through which a stub jumps [Darwin]
130     typeCFString,           // NS/CFString object [Darwin]
131     typeGOT,                // pointer to external symbol
132     typeInitializerPtr,     // pointer to initializer function
133     typeTerminatorPtr,      // pointer to terminator function
134     typeCStringPtr,         // pointer to UTF8 C string [Darwin]
135     typeObjCClassPtr,       // pointer to ObjC class [Darwin]
136     typeObjC2CategoryList,  // pointers to ObjC category [Darwin]
137     typeDTraceDOF,          // runtime data for Dtrace [Darwin]
138     typeInterposingTuples,  // tuples of interposing info for dyld [Darwin]
139     typeTempLTO,            // temporary atom for bitcode reader
140     typeCompactUnwindInfo,  // runtime data for unwinder [Darwin]
141     typeProcessedUnwindInfo,// compressed compact unwind info [Darwin]
142     typeThunkTLV,           // thunk used to access a TLV [Darwin]
143     typeTLVInitialData,     // initial data for a TLV [Darwin]
144     typeTLVInitialZeroFill, // TLV initial zero fill data [Darwin]
145     typeTLVInitializerPtr,  // pointer to thread local initializer [Darwin]
146     typeMachHeader,         // atom representing mach_header [Darwin]
147     typeThreadZeroFill,     // Uninitialized thread local data(TBSS) [ELF]
148     typeThreadData,         // Initialized thread local data(TDATA) [ELF]
149     typeRONote,             // Identifies readonly note sections [ELF]
150     typeRWNote,             // Identifies readwrite note sections [ELF]
151     typeNoAlloc,            // Identifies non allocatable sections [ELF]
152     typeGroupComdat,        // Identifies a section group [ELF, COFF]
153     typeGnuLinkOnce,        // Identifies a gnu.linkonce section [ELF]
154   };
155
156   // Permission bits for atoms and segments. The order of these values are
157   // important, because the layout pass may sort atoms by permission if other
158   // attributes are the same.
159   enum ContentPermissions {
160     perm___  = 0,           // mapped as unaccessible
161     permR__  = 8,           // mapped read-only
162     permRW_  = 8 + 2,       // mapped readable and writable
163     permRW_L = 8 + 2 + 1,   // initially mapped r/w, then made read-only
164                             // loader writable
165     permR_X  = 8 + 4,       // mapped readable and executable
166     permRWX  = 8 + 2 + 4,   // mapped readable and writable and executable
167     permUnknown = 16        // unknown or invalid permissions
168   };
169
170   enum SectionChoice {
171     sectionBasedOnContent,  // linker infers final section based on content
172     sectionCustomPreferred, // linker may place in specific section
173     sectionCustomRequired   // linker must place in specific section
174   };
175
176   enum DeadStripKind {
177     deadStripNormal,        // linker may dead strip this atom
178     deadStripNever,         // linker must never dead strip this atom
179     deadStripAlways         // linker must remove this atom if unused
180   };
181
182   enum DynamicExport {
183     /// \brief The linker may or may not export this atom dynamically depending
184     ///   on the output type and other context of the link.
185     dynamicExportNormal,
186     /// \brief The linker will always export this atom dynamically.
187     dynamicExportAlways,
188   };
189
190   // Attributes describe a code model used by the atom.
191   enum CodeModel {
192     codeNA,           // no specific code model
193     codeMipsPIC,      // PIC function in a PIC / non-PIC mixed file
194     codeMipsMicro,    // microMIPS instruction encoding
195     codeMipsMicroPIC, // microMIPS instruction encoding + PIC
196     codeMips16,       // MIPS-16 instruction encoding
197     codeARMThumb,     // ARM Thumb instruction set
198   };
199
200   struct Alignment {
201     Alignment(int p2, int m = 0)
202       : powerOf2(p2)
203       , modulus(m) {}
204
205     uint16_t powerOf2;
206     uint16_t modulus;
207
208     bool operator==(const Alignment &rhs) const {
209       return (powerOf2 == rhs.powerOf2) && (modulus == rhs.modulus);
210     }
211   };
212
213   /// \brief returns a value for the order of this Atom within its file.
214   ///
215   /// This is used by the linker to order the layout of Atoms so that the
216   /// resulting image is stable and reproducible.
217   ///
218   /// Note that this should not be confused with ordinals of exported symbols in
219   /// Windows DLLs. In Windows terminology, ordinals are symbols' export table
220   /// indices (small integers) which can be used instead of symbol names to
221   /// refer items in a DLL.
222   virtual uint64_t ordinal() const = 0;
223
224   /// \brief the number of bytes of space this atom's content will occupy in the
225   /// final linked image.
226   ///
227   /// For a function atom, it is the number of bytes of code in the function.
228   virtual uint64_t size() const = 0;
229
230   /// \brief The size of the section from which the atom is instantiated.
231   ///
232   /// Merge::mergeByLargestSection is defined in terms of section size
233   /// and not in terms of atom size, so we need this function separate
234   /// from size().
235   virtual uint64_t sectionSize() const { return 0; }
236
237   /// \brief The visibility of this atom to other atoms.
238   ///
239   /// C static functions have scope scopeTranslationUnit.  Regular C functions
240   /// have scope scopeGlobal.  Functions compiled with visibility=hidden have
241   /// scope scopeLinkageUnit so they can be see by other atoms being linked but
242   /// not by the OS loader.
243   virtual Scope scope() const = 0;
244
245   /// \brief Whether the linker should use direct or indirect access to this
246   /// atom.
247   virtual Interposable interposable() const = 0;
248
249   /// \brief how the linker should handle if multiple atoms have the same name.
250   virtual Merge merge() const = 0;
251
252   /// \brief The type of this atom, such as code or data.
253   virtual ContentType contentType() const = 0;
254
255   /// \brief The alignment constraints on how this atom must be laid out in the
256   /// final linked image (e.g. 16-byte aligned).
257   virtual Alignment alignment() const = 0;
258
259   /// \brief Whether this atom must be in a specially named section in the final
260   /// linked image, or if the linker can infer the section based on the
261   /// contentType().
262   virtual SectionChoice sectionChoice() const = 0;
263
264   /// \brief If sectionChoice() != sectionBasedOnContent, then this return the
265   /// name of the section the atom should be placed into.
266   virtual StringRef customSectionName() const = 0;
267
268   /// \brief constraints on whether the linker may dead strip away this atom.
269   virtual DeadStripKind deadStrip() const = 0;
270
271   /// \brief Under which conditions should this atom be dynamically exported.
272   virtual DynamicExport dynamicExport() const {
273     return dynamicExportNormal;
274   }
275
276   /// \brief Code model used by the atom.
277   virtual CodeModel codeModel() const { return codeNA; }
278
279   /// \brief Returns the OS memory protections required for this atom's content
280   /// at runtime.
281   ///
282   /// A function atom is R_X, a global variable is RW_, and a read-only constant
283   /// is R__.
284   virtual ContentPermissions permissions() const;
285
286   /// \brief returns a reference to the raw (unrelocated) bytes of this Atom's
287   /// content.
288   virtual ArrayRef<uint8_t> rawContent() const = 0;
289
290   /// This class abstracts iterating over the sequence of References
291   /// in an Atom.  Concrete instances of DefinedAtom must implement
292   /// the derefIterator() and incrementIterator() methods.
293   class reference_iterator {
294   public:
295     reference_iterator(const DefinedAtom &a, const void *it)
296       : _atom(a), _it(it) { }
297
298     const Reference *operator*() const {
299       return _atom.derefIterator(_it);
300     }
301
302     const Reference *operator->() const {
303       return _atom.derefIterator(_it);
304     }
305
306     bool operator!=(const reference_iterator &other) const {
307       return _it != other._it;
308     }
309
310     reference_iterator &operator++() {
311       _atom.incrementIterator(_it);
312       return *this;
313     }
314   private:
315     const DefinedAtom &_atom;
316     const void *_it;
317   };
318
319   /// \brief Returns an iterator to the beginning of this Atom's References.
320   virtual reference_iterator begin() const = 0;
321
322   /// \brief Returns an iterator to the end of this Atom's References.
323   virtual reference_iterator end() const = 0;
324
325   static bool classof(const Atom *a) {
326     return a->definition() == definitionRegular;
327   }
328
329   /// Utility for deriving permissions from content type
330   static ContentPermissions permissions(ContentType type);
331
332   /// Utility function to check if the atom occupies file space
333   bool occupiesDiskSpace() const {
334     ContentType atomContentType = contentType();
335     return !(atomContentType == DefinedAtom::typeZeroFill ||
336              atomContentType == DefinedAtom::typeZeroFillFast ||
337              atomContentType == DefinedAtom::typeTLVInitialZeroFill ||
338              atomContentType == DefinedAtom::typeThreadZeroFill);
339   }
340
341   /// Utility function to check if the atom belongs to a group section
342   /// that represents section groups or .gnu.linkonce sections.
343   bool isGroupParent() const {
344     ContentType atomContentType = contentType();
345     return (atomContentType == DefinedAtom::typeGroupComdat ||
346             atomContentType == DefinedAtom::typeGnuLinkOnce);
347   }
348
349   // Returns true if lhs should be placed before rhs in the final output.
350   static bool compareByPosition(const DefinedAtom *lhs,
351                                 const DefinedAtom *rhs);
352
353 protected:
354   // DefinedAtom is an abstract base class. Only subclasses can access
355   // constructor.
356   DefinedAtom() : Atom(definitionRegular) { }
357
358   /// \brief Returns a pointer to the Reference object that the abstract
359   /// iterator "points" to.
360   virtual const Reference *derefIterator(const void *iter) const = 0;
361
362   /// \brief Adjusts the abstract iterator to "point" to the next Reference
363   /// object for this Atom.
364   virtual void incrementIterator(const void *&iter) const = 0;
365 };
366 } // end namespace lld
367
368 #endif