summaryrefslogtreecommitdiffstats
path: root/common/ELF.h
blob: f477610e9426d1634aecf146105991b66d6e56b8 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
/*
 * File:	ELF.h
 *
 * Copyright (c) Freescale Semiconductor, Inc. All rights reserved.
 * See included license file for license details.
 */
#if !defined(_ELF_h_)
#define _ELF_h_

//! \name ELF types
//! Types used in ELF file structures.
//@{
typedef uint32_t Elf32_Addr;
typedef uint16_t Elf32_Half;
typedef /*off_t*/ uint32_t Elf32_Off;
typedef int32_t Elf32_Sword;
typedef uint32_t Elf32_Word;
//@}

// All ELF structures are byte aligned. Any alignment padding is explicit.
#pragma pack(1)

//! \name File header
//@{

/*!
 * Constants for the various fields of Elf32_Ehdr.e_ident.
 */
enum {
	EI_MAG0 = 0,
	EI_MAG1,
	EI_MAG2,
	EI_MAG3,
	EI_CLASS,
	EI_DATA,
	EI_VERSION,
	EI_PAD,
	EI_NIDENT = 16,
	
	// Magic number.
	ELFMAG0 = 0x7f,
	ELFMAG1 = 'E',
	ELFMAG2 = 'L',
	ELFMAG3 = 'F',
	
	// EI_CLASS
	ELFCLASSNONE = 0,
	ELFCLASS32 = 1,
	ELFCLASS64 = 2,
	
	// EI_DATA
	ELFDATANONE = 0,
	ELFDATA2LSB = 1,
	ELFDATA2MSB = 2
};

/*!
 * \brief ELF file header.
 */
struct Elf32_Ehdr
{
	unsigned char e_ident[EI_NIDENT];	//!< Magic number identifying the file format.
	Elf32_Half e_type;		//!< Identifies the object file format.
	Elf32_Half e_machine;	//!< Specified the architecture for the object file.
	Elf32_Word e_version;	//!< Object file version.
	Elf32_Addr e_entry;		//!< Virtual address of the entry point, or 0.
	Elf32_Off e_phoff;		//!< Program header table offset in bytes, or 0 if no program header table.
	Elf32_Off e_shoff;		//!< Section header table offset in bytes, or 0 if no section header table.
	Elf32_Word e_flags;		//!< Processor-specific flags associated with the file.
	Elf32_Half e_ehsize;	//!< The ELF header's size in bytes.
	Elf32_Half e_phentsize;	//!< Size in bytes of one entry in the program header table.
	Elf32_Half e_phnum;		//!< Number of entries in the program header table.
	Elf32_Half e_shentsize;	//!< Size in bytes of an entry in the section header table.
	Elf32_Half e_shnum;		//!< Number of entries in the section header table.
	Elf32_Half e_shstrndx;	//!< Section header table index of the section name string table.
};

/*!
 * Constants for #Elf32_Ehdr.e_type.
 */
enum {
	ET_NONE,	//!< No file type.
	ET_REL,		//!< Relocatable file.
	ET_EXEC,	//!< Executable file.
	ET_DYN,		//!< Shared object file.
	ET_CORE,	//!< Core file.
	ET_LOPROC,	//!< Low bound of processor-specific file types.
	ET_HIPROC	//!< High bound of processor-specific file types.
};	

/*!
 * ARM-specific #Elf32_Ehdr.e_flags
 */
enum {
	EF_ARM_HASENTRY = 0x02,			//!< #Elf32_Ehdr.e_entry contains a program-loader entry point.
	EF_ARM_SYMSARESORTED = 0x04,	//!< Each subsection of the symbol table is sorted by symbol value.
	EF_ARM_DYNSYMSUSESEGIDX = 0x08,	//!< Symbols in dynamic symbol tables that are defined in sections included in program segment n have #Elf32_Sym.st_shndx = n + 1.
	EF_ARM_MAPSYMSFIRST = 0x10,		//!< Mapping symbols precede other local symbols in the symbol table.
	EF_ARM_EABIMASK = 0xff000000,	//!< This masks an 8-bit version number, the version of the ARM EABI to which this ELF file conforms. The current EABI version is #ARM_EABI_VERSION.
	
	ARM_EABI_VERSION = 0x02000000	//!< Current ARM EABI version.
};

//@}

//! \name Sections
//@{

