parse more (badly)

This commit is contained in:
nora 2023-11-08 21:19:35 +01:00
parent 84ee581387
commit 9575dc4138
9 changed files with 19 additions and 105313 deletions

View file

@ -1,5 +1,4 @@
[target.x86_64-unknown-linux-gnu]
rustflags = [
"-Cforce-frame-pointers=yes", # for the uwuwind fp stack walker
"-Clink-arg=-Wl,-E" # for dladdr
]

Binary file not shown.

105307
eh_frame.txt

File diff suppressed because it is too large Load diff

Binary file not shown.

View file

@ -103,8 +103,6 @@ pub(crate) fn eh_frame(addr: Addr) -> Option<*const u8> {
core::slice::from_raw_parts(eh_frame_ptr as *const u8, 15)
);
crate::dwarf::uwutables(eh_frame_ptr as *const u8);
Some(eh_frame_ptr as *const u8)
}
}

View file

@ -2,7 +2,10 @@
//! unwinding
//!
//! for this we need a DWARF parser and a DWARF call frame information
//! interpreter (yes, that shit is basically a programming language). See https://dwarfstd.org/doc/DWARF5.pdf for more information if more information is desired.
//! interpreter (yes, that shit is basically a programming language).
//! See https://dwarfstd.org/doc/DWARF5.pdf §6.4 for more information if more information is desired.
//! Note that https://refspecs.linuxbase.org/LSB_5.0.0/LSB-Core-generic/LSB-Core-generic/ehframechpt.html
//! contains more details on the precise format, which is slightly different from .debug_frame from DWARF.
mod divination;
mod parse;

View file

@ -106,6 +106,7 @@ pub struct Cie<'a> {
/// .debug_info section, the augmentation string always uses UTF-8
/// encoding.
pub augmentation: Option<AugmentationData>,
pub augmentation_string: &'a str,
/// A constant that is factored out of all advance location instructions
/// (see Section 6.4.2.1 on page 177). The resulting value is
/// (operand * code_alignment_factor).
@ -539,12 +540,14 @@ unsafe fn parse_frame_info<'a>(
loop {
let (cie_id, data, newer_ptr) = parse_frame_head(ptr)?;
trace!("cie id: {cie_id}");
if cie_id != 0 {
return Ok((cie, fdes, prev_ptr));
}
prev_ptr = newer_ptr;
let data = &mut Cursor(data);
let fde = parse_fde(data, cie_id, &cie)?;
trace!("FDE: {fde:?}");
fdes.push(fde);
}
}
@ -590,6 +593,7 @@ fn parse_cie<'a>(data: &mut Cursor<'a>) -> Result<Cie<'a>> {
let cie = Cie {
augmentation: augmentation_data,
augmentation_string: augmentation,
code_alignment_factor,
data_alignment_factor,
return_address_register,
@ -608,6 +612,8 @@ fn parse_fde<'a>(data: &mut Cursor<'a>, cie_id: u32, cie: &Cie<'_>) -> Result<Fd
.as_ref()
.ok_or_else(|| Error("augmentation data not present for CIE with FDEs".into()))?;
trace!("augmentation: {augmentation:?}");
let pointer_encoding = augmentation.pointer_encoding.ok_or_else(|| {
Error("pointer encoding not present in augmentation for CIE with FDEs".into())
})?;
@ -618,7 +624,12 @@ fn parse_fde<'a>(data: &mut Cursor<'a>, cie_id: u32, cie: &Cie<'_>) -> Result<Fd
let (read_size, pc_range) = unsafe { read_encoded(data.0.as_ptr(), pointer_encoding) };
data.0 = &data.0[read_size..];
// This is only present if the aug data of the CIE contains z. But that is
// always the case?
let augmentation_len = read_uleb128(data)?;
let augmentation_data = &data.0[..(augmentation_len as usize)];
let data = parse_augmentation_data(cie.augmentation_string, augmentation_data)?;
trace!("debug data: {data:?}");
Err(Error("aa".into()))
}

View file

@ -24,6 +24,7 @@ fn parse_simple_cie() {
)),
personality: None
}),
augmentation_string: "meow",
code_alignment_factor: 1,
data_alignment_factor: -8,
return_address_register: 16,

View file

@ -31,7 +31,8 @@ pub unsafe extern "C" fn _UnwindRaiseException(
exception_object: *mut uw::_Unwind_Exception,
) -> uw::_Unwind_Reason_Code {
trace!("someone raised an exception with addr {exception_object:p}");
let _ = crate::dwarf::eh_frame(arch::get_rip()).unwrap();
let eh_frame = crate::dwarf::eh_frame(arch::get_rip()).unwrap();
crate::dwarf::uwutables(eh_frame);
stdext::abort();
}