elb/
enums.rs

1#![allow(missing_docs)]
2
3use crate::define_enum_v2;
4use crate::define_infallible_enum;
5use crate::Error;
6
7define_infallible_enum! {
8    "ELF file type.",
9    FileKind, u16,
10    (None, 0, "Unknown file type."),
11    (Relocatable, 1, "Relocatable file."),
12    (Executable, 2, "Executable file."),
13    (Shared, 3, "Shared object."),
14    (Core, 4, "Core dump."),
15}
16
17impl FileKind {
18    /// Cast to `u16`.
19    pub const fn as_u16(self) -> u16 {
20        self.as_number()
21    }
22}
23
24define_infallible_enum! {
25    "Operating system ABI.",
26    OsAbi, u8,
27    (Sysv, 0, "UNIX System V."),
28    (Hpux, 1, "HP-UX."),
29    (Netbsd, 2, "NetBSD."),
30    (Gnu, 3, "Linux/GNU."),
31    (Solaris, 6, "Solaris."),
32    (Aix, 7, "IBM AIX."),
33    (Irix, 8, "SGI IRIX."),
34    (Freebsd, 9, "FreeBSD."),
35    (Tru64, 10, "Compaq TRU64 UNIX."),
36    (Modesto, 11, "Novell Modesto."),
37    (Openbsd, 12, "OpenBSD."),
38    (ArmAeabi, 64, "Arm EABI."),
39    (Arm, 97, "Arm."),
40    (Standalone, 255, "Standalone (embedded)."),
41}
42
43impl OsAbi {
44    /// Cast to `u8`.
45    pub const fn as_u8(self) -> u8 {
46        self.as_number()
47    }
48}
49
50define_infallible_enum! {
51    "Architecture.",
52    Machine, u16,
53    (None, 0, "Unknown architecture."),
54    (M32, 1),
55    (Sparc, 2),
56    (I386, 3, "Intel 386."),
57    (M68k, 4),
58    (M88k, 5),
59    (Iamcu, 6),
60    (I860, 7),
61    (Mips, 8, "MIPS."),
62    (S370, 9),
63    (MipsRs3Le, 10),
64    (Parisc, 15),
65    (Vpp500, 17),
66    (Sparc32plus, 18),
67    (I960, 19),
68    (Ppc, 20),
69    (Ppc64, 21),
70    (S390, 22),
71    (Spu, 23),
72    (V800, 36),
73    (Fr20, 37),
74    (Rh32, 38),
75    (Rce, 39),
76    (Arm, 40, "Arm 32-bit."),
77    (FakeAlpha, 41),
78    (Sh, 42),
79    (Sparcv9, 43),
80    (Tricore, 44),
81    (Arc, 45),
82    (H8300, 46),
83    (H8300h, 47),
84    (H8s, 48),
85    (H8500, 49),
86    (Ia64, 50),
87    (MipsX, 51),
88    (Coldfire, 52),
89    (M68hc12, 53),
90    (Mma, 54),
91    (Pcp, 55),
92    (Ncpu, 56),
93    (Ndr1, 57),
94    (Starcore, 58),
95    (Me16, 59),
96    (St100, 60),
97    (Tinyj, 61),
98    (X86_64, 62, "AMD x86-64."),
99    (Pdsp, 63),
100    (Pdp10, 64),
101    (Pdp11, 65),
102    (Fx66, 66),
103    (St9plus, 67),
104    (St7, 68),
105    (M68hc16, 69),
106    (M68hc11, 70),
107    (M68hc08, 71),
108    (M68hc05, 72),
109    (Svx, 73),
110    (St19, 74),
111    (Vax, 75),
112    (Cris, 76),
113    (Javelin, 77),
114    (Firepath, 78),
115    (Zsp, 79),
116    (Mmix, 80),
117    (Huany, 81),
118    (Prism, 82),
119    (Avr, 83),
120    (Fr30, 84),
121    (D10v, 85),
122    (D30v, 86),
123    (V850, 87),
124    (M32r, 88),
125    (Mn10300, 89),
126    (Mn10200, 90),
127    (Pj, 91),
128    (Openrisc, 92),
129    (ArcCompact, 93),
130    (Xtensa, 94),
131    (Videocore, 95),
132    (TmmGpp, 96),
133    (Ns32k, 97),
134    (Tpc, 98),
135    (Snp1k, 99),
136    (St200, 100),
137    (Ip2k, 101),
138    (Max, 102),
139    (Cr, 103),
140    (F2mc16, 104),
141    (Msp430, 105),
142    (Blackfin, 106),
143    (SeC33, 107),
144    (Sep, 108),
145    (Arca, 109),
146    (Unicore, 110),
147    (Excess, 111),
148    (Dxp, 112),
149    (AlteraNios2, 113),
150    (Crx, 114),
151    (Xgate, 115),
152    (C166, 116),
153    (M16c, 117),
154    (Dspic30f, 118),
155    (Ce, 119),
156    (M32c, 120),
157    (Tsk3000, 131),
158    (Rs08, 132),
159    (Sharc, 133),
160    (Ecog2, 134),
161    (Score7, 135),
162    (Dsp24, 136),
163    (Videocore3, 137),
164    (Latticemico32, 138),
165    (SeC17, 139),
166    (TiC6000, 140),
167    (TiC2000, 141),
168    (TiC5500, 142),
169    (TiArp32, 143),
170    (TiPru, 144),
171    (MmdspPlus, 160),
172    (CypressM8c, 161),
173    (R32c, 162),
174    (Trimedia, 163),
175    (Qdsp6, 164),
176    (I8051, 165),
177    (Stxp7x, 166),
178    (Nds32, 167),
179    (Ecog1x, 168),
180    (Maxq30, 169),
181    (Ximo16, 170),
182    (Manik, 171),
183    (Craynv2, 172),
184    (Rx, 173),
185    (Metag, 174),
186    (McstElbrus, 175),
187    (Ecog16, 176),
188    (Cr16, 177),
189    (Etpu, 178),
190    (Sle9x, 179),
191    (L10m, 180),
192    (K10m, 181),
193    (Aarch64, 183, "Arm 64-bit."),
194    (Avr32, 185),
195    (Stm8, 186),
196    (Tile64, 187),
197    (Tilepro, 188),
198    (Microblaze, 189),
199    (Cuda, 190, "NVIDIA CUDA."),
200    (Tilegx, 191),
201    (Cloudshield, 192),
202    (Corea1st, 193),
203    (Corea2nd, 194),
204    (Arcv2, 195),
205    (Open8, 196),
206    (Rl78, 197),
207    (Videocore5, 198),
208    (R78kor, 199),
209    (F56800ex, 200),
210    (Ba1, 201),
211    (Ba2, 202),
212    (Xcore, 203),
213    (MchpPic, 204),
214    (Intelgt, 205),
215    (Km32, 210),
216    (Kmx32, 211),
217    (Emx16, 212),
218    (Emx8, 213),
219    (Kvarc, 214),
220    (Cdp, 215),
221    (Coge, 216),
222    (Cool, 217),
223    (Norc, 218),
224    (CsrKalimba, 219),
225    (Z80, 220),
226    (Visium, 221),
227    (Ft32, 222),
228    (Moxie, 223),
229    (Amdgpu, 224, "AMD GPU."),
230    (Riscv, 243, "RISC-V."),
231    (Bpf, 247, "Linux BPF."),
232    (Csky, 252),
233    (Loongarch, 258),
234}
235
236impl Machine {
237    /// Cast to `u16`.
238    pub const fn as_u16(self) -> u16 {
239        self.as_number()
240    }
241}
242
243define_infallible_enum! {
244    "Segment type.",
245    SegmentKind, u32,
246    (Null, 0, "Inactive/removed segment."),
247    (Loadable, 1, "A segment that is mapped from the file into memory segment on program execution."),
248    (Dynamic, 2, "A segment that contains dynamic linking information."),
249    (Interpreter, 3, "A segment that contains NUL-terminated interpreter path."),
250    (Note, 4, "A segment that contains notes."),
251    (Shlib, 5, "Reserved."),
252    (ProgramHeader, 6, "A segment that contains program header itself."),
253    (Tls, 7, "A segment that contains thread-local storage."),
254}
255
256impl SegmentKind {
257    /// Cast to `u32`.
258    pub const fn as_u32(self) -> u32 {
259        self.as_number()
260    }
261}
262
263define_infallible_enum! {
264    "Dynamic table tag.",
265    DynamicTag, u32,
266    (Null, 0, "End of the table."),
267    (Needed, 1, "String table offset to the name of the needed library."),
268    (PltRelSize, 2),
269    (PltGot, 3),
270    (Hash, 4, "The address of the symbol hash table."),
271    (StringTableAddress, 5, "The address of the string table."),
272    (SymbolTableAddress, 6, "The address of the symbol table."),
273    (RelaTableAddress, 7, "The address of the relocation with addends table."),
274    (RelaTableSize, 8, "The size in bytes of the relocation with addends table."),
275    (RelaEntrySize, 9, "Relocation with addends entry size."),
276    (StringTableSize, 10, "The size in bytes of the string table."),
277    (SymbolEntrySize, 11, "Symbol table entry size."),
278    (InitAddress, 12),
279    (FiniAddress, 13),
280    (SharedObjectName, 14, "String table offset to the name of the shared object."),
281    (Rpath, 15, "String table offset to the library search path."),
282    (Symbolic, 16),
283    (RelTableAddress, 17, "The address of relocation table."),
284    (RelTableSize, 18, "The size in bytes of the relocation table."),
285    (RelEntrySize, 19, "Relocation entry size."),
286    (PltRel, 20),
287    (Debug, 21),
288    (TextRel, 22),
289    (JmpRel, 23),
290    (BindNow, 24),
291    (InitArray, 25),
292    (FiniArray, 26),
293    (InitArraySize, 27),
294    (FiniArraySize, 28),
295    (Runpath, 29, "String table offset to the library search path."),
296    (Flags, 30),
297    (PreInitArray, 32),
298    (PreInitArraySize, 33),
299    (SymbolTableIndex, 34),
300    (RelrTableSize, 35, "The size in bytes of the relative relocation table."),
301    (RelrTableAddress, 36, "The address of relative relocation table."),
302    (RelrEntrySize, 37, "Relative relocation entry size."),
303}
304
305impl DynamicTag {
306    /// Cast to `u32`.
307    pub const fn as_u32(self) -> u32 {
308        self.as_number()
309    }
310}
311
312impl TryFrom<u64> for DynamicTag {
313    type Error = Error;
314    fn try_from(other: u64) -> Result<Self, Self::Error> {
315        let number: u32 = other.try_into().map_err(|_| Error::TooBig("dynamic-tag"))?;
316        Ok(number.into())
317    }
318}
319
320define_infallible_enum! {
321    "Section type.",
322    SectionKind, u32,
323    (Null, 0, "Inactive/removed section."),
324    (ProgramBits, 1, "Program-related data."),
325    (SymbolTable, 2, "Symbol table."),
326    (StringTable, 3, "String table."),
327    (RelaTable, 4, "Relocation entries with addends."),
328    (Hash, 5, "Symbol hash table."),
329    (Dynamic, 6, "Dynamic linking information."),
330    (Note, 7, "Notes."),
331    (NoBits, 8, "Same as `ProgramBits` but occupies no space in the file."),
332    (RelTable, 9, "Relocation entries without addends."),
333    (Shlib, 10, "Reserved."),
334    (DynamicSymbolTable, 11, "Dynamic linker symbol table."),
335    (InitArray, 14, "Constructors."),
336    (FiniArray, 15, "Destructors."),
337    (PreInitArray, 16, "Pre-constructors."),
338    (Group, 17, "Section group."),
339    (SymbolTableIndex, 18, "Extended section indices."),
340    (RelrTable, 19, "Relative relocation entries."),
341}
342
343impl SectionKind {
344    /// Cast to `u32`.
345    pub const fn as_u32(self) -> u32 {
346        self.as_number()
347    }
348}
349
350/// Symbol visibility.
351#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Debug)]
352#[cfg_attr(test, derive(arbitrary::Arbitrary))]
353#[repr(u8)]
354pub enum SymbolVisibility {
355    /// Default visibility.
356    Default = 0,
357    /// CPU-specific visibility.
358    Internal = 1,
359    /// The symbol is not available to other modules.
360    Hidden = 2,
361    /// The symbol is available to other modules
362    /// but local module always resolves to the local symbol.
363    Protected = 3,
364}
365
366impl SymbolVisibility {
367    /// Get visibility from symbol's `other` field.
368    pub const fn from_other(other: u8) -> Self {
369        match other & 3 {
370            0 => Self::Default,
371            1 => Self::Internal,
372            2 => Self::Hidden,
373            3 => Self::Protected,
374            _ => unreachable!(),
375        }
376    }
377}
378
379define_enum_v2! {
380    "Symbol binding.",
381    SymbolBinding, u8,
382    (Local, 0, "Local symbol."),
383    (Global, 1, "Global symbol."),
384    (Weak, 2, "Weak symbol."),
385}
386
387impl SymbolBinding {
388    /// Cast to `u8`.
389    pub const fn as_u8(self) -> u8 {
390        self.as_number()
391    }
392
393    /// Convert from symbol's `info` field.
394    pub fn from_info(info: u8) -> Self {
395        Self::from(info >> 4)
396    }
397
398    /// Convert to the bits of the symbol's `info` field.
399    pub const fn to_info_bits(self) -> u8 {
400        self.as_u8() << 4
401    }
402}
403
404define_enum_v2! {
405    "Symbol type.",
406    SymbolKind, u8,
407    (None, 0, "Unspecified."),
408    (Object, 1, "Data object."),
409    (Function, 2, "Code object."),
410    (Section, 3, "Associated with a section."),
411    (File, 4, "File name."),
412    (Common, 5, "Common data object."),
413    (Tls, 6, "Thread-local data object."),
414}
415
416impl SymbolKind {
417    /// Cast to `u8`.
418    pub const fn as_u8(self) -> u8 {
419        self.as_number()
420    }
421
422    /// Convert from symbol's `info` field.
423    pub fn from_info(info: u8) -> Self {
424        Self::from(info & 0xf)
425    }
426
427    /// Convert to the bits of the symbol's `info` field.
428    pub const fn to_info_bits(self) -> u8 {
429        self.as_u8() & 0xf
430    }
431}