williamr@2: // Copyright (c) 2001-2009 Nokia Corporation and/or its subsidiary(-ies). williamr@2: // All rights reserved. williamr@2: // This component and the accompanying materials are made available williamr@2: // under the terms of the License "Symbian Foundation License v1.0" to Symbian Foundation members and "Symbian Foundation End User License Agreement v1.0" to non-members williamr@2: // which accompanies this distribution, and is available williamr@2: // at the URL "http://www.symbianfoundation.org/legal/licencesv10.html". williamr@2: // williamr@2: // Initial Contributors: williamr@2: // Nokia Corporation - initial contribution. williamr@2: // williamr@2: // Contributors: williamr@2: // williamr@2: // Description: williamr@2: // lifted from the ARMELF spec williamr@2: // williamr@2: // williamr@2: williamr@2: #ifndef __ELFDEFS_H__ williamr@2: #define __ELFDEFS_H__ williamr@2: williamr@2: williamr@2: // ARMELF 3.1.2 williamr@2: // Data Representation williamr@2: typedef unsigned int Elf32_Addr; //Unsigned program address williamr@2: typedef unsigned short Elf32_Half; //Unsigned medium integer williamr@2: typedef unsigned int Elf32_Off; //Unsigned file offset williamr@2: typedef signed int Elf32_Sword; //Signed large integer williamr@2: typedef unsigned int Elf32_Word; //Unsigned large integer williamr@2: typedef unsigned char UChar; //Unsigned small integer williamr@2: williamr@2: typedef char* MemAddr; williamr@2: /* williamr@2: 3.2 ELF Header williamr@2: Some object file control structures can grow, because the ELF header williamr@2: contains their actual sizes. If the object file format changes, a williamr@2: program may encounter control structures that are larger or smaller williamr@2: than expected. Programs might therefore ignore extra information. The williamr@2: treatment of missing information depends on context and will be williamr@2: specified when and if extensions are defined. williamr@2: */ williamr@2: #define EI_NIDENT 16 williamr@2: typedef struct { williamr@2: williamr@2: // marks the file as an object file and provide machine-independent williamr@2: // data with which to decode and interpret the file's contents. williamr@2: unsigned char e_ident[EI_NIDENT]; williamr@2: williamr@2: // identifies the object file type. williamr@2: Elf32_Half e_type; williamr@2: williamr@2: // specifies the required architecture for an individual file. williamr@2: Elf32_Half e_machine; williamr@2: williamr@2: // identifies the object file version. williamr@2: Elf32_Word e_version; williamr@2: williamr@2: // gives the virtual address to which the system first transfers williamr@2: // control, thus starting the process. If the file has no associated williamr@2: // entry point, this member holds zero. williamr@2: Elf32_Addr e_entry; williamr@2: williamr@2: // holds the program header table's file offset in bytes. If the williamr@2: // file has no program header table, this member holds zero. williamr@2: Elf32_Off e_phoff; williamr@2: williamr@2: // holds the section header table's file offset in bytes. If the williamr@2: // file has no section header table, this member holds zero. williamr@2: Elf32_Off e_shoff; williamr@2: williamr@2: // holds processor-specific flags associated with the file. Flag williamr@2: // names take the form EF_machine_flag. williamr@2: Elf32_Word e_flags; williamr@2: williamr@2: // holds the ELF header's size in bytes. williamr@2: Elf32_Half e_ehsize; williamr@2: williamr@2: // holds the size in bytes of one entry in the file's program williamr@2: // header table; all entries are the same size. williamr@2: Elf32_Half e_phentsize; williamr@2: williamr@2: // holds the number of entries in the program header table. williamr@2: // Thus the product of e_phentsize and e_phnum gives the table's williamr@2: // size in bytes. If a file has no program header table, e_phnum williamr@2: // holds the value zero. williamr@2: Elf32_Half e_phnum; williamr@2: williamr@2: // holds a section header's size in bytes. A section header is williamr@2: // one entry in the section header table; all entries are the same size. williamr@2: Elf32_Half e_shentsize; williamr@2: williamr@2: // holds the number of entries in the section header table. Thus williamr@2: // the product of e_shentsize and e_shnum gives the section header williamr@2: // table's size in bytes. If a file has no section header table, williamr@2: // e_shnum holds the value zero. williamr@2: Elf32_Half e_shnum; williamr@2: williamr@2: // holds the section header table index of the entry associated williamr@2: // with the section name string table. If the file has no section williamr@2: // name string table, this member holds the value SHN_UNDEF. williamr@2: Elf32_Half e_shstrndx; williamr@2: williamr@2: } Elf32_Ehdr; williamr@2: williamr@2: // values for e_type williamr@2: #define ET_NONE 0 // No file type williamr@2: #define ET_REL 1 // Re-locatable williamr@2: #define ET_EXEC 2 // Executable file williamr@2: #define ET_DYN 3 // Shared object williamr@2: #define ET_CORE 4 // Core file williamr@2: #define ET_LOPROC 0xff00 // Processor-specific williamr@2: #define ET_HIPROC 0xffff // Processor-specific williamr@2: williamr@2: //values for e_machine williamr@2: #define EM_NONE 0 // No machine williamr@2: #define EM_M32 1 // AT&T WE 32100 williamr@2: #define EM_SPARC 2 // SPARC williamr@2: #define EM_386 3 // Intel Architecture williamr@2: #define EM_68K 4 // Moto 68000 williamr@2: #define EM_88K 5 // Moto 88000 williamr@2: #define EM_860 7 // Intel 80860 williamr@2: #define EM_MIPS 8 // MIPS RS3000 Big-Endian williamr@2: #define EM_MIPS_RS4_BE 10 // MIPS RS4000 Big-Endian williamr@2: //#define RESERVED 11-16 Reserved for future use williamr@2: #define EM_ARM 40 //ARM/Thumb Architecture williamr@2: williamr@2: // values for e_version williamr@2: #define EV_NONE 0 // Invalid version williamr@2: #define EV_CURRENT 1 // Current version williamr@2: williamr@2: // ELF Identification williamr@2: #define EI_MAG0 0 // File identification williamr@2: #define EI_MAG1 1 // File identification williamr@2: #define EI_MAG2 2 // File identification williamr@2: #define EI_MAG3 3 // File identification williamr@2: #define EI_CLASS 4 // File class williamr@2: #define EI_DATA 5 // Data encoding williamr@2: #define EI_VERSION 6 // File version williamr@2: #define EI_PAD 7 // Start of padding bytes williamr@2: williamr@2: // values for e_ident[0-3] williamr@2: #define ELFMAG0 0x7f // e_ident[EI_MAG0] williamr@2: #define ELFMAG1 'E' // e_ident[EI_MAG1] williamr@2: #define ELFMAG2 'L' // e_ident[EI_MAG2] williamr@2: #define ELFMAG3 'F' // e_ident[EI_MAG3] williamr@2: williamr@2: // values for e_ident[EI_CLASS]- identifies the file's class, or capacity. williamr@2: #define ELFCLASSNONE 0 // Invalid class williamr@2: #define ELFCLASS32 1 // 32-bit objects williamr@2: #define ELFCLASS64 2 // 64-bit objects williamr@2: williamr@2: // values for e_ident[EI_DATA] - specifies the data encoding of the williamr@2: // processor-specific data in the object file. williamr@2: #define ELFDATANONE 0 // Invalid data encoding williamr@2: #define ELFDATA2LSB 1 // 2's complement , with LSB at lowest address. williamr@2: #define ELFDATA2MSB 2 // 2's complement , with MSB at lowest address. williamr@2: williamr@2: // ARM/THUMB specific values for e_flags williamr@2: williamr@2: // e_entry contains a program-loader entry point williamr@2: #define EF_ARM_HASENTRY 0x02 williamr@2: // Each subsection of the symbol table is sorted by symbol value williamr@2: #define EF_ARM_SYMSARESORTED 0x04 williamr@2: // Symbols in dynamic symbol tables that are defined in sections williamr@2: // included in program segment n have st_shndx = n+ 1. williamr@2: #define EF_ARM_DYNSYMSUSESEGIDX 0x8 williamr@2: // Mapping symbols precede other local symbols in the symbol table williamr@2: #define EF_ARM_MAPSYMSFIRST 0x10 williamr@2: // This masks an 8-bit version number, the version of the ARM EABI to williamr@2: // which this ELF file conforms. This EABI is version 2. A value of 0 williamr@2: // denotes unknown conformance. (current version is 0x02000000) williamr@2: #define EF_ARM_EABIMASK 0xFF000000 williamr@2: williamr@2: #define EF_ARM_EABI_VERSION 0x02000000 williamr@2: #define EF_ARM_BPABI_VERSION 0x04000000 williamr@2: williamr@2: /* williamr@2: 3.3 Sections williamr@2: williamr@2: An object file's section header table lets one locate all the file's williamr@2: sections. The section header table is an array of Elf32_Shdr williamr@2: structures as described below. A section header table index is a williamr@2: subscript into this array. The ELF header's e_shoff member gives the williamr@2: byte offset from the beginning of the file to the section header williamr@2: table; e_shnum tells how many entries the section header table williamr@2: contains; e_shentsize gives the size in bytes of each entry. williamr@2: */ williamr@2: williamr@2: // Some section header table indexes are reserved; an object file will williamr@2: // not have sections for these special indexes. williamr@2: williamr@2: // marks an undefined, missing, irrelevant, or otherwise meaningless williamr@2: // section reference. williamr@2: #define SHN_UNDEF 0 williamr@2: // specifies the lower bound of the range of reserved indexes. williamr@2: #define SHN_LORESERVE 0xff00 williamr@2: // SHN_LOPROC-SHN_HIPRO - this inclusive range reserved for williamr@2: // processor-specific semantics. williamr@2: #define SHN_LOPROC 0xff00 williamr@2: #define SHN_HIPROC 0xff1f williamr@2: // Specifies absolute values for the corresponding reference. williamr@2: // For example, symbols defined relative to section number SHN_ABS have williamr@2: // absolute values and are not affected by relocation. williamr@2: #define SHN_ABS 0xfff1 williamr@2: // Symbols defined relative to this section are common symbols, williamr@2: // such as FORTRAN COMMON or unallocated C external variables. williamr@2: #define SHN_COMMON 0xfff2 williamr@2: // specifies the upper bound of the range of reserved indexes. williamr@2: #define SHN_HIRESERVE 0xffff williamr@2: williamr@2: typedef struct { williamr@2: williamr@2: // specifies the name of the section. Its value is an index into the williamr@2: // section header string table section [see String Tablebelow], williamr@2: // giving the location of a null-terminated string. williamr@2: Elf32_Word sh_name; williamr@2: williamr@2: // categorizes the section's contents and semantics. Section types williamr@2: // and their descriptions appear below. williamr@2: Elf32_Word sh_type; williamr@2: williamr@2: // Sections support 1-bit flags that describe miscellaneous williamr@2: // attributes. Flag definitions appear below. williamr@2: Elf32_Word sh_flags; williamr@2: williamr@2: // If the section will appear in the memory image of a process, this williamr@2: // member gives the address at which the section's first byte should williamr@2: // reside. Otherwise, the member contains 0. williamr@2: Elf32_Addr sh_addr; williamr@2: williamr@2: // gives the byte offset from the beginning of the file to the first williamr@2: // byte in the section.One section type, SHT_NOBITS described below, williamr@2: // occupies no space in the file, and its sh_offset member locates williamr@2: // the conceptual placement in the file. williamr@2: Elf32_Off sh_offset; williamr@2: williamr@2: // gives the section's size in bytes. Unless the section type is williamr@2: // SHT_NOBITS, the section occupies sh_size bytes in the file. A williamr@2: // section of type SHT_NOBITS may have a non-zero size, but it williamr@2: // occupies no space in the file. williamr@2: Elf32_Word sh_size; williamr@2: williamr@2: // holds a section header table index link, whose interpretation williamr@2: // depends on the section type. A table below describes the values. williamr@2: Elf32_Word sh_link; williamr@2: williamr@2: // holds extra information, whose interpretation depends on the williamr@2: // section type. A table below describes the values. williamr@2: Elf32_Word sh_info; williamr@2: williamr@2: // Some sections have address alignment constraints. For example, if williamr@2: // a section holds a doubleword, the system must ensure double-word williamr@2: // alignment for the entire section. That is, the value of sh_addr williamr@2: // must be congruent to 0, modulo the value of williamr@2: // sh_addralign. Currently, only 0 and positive integral powers of williamr@2: // two are allowed. Values 0 and 1 mean the section has no alignment williamr@2: // constraints. williamr@2: Elf32_Word sh_addralign; williamr@2: williamr@2: // Some sections hold a table of fixed-size entries, such as a williamr@2: // symbol table. For such a section, this member gives the size in williamr@2: // bytes of each entry. The member contains 0 if the section does williamr@2: // not hold a table of fixedsize entries. A section header's sh_type williamr@2: // member specifies the section's semantics. williamr@2: Elf32_Word sh_entsize; williamr@2: williamr@2: } Elf32_Shdr; williamr@2: williamr@2: // values for sh_type williamr@2: williamr@2: #define SHT_NULL 0 // marks the section header as inactive; it does williamr@2: // not have an associated section. Other members of the section williamr@2: // header have undefined values. williamr@2: #define SHT_PROGBITS 1 // The section holds information defined by the williamr@2: // program, whose format and meaning are determined solely by the williamr@2: // program. williamr@2: #define SHT_SYMTAB 2 //These sections hold a symbol table. williamr@2: #define SHT_STRTAB 3 // The section holds a string table. williamr@2: #define SHT_RELA 4 // The section holds relocation entries with williamr@2: // explicit addends, such as type Elf32_Rela for the 32-bit class of williamr@2: // object files. An object file may have multiple relocation williamr@2: // sections. See Relocationbelow for details. williamr@2: #define SHT_HASH 5 // The section holds a symbol hash table. williamr@2: #define SHT_DYNAMIC 6 // The section holds information for dynamic williamr@2: // linking. williamr@2: #define SHT_NOTE 7 // This section holds information that marks the williamr@2: // file in some way. williamr@2: #define SHT_NOBITS 8 // A section of this type occupies no space in williamr@2: // the file but otherwise resembles SHT_PROGBITS. Although this williamr@2: // section contains no bytes, the sh_offset member contains the williamr@2: // conceptual file offset. williamr@2: #define SHT_REL 9 // The section holds relocation entries without williamr@2: // explicit addends, such as type Elf32_Rel for the 32-bit class of williamr@2: // object files. An object file may have multiple relocation williamr@2: // sections. See Relocationbelow for details. williamr@2: #define SHT_SHLIB 10 // This section type is reserved but has williamr@2: // unspecified semantics. williamr@2: #define SHT_DYNSYM 11 // This section hold dynamic symbol information williamr@2: // SHT_LOPROC through SHT_HIPROC - Values in this inclusive range are williamr@2: // reserved for processor-specific semantics. williamr@2: #define SHT_LOPROC 0x70000000 williamr@2: #define SHT_ARM_EXIDX 0x70000001 williamr@2: #define SHT_HIPROC 0x7fffffff williamr@2: // Section types between SHT_LOUSER and SHT_HIUSER may be used by the williamr@2: // application, without conflicting with current or future williamr@2: // system-defined section types. williamr@2: #define SHT_LOUSER 0x80000000 // This value specifies the lower bound williamr@2: // of the range of indexes reserved for application programs. williamr@2: #define SHT_HIUSER 0xffffffff // This value specifies the upper bound williamr@2: // of the range of indexes reserved for application programs. williamr@2: williamr@2: // values for sh_flags williamr@2: williamr@2: // The section contains data that should be writable during process execution williamr@2: #define SHF_WRITE 0x1 williamr@2: // The section occupies memory during process execution. Some control williamr@2: // sections do not reside in the memory image of an object file; this williamr@2: // attribute is off for those sections williamr@2: #define SHF_ALLOC 0x2 williamr@2: // The section contains executable machine instructions. williamr@2: #define SHF_EXECINSTR 0x4 williamr@2: // Bits in this mask are reserved for processor-specific semantics. williamr@2: #define SHF_MASKPROC 0xf0000000 williamr@2: williamr@2: williamr@2: typedef struct { williamr@2: williamr@2: // holds an index into the object file's symbol string table, which williamr@2: // holds the character representations of the symbol names. williamr@2: Elf32_Word st_name; williamr@2: williamr@2: // gives the value of the associated symbol. Depending on the williamr@2: // context this may be an absolute value, an address, and so on williamr@2: Elf32_Addr st_value; williamr@2: williamr@2: // Many symbols have associated sizes. For example, a data object's williamr@2: // size is the number of bytes contained in the object. This member williamr@2: // holds 0 if the symbol has no size or an unknown size. williamr@2: Elf32_Word st_size; williamr@2: williamr@2: // This member specifies the symbol's type and binding williamr@2: // attributes. The following code shows how to manipulate the williamr@2: // values. williamr@2: #define ELF32_ST_BIND(i) ((i)>>4) williamr@2: #define ELF32_ST_TYPE(i) ((i)&0xf) williamr@2: #define ELF32_ST_INFO(b,t) (((b)<<4)+((t)&0xf)) williamr@2: unsigned char st_info; williamr@2: williamr@2: // This member currently holds 0 and has no defined meaning. williamr@2: unsigned char st_other; williamr@2: williamr@2: williamr@2: #define ELF32_ST_VISIBILITY(o) ((o)&0x3) williamr@2: #define ELF64_ST_VISIBILITY(o) ((o)&0x3) williamr@2: williamr@2: // Every symbol table entry is defined in relation to some section; williamr@2: // this member holds the relevant section header table index. williamr@2: Elf32_Half st_shndx; williamr@2: williamr@2: } Elf32_Sym; williamr@2: williamr@2: // Local symbols are not visible outside the object file containing williamr@2: // their definition. Local symbols of the same name may exist in williamr@2: // multiple files without interfering with each other. williamr@2: #define STB_LOCAL 0 williamr@2: // Global symbols are visible to all object files being combined. One williamr@2: // file's definition of a global symbol will satisfy another file's williamr@2: // undefined reference to the same global symbol. williamr@2: #define STB_GLOBAL 1 williamr@2: // Weak symbols resemble global symbols, but their definitions have williamr@2: // lower precedence. Undefined weak symbols (weak references) may have williamr@2: // processor- or OS-specific semantics williamr@2: #define STB_WEAK 2 williamr@2: // STB_LOPROC through STB_HIPROC - values in this inclusive range are williamr@2: // reserved for processor-specific semantics. williamr@2: #define STB_LOPROC 13 williamr@2: #define STB_HIPROC 15 williamr@2: williamr@2: // The symbol's type is not specified. williamr@2: #define STT_NOTYPE 0 williamr@2: // The symbol is associated with a data object, such as a variable, an williamr@2: // array, and so on. williamr@2: #define STT_OBJECT 1 williamr@2: // The symbol is associated with a function or other executable code. williamr@2: #define STT_FUNC 2 williamr@2: // The symbol is associated with a section. Symbol table entries of williamr@2: // this type exist primarily for relocation and normally have williamr@2: // STB_LOCAL binding. williamr@2: #define STT_SECTION 3 williamr@2: // A file symbol has STB_LOCAL binding, its section index is SHN_A BS, williamr@2: // and it precedes the other STB_LOCAL symbols for the file, if it is williamr@2: // present. williamr@2: #define STT_FILE 4 williamr@2: // Values in this inclusive range are reserved for processor-specific williamr@2: // semantics. If a symbol's value refers to a specific location within williamr@2: // a section, its section index member, st_shndx, holds an index into williamr@2: // the section header table. As the section moves during relocation, williamr@2: // the symbol's value changes as well, and references to the symbol williamr@2: // continue to point to the same location in the program. Some special williamr@2: // section index values give other semantics. williamr@2: #define STT_LOPROC 13 williamr@2: #define STT_HIPROC 15 williamr@2: williamr@2: /* williamr@2: STV_DEFAULT williamr@2: The visibility of symbols with the STV_DEFAULT attribute is as specified by the symbol's williamr@2: binding type. That is, global and weak symbols are visible outside of their defining williamr@2: component, the executable file or shared object. Local symbols are hidden. Global and weak williamr@2: symbols can also be preempted, that is, they may by interposed by definitions of the same williamr@2: name in another component. williamr@2: williamr@2: STV_PROTECTED williamr@2: A symbol defined in the current component is protected if it is visible in other components williamr@2: but cannot be preempted. Any reference to such a symbol from within the defining component williamr@2: must be resolved to the definition in that component, even if there is a definition in williamr@2: another component that would interpose by the default rules. A symbol with STB_LOCAL binding williamr@2: will not have STV_PROTECTED visibility. williamr@2: williamr@2: STV_HIDDEN williamr@2: A symbol defined in the current component is hidden if its name is not visible to other williamr@2: components. Such a symbol is necessarily protected. This attribute is used to control williamr@2: the external interface of a component. An object named by such a symbol may still be williamr@2: referenced from another component if its address is passed outside. williamr@2: williamr@2: A hidden symbol contained in a relocatable object is either removed or converted to williamr@2: STB_LOCAL binding by the link-editor when the relocatable object is included in an williamr@2: executable file or shared object. williamr@2: williamr@2: STV_INTERNAL williamr@2: This visibility attribute is currently reserved. williamr@2: */ williamr@2: #define STV_DEFAULT 0 williamr@2: #define STV_INTERNAL 1 williamr@2: #define STV_HIDDEN 2 williamr@2: #define STV_PROTECTED 3 williamr@2: williamr@2: // Relocation Entries williamr@2: williamr@2: typedef struct { williamr@2: williamr@2: // r_offset gives the location at which to apply the relocation williamr@2: // action. For a relocatable file, the value is the byte offset from williamr@2: // the beginning of the section to the storage unit affected by the williamr@2: // relocation. For an executable file or a shared object, the value williamr@2: // is the virtual address of the storage unit affected by the williamr@2: // relocation. williamr@2: Elf32_Addr r_offset; williamr@2: williamr@2: // r_info gives both the symbol table index with respect to which williamr@2: // the relocation must be made, and the type of relocation to williamr@2: // apply. For example, a call instruction's relocation entry would williamr@2: // hold the symbol table index of the function being called. If the williamr@2: // index is STN_UNDEF, the undefined symbol index, the relocation williamr@2: // uses 0 as the symbol value. Relocation types are williamr@2: // processor-specific; descriptions of their behavior appear in williamr@2: // section 4.5, Relocation types. When the text in section 4.5 williamr@2: // refers to a relocation entry's relocation type or symbol table williamr@2: // index, it means the result of applying ELF32_R_TYPE or williamr@2: // ELF32_R_SYM, respectively, to the entry's r_info member. williamr@2: williamr@2: #define ELF32_R_SYM(i) ((i)>>8) williamr@2: #define ELF32_R_TYPE(i) ((unsigned char)(i)) williamr@2: #define ELF32_R_INFO(s,t) (((s)<<8)+(unsigned char)(t)) williamr@2: williamr@2: Elf32_Word r_info; williamr@2: } Elf32_Rel; williamr@2: williamr@2: typedef struct { williamr@2: Elf32_Addr r_offset; williamr@2: Elf32_Word r_info; williamr@2: Elf32_Sword r_addend; williamr@2: } Elf32_Rela; williamr@2: williamr@2: // Program Header williamr@2: williamr@2: typedef struct { williamr@2: williamr@2: // p_type tells what kind of segment this array element describes or williamr@2: // how to interpret the array element's information. Type values and williamr@2: // their meanings are given below. williamr@2: Elf32_Word p_type; williamr@2: williamr@2: // p_offset gives the offset from the start of the file at which the williamr@2: // first byte of the segment resides. williamr@2: Elf32_Off p_offset; williamr@2: williamr@2: // p_vaddr gives the virtual address at which the first byte of the williamr@2: // segment resides in memory. williamr@2: Elf32_Addr p_vaddr; williamr@2: williamr@2: // p_paddr - On systems for which physical addressing is relevant, williamr@2: // this member is reserved for the segment's physical address. This williamr@2: // member requires operating system specific information. williamr@2: Elf32_Addr p_paddr; williamr@2: williamr@2: // p_filesz gives the number of bytes in the file image of the williamr@2: // segment; it may be zero. williamr@2: Elf32_Word p_filesz; williamr@2: williamr@2: // p_memsz gives the number of bytes in the memory image of the williamr@2: // segment; it may be zero. williamr@2: Elf32_Word p_memsz; williamr@2: williamr@2: // p_flags gives flags relevant to the segment. Defined flag values williamr@2: // are given below. williamr@2: Elf32_Word p_flags; williamr@2: williamr@2: // p_align - Loadable process segments must have congruent values williamr@2: // for p_vaddr and p_offset, modulo the page size. This member gives williamr@2: // the value to which the segments are aligned in memory and in the williamr@2: // file. Values 0 and 1 mean that no alignment is williamr@2: // required. Otherwise, p_align should be a positive, integral power williamr@2: // of 2, and p_vaddr should equal p_offset, modulo p_align. williamr@2: Elf32_Word p_align; williamr@2: williamr@2: } Elf32_Phdr; williamr@2: williamr@2: // Segment types - values for p_type williamr@2: williamr@2: // The array element is unused; other members' values are williamr@2: // undefined. This type lets the program header table have ignored williamr@2: // entries. williamr@2: #define PT_NULL 0 williamr@2: // The array element specifies a loadable segment, described by williamr@2: // p_filesz and p_memsz (for additional explanation, see williamr@2: // PT_LOAD below). williamr@2: #define PT_LOAD 1 williamr@2: // The array element specifies dynamic linking information. See williamr@2: // subsection 4.7. williamr@2: #define PT_DYNAMIC 2 williamr@2: // The array element specifies the location and size of a williamr@2: // null-terminated pathname to invoke as an interpreter. williamr@2: #define PT_INTERP 3 williamr@2: // The array element specifies the location and size of auxiliary williamr@2: // information. williamr@2: #define PT_NOTE 4 williamr@2: // This segment type is reserved but has unspecified semantics. williamr@2: #define PT_SHLIB 5 williamr@2: // The array element, if present, specifies the location and size of williamr@2: // the program header table itself (for additional explanation, see williamr@2: // PT_ PHDR below). williamr@2: #define PT_PHDR 6 williamr@2: // Values in the inclusive [PT_LOPROC, PT_HIPROC] range are reserved williamr@2: // for processor-specific semantics. williamr@2: #define PT_LOPROC 0x70000000 williamr@2: #define PT_HIPROC 0x7fffffff williamr@2: williamr@2: // values for p_flags williamr@2: // The segment may be executed. williamr@2: #define PF_X 1 williamr@2: // The segment may be written to. williamr@2: #define PF_W 2 williamr@2: // The segment may be read. williamr@2: #define PF_R 4 williamr@2: // Reserved for processor-specific purposes (see 4.6, Program williamr@2: // headers). williamr@2: #define PF_MASKPROC 0xf0000000 williamr@2: #define PF_ARM_ENTRY 0x80000000 williamr@2: williamr@2: williamr@2: // Relocation types williamr@2: williamr@2: // ELF defines two sorts of relocation directive, SHT_REL, and williamr@2: // SHT_RELA. Both identify: williamr@2: // williamr@2: // o A section containing the storage unit - byte, half-word, word, or williamr@2: // instruction - being relocated. williamr@2: // o An offset within the section - or the address within an williamr@2: // executable program - of the storage unit itself. williamr@2: // o A symbol,the value of which helps to define a new value for the williamr@2: // storage unit. williamr@2: // o A relocation typethat defines the computation to be williamr@2: // performed. Computations are performed using 2's complement, 32-bit, williamr@2: // unsigned arithmetic with silent overflow. williamr@2: // o An addend, that also helps to define a new value for the storage williamr@2: // unit. williamr@2: // williamr@2: // The addend may be encoded wholly in a field of the storage unit williamr@2: // being relocated - relocation sort SHT_REL - or partly there and williamr@2: // partly in the addendfield of the relocation directive - relocation williamr@2: // sort SHT_RELA. Tables below describe the computation associated williamr@2: // with each relocation type, using the following notation: williamr@2: // williamr@2: // A - denotes the addend used to compute the new value of the storage williamr@2: // unit being relocated. williamr@2: // - It is the value extracted from the storage unit being relocated williamr@2: // (relocation directives of sort SHT_REL) or the sum of that williamr@2: // value and the r_addend field of the relocation directive (sort williamr@2: // SHT_RELA). williamr@2: // - If it has a unit, the unit is bytes. An encoded address or williamr@2: // offset value is converted to bytes on extraction from a storage williamr@2: // unit and re-encoded on insertion into a storage unit. williamr@2: // williamr@2: // P - denotes the place (section offset or address of the storage williamr@2: // unit) being re-located. It is the sum of the r_offset field of williamr@2: // the relocation directive and the base address of the section williamr@2: // being re-located. williamr@2: // williamr@2: // S - denotes the value of the symbol whose symbol table index is williamr@2: // given in the r_info field of the relocation directive. williamr@2: // williamr@2: // B - denotes the base address of the consolidated section in which williamr@2: // the symbol is defined. For relocations of type R_ARM_SBREL32, williamr@2: // this is the least static data address (the static base). williamr@2: // williamr@2: // relocation types 0-16 are generic williamr@2: // Name Type Field Computation williamr@2: //==================================================================== williamr@2: #define R_ARM_NONE 0 // Any No relocation. williamr@2: #define R_ARM_PC24 1 // ARM B/BL S - P + A williamr@2: #define R_ARM_ABS32 2 // 32-bit word S + A williamr@2: #define R_ARM_REL32 3 // 32-bit word S - P + A williamr@2: #define R_ARM_PC13 4 // ARM LDR r, [pc,...] S - P + A williamr@2: #define R_ARM_ABS16 5 // 16-bit half-word S + A williamr@2: #define R_ARM_ABS12 6 // ARM LDR/STR S + A williamr@2: #define R_ARM_THM_ABS5 7 // Thumb LDR/STR S + A williamr@2: #define R_ARM_ABS8 8 // 8-bit byte S + A williamr@2: #define R_ARM_SBREL32 9 // 32-bit word S - B + A williamr@2: #define R_ARM_THM_PC22 10 // Thumb BL pair S - P + A williamr@2: #define R_ARM_THM_PC8 11 // Thumb LDR r, [pc,...] S - P + A williamr@2: #define R_ARM_AMP_VCALL9 12 // AMP VCALL Obsolete - SA-1500 williamr@2: #define R_ARM_SWI24 13 // ARM SWI S + A williamr@2: #define R_ARM_THM_SWI8 14 // Thumb SWI S + A williamr@2: #define R_ARM_XPC25 15 // ARM BLX S - P + A williamr@2: #define R_ARM_THM_XPC22 16 // Thumb BLX pair S - P + A williamr@2: williamr@2: // relocation types 17-31 are reserved for ARM Linux williamr@2: #define R_ARM_GLOB_DAT 21 // PLT related S + A williamr@2: #define R_ARM_JUMP_SLOT 22 // PLT related S + A williamr@2: #define R_ARM_RELATIVE 23 // 32-bit word B(S) + A williamr@2: williamr@2: #define R_ARM_GOT_BREL 26 // williamr@2: williamr@2: #define R_ARM_ALU_PCREL_7_0 32 // ARM ADD/SUB (S - P + A) & 0x000000FF williamr@2: #define R_ARM_ALU_PCREL_15_8 33 // ARM ADD/SUB (S - P + A) & 0x0000FF00 williamr@2: #define R_ARM_ALU_PCREL_23_15 34 // ARM ADD/SUB (S - P + A) & 0x00FF0000 williamr@2: #define R_ARM_LDR_SBREL_11_0 35 // ARM ADD/SUB (S - B + A) & 0x00000FFF williamr@2: #define R_ARM_ALU_SBREL_19_12 36 // ARM ADD/SUB (S - B + A) & 0x000FF000 williamr@2: #define R_ARM_ALU_SBREL_27_20 37 // ARM ADD/SUB (S - B + A) & 0x0FF00000 williamr@2: williamr@2: // Dynamic relocation types williamr@2: williamr@2: // A small set of relocation types supports relocating executable ELF williamr@2: // files. They are used only in a relocation section embedded in a williamr@2: // dynamic segment (see section 4.7, Dynamic linking and williamr@2: // relocation). They cannot be used in a relocation section in a williamr@2: // re-locatable ELF file. In Figure 4-13 below: williamr@2: // williamr@2: // .S is the displacement from its statically linked virtual address williamr@2: // of the segment containing the symbol definition. williamr@2: // williamr@2: // .P is the displacement from its statically linked virtual address williamr@2: // of the segment containing the place to be relocated. williamr@2: // williamr@2: // .SB is the displacement of the segment pointed to by the static williamr@2: // base (PF_ARM_SB is set in the p_flags field of this segment's williamr@2: // program header - see 4.6, Program headers). williamr@2: williamr@2: williamr@2: // types 249 - 255 are dynamic relocation types and are only used in dynamic sections williamr@2: #define R_ARM_RXPC25 249 // ARM BLX (.S - .P) + A williamr@2: // For calls between program segments. williamr@2: #define R_ARM_RSBREL32 250 // Word (.S - .SB) + A williamr@2: // For an offset from SB, the static base. williamr@2: #define R_ARM_THM_RPC22 251 // Thumb BL/BLX pair (.S - .P) + A williamr@2: // For calls between program segments. williamr@2: #define R_ARM_RREL32 252 // Word (.S - .P) + A williamr@2: // For on offset between two segments. williamr@2: #define R_ARM_RABS32 253 // Word .S + A williamr@2: // For the address of a location in the target segment. williamr@2: #define R_ARM_RPC24 254 // ARM B/BL (.S - .P) + A williamr@2: // For calls between program segments. williamr@2: #define R_ARM_RBASE 255 // None Identifies the segment being relocated by williamr@2: // the following relocation directives. williamr@2: // DYNAMIC SEGMENT williamr@2: // The dynamic segment begins with a dynamic section containing an array of structures of type: williamr@2: typedef struct Elf32_Dyn { williamr@2: Elf32_Sword d_tag; williamr@2: Elf32_Word d_val; williamr@2: } Elf32_Dyn; williamr@2: williamr@2: // This entry marks the end of the dynamic array. mandatory williamr@2: #define DT_NULL 0 williamr@2: // Index in the string table of the name of a needed library. multiple williamr@2: #define DT_NEEDED 1 williamr@2: // These entries are unused by versions 1-2 of the ARM EABI. unused williamr@2: #define DT_PLTRELSZ 2 williamr@2: #define DT_PLTGOT 3 williamr@2: // The offset of the hash table section in the dynamic segment. mandatory williamr@2: #define DT_HASH 4 williamr@2: // The offset of the string table section in the dynamic segment. mandatory williamr@2: #define DT_STRTAB 5 williamr@2: // The offset of the symbol table section in the dynamic segment. mandatory williamr@2: #define DT_SYMTAB 6 williamr@2: // The offset in the dynamic segment of an SHT_RELA relocation williamr@2: // section, Its bytesize,and the byte size of an ARMRELA-type williamr@2: // relocation entry. optional williamr@2: #define DT_RELA 7 williamr@2: #define DT_RELASZ 8 williamr@2: #define DT_RELAENT 9 williamr@2: // The byte size of the string table section. mandatory williamr@2: #define DT_STRSZ 10 williamr@2: // The byte size of an ARM symbol table entry. mandatory williamr@2: #define DT_SYMENT 11 williamr@2: // These entries are unused by versions 1-2 of the ARM EABI. unused williamr@2: #define DT_INIT 12 williamr@2: #define DT_FINI 13 williamr@2: // The Index in the string table of the name of this shared object. mandatory williamr@2: #define DT_SONAME 14 williamr@2: // Unused by the ARM EABI. unused williamr@2: #define DT_RPATH 15 williamr@2: #define DT_SYMBOLIC 16 williamr@2: //The offset in the dynamic segment of an SHT_REL relocation section, williamr@2: //Its bytesize, and the byte size of an ARMREL-type relocation williamr@2: //entry. optional williamr@2: #define DT_REL 17 williamr@2: #define DT_RELSZ 18 williamr@2: #define DT_RELENT 19 williamr@2: // These entries are unused by versions 1-2 of the ARM EABI. unused williamr@2: #define DT_PLTREL 20 williamr@2: #define DT_DEBUG 21 williamr@2: #define DT_TEXTREL 22 williamr@2: #define DT_JMPREL 23 williamr@2: #define DT_BIND_NOW 24 williamr@2: #define DT_INIT_ARRAY 25 williamr@2: #define DT_FINI_ARRAY 26 williamr@2: #define DT_INIT_ARRAYSZ 27 williamr@2: #define DT_FINI_ARRAYSZ 28 williamr@2: williamr@2: #define DT_VERSYM 0x6ffffff0 /* see section 3.3.3.1 in bpabi*/ williamr@2: #define DT_RELCOUNT 0x6ffffffa williamr@2: #define DT_VERDEF 0x6ffffffc /* Address of version definition williamr@2: table */ williamr@2: #define DT_VERDEFNUM 0x6ffffffd /* Number of version definitions */ williamr@2: #define DT_VERNEED 0x6ffffffe /* Address of table with needed williamr@2: versions */ williamr@2: #define DT_VERNEEDNUM 0x6fffffff /* Number of needed versions */ williamr@2: williamr@2: // Values in this range are reserved to the ARM EABI. unused williamr@2: #define DT_LOPROC 0x70000000 williamr@2: #define DT_HIPROC 0x7fffffff williamr@2: #define DT_ARM_RESERVED1 0x70000000 williamr@2: /* Number of entries in the dynamic symbol table, including the initial dummy symbol. */ williamr@2: #define DT_ARM_SYMTABSZ_21 0x70000000 // For RVCT 2.1 williamr@2: #define DT_ARM_SYMTABSZ 0x70000001 // The DT_ARM_SYMTABSZ tag value has been changed from RVCT2.2 williamr@2: /* Holds the address of the pre-emption map for platforms that use the DLL static binding model. */ williamr@2: #define DT_ARM_PREEMPTMAP 0x70000002 williamr@2: #define DT_ARM_RESERVED2 0x70000003 williamr@2: #define DT_ARM_PLTGOTBASE 0x70000004 williamr@2: #define DT_ARM_PLTGOTLIMIT 0x70000005 williamr@2: williamr@2: // What the hash table looks like in the dynamic segment williamr@2: typedef struct Elf32_HashTable { williamr@2: Elf32_Word nBuckets; williamr@2: Elf32_Word nChains; williamr@2: // Elf32_Word bucket[nBuckets]; williamr@2: // Elf32_Word chain[nChains]; williamr@2: } Elf32_HashTable; williamr@2: williamr@2: williamr@2: typedef struct williamr@2: { williamr@2: Elf32_Half vd_version; /* Version revision */ williamr@2: Elf32_Half vd_flags; /* Version information */ williamr@2: Elf32_Half vd_ndx; /* Version Index */ williamr@2: Elf32_Half vd_cnt; /* Number of associated aux entries */ williamr@2: Elf32_Word vd_hash; /* Version name hash value */ williamr@2: Elf32_Word vd_aux; /* Offset in bytes to verdaux array */ williamr@2: Elf32_Word vd_next; /* Offset in bytes to next verdef williamr@2: entry */ williamr@2: } Elf32_Verdef; williamr@2: williamr@2: typedef struct williamr@2: { williamr@2: Elf32_Word vda_name; /* Version or dependency names */ williamr@2: Elf32_Word vda_next; /* Offset in bytes to next verdaux williamr@2: entry */ williamr@2: } Elf32_Verdaux; williamr@2: williamr@2: williamr@2: typedef struct williamr@2: { williamr@2: Elf32_Half vn_version; /* Version of structure */ williamr@2: Elf32_Half vn_cnt; /* Number of associated aux entries */ williamr@2: Elf32_Word vn_file; /* Offset of filename for this williamr@2: dependency */ williamr@2: Elf32_Word vn_aux; /* Offset in bytes to vernaux array */ williamr@2: Elf32_Word vn_next; /* Offset in bytes to next verneed williamr@2: entry */ williamr@2: } Elf32_Verneed; williamr@2: williamr@2: typedef struct { williamr@2: Elf32_Word vna_hash; williamr@2: Elf32_Half vna_flags; williamr@2: Elf32_Half vna_other; williamr@2: Elf32_Word vna_name; williamr@2: Elf32_Word vna_next; williamr@2: } Elf32_Vernaux; williamr@2: williamr@2: williamr@2: enum ESegmentType williamr@2: { williamr@2: ESegmentUndefined = SHN_UNDEF, // undefined or meaningless section/segment reference williamr@2: ESegmentRO, // Read Only (text) segment williamr@2: ESegmentRW, // Read Write (data) segment williamr@2: ESegmentDynamic, // Dynamic segment williamr@2: ESegmentABS = SHN_ABS, // Symbols defined relative to section number SHN_ABS have williamr@2: // absolute values and are not affected by relocation. williamr@2: ESegmentCommon = SHN_COMMON, // Symbols defined relative to section number SHN_ABS have williamr@2: // absolute values and are not affected by relocation. williamr@2: }; williamr@2: williamr@2: #endif