From 3b38ef6c319d7f6fcda106f529aaeca843fdb4c1 Mon Sep 17 00:00:00 2001 From: Nick Clifton Date: Tue, 25 Aug 2020 14:00:42 +0100 Subject: [PATCH] Backport patches from the mainline to fix bugs in the assembler's support for DWARF-5. 2020-08-04 Mark Wielaard * dwarf2dbg.c (out_debug_abbrev): When DWARF2_VERSION >= 4, use DW_FORM_udata for DW_AT_high_pc. (out_debug_info): Use emit_leb128_expr for DW_AT_high_pc, when DWARF2_VERSION >= 4. * read.c (emit_leb128_exp): No longer static. * read.h (emit_leb128_exp): Define. 2020-08-02 Mark Wielaard * gas/dwarf2dbg.c (out_dir_and_file_list): For DWARF5 emit at least one directory if there is at least one file. Use dirs[1] if dirs[0] is not set, or if there is no dirs[1] the current working directory. Use files[1] filename, when files[0] filename isn't set. 2020-08-02 Mark Wielaard * dwarf2dbg.c (out_debug_info): Emit unit type and abbrev offset for DWARF5. * gas/testsuite/gas/elf/dwarf-4-cu.d: New file. * gas/testsuite/gas/elf/dwarf-4-cu.s: Likewise. * gas/testsuite/gas/elf/dwarf-5-cu.d: Likewise. * gas/testsuite/gas/elf/dwarf-5-cu.s: Likewise. * testsuite/gas/elf/elf.exp: Run dwarf-4-cu and dwarf-5-cu. --- gas/ChangeLog | 30 +++++++++++++++ gas/dwarf2dbg.c | 61 +++++++++++++++++++++++------- gas/read.c | 2 +- gas/read.h | 1 + gas/testsuite/gas/elf/dwarf-4-cu.d | 11 ++++++ gas/testsuite/gas/elf/dwarf-4-cu.s | 14 +++++++ gas/testsuite/gas/elf/dwarf-5-cu.d | 11 ++++++ gas/testsuite/gas/elf/dwarf-5-cu.s | 14 +++++++ gas/testsuite/gas/elf/elf.exp | 2 + 9 files changed, 131 insertions(+), 15 deletions(-) create mode 100644 gas/testsuite/gas/elf/dwarf-4-cu.d create mode 100644 gas/testsuite/gas/elf/dwarf-4-cu.s create mode 100644 gas/testsuite/gas/elf/dwarf-5-cu.d create mode 100644 gas/testsuite/gas/elf/dwarf-5-cu.s diff --git a/gas/ChangeLog b/gas/ChangeLog index d5696dc1e57..a8b4e07227b 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,33 @@ +2020-08-25 Nick Clifton + + Backport from mainline: + 2020-08-04 Mark Wielaard + + * dwarf2dbg.c (out_debug_abbrev): When DWARF2_VERSION >= 4, use + DW_FORM_udata for DW_AT_high_pc. + (out_debug_info): Use emit_leb128_expr for DW_AT_high_pc, when + DWARF2_VERSION >= 4. + * read.c (emit_leb128_exp): No longer static. + * read.h (emit_leb128_exp): Define. + + 2020-08-02 Mark Wielaard + + * gas/dwarf2dbg.c (out_dir_and_file_list): For DWARF5 emit at + least one directory if there is at least one file. Use dirs[1] + if dirs[0] is not set, or if there is no dirs[1] the current + working directory. Use files[1] filename, when files[0] filename + isn't set. + + 2020-08-02 Mark Wielaard + + * dwarf2dbg.c (out_debug_info): Emit unit type and abbrev offset + for DWARF5. + * gas/testsuite/gas/elf/dwarf-4-cu.d: New file. + * gas/testsuite/gas/elf/dwarf-4-cu.s: Likewise. + * gas/testsuite/gas/elf/dwarf-5-cu.d: Likewise. + * gas/testsuite/gas/elf/dwarf-5-cu.s: Likewise. + * testsuite/gas/elf/elf.exp: Run dwarf-4-cu and dwarf-5-cu. + 2020-08-18 Peter Bergner Backported from master: diff --git a/gas/dwarf2dbg.c b/gas/dwarf2dbg.c index 69955fea5bf..a95c29736f0 100644 --- a/gas/dwarf2dbg.c +++ b/gas/dwarf2dbg.c @@ -1992,18 +1992,29 @@ out_dir_and_file_list (void) the .debug_line_str section and reference them here. */ out_uleb128 (DW_FORM_string); - /* Now state how many rows there are in the table. */ - out_uleb128 (dirs_in_use); + /* Now state how many rows there are in the table. We need at + least 1 if there is one or more file names to store the + "working directory". */ + if (dirs_in_use == 0 && files_in_use > 0) + out_uleb128 (1); + else + out_uleb128 (dirs_in_use); } /* Emit directory list. */ - if (DWARF2_LINE_VERSION >= 5 && dirs_in_use > 0) + if (DWARF2_LINE_VERSION >= 5 && (dirs_in_use > 0 || files_in_use > 0)) { - if (dirs == NULL || dirs[0] == NULL) - dir = remap_debug_filename ("."); - else + /* DWARF5 uses slot zero, but that is only set explicitly + using a .file 0 directive. If that isn't used, but dir + one is used, then use that as main file directory. + Otherwise use pwd as main file directory. */ + if (dirs_in_use > 0 && dirs != NULL && dirs[0] != NULL) dir = remap_debug_filename (dirs[0]); - + else if (dirs_in_use > 1 && dirs != NULL && dirs[1] != NULL) + dir = remap_debug_filename (dirs[1]); + else + dir = remap_debug_filename (getpwd ()); + size = strlen (dir) + 1; cp = frag_more (size); memcpy (cp, dir, size); @@ -2089,8 +2100,14 @@ out_dir_and_file_list (void) if (files[i].filename == NULL) { - /* Prevent a crash later, particularly for file 1. */ - files[i].filename = ""; + /* Prevent a crash later, particularly for file 1. DWARF5 + uses slot zero, but that is only set explicitly using a + .file 0 directive. If that isn't used, but file 1 is, + then use that as main file name. */ + if (DWARF2_LINE_VERSION >= 5 && i == 0 && files_in_use >= 1) + files[0].filename = files[1].filename; + else + files[i].filename = ""; if (DWARF2_LINE_VERSION < 5 || i != 0) { as_bad (_("unassigned file number %ld"), (long) i); @@ -2427,8 +2444,7 @@ out_debug_abbrev (segT abbrev_seg, if (DWARF2_VERSION < 4) out_abbrev (DW_AT_high_pc, DW_FORM_addr); else - out_abbrev (DW_AT_high_pc, (sizeof_address == 4 - ? DW_FORM_data4 : DW_FORM_data8)); + out_abbrev (DW_AT_high_pc, DW_FORM_udata); } else { @@ -2464,12 +2480,26 @@ out_debug_info (segT info_seg, segT abbrev_seg, segT line_seg, segT ranges_seg, /* DWARF version. */ out_two (DWARF2_VERSION); - /* .debug_abbrev offset */ - TC_DWARF2_EMIT_OFFSET (section_symbol (abbrev_seg), sizeof_offset); + if (DWARF2_VERSION < 5) + { + /* .debug_abbrev offset */ + TC_DWARF2_EMIT_OFFSET (section_symbol (abbrev_seg), sizeof_offset); + } + else + { + /* unit (header) type */ + out_byte (DW_UT_compile); + } /* Target address size. */ out_byte (sizeof_address); + if (DWARF2_VERSION >= 5) + { + /* .debug_abbrev offset */ + TC_DWARF2_EMIT_OFFSET (section_symbol (abbrev_seg), sizeof_offset); + } + /* DW_TAG_compile_unit DIE abbrev */ out_uleb128 (1); @@ -2497,7 +2527,10 @@ out_debug_info (segT info_seg, segT abbrev_seg, segT line_seg, segT ranges_seg, } exp.X_add_symbol = all_segs->text_end; exp.X_add_number = 0; - emit_expr (&exp, sizeof_address); + if (DWARF2_VERSION < 4) + emit_expr (&exp, sizeof_address); + else + emit_leb128_expr (&exp, 0); } else { diff --git a/gas/read.c b/gas/read.c index 8f93c2ba2b4..f192cc16d57 100644 --- a/gas/read.c +++ b/gas/read.c @@ -5138,7 +5138,7 @@ output_big_leb128 (char *p, LITTLENUM_TYPE *bignum, unsigned int size, int sign) /* Generate the appropriate fragments for a given expression to emit a leb128 value. SIGN is 1 for sleb, 0 for uleb. */ -static void +void emit_leb128_expr (expressionS *exp, int sign) { operatorT op = exp->X_op; diff --git a/gas/read.h b/gas/read.h index 502f3b6f2da..ffcdbb69a7b 100644 --- a/gas/read.h +++ b/gas/read.h @@ -132,6 +132,7 @@ extern void emit_expr_with_reloc (expressionS *exp, unsigned int nbytes, TC_PARSE_CONS_RETURN_TYPE); extern void emit_expr_fix (expressionS *, unsigned int, fragS *, char *, TC_PARSE_CONS_RETURN_TYPE); +extern void emit_leb128_expr (expressionS *, int); extern void equals (char *, int); extern void float_cons (int); extern void ignore_rest_of_line (void); diff --git a/gas/testsuite/gas/elf/dwarf-4-cu.d b/gas/testsuite/gas/elf/dwarf-4-cu.d new file mode 100644 index 00000000000..85a07390d38 --- /dev/null +++ b/gas/testsuite/gas/elf/dwarf-4-cu.d @@ -0,0 +1,11 @@ +#as: --gdwarf-4 +#name: DWARF4 CU +#readelf: -wi + +#... + Compilation Unit @ offset 0x0: + Length: 0x.* + Version: 4 + Abbrev Offset: 0x0 + Pointer Size: . +#pass diff --git a/gas/testsuite/gas/elf/dwarf-4-cu.s b/gas/testsuite/gas/elf/dwarf-4-cu.s new file mode 100644 index 00000000000..828f4102a3b --- /dev/null +++ b/gas/testsuite/gas/elf/dwarf-4-cu.s @@ -0,0 +1,14 @@ + .text + .file 1 "foo/bar.s" + .loc_mark_labels 1 + .globl foobar + .type foobar, %function +foobar: + .quad 0x1 + .size foobar, .-foobar + + .globl baz + .type baz, %function +baz: + .quad 0x1 + .size baz, .-baz diff --git a/gas/testsuite/gas/elf/dwarf-5-cu.d b/gas/testsuite/gas/elf/dwarf-5-cu.d new file mode 100644 index 00000000000..839b4b7c77b --- /dev/null +++ b/gas/testsuite/gas/elf/dwarf-5-cu.d @@ -0,0 +1,11 @@ +#as: --gdwarf-5 +#name: DWARF5 CU +#readelf: -wi + +#... + Compilation Unit @ offset 0x0: + Length: 0x.* + Version: 5 + Abbrev Offset: 0x0 + Pointer Size: . +#pass diff --git a/gas/testsuite/gas/elf/dwarf-5-cu.s b/gas/testsuite/gas/elf/dwarf-5-cu.s new file mode 100644 index 00000000000..828f4102a3b --- /dev/null +++ b/gas/testsuite/gas/elf/dwarf-5-cu.s @@ -0,0 +1,14 @@ + .text + .file 1 "foo/bar.s" + .loc_mark_labels 1 + .globl foobar + .type foobar, %function +foobar: + .quad 0x1 + .size foobar, .-foobar + + .globl baz + .type baz, %function +baz: + .quad 0x1 + .size baz, .-baz diff --git a/gas/testsuite/gas/elf/elf.exp b/gas/testsuite/gas/elf/elf.exp index 86b304ae34f..155f78efa7f 100644 --- a/gas/testsuite/gas/elf/elf.exp +++ b/gas/testsuite/gas/elf/elf.exp @@ -274,6 +274,8 @@ if { [is_elf_format] } then { run_dump_test "dwarf2-18" $dump_opts run_dump_test "dwarf2-19" $dump_opts run_dump_test "dwarf-5-file0" $dump_opts + run_dump_test "dwarf-4-cu" $dump_opts + run_dump_test "dwarf-5-cu" $dump_opts run_dump_test "pr25917" run_dump_test "bss" run_dump_test "bad-bss" -- 2.47.3