diff options
author | Alan Modra <amodra@gmail.com> | 2019-12-23 18:01:34 +1030 |
---|---|---|
committer | Alan Modra <amodra@gmail.com> | 2019-12-23 18:01:34 +1030 |
commit | cd30bcef4a685ae4a67f8b4a793af0cf7230b9fc (patch) | |
tree | ae8ab56c2f996c81fb1d395fdad4e35f94c1e296 /binutils/dwarf.h | |
parent | 27c1c4271a14cc2ebc27227212c19d4227ef212d (diff) | |
download | binutils-cd30bcef4a685ae4a67f8b4a793af0cf7230b9fc.zip binutils-cd30bcef4a685ae4a67f8b4a793af0cf7230b9fc.tar.gz binutils-cd30bcef4a685ae4a67f8b4a793af0cf7230b9fc.tar.bz2 |
Revise sleb128 and uleb128 reader
This patch catches and reports errors when reading leb128 values,
addressing a FIXME in read_leb128.
* dwarf.h (read_leb128): Update prototype.
(report_leb_status): New inline function.
(SKIP_ULEB, SKIP_SLEB, READ_ULEB, READ_SLEB): Define.
* dwarf.c: Use above macros throughout file. Formatting.
(read_leb128): Reorder params. Add status return param.
Don't stop reading until finding terminator or end of data.
Detect loss of significant bits. Sign extend only on
terminating byte.
(read_sleb128, read_uleb128): Delete functions.
(SKIP_ULEB, SKIP_SLEB, READ_ULEB, READ_SLEB): Delete macros.
(read_and_print_leb128): Rewrite.
(process_extended_line_op): Return a size_t. Use size_t vars.
Adjust to suit new macros. Add proper name size to "data" when
processing DW_LNE_define_file.
(process_abbrev_section): Adjust to suit new macros.
(decode_location_expression, skip_attr_bytes): Likewise.
(get_type_signedness): Likewise.
(read_and_display_attr_value): Likewise. Consolidate block code.
(process_debug_info): Adjust to suit new macros.
(display_formatted_table, display_debug_lines_raw): Likewise.
(display_debug_lines_decoded): Likewise. Properly check for end
of DW_LNS_extended_op.
(display_debug_macinfo): Adjust to suit new macros.
(get_line_filename_and_dirname, display_debug_macro): Likewise.
(display_view_pair_list): Likewise. Don't back off when hitting
end of data.
(display_loc_list): Adjust to suit new macros.
(display_loclists_list, display_loc_list_dwo): Likewise.
(display_debug_rnglists_list, read_cie): Likewise.
(display_debug_frames): Likewise.
* readelf.c: Use new ULEB macros throughout file.
(read_uleb128): Delete.
(decode_arm_unwind_bytecode): Use read_leb128.
(decode_tic6x_unwind_bytecode): Likewise.
(display_tag_value): Adjust to suit new macros.
(display_arc_attribute, display_arm_attribute): Likewise.
(display_gnu_attribute, display_power_gnu_attribute): Likewise.
(display_s390_gnu_attribute, display_sparc_gnu_attribute): Likewise.
(display_mips_gnu_attribute, display_tic6x_attribute): Likewise.
(display_msp430x_attribute, display_msp430_gnu_attribute): Likewise.
(display_riscv_attribute, process_attributes): Likewise.
Diffstat (limited to 'binutils/dwarf.h')
-rw-r--r-- | binutils/dwarf.h | 60 |
1 files changed, 58 insertions, 2 deletions
diff --git a/binutils/dwarf.h b/binutils/dwarf.h index 5ea85d9..cfb3abe 100644 --- a/binutils/dwarf.h +++ b/binutils/dwarf.h @@ -248,9 +248,65 @@ extern void * xcalloc2 (size_t, size_t); extern void * xcmalloc (size_t, size_t); extern void * xcrealloc (void *, size_t, size_t); -extern dwarf_vma read_leb128 (unsigned char *, unsigned int *, bfd_boolean, const unsigned char * const); - /* A callback into the client. Returns TRUE if there is a relocation against the given debug section at the given offset. */ extern bfd_boolean reloc_at (struct dwarf_section *, dwarf_vma); + +extern dwarf_vma read_leb128 (unsigned char *, const unsigned char *const, + bfd_boolean, unsigned int *, int *); + +static inline void +report_leb_status (int status) +{ + if ((status & 1) != 0) + error (_("LEB end of data\n")); + else if ((status & 2) != 0) + error (_("LEB value too large\n")); +} + +#define SKIP_ULEB(start, end) \ + do \ + { \ + unsigned int _len; \ + read_leb128 (start, end, FALSE, &_len, NULL); \ + start += _len; \ + } while (0) + +#define SKIP_SLEB(start, end) \ + do \ + { \ + unsigned int _len; \ + read_leb128 (start, end, TRUE, &_len, NULL); \ + start += _len; \ + } while (0) + +#define READ_ULEB(var, start, end) \ + do \ + { \ + dwarf_vma _val; \ + unsigned int _len; \ + int _status; \ + \ + _val = read_leb128 (start, end, FALSE, &_len, &_status); \ + start += _len; \ + (var) = _val; \ + if ((var) != _val) \ + _status |= 2; \ + report_leb_status (_status); \ + } while (0) + +#define READ_SLEB(var, start, end) \ + do \ + { \ + dwarf_signed_vma _val; \ + unsigned int _len; \ + int _status; \ + \ + _val = read_leb128 (start, end, TRUE, &_len, &_status); \ + start += _len; \ + (var) = _val; \ + if ((var) != _val) \ + _status |= 2; \ + report_leb_status (_status); \ + } while (0) |