struct FrameDescriptionEntry [src]

Fields

cie_length_offset: u64
pc_begin: u64
pc_range: u64
lsda_pointer: ?u64
aug_data: []const u8
instructions: []const u8

Members

Source

pub const FrameDescriptionEntry = struct { // Offset into eh_frame where the CIE for this FDE is stored cie_length_offset: u64, pc_begin: u64, pc_range: u64, lsda_pointer: ?u64, aug_data: []const u8, instructions: []const u8, /// This function expects to read the FDE starting at the PC Begin field. /// The returned struct references memory backed by `fde_bytes`. /// /// `pc_rel_offset` specifies an offset to be applied to pc_rel_base values /// used when decoding pointers. This should be set to zero if fde_bytes is /// backed by the memory of a .eh_frame / .debug_frame section in the running executable. /// Otherwise, it should be the relative offset to translate addresses from /// where the section is currently stored in memory, to where it *would* be /// stored at runtime: section base addr - backing data base ptr. /// /// Similarly, `is_runtime` specifies this function is being called on a runtime /// section, and so indirect pointers can be followed. pub fn parse( fde_bytes: []const u8, pc_rel_offset: i64, is_runtime: bool, cie: CommonInformationEntry, addr_size_bytes: u8, endian: std.builtin.Endian, ) !FrameDescriptionEntry { if (addr_size_bytes > 8) return error.InvalidAddrSize; var fbr: FixedBufferReader = .{ .buf = fde_bytes, .endian = endian }; const pc_begin = try readEhPointer(&fbr, cie.fde_pointer_enc, addr_size_bytes, .{ .pc_rel_base = try pcRelBase(@intFromPtr(&fde_bytes[fbr.pos]), pc_rel_offset), .follow_indirect = is_runtime, }) orelse return bad(); const pc_range = try readEhPointer(&fbr, cie.fde_pointer_enc, addr_size_bytes, .{ .pc_rel_base = 0, .follow_indirect = false, }) orelse return bad(); var aug_data: []const u8 = &[_]u8{}; const lsda_pointer = if (cie.aug_str.len > 0) blk: { const aug_data_len = try fbr.readUleb128(usize); const aug_data_start = fbr.pos; aug_data = fde_bytes[aug_data_start..][0..aug_data_len]; const lsda_pointer = if (cie.lsda_pointer_enc != EH.PE.omit) try readEhPointer(&fbr, cie.lsda_pointer_enc, addr_size_bytes, .{ .pc_rel_base = try pcRelBase(@intFromPtr(&fde_bytes[fbr.pos]), pc_rel_offset), .follow_indirect = is_runtime, }) else null; fbr.pos = aug_data_start + aug_data_len; break :blk lsda_pointer; } else null; const instructions = fde_bytes[fbr.pos..]; return .{ .cie_length_offset = cie.length_offset, .pc_begin = pc_begin, .pc_range = pc_range, .lsda_pointer = lsda_pointer, .aug_data = aug_data, .instructions = instructions, }; } }