1 //===-- ObjectFileELF.h --------------------------------------- -*- 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 #ifndef liblldb_ObjectFileELF_h_
11 #define liblldb_ObjectFileELF_h_
12 
13 #include <stdint.h>
14 #include <vector>
15 
16 #include "lldb/lldb-private.h"
17 #include "lldb/Host/FileSpec.h"
18 #include "lldb/Symbol/ObjectFile.h"
19 #include "lldb/Core/UUID.h"
20 
21 #include "ELFHeader.h"
22 
23 //------------------------------------------------------------------------------
24 /// @class ObjectFileELF
25 /// @brief Generic ELF object file reader.
26 ///
27 /// This class provides a generic ELF (32/64 bit) reader plugin implementing the
28 /// ObjectFile protocol.
29 class ObjectFileELF :
30     public lldb_private::ObjectFile
31 {
32 public:
33     //------------------------------------------------------------------
34     // Static Functions
35     //------------------------------------------------------------------
36     static void
37     Initialize();
38 
39     static void
40     Terminate();
41 
42     static lldb_private::ConstString
43     GetPluginNameStatic();
44 
45     static const char *
46     GetPluginDescriptionStatic();
47 
48     static lldb_private::ObjectFile *
49     CreateInstance(const lldb::ModuleSP &module_sp,
50                    lldb::DataBufferSP& data_sp,
51                    lldb::offset_t data_offset,
52                    const lldb_private::FileSpec* file,
53                    lldb::offset_t file_offset,
54                    lldb::offset_t length);
55 
56     static lldb_private::ObjectFile *
57     CreateMemoryInstance (const lldb::ModuleSP &module_sp,
58                           lldb::DataBufferSP& data_sp,
59                           const lldb::ProcessSP &process_sp,
60                           lldb::addr_t header_addr);
61 
62     static size_t
63     GetModuleSpecifications (const lldb_private::FileSpec& file,
64                              lldb::DataBufferSP& data_sp,
65                              lldb::offset_t data_offset,
66                              lldb::offset_t file_offset,
67                              lldb::offset_t length,
68                              lldb_private::ModuleSpecList &specs);
69 
70     static bool
71     MagicBytesMatch (lldb::DataBufferSP& data_sp,
72                      lldb::addr_t offset,
73                      lldb::addr_t length);
74 
75     //------------------------------------------------------------------
76     // PluginInterface protocol
77     //------------------------------------------------------------------
78     virtual lldb_private::ConstString
79     GetPluginName();
80 
81     virtual uint32_t
82     GetPluginVersion();
83 
84     //------------------------------------------------------------------
85     // ObjectFile Protocol.
86     //------------------------------------------------------------------
87     virtual
88     ~ObjectFileELF();
89 
90     virtual bool
91     ParseHeader();
92 
93     virtual lldb::ByteOrder
94     GetByteOrder() const;
95 
96     virtual bool
97     IsExecutable () const;
98 
99     virtual uint32_t
100     GetAddressByteSize() const;
101 
102     virtual lldb_private::Symtab *
103     GetSymtab();
104 
105     virtual lldb_private::Symbol *
106     ResolveSymbolForAddress(const lldb_private::Address& so_addr, bool verify_unique);
107 
108     virtual bool
109     IsStripped ();
110 
111     virtual void
112     CreateSections (lldb_private::SectionList &unified_section_list);
113 
114     virtual void
115     Dump(lldb_private::Stream *s);
116 
117     virtual bool
118     GetArchitecture (lldb_private::ArchSpec &arch);
119 
120     virtual bool
121     GetUUID(lldb_private::UUID* uuid);
122 
123     virtual lldb_private::FileSpecList
124     GetDebugSymbolFilePaths();
125 
126     virtual uint32_t
127     GetDependentModules(lldb_private::FileSpecList& files);
128 
129     virtual lldb_private::Address
130     GetImageInfoAddress(lldb_private::Target *target);
131 
132     virtual lldb_private::Address
133     GetEntryPointAddress ();
134 
135     virtual ObjectFile::Type
136     CalculateType();
137 
138     virtual ObjectFile::Strata
139     CalculateStrata();
140 
141     // Returns number of program headers found in the ELF file.
142     size_t
143     GetProgramHeaderCount();
144 
145     // Returns the program header with the given index.
146     const elf::ELFProgramHeader *
147     GetProgramHeaderByIndex(lldb::user_id_t id);
148 
149     // Returns segment data for the given index.
150     lldb_private::DataExtractor
151     GetSegmentDataByIndex(lldb::user_id_t id);
152 
153 private:
154     ObjectFileELF(const lldb::ModuleSP &module_sp,
155                   lldb::DataBufferSP& data_sp,
156                   lldb::offset_t data_offset,
157                   const lldb_private::FileSpec* file,
158                   lldb::offset_t offset,
159                   lldb::offset_t length);
160 
161     typedef std::vector<elf::ELFProgramHeader>  ProgramHeaderColl;
162     typedef ProgramHeaderColl::iterator         ProgramHeaderCollIter;
163     typedef ProgramHeaderColl::const_iterator   ProgramHeaderCollConstIter;
164 
165     struct ELFSectionHeaderInfo : public elf::ELFSectionHeader
166     {
167         lldb_private::ConstString section_name;
168     };
169     typedef std::vector<ELFSectionHeaderInfo>   SectionHeaderColl;
170     typedef SectionHeaderColl::iterator         SectionHeaderCollIter;
171     typedef SectionHeaderColl::const_iterator   SectionHeaderCollConstIter;
172 
173     typedef std::vector<elf::ELFDynamic>        DynamicSymbolColl;
174     typedef DynamicSymbolColl::iterator         DynamicSymbolCollIter;
175     typedef DynamicSymbolColl::const_iterator   DynamicSymbolCollConstIter;
176 
177     /// Version of this reader common to all plugins based on this class.
178     static const uint32_t m_plugin_version = 1;
179 
180     /// ELF file header.
181     elf::ELFHeader m_header;
182 
183     /// ELF build ID.
184     lldb_private::UUID m_uuid;
185 
186     /// ELF .gnu_debuglink file and crc data if available.
187     std::string m_gnu_debuglink_file;
188     uint32_t m_gnu_debuglink_crc;
189 
190     /// Collection of program headers.
191     ProgramHeaderColl m_program_headers;
192 
193     /// Collection of section headers.
194     SectionHeaderColl m_section_headers;
195 
196     /// Collection of symbols from the dynamic table.
197     DynamicSymbolColl m_dynamic_symbols;
198 
199     /// List of file specifications corresponding to the modules (shared
200     /// libraries) on which this object file depends.
201     mutable std::unique_ptr<lldb_private::FileSpecList> m_filespec_ap;
202 
203     /// Cached value of the entry point for this module.
204     lldb_private::Address  m_entry_point_address;
205 
206     /// Returns a 1 based index of the given section header.
207     size_t
208     SectionIndex(const SectionHeaderCollIter &I);
209 
210     /// Returns a 1 based index of the given section header.
211     size_t
212     SectionIndex(const SectionHeaderCollConstIter &I) const;
213 
214     /// Parses all section headers present in this object file and populates
215     /// m_program_headers.  This method will compute the header list only once.
216     /// Returns the number of headers parsed.
217     size_t
218     ParseProgramHeaders();
219 
220     /// Parses all section headers present in this object file and populates
221     /// m_section_headers.  This method will compute the header list only once.
222     /// Returns the number of headers parsed.
223     size_t
224     ParseSectionHeaders();
225 
226     /// Parses the elf section headers and returns the uuid, debug link name, crc.
227     static size_t
228     GetSectionHeaderInfo(SectionHeaderColl &section_headers,
229                          lldb_private::DataExtractor &data,
230                          const elf::ELFHeader &header,
231                          lldb_private::UUID &uuid,
232                          std::string &gnu_debuglink_file,
233                          uint32_t &gnu_debuglink_crc);
234 
235     /// Scans the dynamic section and locates all dependent modules (shared
236     /// libraries) populating m_filespec_ap.  This method will compute the
237     /// dependent module list only once.  Returns the number of dependent
238     /// modules parsed.
239     size_t
240     ParseDependentModules();
241 
242     /// Parses the dynamic symbol table and populates m_dynamic_symbols.  The
243     /// vector retains the order as found in the object file.  Returns the
244     /// number of dynamic symbols parsed.
245     size_t
246     ParseDynamicSymbols();
247 
248     /// Populates m_symtab_ap will all non-dynamic linker symbols.  This method
249     /// will parse the symbols only once.  Returns the number of symbols parsed.
250     unsigned
251     ParseSymbolTable(lldb_private::Symtab *symbol_table,
252                      lldb::user_id_t start_id,
253                      lldb_private::Section *symtab);
254 
255     /// Helper routine for ParseSymbolTable().
256     unsigned
257     ParseSymbols(lldb_private::Symtab *symbol_table,
258                  lldb::user_id_t start_id,
259                  lldb_private::SectionList *section_list,
260                  const size_t num_symbols,
261                  const lldb_private::DataExtractor &symtab_data,
262                  const lldb_private::DataExtractor &strtab_data);
263 
264     /// Scans the relocation entries and adds a set of artificial symbols to the
265     /// given symbol table for each PLT slot.  Returns the number of symbols
266     /// added.
267     unsigned
268     ParseTrampolineSymbols(lldb_private::Symtab *symbol_table,
269                            lldb::user_id_t start_id,
270                            const ELFSectionHeaderInfo *rela_hdr,
271                            lldb::user_id_t section_id);
272 
273     /// Returns the section header with the given id or NULL.
274     const ELFSectionHeaderInfo *
275     GetSectionHeaderByIndex(lldb::user_id_t id);
276 
277     /// @name  ELF header dump routines
278     //@{
279     static void
280     DumpELFHeader(lldb_private::Stream *s, const elf::ELFHeader& header);
281 
282     static void
283     DumpELFHeader_e_ident_EI_DATA(lldb_private::Stream *s,
284                                   unsigned char ei_data);
285 
286     static void
287     DumpELFHeader_e_type(lldb_private::Stream *s, elf::elf_half e_type);
288     //@}
289 
290     /// @name ELF program header dump routines
291     //@{
292     void
293     DumpELFProgramHeaders(lldb_private::Stream *s);
294 
295     static void
296     DumpELFProgramHeader(lldb_private::Stream *s,
297                          const elf::ELFProgramHeader &ph);
298 
299     static void
300     DumpELFProgramHeader_p_type(lldb_private::Stream *s, elf::elf_word p_type);
301 
302     static void
303     DumpELFProgramHeader_p_flags(lldb_private::Stream *s,
304                                  elf::elf_word p_flags);
305     //@}
306 
307     /// @name ELF section header dump routines
308     //@{
309     void
310     DumpELFSectionHeaders(lldb_private::Stream *s);
311 
312     static void
313     DumpELFSectionHeader(lldb_private::Stream *s,
314                          const ELFSectionHeaderInfo& sh);
315 
316     static void
317     DumpELFSectionHeader_sh_type(lldb_private::Stream *s,
318                                  elf::elf_word sh_type);
319 
320     static void
321     DumpELFSectionHeader_sh_flags(lldb_private::Stream *s,
322                                   elf::elf_xword sh_flags);
323     //@}
324 
325     /// ELF dependent module dump routine.
326     void
327     DumpDependentModules(lldb_private::Stream *s);
328 
329     const elf::ELFDynamic *
330     FindDynamicSymbol(unsigned tag);
331 
332     unsigned
333     PLTRelocationType();
334 };
335 
336 #endif // #ifndef liblldb_ObjectFileELF_h_
337