Parse sectoin header flags
This commit is contained in:
@@ -12,7 +12,7 @@ pub struct BigEndian;
|
||||
pub struct LittleEndian;
|
||||
|
||||
pub trait Decode: Copy + Zeroable + Pod {
|
||||
type Native: Debug + Copy + TryInto<usize> + TryInto<u32> + Into<u64>;
|
||||
type Native: Debug + Copy + TryInto<usize> + TryInto<u32> + Into<u64> + Serialize;
|
||||
fn to_native(self) -> Self::Native;
|
||||
}
|
||||
|
||||
@@ -114,7 +114,7 @@ where
|
||||
where
|
||||
S: serde::Serializer,
|
||||
{
|
||||
format!("{:?}", self.to_native()).serialize(serializer)
|
||||
self.to_native().serialize(serializer)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -126,7 +126,7 @@ where
|
||||
where
|
||||
S: serde::Serializer,
|
||||
{
|
||||
format!("{:?}", self.to_native()).serialize(serializer)
|
||||
self.to_native().serialize(serializer)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -138,6 +138,6 @@ where
|
||||
where
|
||||
S: serde::Serializer,
|
||||
{
|
||||
format!("{:?}", self.to_native()).serialize(serializer)
|
||||
self.to_native().serialize(serializer)
|
||||
}
|
||||
}
|
||||
|
||||
11
src/main.rs
11
src/main.rs
@@ -1,9 +1,11 @@
|
||||
mod ints;
|
||||
mod output;
|
||||
mod section_header;
|
||||
mod structs;
|
||||
|
||||
use crate::{
|
||||
output::Output,
|
||||
section_header::SectionHeaderFlags,
|
||||
structs::{
|
||||
BigEndian32, BigEndian64, ElfConfig, ElfHeader1, ElfHeader2, LittleEndian32,
|
||||
LittleEndian64, SectionHeaderEntry, SymbolTableEntry,
|
||||
@@ -113,7 +115,16 @@ macro_rules! parse_elf {
|
||||
unreachable!()
|
||||
};
|
||||
|
||||
|
||||
let flags = SectionHeaderFlags::try_from(u64::from(entry.sh_flags.to_native()))
|
||||
.wrap_err(eyre!("invalid sh_flags in section {name:?}"))?;
|
||||
|
||||
let flags: Vec<_> = flags.iter()
|
||||
.map(|flag| format!("{flag:?}"))
|
||||
.collect();
|
||||
|
||||
fields.insert("name".to_string(), Value::String(name.to_string()));
|
||||
fields.insert("flags".to_string(), flags.into());
|
||||
section_header_entries_with_names.push(entry_json);
|
||||
}
|
||||
let _ = out.write("sections", §ion_header_entries_with_names);
|
||||
|
||||
97
src/section_header.rs
Normal file
97
src/section_header.rs
Normal file
@@ -0,0 +1,97 @@
|
||||
use eyre::bail;
|
||||
|
||||
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
|
||||
#[repr(transparent)]
|
||||
pub struct SectionHeaderFlags(u64);
|
||||
|
||||
const ALL_FLAGS: [SectionHeaderFlag; 14] = [
|
||||
SectionHeaderFlag::Write,
|
||||
SectionHeaderFlag::Alloc,
|
||||
SectionHeaderFlag::Execinstr,
|
||||
SectionHeaderFlag::Merge,
|
||||
SectionHeaderFlag::Strings,
|
||||
SectionHeaderFlag::InfoLink,
|
||||
SectionHeaderFlag::LinkOrder,
|
||||
SectionHeaderFlag::OsNonconforming,
|
||||
SectionHeaderFlag::Group,
|
||||
SectionHeaderFlag::Tls,
|
||||
SectionHeaderFlag::Maskos,
|
||||
SectionHeaderFlag::Maskproc,
|
||||
SectionHeaderFlag::Ordered,
|
||||
SectionHeaderFlag::Exclude,
|
||||
];
|
||||
|
||||
fn flag_bitmask() -> u64 {
|
||||
ALL_FLAGS
|
||||
.iter()
|
||||
.copied()
|
||||
.fold(0u64, |acc, e| acc | e as u64)
|
||||
}
|
||||
|
||||
#[repr(u64)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum SectionHeaderFlag {
|
||||
/// Writable
|
||||
Write = 0x1,
|
||||
|
||||
/// Occupies memory during execution
|
||||
Alloc = 0x2,
|
||||
|
||||
/// Executable
|
||||
Execinstr = 0x4,
|
||||
|
||||
/// Might be merged
|
||||
Merge = 0x10,
|
||||
|
||||
/// Contains null-terminated strings
|
||||
Strings = 0x20,
|
||||
|
||||
/// 'sh_info' contains SHT index
|
||||
InfoLink = 0x40,
|
||||
|
||||
/// Preserve order after combining
|
||||
LinkOrder = 0x80,
|
||||
|
||||
/// Non-standard OS specific handling required
|
||||
OsNonconforming = 0x100,
|
||||
|
||||
/// Section is member of a group
|
||||
Group = 0x200,
|
||||
|
||||
/// Section hold thread-local data
|
||||
Tls = 0x400,
|
||||
|
||||
/// OS-specific
|
||||
Maskos = 0x0FF00000,
|
||||
|
||||
/// Processor-specific
|
||||
Maskproc = 0xF0000000,
|
||||
|
||||
/// Special ordering requirement (Solaris)
|
||||
Ordered = 0x4000000,
|
||||
|
||||
/// Section is excluded unless referenced or allocated (Solaris)
|
||||
Exclude = 0x8000000,
|
||||
}
|
||||
|
||||
impl TryFrom<u64> for SectionHeaderFlags {
|
||||
type Error = eyre::Error;
|
||||
|
||||
fn try_from(value: u64) -> Result<Self, Self::Error> {
|
||||
if value & !flag_bitmask() != 0 {
|
||||
bail!("Invalid section header flag, unknown bit pattern: 0x{value:x}");
|
||||
}
|
||||
|
||||
Ok(SectionHeaderFlags(value))
|
||||
}
|
||||
}
|
||||
|
||||
impl SectionHeaderFlags {
|
||||
/// Iterate over set flags
|
||||
pub fn iter(&self) -> impl Iterator<Item = SectionHeaderFlag> + '_ {
|
||||
ALL_FLAGS
|
||||
.iter()
|
||||
.copied()
|
||||
.filter(|&flag| (self.0 & flag as u64) != 0)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user