/*!
 * \brief ELF section header.
 *
 * An object file's section header table lets one locate all the file's
 * sections. The section header table is an array of #Elf32_Shdr structures.
 * A section header table index is a subscript into this array. The ELF
 * header's #Elf32_Ehdr::e_shoff member gives the byte offset from the beginning of
 * the file to the section header table; #Elf32_Ehdr::e_shnum tells how many entries
 * the section header table contains; #Elf32_Ehdr::e_shentsize gives the size in bytes
 * of each entry.
 *
 * Some section header table indexes are reserved. An object file will not
 * have sections for these special indexes:
 *  - #SHN_UNDEF
 *  - #SHN_LORESERVE
 *  - #SHN_LOPROC
 *  - #SHN_HIPROC
 *  - #SHN_ABS
 *  - #SHN_COMMON
 *  - #SHN_HIRESERVE
 */
struct Elf32_Shdr
{
	Elf32_Word sh_name;		//!< The section's name. Index into the section header string table section.
	Elf32_Word sh_type;		//!< Section type, describing the contents and semantics.
	Elf32_Word sh_flags;	//!< Section flags describing various attributes.
	Elf32_Addr sh_addr;		//!< The address at which the section will appear in the memory image, or 0.
	Elf32_Off sh_offset;	//!< Offset from beginning of the file to the first byte in the section.
	Elf32_Word sh_size;		//!< The section's size in bytes.
	Elf32_Word sh_link;		//!< Section header table link index. Interpretation depends on section type.
	Elf32_Word sh_info;		//!< Extra information about the section. Depends on section type.
	Elf32_Word sh_addralign;	//!< Address alignment constraint. Values are 0 and positive powers of 2.
	Elf32_Word sh_entsize;	//!< Size in bytes of section entries, or 0 if the section does not have fixed-size entries.
};

/*!
 * Special section indexes.
 */
enum {
	SHN_UNDEF = 0,
	SHN_LORESERVE = 0xff00,
	SHN_LOPROC = 0xff00,
	SHN_HIPROC = 0xff1f,
	SHN_ABS = 0xfff1,		//!< The symbol has an absolute value that will not change because of relocation.
	SHN_COMMON = 0xfff2,	//!< The symbol labels a common block that has not yet been allocated.
	SHN_HIRESERVE = 0xffff
};

/*!
 * Section type constants.
 */
enum {
	SHT_NULL = 0,
	SHT_PROGBITS = 1,
	SHT_SYMTAB = 2,
	SHT_STRTAB = 3,
	SHT_RELA = 4,
	SHT_HASH = 5,
	SHT_DYNAMIC = 6,
	SHT_NOTE = 7,
	SHT_NOBITS = 8,
	SHT_REL = 9,
	SHT_SHLIB = 10,
	SHT_DYNSYM = 11
};

/*!
 * Section flag constants.
 */
enum {
	SHF_WRITE = 0x1,	//!< Section is writable.
	SHF_ALLOC = 0x2,	//!< Allocate section.
	SHF_EXECINSTR = 0x4	//!< Section contains executable instructions.
};

/*!
 * ARM-specific section flag constants
 */
enum {
	SHF_ENTRYSECT = 0x10000000,	//!< The section contains an entry point.
	SHF_COMDEF = 0x80000000		//!< The section may be multiply defined in the input to a link step.
};

#define BSS_SECTION_NAME ".bss"
#define DATA_SECTION_NAME ".data"
#define TEXT_SECTION_NAME ".text"
#define SHSTRTAB_SECTION_NAME ".shstrtab"
#define STRTAB_SECTION_NAME ".strtab"
#define SYMTAB_SECTION_NAME ".symtab"

//@}

//! \name Segments
//@{

/*!
 * \brief ELF program header.
 *
 * An executable or shared object file's program header table is an array of
 * structures, each describing a segment or other information the system needs
 * to prepare the program for execution. An object file segment contains one
 * or more sections. Program headers are meaningful only for executable and
 * shared object files. A file specifies its own program header size with the
 * ELF header's #Elf32_Ehdr::e_phentsize and #Elf32_Ehdr::e_phnum members.
 */
