Add LLVMObject Library.
[oota-llvm.git] / include / llvm / Object / ObjectFile.h
1 //===- ObjectFile.h - File format independent object file -------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file declares a file format independent ObjectFile class.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #ifndef LLVM_OBJECT_OBJECT_FILE_H
15 #define LLVM_OBJECT_OBJECT_FILE_H
16
17 #include "llvm/ADT/Triple.h"
18 #include "llvm/System/Path.h"
19
20 namespace llvm {
21
22 class MemoryBuffer;
23
24 namespace object {
25
26 class ObjectFile;
27 typedef uint64_t DataRefImpl;
28
29 /// SymbolRef - This is a value type class that represents a single symbol in
30 /// the list of symbols in the object file.
31 class SymbolRef {
32   DataRefImpl SymbolPimpl;
33   const ObjectFile *OwningObject;
34
35 public:
36   SymbolRef(DataRefImpl SymbolP, const ObjectFile *Owner);
37
38   bool operator==(const SymbolRef &Other) const;
39
40   SymbolRef getNext() const;
41
42   StringRef getName() const;
43   uint64_t  getAddress() const;
44   uint64_t  getSize() const;
45
46   /// Returns the ascii char that should be displayed in a symbol table dump via
47   /// nm for this symbol.
48   char      getNMTypeChar() const;
49
50   /// Returns true for symbols that are internal to the object file format such
51   /// as section symbols.
52   bool      isInternal() const;
53 };
54
55 /// SectionRef - This is a value type class that represents a single section in
56 /// the list of sections in the object file.
57 class SectionRef {
58   DataRefImpl SectionPimpl;
59   const ObjectFile *OwningObject;
60
61 public:
62   SectionRef(DataRefImpl SectionP, const ObjectFile *Owner);
63
64   bool operator==(const SectionRef &Other) const;
65
66   SectionRef getNext() const;
67
68   StringRef getName() const;
69   uint64_t  getAddress() const;
70   uint64_t  getSize() const;
71   StringRef getContents() const;
72
73   // FIXME: Move to the normalization layer when it's created.
74   bool      isText() const;
75 };
76
77 const uint64_t UnknownAddressOrSize = ~0ULL;
78
79 /// ObjectFile - This class is the base class for all object file types.
80 /// Concrete instances of this object are created by createObjectFile, which
81 /// figure out which type to create.
82 class ObjectFile {
83 private:
84   ObjectFile(); // = delete
85   ObjectFile(const ObjectFile &other); // = delete
86
87 protected:
88   MemoryBuffer *MapFile;
89   const uint8_t *base;
90
91   ObjectFile(MemoryBuffer *Object);
92
93   // These functions are for SymbolRef to call internally. The main goal of
94   // this is to allow SymbolRef::SymbolPimpl to point directly to the symbol
95   // entry in the memory mapped object file. SymbolPimpl cannot contain any
96   // virtual functions because then it could not point into the memory mapped
97   // file.
98   friend class SymbolRef;
99   virtual SymbolRef getSymbolNext(DataRefImpl Symb) const = 0;
100   virtual StringRef getSymbolName(DataRefImpl Symb) const = 0;
101   virtual uint64_t  getSymbolAddress(DataRefImpl Symb) const = 0;
102   virtual uint64_t  getSymbolSize(DataRefImpl Symb) const = 0;
103   virtual char      getSymbolNMTypeChar(DataRefImpl Symb) const = 0;
104   virtual bool      isSymbolInternal(DataRefImpl Symb) const = 0;
105
106   // Same as above for SectionRef.
107   friend class SectionRef;
108   virtual SectionRef getSectionNext(DataRefImpl Sec) const = 0;
109   virtual StringRef  getSectionName(DataRefImpl Sec) const = 0;
110   virtual uint64_t   getSectionAddress(DataRefImpl Sec) const = 0;
111   virtual uint64_t   getSectionSize(DataRefImpl Sec) const = 0;
112   virtual StringRef  getSectionContents(DataRefImpl Sec) const = 0;
113   virtual bool       isSectionText(DataRefImpl Sec) const = 0;
114
115
116 public:
117   template<class content_type>
118   class content_iterator {
119     content_type Current;
120   public:
121     content_iterator(content_type symb)
122       : Current(symb) {}
123
124     const content_type* operator->() const {
125       return &Current;
126     }
127
128     bool operator==(const content_iterator &other) const {
129       return Current == other.Current;
130     }
131
132     bool operator!=(const content_iterator &other) const {
133       return !(*this == other);
134     }
135
136     content_iterator& operator++() {  // Preincrement
137       Current = Current.getNext();
138       return *this;
139     }
140   };
141
142   typedef content_iterator<SymbolRef> symbol_iterator;
143   typedef content_iterator<SectionRef> section_iterator;
144
145   virtual ~ObjectFile();
146
147   virtual symbol_iterator begin_symbols() const = 0;
148   virtual symbol_iterator end_symbols() const = 0;
149
150   virtual section_iterator begin_sections() const = 0;
151   virtual section_iterator end_sections() const = 0;
152
153   /// @brief The number of bytes used to represent an address in this object
154   ///        file format.
155   virtual uint8_t getBytesInAddress() const = 0;
156
157   virtual StringRef getFileFormatName() const = 0;
158   virtual Triple::ArchType getArch() const = 0;
159
160   StringRef getFilename() const;
161
162   /// @returns Pointer to ObjectFile subclass to handle this type of object.
163   /// @param ObjectPath The path to the object file. ObjectPath.isObject must
164   ///        return true.
165   /// @brief Create ObjectFile from path.
166   static ObjectFile *createObjectFile(const sys::Path &ObjectPath);
167   static ObjectFile *createObjectFile(MemoryBuffer *Object);
168
169 private:
170   static ObjectFile *createCOFFObjectFile(MemoryBuffer *Object);
171   static ObjectFile *createELFObjectFile(MemoryBuffer *Object);
172   static ObjectFile *createMachOObjectFile(MemoryBuffer *Object);
173   static ObjectFile *createArchiveObjectFile(MemoryBuffer *Object);
174   static ObjectFile *createLibObjectFile(MemoryBuffer *Object);
175 };
176
177 // Inline function definitions.
178 inline SymbolRef::SymbolRef(DataRefImpl SymbolP, const ObjectFile *Owner)
179   : SymbolPimpl(SymbolP)
180   , OwningObject(Owner) {}
181
182 inline bool SymbolRef::operator==(const SymbolRef &Other) const {
183   return SymbolPimpl == Other.SymbolPimpl;
184 }
185
186 inline SymbolRef SymbolRef::getNext() const {
187   return OwningObject->getSymbolNext(SymbolPimpl);
188 }
189
190 inline StringRef SymbolRef::getName() const {
191   return OwningObject->getSymbolName(SymbolPimpl);
192 }
193
194 inline uint64_t SymbolRef::getAddress() const {
195   return OwningObject->getSymbolAddress(SymbolPimpl);
196 }
197
198 inline uint64_t SymbolRef::getSize() const {
199   return OwningObject->getSymbolSize(SymbolPimpl);
200 }
201
202 inline char SymbolRef::getNMTypeChar() const {
203   return OwningObject->getSymbolNMTypeChar(SymbolPimpl);
204 }
205
206 inline bool SymbolRef::isInternal() const {
207   return OwningObject->isSymbolInternal(SymbolPimpl);
208 }
209
210
211 /// SectionRef
212 inline SectionRef::SectionRef(DataRefImpl SectionP,
213                               const ObjectFile *Owner)
214   : SectionPimpl(SectionP)
215   , OwningObject(Owner) {}
216
217 inline bool SectionRef::operator==(const SectionRef &Other) const {
218   return SectionPimpl == Other.SectionPimpl;
219 }
220
221 inline SectionRef SectionRef::getNext() const {
222   return OwningObject->getSectionNext(SectionPimpl);
223 }
224
225 inline StringRef SectionRef::getName() const {
226   return OwningObject->getSectionName(SectionPimpl);
227 }
228
229 inline uint64_t SectionRef::getAddress() const {
230   return OwningObject->getSectionAddress(SectionPimpl);
231 }
232
233 inline uint64_t SectionRef::getSize() const {
234   return OwningObject->getSectionSize(SectionPimpl);
235 }
236
237 inline StringRef SectionRef::getContents() const {
238   return OwningObject->getSectionContents(SectionPimpl);
239 }
240
241 inline bool SectionRef::isText() const {
242   return OwningObject->isSectionText(SectionPimpl);
243 }
244
245 } // end namespace object
246 } // end namespace llvm
247
248 #endif