module parsing cleanup
[dyninst.git] / pdutil / h / Object-elf.h
1 /*
2  * Copyright (c) 1996 Barton P. Miller
3  * 
4  * We provide the Paradyn Parallel Performance Tools (below
5  * described as Paradyn") on an AS IS basis, and do not warrant its
6  * validity or performance.  We reserve the right to update, modify,
7  * or discontinue this software at any time.  We shall have no
8  * obligation to supply such updates or modifications or any other
9  * form of support to you.
10  * 
11  * This license is for research uses.  For such uses, there is no
12  * charge. We define "research use" to mean you may freely use it
13  * inside your organization for whatever purposes you see fit. But you
14  * may not re-distribute Paradyn or parts of Paradyn, in any form
15  * source or binary (including derivatives), electronic or otherwise,
16  * to any other organization or entity without our permission.
17  * 
18  * (for other uses, please contact us at paradyn@cs.wisc.edu)
19  * 
20  * All warranties, including without limitation, any warranty of
21  * merchantability or fitness for a particular purpose, are hereby
22  * excluded.
23  * 
24  * By your use of Paradyn, you understand and agree that we (or any
25  * other person or entity with proprietary rights in Paradyn) are
26  * under no obligation to provide either maintenance services,
27  * update services, notices of latent defects, or correction of
28  * defects for Paradyn.
29  * 
30  * Even if advised of the possibility of such damages, under no
31  * circumstances shall we (or any other person or entity with
32  * proprietary rights in the software licensed hereunder) be liable
33  * to you or any third party for direct, indirect, or consequential
34  * damages of any character regardless of type of action, including,
35  * without limitation, loss of profits, loss of use, loss of good
36  * will, or computer failure or malfunction.  You agree to indemnify
37  * us (and any other person or entity with proprietary rights in the
38  * software licensed hereunder) for any and all liability it may
39  * incur to third parties resulting from your use of Paradyn.
40  */
41
42 /************************************************************************
43  * $Id: Object-elf.h,v 1.34 1999/06/08 06:57:12 csserra Exp $
44  * Object-elf32.h: ELF-32 object files.
45 ************************************************************************/
46
47
48 #if !defined(_Object_elf32_h_)
49 #define _Object_elf32_h_
50
51
52
53 /************************************************************************
54  * header files.
55 ************************************************************************/
56 #include "util/h/String.h"
57 #include "util/h/Symbol.h"
58 #include "util/h/Types.h"
59 #include "util/h/Vector.h"
60 #include <elf.h>
61 #include <libelf.h>
62
63 extern "C" {
64 #include <libelf.h>
65 #include <fcntl.h>
66 #include <stdlib.h>
67 #include <unistd.h>
68
69 #include <sys/types.h>
70 #include <sys/mman.h>
71 #include <sys/stat.h>
72 }
73
74 /***
75    The standard symbol table in an elf file is the .symtab section. This section does
76    not have information to find the module to which a global symbol belongs, so we must
77    also read the .stab section to get this info.
78 ***/
79
80 // Declarations for the .stab section.
81 // These are not declared in any system header files, so we must provide our own
82 // declarations. The declarations below were taken from:
83 //       SPARCWorks 3.0.x Debugger Interface, July 1994/
84
85 struct stab_entry { // an entry in the stab section
86   unsigned long name;  // stabstr table index for this symbol
87   unsigned char type; // type of this symbol
88   unsigned char other; 
89   unsigned short desc; 
90   unsigned long val; // value of this symbol -- usually zero. The real value must
91                      // be obtained from the symtab section
92 };
93
94 // Types 
95 #define N_UNDF  0x00 /* start of object file */
96 #define N_GSYM  0x20 /* global symbol */
97 #define N_FUN   0x24 /* function or procedure */
98 #define N_STSYM 0x26 /* initialized static symbol */
99 #define N_LCSYM 0x28 /* unitialized static symbol */
100 #define N_ROSYM 0x2c /* read-only static symbol */
101 #define N_ENDM  0x62 /* end module */
102 #define N_SO    0x64 /* source directory and file */
103 #define N_ENTRY 0xa4 /* fortran alternate subroutine entry point */
104
105 // Language code -- the desc field in a N_SO entry is a language code
106 #define N_SO_AS      1 /* assembler source */
107 #define N_SO_C       2 /* K & R C source */
108 #define N_SO_ANSI_C  3 /* ANSI C source */
109 #define N_SO_CC      4 /* C++ source */
110 #define N_SO_FORTRAN 5 /* fortran source */
111 #define N_SO_PASCAL  6 /* Pascal source */
112
113 // Symbol descriptors
114 // The format of a name is "<name>:<symbol descriptor><rest of name>
115 // The following are the descriptors of interest
116 #define SD_GLOBAL_FUN 'F' /* global function or procedure */
117 #define SD_PROTOTYPE 'P'  /* function prototypes */
118 #define SD_GLOBAL_VAR 'G' /* global variable */
119
120 // end of stab declarations
121
122 \f
123
124
125 /************************************************************************
126  * class Object
127 ************************************************************************/
128
129 class Object : public AObject {
130 public:
131              // executable file version of constructor....
132              Object (const string, void (*)(const char *) = log_msg);
133              // shared library version of constructor....
134              Object (const string, const Address baseAddr, 
135                      void (*)(const char *) = log_msg);
136              Object (const Object &);
137     virtual ~Object ();
138
139     const Object& operator= (const Object &);
140
141     // for debuggering ....
142     const ostream &dump_state_info(ostream &s);
143
144     bool     needs_function_binding() const {return (plt_addr_  > 0);} 
145     bool     get_func_binding_table(vector<relocationEntry> &fbt) const;
146     bool     get_func_binding_table_ptr(const vector<relocationEntry> *&fbt) const;
147
148 private:
149     static
150     void    log_elferror (void (*)(const char *), const char *);
151
152     bool    EEL ; //set to true if EEL rewritten
153     //added char *ptr, to deal with EEL rewritten software
154     //
155     bool      loaded_elf (int, char *, bool &, Elf* &, Elf32_Ehdr* &, 
156                           Elf32_Phdr* &, Address &, Address &, Elf_Scn* &, 
157                           Elf_Scn* &, Elf_Scn* &, Elf_Scn* &,
158                           Elf_Scn*& rel_plt_scnp, Elf_Scn*& plt_scnp, 
159                           Elf_Scn*& got_scnp,  Elf_Scn*& dynsym_scnp,
160                           Elf_Scn*& dynstr_scnp, bool a_out=false);
161
162     // Code for loading in executable files && shared libraries, 
163     //  respectively....
164     void     load_object ();
165     void     load_shared_object ();
166
167     // initialize relocation_table_ from .rel.plt or .rela.plt section entryies 
168     bool     get_relocation_entries(Elf_Scn*& rel_plt_scnp,
169                         Elf_Scn*& dynsymscnp, Elf_Scn*& dynstrcnp);
170
171     // elf-specific stuff from dynamic executables and shared objects
172     Address     plt_addr_;      // address of _PROCEDURE_LINKAGE_TABLE_ 
173     u_int       plt_size_;
174     u_int       plt_entry_size_;
175     Address     got_addr_;      // address of _GLOBAL_OFFSET_TABLE_
176     Address     rel_plt_addr_;  // address of .rela.plt or .rel.plt section 
177     u_int       rel_plt_size_;
178     u_int       rel_plt_entry_size_;
179     Address     dyn_sym_addr_;  // address of .dynsym section
180     Address     dyn_str_addr_;  // address of .dynstr section
181
182     // for sparc-solaris this is a table of PLT entry addr, function_name
183     // for x86-solaris this is a table of GOT entry addr, function_name
184     // on sparc-solaris the runtime linker modifies the PLT entry when it
185     // binds a function, on X86 the PLT entry is not modified, but it uses
186     // an indirect jump to a GOT entry that is modified when the function 
187     // is bound....is this correct???? or should it be <PLTentry_addr, name> 
188     // for both?
189     vector<relocationEntry> relocation_table_;
190
191     void parse_symbols(vector<Symbol> &allsymbols, Elf32_Sym *syms,
192         unsigned nsyms, const char *strs, bool shared_library,
193         string module);
194
195     void fix_zero_function_sizes(vector<Symbol> &allsymbols, bool EEL);
196     void override_weak_symbols(vector<Symbol> &allsymbols);
197     void insert_symbols_shared(vector<Symbol> allsymbols);
198     void find_code_and_data(Elf32_Ehdr* ehdrp, Elf32_Phdr* phdrp,
199         char *ptr, Address txtaddr, Address bssaddr);
200     void insert_symbols_static(vector<Symbol> allsymbols,
201         dictionary_hash<string, Symbol> &global_symbols);
202     bool fix_global_symbol_modules_static_stab(
203         dictionary_hash<string, Symbol> &global_symbols,
204         Elf_Scn* stabscnp, Elf_Scn* stabstrscnp);
205     bool fix_global_symbol_modules_static_dwarf(
206         dictionary_hash<string, Symbol> &global_symbols, Elf *elfp);
207     void fix_global_symbol_unknowns_static(
208         dictionary_hash<string, Symbol> &global_symbols);
209
210 #if defined(mips_sgi_irix6_4)
211  public:
212     Address get_gp_value()  const { return gp_value; }
213     Address get_rbrk_addr() const { return rbrk_addr; }
214     Address get_base_addr() const { return base_addr; }
215  private:
216     Address gp_value;
217     Address rbrk_addr;
218     Address base_addr;
219 #endif /* mips_sgi_irix6_4 */
220
221 };
222  
223
224 #endif /* !defined(_Object_elf32_h_) */
225
226
227
228
229
230