struct Elf32_Phdr
{
	Elf32_Word p_type;		//!< What type of segment this header describes.
	Elf32_Off p_offset;		//!< Offset in bytes from start of file to the first byte of the segment.
	Elf32_Addr p_vaddr;		//!< Virtual address at which the segment will reside in memory.
	Elf32_Addr p_paddr;		//!< Physical address, for systems where this is relevant.
	Elf32_Word p_filesz;	//!< Number of bytes of file data the segment consumes. May be zero.
	Elf32_Word p_memsz;		//!< Size in bytes of the segment in memory. May be zero.
	Elf32_Word p_flags;		//!< Flags relevant to the segment.
	Elf32_Word p_align;		//!< Alignment constraint for segment addresses. Possible values are 0 and positive powers of 2.
};

/*!
 * Segment type constants.
 */
enum {
	PT_NULL = 0,
	PT_LOAD = 1,
	PT_DYNAMIC = 2,
	PT_INTERP = 3,
	PT_NOTE = 4,
	PT_SHLIB = 5,
	PT_PHDR = 6
};

/*!
 * Program header flag constants.
 */
enum {
	PF_X = 0x1,	//!< Segment is executable.
	PF_W = 0x2,	//!< Segment is writable.
	PF_R = 0x4	//!< Segment is readable.
};

//@}

//! \name Symbol table
//@{

enum {
	STN_UNDEF = 0	//!< Undefined symbol index.
};

/*!
 * \brief ELF symbol table entry.
 *
 * An object file's symbol table holds information needed to locate and
 * relocate a program's symbolic definitions and references. A symbol
 * table index is a subscript into this array. Index 0 both designates
 * the first entry in the table and serves as the undefined symbol index.
 */
struct Elf32_Sym
{
	Elf32_Word st_name;		//!< Index into file's string table.
	Elf32_Addr st_value;	//!< Value associated with the symbol. Depends on context.
	Elf32_Word st_size;		//!< Size associated with symbol. 0 if the symbol has no size or an unknown size.
	unsigned char st_info;	//!< Specified the symbol's type and binding attributes.
	unsigned char st_other;	//!< Currently 0 (reserved).
	Elf32_Half st_shndx;	//!< Section header table index for this symbol.
};

//! \name st_info macros
//! Macros for manipulating the st_info field of Elf32_Sym struct.
//@{
#define ELF32_ST_BIND(i) ((i) >> 4)			//!< Get binding attributes.
#define ELF32_ST_TYPE(i) ((i) & 0x0f)		//!< Get symbol type.
#define ELF32_ST_INFO(b, t) (((b) << 4) + ((t) & 0x0f))	//!< Construct st_info value from binding attributes and symbol type.
//@}

/*!
 * \brief Symbol binding attributes.
 *
 * These constants are mask values.
 */
enum {
	STB_LOCAL = 0,	//!< Local symbol not visible outside the object file.
	STB_GLOBAL = 1,	//!< Symbol is visible to all object files being linked together.
	STB_WEAK = 2,	//!< Like global symbols, but with lower precedence.
	
	// Processor-specific semantics.
	STB_LOPROC = 13,
	STB_HIPROC = 15
};

/*!
 * \brief Symbol types.
 */
enum {
	STT_NOTYPE = 0,		//!< The symbol's type is not specified.
	STT_OBJECT = 1,		//!< The symbol is associated with a data object, such as a variable or array.
	STT_FUNC = 2,		//!< The symbol is associated with a function or other executable code.
	STT_SECTION = 3,	//!< The synmbol is associated with a section. Primarily used for relocation.
	STT_FILE = 4,		//!< A file symbol has STB_LOCAL binding, its section index is SHN_ABS, and it precedes the other STB_LOCAL symbols for the file, if it is present.
	
	STT_LOPROC = 13,	//!< Low bound of processor-specific symbol types.
	STT_HIPROC = 15		//!< High bound of processor-specific symbol types.
};

/*!
 * GHS-specific constants
 */
enum {
	STO_THUMB = 1	//!< This flag is set on #Elf32_Sym.st_other if the symbol is Thumb mode code.
};

#define ARM_SEQUENCE_MAPSYM "$a"
#define DATA_SEQUENCE_MAPSYM "$d"
#define THUMB_SEQUENCE_MAPSYM "$t"

#define THUMB_BL_TAGSYM "$b"
#define FN_PTR_CONST_TAGSYM "$f"
#define INDIRECT_FN_CALL_TAGSYM "$p"
#define MAPPING_SYMBOL_COUNT_TAGSYM "$m"

//@}

#pragma pack()

#endif // _ELF_h_