RTEMS Linker  0.0.1
RTEMS Tools Project
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
/Users/chris/Development/rtems/src/apps/rtl-host.chrisj/rld-elf.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2011, Chris Johns <chrisj@rtems.org>
3  *
4  * Permission to use, copy, modify, and/or distribute this software for any
5  * purpose with or without fee is hereby granted, provided that the above
6  * copyright notice and this permission notice appear in all copies.
7  *
8  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  */
16 /**
17  * @file
18  *
19  * @ingroup rtems-ld
20  *
21  * @brief RTEMS Linker ELF module manages the libelf interface.
22  *
23  */
24 
25 #if !defined (_RLD_ELF_H_)
26 #define _RLD_ELF_H_
27 
28 #include <list>
29 #include <map>
30 #include <vector>
31 
32 #include <rld.h>
33 
34 namespace rld
35 {
36  namespace elf
37  {
38  /**
39  * Forward decl.
40  */
41  class file;
42 
43  /**
44  * A relocation record.
45  */
46  class relocation
47  {
48  public:
49  /**
50  * Construct a relocation record.
51  *
52  * @param sym The symbol the relocation references.
53  * @param offset The offset in the section the relocation applies to.
54  * @param info The relocation info.
55  * @param addend The constant addend value.
56  */
57  relocation (const symbols::symbol& sym,
60  elf_sxword addend = 0);
61 
62  /**
63  * Default constructor.
64  */
65  relocation ();
66 
67  /**
68  * The offset.
69  */
70  elf_addr offset () const;
71 
72  /**
73  * The type of the relocation record.
74  */
75  uint32_t type () const;
76 
77  /**
78  * The info.
79  */
80  elf_xword info () const;
81 
82  /**
83  * The constant addend.
84  */
85  elf_sxword addend () const;
86 
87  /**
88  * Return the symbol.
89  */
90  const symbols::symbol& symbol () const;
91 
92  private:
93  const symbols::symbol* sym; //< The symbol reference.
94  elf_addr offset_; //< The offset in the section.
95  elf_xword info_; //< The record's information.
96  elf_sxword addend_; //< The constant addend value.
97  };
98 
99  /**
100  * A container of relocation records.
101  */
102  typedef std::vector < relocation > relocations;
103 
104  /**
105  * An ELF Section. The current implementation only supports a single data
106  * descriptor with a section.
107  */
108  class section
109  {
110  public:
111  /**
112  * Construct the section getting the details from the ELF file given the
113  * section index.
114  *
115  * The section types are (from elf(3)):
116  *
117  * Section Type Library Type Description
118  * ------------ ------------ -----------
119  * SHT_DYNAMIC ELF_T_DYN `.dynamic' section entries.
120  * SHT_DYNSYM ELF_T_SYM Symbols for dynamic linking.
121  * SHT_FINI_ARRAY ELF_T_ADDR Termination function pointers.
122  * SHT_GROUP ELF_T_WORD Section group marker.
123  * SHT_HASH ELF_T_HASH Symbol hashes.
124  * SHT_INIT_ARRAY ELF_T_ADDR Initialization function pointers.
125  * SHT_NOBITS ELF_T_BYTE Empty sections. See elf(5).
126  * SHT_NOTE ELF_T_NOTE ELF note records.
127  * SHT_PREINIT_ARRAY ELF_T_ADDR Pre-initialization function
128  * pointers.
129  * SHT_PROGBITS ELF_T_BYTE Machine code.
130  * SHT_REL ELF_T_REL ELF relocation records.
131  * SHT_RELA ELF_T_RELA Relocation records with addends.
132  * SHT_STRTAB ELF_T_BYTE String tables.
133  * SHT_SYMTAB ELF_T_SYM Symbol tables.
134  * SHT_SYMTAB_SHNDX ELF_T_WORD Used with extended section
135  * numbering.
136  * SHT_GNU_verdef ELF_T_VDEF Symbol version definitions.
137  * SHT_GNU_verneed ELF_T_VNEED Symbol versioning requirements.
138  * SHT_GNU_versym ELF_T_HALF Version symbols.
139  * SHT_SUNW_move ELF_T_MOVE ELF move records.
140  * SHT_SUNW_syminfo ELF_T_SYMINFO Additional symbol flags.
141  *
142  * @param file_ The ELF file this section is part of.
143  * @param index_ The section's index.
144  * @param name The section's name.
145  * @param type The section's type.
146  * @param alignment The section's alignment.
147  * @param flags The section's flags.
148  * @param addr The section's in-memory address.
149  * @param offset The section's offset in the file.
150  * @param size The section's file in bytes.
151  * @param link The section's header table link.
152  * @param info The section's extra information.
153  * @param entry_size The section's entry size.
154  */
155  section (file& file_,
156  int index_,
157  const std::string& name,
158  elf_word type,
161  elf_addr addr,
162  elf_off offset,
163  elf_xword size,
164  elf_word link = 0,
165  elf_word info = 0,
166  elf_xword entry_size = 0);
167 
168  /**
169  * Construct the section given the details. The ELF file must be
170  * writable.
171  *
172  * @param file_ The ELF file this section is part of.
173  * @param index The section's index in the ELF file.
174  */
175  section (file& file_, int index);
176 
177  /**
178  * Copy constructor.
179  */
180  section (const section& orig);
181 
182  /**
183  * Default constructor.
184  */
185  section ();
186 
187  /**
188  * Add a data segment descriptor to the section if the file is writable.
189  *
190  * These are following data types (from elf(3)):
191  *
192  * ELF_T_ADDR Machine addresses.
193  * ELF_T_BYTE Byte data. The library will not attempt to translate
194  * byte data.
195  * ELF_T_CAP Software and hardware capability records.
196  * ELF_T_DYN Records used in a section of type SHT_DYNAMIC.
197  * ELF_T_EHDR ELF executable header.
198  * ELF_T_HALF 16-bit unsigned words.
199  * ELF_T_LWORD 64 bit unsigned words.
200  * ELF_T_MOVE ELF Move records.
201  * ELF_T_NOTE ELF Note structures.
202  * ELF_T_OFF File offsets.
203  * ELF_T_PHDR ELF program header table entries.
204  * ELF_T_REL ELF relocation entries.
205  * ELF_T_RELA ELF relocation entries with addends.
206  * ELF_T_SHDR ELF section header entries.
207  * ELF_T_SWORD Signed 32-bit words.
208  * ELF_T_SXWORD Signed 64-bit words.
209  * ELF_T_SYMINFO ELF symbol information.
210  * ELF_T_SYM ELF symbol table entries.
211  * ELF_T_VDEF Symbol version definition records.
212  * ELF_T_VNEED Symbol version requirement records.
213  * ELF_T_WORD Unsigned 32-bit words.
214  * ELF_T_XWORD Unsigned 64-bit words.
215  *
216  * @param type The type of data in the segment.
217  * @param alignment The in-file alignment of the data. Must be a power of 2.
218  * @param size The number of bytes in this data descriptor.
219  * @param buffer The data in memory.
220  * @param offset The offset within the containing section. Can be computed.
221  */
222  void add_data (elf_type type,
223  elf_xword alignment,
224  elf_xword size,
225  void* buffer = 0,
226  elf_off offset = 0);
227 
228  /**
229  * The section's index in the ELF file.
230  *
231  * @return int The section number.
232  */
233  int index () const;
234 
235  /**
236  * The name of the section.
237  *
238  * @return const std::string& The section's name.
239  */
240  const std::string& name () const;
241 
242  /**
243  * The section's data.
244  */
245  elf_data* data ();
246 
247  /**
248  * Get the type of the section.
249  */
250  elf_word type () const;
251 
252  /**
253  * The section flags.
254  */
255  elf_xword flags () const;
256 
257  /**
258  * In-memory address of the section.
259  */
260  elf_addr address () const;
261 
262  /**
263  * Alignment constraint.
264  */
265  elf_xword alignment () const;
266 
267  /**
268  * The file offset of the section.
269  */
270  elf_off offset () const;
271 
272  /**
273  * The header table link.
274  */
275  elf_word link () const;
276 
277  /**
278  * Extra information.
279  */
280  elf_word info () const;
281 
282  /**
283  * Size of the section.
284  */
285  elf_xword size () const;
286 
287  /**
288  * Size of the entries in the section.
289  */
290  elf_xword entry_size () const;
291 
292  /**
293  * Number of entries.
294  */
295  int entries () const;
296 
297  /**
298  * Return true if the relocation record have an addend field.
299  *
300  * @retval true The relocation record have the addend field.
301  */
302  bool get_reloc_type () const;
303 
304  /**
305  * Set the name index if writable. This is normally done
306  * automatically when adding the section to the file.
307  */
308  void set_name (unsigned int index);
309 
310  /**
311  * Set the type of relocation records.
312  *
313  * @param rela If true the records are rela type.
314  */
315  void set_reloc_type (bool rela);
316 
317  /**
318  * Add a relocation.
319  *
320  * @param reloc The relocation record to add.
321  */
322  void add (const relocation& reloc);
323 
324  /**
325  * Get the relocations.
326  */
327  const relocations& get_relocations () const;
328 
329  private:
330 
331  /**
332  * Check the section is valid.
333  *
334  * @param where Where the check is being made.
335  */
336  void check (const char* where) const;
337 
338  /**
339  * Check the section is valid and writable.
340  *
341  * @param where Where the check is being made.
342  */
343  void check_writable (const char* where) const;
344 
345  file* file_; //< The ELF file.
346  int index_; //< The section header index.
347  std::string name_; //< The section's name.
348  elf_scn* scn; //< ELF private section data.
349  elf_shdr shdr; //< The section header.
350  elf_data* data_; //< The section's data.
351  bool rela; //< The type of relocation records.
352  relocations relocs; //< The relocation records.
353  };
354 
355  /**
356  * Container of ELF section pointers.
357  */
358  typedef std::list < section* > sections;
359 
360  /**
361  * Container of ELF section as a map, ie associative array.
362  */
363  typedef std::map < std::string, section > section_table;
364 
365  /**
366  * An ELF program header.
367  */
369  {
370  public:
371  /**
372  * Construct a program header.
373  */
374  program_header ();
375 
376  /**
377  * Desctruct a program header.
378  */
379  ~program_header ();
380 
381  /**
382  * Set the program header.
383  *
384  * @param type The type of segment.
385  * @param flags The segment's flags.
386  * @param offset The offet to segment.
387  * @param filesz The segment size in the file.
388  * @param memsz The segment size in memory.
389  * @param align The segment alignment.
390  * @param vaddr The virtual address in memory.
391  * @param paddr The physical address if any.
392  */
393  void set (elf_word type,
394  elf_word flags,
395  elf_off offset,
396  elf_xword filesz,
397  elf_xword memsz,
398  elf_xword align,
399  elf_addr vaddr,
400  elf_addr paddr = 0);
401 
402  private:
403 
404  elf_phdr phdr; //< The ELF program header.
405  };
406 
407  /**
408  * A container of program headers.
409  */
410  typedef std::list < program_header > program_headers;
411 
412  /**
413  * An ELF file.
414  */
415  class file
416  {
417  public:
418  /**
419  * Construct an ELF file.
420  */
421  file ();
422 
423  /**
424  * Destruct the ELF file object.
425  */
426  ~file ();
427 
428  /**
429  * Begin using the ELF file.
430  *
431  * @param name The full name of the file.
432  * @param fd The file descriptor to read or write the file.
433  * @param writable The file is writeable. The default is false.
434  */
435  void begin (const std::string& name, int fd, const bool writable = false);
436 
437  /**
438  * Begin using the ELF file in an archive.
439  *
440  * @param name The full name of the file.
441  * @param archive The file that is the archive.
442  * @param offset The offset of the ELF file in the archive.
443  */
444  void begin (const std::string& name, file& archive, off_t offset);
445 
446  /**
447  * End using the ELF file.
448  */
449  void end ();
450 
451  /**
452  * Write the ELF file creating it if it is writable. You should have
453  * added the sections and the data segment descriptors to the sections
454  * before calling write.
455  */
456  void write ();
457 
458  /**
459  * Load the header. Done automatically.
460  */
461  void load_header ();
462 
463  /**
464  * Get the machine type.
465  */
466  unsigned int machinetype () const;
467 
468  /**
469  * Get the type of ELF file.
470  */
471  unsigned int type () const;
472 
473  /**
474  * Get the class of the object file.
475  */
476  unsigned int object_class () const;
477 
478  /**
479  * Get the data type, ie LSB or MSB.
480  */
481  unsigned int data_type () const;
482 
483  /**
484  * Is the file an archive format file ?
485  */
486  bool is_archive () const;
487 
488  /**
489  * Is the file an executable ?
490  */
491  bool is_executable () const;
492 
493  /**
494  * Is the file relocatable ?
495  */
496  bool is_relocatable() const;
497 
498  /**
499  * The number of sections in the file.
500  */
501  int section_count () const;
502 
503  /**
504  * Load the sections.
505  */
506  void load_sections ();
507 
508  /**
509  * Get a filtered container of the sections. The key is the section
510  * type. If the sections are not loaded they are loaded. If the type is 0
511  * all sections are returned.
512  *
513  * @param filtered_secs The container the copy of the filtered sections
514  * are placed in.
515  * @param type The type of sections to filter on. If 0 all sections are
516  * matched.
517  */
518  void get_sections (sections& filtered_secs, unsigned int type);
519 
520  /**
521  * Return the section with given index.
522  *
523  * @param index The section's index to look for.
524  * @retval section The section matching the index.
525  */
526  section& get_section (int index);
527 
528  /**
529  * Return the index of the string section.
530  */
531  int strings_section () const;
532 
533  /**
534  * Get the string from the specified section at the requested offset.
535  *
536  * @param section The section to search for the string.
537  * @param offset The offset in the string section.
538  * @return std::string The string.
539  */
540  std::string get_string (int section, size_t offset);
541 
542  /**
543  * Get the string from the ELF header declared string section at the
544  * requested offset.
545  *
546  * @param offset The offset in the string section.
547  * @return std::string The string.
548  */
549  std::string get_string (size_t offset);
550 
551  /**
552  * Load the symbols.
553  */
554  void load_symbols ();
555 
556  /**
557  * Get a filtered container of symbols given the various types. If the
558  * symbols are not loaded they are loaded.
559  *
560  * @param filtered_syms The filtered symbols found in the file. This is a
561  * container of pointers.
562  * @param unresolved Return unresolved symbols.
563  * @param local Return local symbols.
564  * @param weak Return weak symbols.
565  * @param global Return global symbols.
566  */
567  void get_symbols (rld::symbols::pointers& filtered_syms,
568  bool unresolved = false,
569  bool local = false,
570  bool weak = true,
571  bool global = true);
572 
573  /**
574  * Get the symbol by index in the symtabl section.
575  */
576  const symbols::symbol& get_symbol (const int index) const;
577 
578  /**
579  * Load the relocation records.
580  */
581  void load_relocations ();
582 
583  /**
584  * Clear the relocation records.
585  */
586  void clear_relocations ();
587 
588  /**
589  * Set the ELF header. Must be writable.
590  *
591  * The classes are:
592  * ELFCLASSNONE This class is invalid.
593  * ELFCLASS32 This defines the 32-bit architecture. It sup- ports
594  * machines with files and virtual address spa- ces up to
595  * 4 Gigabytes.
596  * ELFCLASS64 This defines the 64-bit architecture.
597  *
598  * The types are:
599  * ET_NONE An unknown type.
600  * ET_REL A relocatable file.
601  * ET_EXEC An executable file.
602  * ET_DYN A shared object.
603  * ET_CORE A core file.
604  *
605  * The machine types are:
606  * TDB
607  *
608  * The datatypes are:
609  * ELFDATA2LSB Two's complement, little-endian.
610  * ELFDATA2MSB Two's complement, big-endian.
611  *
612  * @param type The type of ELF file, ie executable, relocatable etc.
613  * @param class_ The files ELF class.
614  * @param machinetype The type of machine code present in the ELF file.
615  * @param datatype The data type, ie LSB or MSB.
616  */
617  void set_header (elf_half type,
618  int class_,
619  elf_half machinetype,
620  unsigned char datatype);
621 
622  /**
623  * Add a section to the ELF file if writable.
624  */
625  void add (section& sec);
626 
627  /**
628  * Add a program header to the ELF file if writable.
629  */
630  void add (program_header& phdr);
631 
632  /**
633  * Get the ELF reference.
634  */
635  elf* get_elf ();
636 
637  /**
638  * Get the name of the file.
639  */
640  const std::string& name () const;
641 
642  /**
643  * Is the file writable ?
644  */
645  bool is_writable () const;
646 
647  private:
648 
649  /**
650  * Begin using the ELF file.
651  *
652  * @param name The full name of the file.
653  * @param fd The file descriptor to read or write the file.
654  * @param writable The file is writeable. It cannot be part of an archive.
655  * @param archive The archive's ELF handle or 0 if not an archive.
656  * @param offset The offset of the ELF file in the archive if elf is non-zero.
657  */
658  void begin (const std::string& name,
659  int fd,
660  const bool writable,
661  file* archive,
662  off_t offset);
663 
664  /**
665  * Check if the file is usable. Throw an exception if not.
666  *
667  * @param where Where the check is performed.
668  */
669  void check (const char* where) const;
670 
671  /**
672  * Check if the file is usable and writable. Throw an exception if not.
673  *
674  * @param where Where the check is performed.
675  */
676  void check_writable (const char* where) const;
677 
678  /**
679  * Check if the ELF header is valid. Throw an exception if not.
680  *
681  * @param where Where the check is performed.
682  */
683  void check_ehdr (const char* where) const;
684 
685  /**
686  * Check if the ELF program header is valid. Throw an exception if not.
687  *
688  * @param where Where the check is performed.
689  */
690  void check_phdr (const char* where) const;
691 
692  /**
693  * Generate libelf error.
694  *
695  * @param where Where the error is generated.
696  */
697  void error (const char* where) const;
698 
699  int fd_; //< The file handle.
700  std::string name_; //< The name of the file.
701  bool archive; //< The ELF file is part of an archive.
702  bool writable; //< The file is writeable.
703  elf* elf_; //< The ELF handle.
704  unsigned int mtype; //< The machine type.
705  unsigned int oclass; //< The object class.
706  const char* ident_str; //< The ELF file's ident string.
707  size_t ident_size; //< The size of the ident.
708  elf_ehdr* ehdr; //< The ELF header.
709  elf_phdr* phdr; //< The ELF program header.
710  section_table secs; //< The sections as a table.
711  program_headers phdrs; //< The program headers when creating
712  // ELF files.
713  rld::symbols::bucket symbols; //< The symbols. All tables point here.
714  };
715 
716  /**
717  * Return the machine type label given the machine type.
718  *
719  * @param machinetype The ELF machine type.
720  */
721  const std::string machine_type (unsigned int machinetype);
722 
723  /**
724  * Return the global machine type set by the check_file call as a string.
725  */
726  const std::string machine_type ();
727 
728  /**
729  * Return the global class set by the check_file call.
730  */
731  unsigned int object_class ();
732 
733  /**
734  * Return the global machine type set by the check_file call.
735  */
736  unsigned int object_machine_type ();
737 
738  /**
739  * Return the global data type set by the check_file call.
740  */
741  unsigned int object_datatype ();
742 
743  /**
744  * Check the file against the global machine type, object class and data
745  * type. If this is the first file checked it becomes the default all
746  * others are checked against. This is a simple way to make sure all files
747  * are the same type.
748  *
749  * @param file The check to check.
750  */
751  void check_file(const file& file);
752 
753  }
754 }
755 
756 #endif