/rust/registry/src/index.crates.io-6f17d22bba15001f/linux-raw-sys-0.9.4/src/elf.rs
Line | Count | Source (jump to first uncovered line) |
1 | | //! The ELF ABI. 🧝 |
2 | | //! |
3 | | //! This module is not as comprehensive as bindgened [`elf_uapi`] and provides only types for target |
4 | | //! pointer width: instead of [`elf32_phdr`] and [`elf64_phdr`] there's only [`Elf_Phdr`]. |
5 | | //! |
6 | | //! [`elf_uapi`]: super::elf_uapi |
7 | | //! [`elf32_phdr`]: super::elf_uapi::elf32_phdr |
8 | | //! [`elf64_phdr`]: super::elf_uapi::elf64_phdr |
9 | | |
10 | | pub const SELFMAG: usize = 4; |
11 | | pub const ELFMAG: [u8; SELFMAG] = [0x7f, b'E', b'L', b'F']; |
12 | | pub const EI_CLASS: usize = 4; |
13 | | pub const EI_DATA: usize = 5; |
14 | | pub const EI_VERSION: usize = 6; |
15 | | pub const EI_OSABI: usize = 7; |
16 | | pub const EI_ABIVERSION: usize = 8; |
17 | | pub const EV_CURRENT: u8 = 1; |
18 | | #[cfg(target_pointer_width = "32")] |
19 | | pub const ELFCLASS: u8 = 1; // ELFCLASS32 |
20 | | #[cfg(target_pointer_width = "64")] |
21 | | pub const ELFCLASS: u8 = 2; // ELFCLASS64 |
22 | | #[cfg(target_endian = "little")] |
23 | | pub const ELFDATA: u8 = 1; // ELFDATA2LSB |
24 | | #[cfg(target_endian = "big")] |
25 | | pub const ELFDATA: u8 = 2; // ELFDATA2MSB |
26 | | pub const ELFOSABI_SYSV: u8 = 0; |
27 | | pub const ELFOSABI_LINUX: u8 = 3; |
28 | | // At present all of our supported platforms use 0. |
29 | | pub const ELFABIVERSION: u8 = 0; |
30 | | pub const ET_DYN: u16 = 3; |
31 | | pub const EI_NIDENT: usize = 16; |
32 | | pub const SHN_UNDEF: u16 = 0; |
33 | | pub const SHN_ABS: u16 = 0xfff1; |
34 | | pub const PN_XNUM: u16 = 0xffff; |
35 | | pub const PT_LOAD: u32 = 1; |
36 | | pub const PT_DYNAMIC: u32 = 2; |
37 | | pub const PT_INTERP: u32 = 3; |
38 | | pub const PT_PHDR: u32 = 6; |
39 | | pub const PT_TLS: u32 = 7; |
40 | | pub const PT_GNU_STACK: u32 = 0x6474_e551; |
41 | | pub const PT_GNU_RELRO: u32 = 0x6474_e552; |
42 | | pub const PF_X: u32 = 1; |
43 | | pub const PF_W: u32 = 2; |
44 | | pub const PF_R: u32 = 4; |
45 | | pub const DT_NULL: usize = 0; |
46 | | pub const DT_HASH: usize = 4; |
47 | | pub const DT_STRTAB: usize = 5; |
48 | | pub const DT_SYMTAB: usize = 6; |
49 | | pub const DT_RELA: usize = 7; |
50 | | pub const DT_RELASZ: usize = 8; |
51 | | pub const DT_RELAENT: usize = 9; |
52 | | pub const DT_REL: usize = 17; |
53 | | pub const DT_RELSZ: usize = 18; |
54 | | pub const DT_RELENT: usize = 19; |
55 | | pub const DT_SYMENT: usize = 11; |
56 | | pub const DT_GNU_HASH: usize = 0x6fff_fef5; |
57 | | pub const DT_VERSYM: usize = 0x6fff_fff0; |
58 | | pub const DT_VERDEF: usize = 0x6fff_fffc; |
59 | | pub const STB_WEAK: u8 = 2; |
60 | | pub const STB_GLOBAL: u8 = 1; |
61 | | pub const STT_NOTYPE: u8 = 0; |
62 | | pub const STT_FUNC: u8 = 2; |
63 | | pub const STN_UNDEF: u32 = 0; |
64 | | pub const VER_FLG_BASE: u16 = 0x1; |
65 | | pub const VER_DEF_CURRENT: u16 = 1; |
66 | | pub const STV_DEFAULT: u8 = 0; |
67 | | #[cfg(target_arch = "arm")] |
68 | | pub const EM_CURRENT: u16 = 40; // EM_ARM |
69 | | #[cfg(target_arch = "x86")] |
70 | | pub const EM_CURRENT: u16 = 3; // EM_386 |
71 | | #[cfg(target_arch = "powerpc")] |
72 | | pub const EM_CURRENT: u16 = 20; // EM_PPC |
73 | | #[cfg(target_arch = "powerpc64")] |
74 | | pub const EM_CURRENT: u16 = 21; // EM_PPC64 |
75 | | #[cfg(target_arch = "s390x")] |
76 | | pub const EM_CURRENT: u16 = 22; // EM_S390 |
77 | | #[cfg(any( |
78 | | target_arch = "mips", |
79 | | target_arch = "mips32r6", |
80 | | target_arch = "mips64", |
81 | | target_arch = "mips64r6" |
82 | | ))] |
83 | | pub const EM_CURRENT: u16 = 8; // EM_MIPS |
84 | | #[cfg(target_arch = "x86_64")] |
85 | | pub const EM_CURRENT: u16 = 62; // EM_X86_64 |
86 | | #[cfg(target_arch = "aarch64")] |
87 | | pub const EM_CURRENT: u16 = 183; // EM_AARCH64 |
88 | | #[cfg(target_arch = "riscv64")] |
89 | | pub const EM_CURRENT: u16 = 243; // EM_RISCV |
90 | | |
91 | | #[inline] |
92 | | pub const fn ELF_ST_VISIBILITY(o: u8) -> u8 { |
93 | | o & 0x03 |
94 | | } |
95 | | |
96 | | #[inline] |
97 | 0 | pub const fn ELF_ST_BIND(val: u8) -> u8 { |
98 | 0 | val >> 4 |
99 | 0 | } |
100 | | |
101 | | #[inline] |
102 | 0 | pub const fn ELF_ST_TYPE(val: u8) -> u8 { |
103 | 0 | val & 0xf |
104 | 0 | } |
105 | | |
106 | | #[repr(C)] |
107 | | pub struct Elf_Ehdr { |
108 | | pub e_ident: [u8; EI_NIDENT], |
109 | | pub e_type: u16, |
110 | | pub e_machine: u16, |
111 | | pub e_version: u32, |
112 | | pub e_entry: usize, |
113 | | pub e_phoff: usize, |
114 | | pub e_shoff: usize, |
115 | | pub e_flags: u32, |
116 | | pub e_ehsize: u16, |
117 | | pub e_phentsize: u16, |
118 | | pub e_phnum: u16, |
119 | | pub e_shentsize: u16, |
120 | | pub e_shnum: u16, |
121 | | pub e_shstrndx: u16, |
122 | | } |
123 | | |
124 | | #[cfg(target_pointer_width = "32")] |
125 | | #[repr(C)] |
126 | | pub struct Elf_Phdr { |
127 | | pub p_type: u32, |
128 | | pub p_offset: usize, |
129 | | pub p_vaddr: usize, |
130 | | pub p_paddr: usize, |
131 | | pub p_filesz: usize, |
132 | | pub p_memsz: usize, |
133 | | pub p_flags: u32, |
134 | | pub p_align: usize, |
135 | | } |
136 | | |
137 | | #[cfg(target_pointer_width = "64")] |
138 | | #[repr(C)] |
139 | | pub struct Elf_Phdr { |
140 | | pub p_type: u32, |
141 | | pub p_flags: u32, |
142 | | pub p_offset: usize, |
143 | | pub p_vaddr: usize, |
144 | | pub p_paddr: usize, |
145 | | pub p_filesz: usize, |
146 | | pub p_memsz: usize, |
147 | | pub p_align: usize, |
148 | | } |
149 | | |
150 | | #[cfg(target_pointer_width = "32")] |
151 | | #[repr(C)] |
152 | | pub struct Elf_Sym { |
153 | | pub st_name: u32, |
154 | | pub st_value: usize, |
155 | | pub st_size: usize, |
156 | | pub st_info: u8, |
157 | | pub st_other: u8, |
158 | | pub st_shndx: u16, |
159 | | } |
160 | | |
161 | | #[cfg(target_pointer_width = "64")] |
162 | | #[repr(C)] |
163 | | pub struct Elf_Sym { |
164 | | pub st_name: u32, |
165 | | pub st_info: u8, |
166 | | pub st_other: u8, |
167 | | pub st_shndx: u16, |
168 | | pub st_value: usize, |
169 | | pub st_size: usize, |
170 | | } |
171 | | |
172 | | #[repr(C)] |
173 | | pub struct Elf_Verdef { |
174 | | pub vd_version: u16, |
175 | | pub vd_flags: u16, |
176 | | pub vd_ndx: u16, |
177 | | pub vd_cnt: u16, |
178 | | pub vd_hash: u32, |
179 | | pub vd_aux: u32, |
180 | | pub vd_next: u32, |
181 | | } |
182 | | |
183 | | #[repr(C)] |
184 | | pub struct Elf_Verdaux { |
185 | | pub vda_name: u32, |
186 | | pub _vda_next: u32, |
187 | | } |
188 | | |
189 | | #[cfg(target_pointer_width = "32")] |
190 | | #[repr(C)] |
191 | | #[derive(Copy, Clone)] |
192 | | pub struct Elf_Dyn { |
193 | | pub d_tag: usize, |
194 | | pub d_un: Elf_Dyn_Union, |
195 | | } |
196 | | |
197 | | #[cfg(target_pointer_width = "32")] |
198 | | #[repr(C)] |
199 | | #[derive(Copy, Clone)] |
200 | | pub union Elf_Dyn_Union { |
201 | | pub d_val: u32, |
202 | | pub d_ptr: usize, |
203 | | } |
204 | | |
205 | | #[cfg(target_pointer_width = "64")] |
206 | | #[repr(C)] |
207 | | #[derive(Copy, Clone)] |
208 | | pub struct Elf_Dyn { |
209 | | pub d_tag: usize, |
210 | | pub d_un: Elf_Dyn_Union, |
211 | | } |
212 | | |
213 | | #[cfg(target_pointer_width = "64")] |
214 | | #[repr(C)] |
215 | | #[derive(Copy, Clone)] |
216 | | pub union Elf_Dyn_Union { |
217 | | pub d_val: u64, |
218 | | pub d_ptr: usize, |
219 | | } |
220 | | |
221 | | #[cfg(target_pointer_width = "32")] |
222 | | #[repr(C)] |
223 | | pub struct Elf_Rela { |
224 | | pub r_offset: usize, |
225 | | pub r_info: u32, |
226 | | pub r_addend: usize, |
227 | | } |
228 | | |
229 | | #[cfg(target_pointer_width = "64")] |
230 | | #[repr(C)] |
231 | | pub struct Elf_Rela { |
232 | | pub r_offset: usize, |
233 | | pub r_info: u64, |
234 | | pub r_addend: usize, |
235 | | } |
236 | | |
237 | | impl Elf_Rela { |
238 | | #[inline] |
239 | | pub fn type_(&self) -> u32 { |
240 | | #[cfg(target_pointer_width = "32")] |
241 | | { |
242 | | self.r_info & 0xff |
243 | | } |
244 | | #[cfg(target_pointer_width = "64")] |
245 | | { |
246 | | (self.r_info & 0xffff_ffff) as u32 |
247 | | } |
248 | | } |
249 | | } |
250 | | |
251 | | #[cfg(target_pointer_width = "32")] |
252 | | #[repr(C)] |
253 | | pub struct Elf_Rel { |
254 | | pub r_offset: usize, |
255 | | pub r_info: u32, |
256 | | } |
257 | | |
258 | | #[cfg(target_pointer_width = "64")] |
259 | | #[repr(C)] |
260 | | pub struct Elf_Rel { |
261 | | pub r_offset: usize, |
262 | | pub r_info: u64, |
263 | | } |
264 | | |
265 | | impl Elf_Rel { |
266 | | #[inline] |
267 | | pub fn type_(&self) -> u32 { |
268 | | #[cfg(target_pointer_width = "32")] |
269 | | { |
270 | | self.r_info & 0xff |
271 | | } |
272 | | #[cfg(target_pointer_width = "64")] |
273 | | { |
274 | | (self.r_info & 0xffff_ffff) as u32 |
275 | | } |
276 | | } |
277 | | } |
278 | | |
279 | | #[cfg(target_arch = "x86_64")] |
280 | | pub const R_RELATIVE: u32 = 8; // `R_X86_64_RELATIVE` |
281 | | #[cfg(target_arch = "x86")] |
282 | | pub const R_RELATIVE: u32 = 8; // `R_386_RELATIVE` |
283 | | #[cfg(target_arch = "aarch64")] |
284 | | pub const R_RELATIVE: u32 = 1027; // `R_AARCH64_RELATIVE` |
285 | | #[cfg(target_arch = "riscv64")] |
286 | | pub const R_RELATIVE: u32 = 3; // `R_RISCV_RELATIVE` |
287 | | #[cfg(target_arch = "arm")] |
288 | | pub const R_RELATIVE: u32 = 23; // `R_ARM_RELATIVE` |
289 | | |
290 | | #[repr(C)] |
291 | | #[derive(Clone)] |
292 | | pub struct Elf_auxv_t { |
293 | | pub a_type: usize, |
294 | | |
295 | | // Some of the values in the auxv array are pointers, so we make `a_val` a |
296 | | // pointer, in order to preserve their provenance. For the values which are |
297 | | // integers, we cast this to `usize`. |
298 | | pub a_val: *mut crate::ctypes::c_void, |
299 | | } |