Hi! Another set of GNU extensions that were accepted into DWARF5, so we should emit them even for -gstrict-dwarf -gdwarf-5, and for -gdwarf-5 should use the accepted standard opcodes instead of the corresponding GNU ones.
Bootstrapped/regtested on x86_64-linux and i686-linux on top of the dwarf2.{def,h} patch, ok for trunk? 2016-10-14 Jakub Jelinek <ja...@redhat.com> * dwarf2out.c (dwarf_op): New function. (size_of_loc_descr): Handle DW_OP_{implicit_pointer,entry_value}, DW_OP_{const,regval,deref}_type and DW_OP_{convert,reinterpret}. (output_loc_operands, output_loc_operands_raw): Likewise. (resolve_args_picking_1, prune_unused_types_walk_loc_descr, mark_base_types, hash_loc_operands, compare_loc_operands): Likewise. (resolve_addr_in_expr): Likewise. Only punt for !dwarf_strict if dwarf_version < 5. (convert_descriptor_to_mode): Use dwarf_op (DW_OP_xxx) instead of DW_OP_GNU_xxx. (scompare_loc_descriptor, ucompare_loc_descriptor, minmax_loc_descriptor, typed_binop, mem_loc_descriptor, implicit_ptr_descriptor, optimize_one_addr_into_implicit_ptr, optimize_location_into_implicit_ptr): Likewise. Only punt for !dwarf_strict if dwarf_version < 5. (string_cst_pool_decl): Adjust comment. (non_dwarf_expression): Handle DW_OP_implicit_pointer. --- gcc/dwarf2out.c.jj 2016-10-14 18:09:22.000000000 +0200 +++ gcc/dwarf2out.c 2016-10-14 19:02:00.291876232 +0200 @@ -1514,6 +1514,54 @@ loc_list_plus_const (dw_loc_list_ref lis #define DWARF_REF_SIZE \ (dwarf_version == 2 ? DWARF2_ADDR_SIZE : DWARF_OFFSET_SIZE) +/* Utility inline function for construction of ops that were GNU extension + before DWARF 5. */ +static inline enum dwarf_location_atom +dwarf_op (enum dwarf_location_atom op) +{ + switch (op) + { + case DW_OP_implicit_pointer: + if (dwarf_version < 5) + return DW_OP_GNU_implicit_pointer; + break; + + case DW_OP_entry_value: + if (dwarf_version < 5) + return DW_OP_GNU_entry_value; + break; + + case DW_OP_const_type: + if (dwarf_version < 5) + return DW_OP_GNU_const_type; + break; + + case DW_OP_regval_type: + if (dwarf_version < 5) + return DW_OP_GNU_regval_type; + break; + + case DW_OP_deref_type: + if (dwarf_version < 5) + return DW_OP_GNU_deref_type; + break; + + case DW_OP_convert: + if (dwarf_version < 5) + return DW_OP_GNU_convert; + break; + + case DW_OP_reinterpret: + if (dwarf_version < 5) + return DW_OP_GNU_reinterpret; + break; + + default: + break; + } + return op; +} + static unsigned long int get_base_type_offset (dw_die_ref); /* Return the size of a location descriptor. */ @@ -1633,15 +1681,18 @@ size_of_loc_descr (dw_loc_descr_ref loc) size += size_of_uleb128 (loc->dw_loc_oprnd1.v.val_unsigned) + loc->dw_loc_oprnd1.v.val_unsigned; break; + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: size += DWARF_REF_SIZE + size_of_sleb128 (loc->dw_loc_oprnd2.v.val_int); break; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: { unsigned long op_size = size_of_locs (loc->dw_loc_oprnd1.v.val_loc); size += size_of_uleb128 (op_size) + op_size; break; } + case DW_OP_const_type: case DW_OP_GNU_const_type: { unsigned long o @@ -1668,6 +1719,7 @@ size_of_loc_descr (dw_loc_descr_ref loc) } break; } + case DW_OP_regval_type: case DW_OP_GNU_regval_type: { unsigned long o @@ -1676,6 +1728,7 @@ size_of_loc_descr (dw_loc_descr_ref loc) + size_of_uleb128 (o); } break; + case DW_OP_deref_type: case DW_OP_GNU_deref_type: { unsigned long o @@ -1683,6 +1736,8 @@ size_of_loc_descr (dw_loc_descr_ref loc) size += 1 + size_of_uleb128 (o); } break; + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: if (loc->dw_loc_oprnd1.val_class == dw_val_class_unsigned_const) @@ -2043,6 +2098,7 @@ output_loc_operands (dw_loc_descr_ref lo } break; + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: { char label[MAX_ARTIFICIAL_LABEL_BYTES @@ -2054,11 +2110,13 @@ output_loc_operands (dw_loc_descr_ref lo } break; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: dw2_asm_output_data_uleb128 (size_of_locs (val1->v.val_loc), NULL); output_loc_sequence (val1->v.val_loc, for_eh_or_skip); break; + case DW_OP_const_type: case DW_OP_GNU_const_type: { unsigned long o = get_base_type_offset (val1->v.val_die_ref.die), l; @@ -2132,6 +2190,7 @@ output_loc_operands (dw_loc_descr_ref lo } } break; + case DW_OP_regval_type: case DW_OP_GNU_regval_type: { unsigned r = val1->v.val_unsigned; @@ -2147,6 +2206,7 @@ output_loc_operands (dw_loc_descr_ref lo dw2_asm_output_data_uleb128 (o, NULL); } break; + case DW_OP_deref_type: case DW_OP_GNU_deref_type: { unsigned long o = get_base_type_offset (val2->v.val_die_ref.die); @@ -2155,6 +2215,8 @@ output_loc_operands (dw_loc_descr_ref lo dw2_asm_output_data_uleb128 (o, NULL); } break; + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: if (loc->dw_loc_oprnd1.val_class == dw_val_class_unsigned_const) @@ -2353,6 +2415,13 @@ output_loc_operands_raw (dw_loc_descr_re } break; + case DW_OP_implicit_pointer: + case DW_OP_entry_value: + case DW_OP_const_type: + case DW_OP_regval_type: + case DW_OP_deref_type: + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_implicit_pointer: case DW_OP_GNU_entry_value: case DW_OP_GNU_const_type: @@ -12627,13 +12696,13 @@ convert_descriptor_to_mode (machine_mode if (GET_MODE_SIZE (mode) <= DWARF2_ADDR_SIZE) { - add_loc_descr (&op, new_loc_descr (DW_OP_GNU_convert, 0, 0)); + add_loc_descr (&op, new_loc_descr (dwarf_op (DW_OP_convert), 0, 0)); return op; } type_die = base_type_for_mode (outer_mode, 1); if (type_die == NULL) return NULL; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -12674,6 +12743,7 @@ scompare_loc_descriptor (enum dwarf_loca return NULL; if (dwarf_strict + && dwarf_version < 5 && (!SCALAR_INT_MODE_P (op_mode) || GET_MODE_SIZE (op_mode) > DWARF2_ADDR_SIZE)) return NULL; @@ -12697,12 +12767,12 @@ scompare_loc_descriptor (enum dwarf_loca if (type_die == NULL) return NULL; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; add_loc_descr (&op0, cvt); - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -12784,7 +12854,9 @@ ucompare_loc_descriptor (enum dwarf_loca if (!SCALAR_INT_MODE_P (op_mode)) return NULL; - if (dwarf_strict && GET_MODE_SIZE (op_mode) > DWARF2_ADDR_SIZE) + if (dwarf_strict + && dwarf_version < 5 + && GET_MODE_SIZE (op_mode) > DWARF2_ADDR_SIZE) return NULL; op0 = mem_loc_descriptor (XEXP (rtl, 0), op_mode, mem_mode, @@ -12847,7 +12919,8 @@ minmax_loc_descriptor (rtx rtl, machine_ dw_loc_descr_ref op0, op1, ret; dw_loc_descr_ref bra_node, drop_node; - if (dwarf_strict + if (dwarf_strict + && dwarf_version < 5 && (!SCALAR_INT_MODE_P (mode) || GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE)) return NULL; @@ -12897,12 +12970,12 @@ minmax_loc_descriptor (rtx rtl, machine_ dw_loc_descr_ref cvt; if (type_die == NULL) return NULL; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; add_loc_descr (&op0, cvt); - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -12948,12 +13021,12 @@ typed_binop (enum dwarf_location_atom op VAR_INIT_STATUS_INITIALIZED); if (op0 == NULL || op1 == NULL) return NULL; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; add_loc_descr (&op0, cvt); - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -13421,7 +13494,7 @@ mem_loc_descriptor (rtx rtl, machine_mod mem_mode, initialized); break; } - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) break; if (GET_MODE_SIZE (mode) > GET_MODE_SIZE (GET_MODE (inner))) break; @@ -13447,9 +13520,9 @@ mem_loc_descriptor (rtx rtl, machine_mod } if (GET_MODE_SIZE (mode) != GET_MODE_SIZE (GET_MODE (inner))) - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); else - cvt = new_loc_descr (DW_OP_GNU_reinterpret, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_reinterpret), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -13458,7 +13531,7 @@ mem_loc_descriptor (rtx rtl, machine_mod && GET_MODE_SIZE (mode) <= DWARF2_ADDR_SIZE) { /* Convert it to untyped afterwards. */ - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); add_loc_descr (&mem_loc_result, cvt); } } @@ -13477,7 +13550,7 @@ mem_loc_descriptor (rtx rtl, machine_mod dw_die_ref type_die; unsigned int dbx_regnum; - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) break; if (REGNO (rtl) > FIRST_PSEUDO_REGISTER) break; @@ -13488,7 +13561,7 @@ mem_loc_descriptor (rtx rtl, machine_mod dbx_regnum = dbx_reg_number (rtl); if (dbx_regnum == IGNORED_DWARF_REGNUM) break; - mem_loc_result = new_loc_descr (DW_OP_GNU_regval_type, + mem_loc_result = new_loc_descr (dwarf_op (DW_OP_regval_type), dbx_regnum, 0); mem_loc_result->dw_loc_oprnd2.val_class = dw_val_class_die_ref; mem_loc_result->dw_loc_oprnd2.v.val_die_ref.die = type_die; @@ -13560,7 +13633,7 @@ mem_loc_descriptor (rtx rtl, machine_mod add_loc_descr (&mem_loc_result, int_loc_descriptor (shift)); add_loc_descr (&mem_loc_result, new_loc_descr (op, 0, 0)); } - else if (!dwarf_strict) + else if (!dwarf_strict || dwarf_version >= 5) { dw_die_ref type_die1, type_die2; dw_loc_descr_ref cvt; @@ -13573,12 +13646,12 @@ mem_loc_descriptor (rtx rtl, machine_mod if (type_die2 == NULL) break; mem_loc_result = op0; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die1; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; add_loc_descr (&mem_loc_result, cvt); - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die2; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -13610,13 +13683,13 @@ mem_loc_descriptor (rtx rtl, machine_mod dw_die_ref type_die; dw_loc_descr_ref deref; - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) return NULL; type_die = base_type_for_mode (mode, SCALAR_INT_MODE_P (mode)); if (type_die == NULL) return NULL; - deref = new_loc_descr (DW_OP_GNU_deref_type, + deref = new_loc_descr (dwarf_op (DW_OP_deref_type), GET_MODE_SIZE (mode), 0); deref->dw_loc_oprnd2.val_class = dw_val_class_die_ref; deref->dw_loc_oprnd2.v.val_die_ref.die = type_die; @@ -13687,7 +13760,7 @@ mem_loc_descriptor (rtx rtl, machine_mod return 0; case ENTRY_VALUE: - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) return NULL; if (REG_P (ENTRY_VALUE_EXP (rtl))) { @@ -13716,7 +13789,7 @@ mem_loc_descriptor (rtx rtl, machine_mod gcc_unreachable (); if (op0 == NULL) return NULL; - mem_loc_result = new_loc_descr (DW_OP_GNU_entry_value, 0, 0); + mem_loc_result = new_loc_descr (dwarf_op (DW_OP_entry_value), 0, 0); mem_loc_result->dw_loc_oprnd1.val_class = dw_val_class_loc; mem_loc_result->dw_loc_oprnd1.v.val_loc = op0; break; @@ -13787,7 +13860,7 @@ mem_loc_descriptor (rtx rtl, machine_mod goto do_binop; case DIV: - if (!dwarf_strict + if ((!dwarf_strict || dwarf_version >= 5) && SCALAR_INT_MODE_P (mode) && GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE) { @@ -13865,7 +13938,8 @@ mem_loc_descriptor (rtx rtl, machine_mod break; case MOD: - if (GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE && !dwarf_strict) + if (GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE + && (!dwarf_strict || dwarf_version >= 5)) { mem_loc_result = typed_binop (DW_OP_mod, rtl, base_type_for_mode (mode, 0), @@ -13891,7 +13965,8 @@ mem_loc_descriptor (rtx rtl, machine_mod break; case UDIV: - if (!dwarf_strict && SCALAR_INT_MODE_P (mode)) + if ((!dwarf_strict || dwarf_version >= 5) + && SCALAR_INT_MODE_P (mode)) { if (GET_MODE_CLASS (mode) > DWARF2_ADDR_SIZE) { @@ -13939,7 +14014,7 @@ mem_loc_descriptor (rtx rtl, machine_mod mem_loc_result = int_loc_descriptor (INTVAL (rtl)); break; } - if (!dwarf_strict + if ((!dwarf_strict || dwarf_version >= 5) && (GET_MODE_BITSIZE (mode) == HOST_BITS_PER_WIDE_INT || GET_MODE_BITSIZE (mode) == HOST_BITS_PER_DOUBLE_INT)) { @@ -13952,20 +14027,20 @@ mem_loc_descriptor (rtx rtl, machine_mod if (INTVAL (rtl) >= 0 && amode != BLKmode && trunc_int_for_mode (INTVAL (rtl), amode) == INTVAL (rtl) - /* const DW_OP_GNU_convert <XXX> vs. - DW_OP_GNU_const_type <XXX, 1, const>. */ + /* const DW_OP_convert <XXX> vs. + DW_OP_const_type <XXX, 1, const>. */ && size_of_int_loc_descriptor (INTVAL (rtl)) + 1 + 1 < (unsigned long) 1 + 1 + 1 + GET_MODE_SIZE (mode)) { mem_loc_result = int_loc_descriptor (INTVAL (rtl)); - op0 = new_loc_descr (DW_OP_GNU_convert, 0, 0); + op0 = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); op0->dw_loc_oprnd1.val_class = dw_val_class_die_ref; op0->dw_loc_oprnd1.v.val_die_ref.die = type_die; op0->dw_loc_oprnd1.v.val_die_ref.external = 0; add_loc_descr (&mem_loc_result, op0); return mem_loc_result; } - mem_loc_result = new_loc_descr (DW_OP_GNU_const_type, 0, + mem_loc_result = new_loc_descr (dwarf_op (DW_OP_const_type), 0, INTVAL (rtl)); mem_loc_result->dw_loc_oprnd1.val_class = dw_val_class_die_ref; mem_loc_result->dw_loc_oprnd1.v.val_die_ref.die = type_die; @@ -13983,7 +14058,7 @@ mem_loc_descriptor (rtx rtl, machine_mod break; case CONST_DOUBLE: - if (!dwarf_strict) + if (!dwarf_strict || dwarf_version >= 5) { dw_die_ref type_die; @@ -14002,7 +14077,7 @@ mem_loc_descriptor (rtx rtl, machine_mod type_die = base_type_for_mode (mode, SCALAR_INT_MODE_P (mode)); if (type_die == NULL) return NULL; - mem_loc_result = new_loc_descr (DW_OP_GNU_const_type, 0, 0); + mem_loc_result = new_loc_descr (dwarf_op (DW_OP_const_type), 0, 0); mem_loc_result->dw_loc_oprnd1.val_class = dw_val_class_die_ref; mem_loc_result->dw_loc_oprnd1.v.val_die_ref.die = type_die; mem_loc_result->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -14030,14 +14105,14 @@ mem_loc_descriptor (rtx rtl, machine_mod break; case CONST_WIDE_INT: - if (!dwarf_strict) + if (!dwarf_strict || dwarf_version >= 5) { dw_die_ref type_die; type_die = base_type_for_mode (mode, SCALAR_INT_MODE_P (mode)); if (type_die == NULL) return NULL; - mem_loc_result = new_loc_descr (DW_OP_GNU_const_type, 0, 0); + mem_loc_result = new_loc_descr (dwarf_op (DW_OP_const_type), 0, 0); mem_loc_result->dw_loc_oprnd1.val_class = dw_val_class_die_ref; mem_loc_result->dw_loc_oprnd1.v.val_die_ref.die = type_die; mem_loc_result->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -14173,7 +14248,7 @@ mem_loc_descriptor (rtx rtl, machine_mod case UNSIGNED_FLOAT: case FIX: case UNSIGNED_FIX: - if (!dwarf_strict) + if (!dwarf_strict || dwarf_version >= 5) { dw_die_ref type_die; dw_loc_descr_ref cvt; @@ -14191,7 +14266,7 @@ mem_loc_descriptor (rtx rtl, machine_mod GET_CODE (rtl) == UNSIGNED_FLOAT); if (type_die == NULL) break; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -14200,7 +14275,7 @@ mem_loc_descriptor (rtx rtl, machine_mod type_die = base_type_for_mode (mode, GET_CODE (rtl) == UNSIGNED_FIX); if (type_die == NULL) break; - cvt = new_loc_descr (DW_OP_GNU_convert, 0, 0); + cvt = new_loc_descr (dwarf_op (DW_OP_convert), 0, 0); cvt->dw_loc_oprnd1.val_class = dw_val_class_die_ref; cvt->dw_loc_oprnd1.v.val_die_ref.die = type_die; cvt->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -14362,7 +14437,7 @@ concatn_loc_descriptor (rtx concatn, enu return cc_loc_result; } -/* Helper function for loc_descriptor. Return DW_OP_GNU_implicit_pointer +/* Helper function for loc_descriptor. Return DW_OP_implicit_pointer for DEBUG_IMPLICIT_PTR RTL. */ static dw_loc_descr_ref @@ -14371,13 +14446,13 @@ implicit_ptr_descriptor (rtx rtl, HOST_W dw_loc_descr_ref ret; dw_die_ref ref; - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) return NULL; gcc_assert (TREE_CODE (DEBUG_IMPLICIT_PTR_DECL (rtl)) == VAR_DECL || TREE_CODE (DEBUG_IMPLICIT_PTR_DECL (rtl)) == PARM_DECL || TREE_CODE (DEBUG_IMPLICIT_PTR_DECL (rtl)) == RESULT_DECL); ref = lookup_decl_die (DEBUG_IMPLICIT_PTR_DECL (rtl)); - ret = new_loc_descr (DW_OP_GNU_implicit_pointer, 0, offset); + ret = new_loc_descr (dwarf_op (DW_OP_implicit_pointer), 0, offset); ret->dw_loc_oprnd2.val_class = dw_val_class_const; if (ref) { @@ -15635,6 +15710,13 @@ resolve_args_picking_1 (dw_loc_descr_ref break; } + case DW_OP_implicit_pointer: + case DW_OP_entry_value: + case DW_OP_const_type: + case DW_OP_regval_type: + case DW_OP_deref_type: + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_push_tls_address: case DW_OP_GNU_uninit: case DW_OP_GNU_encoded_addr: @@ -26020,6 +26102,9 @@ prune_unused_types_walk_loc_descr (dw_lo for (; loc != NULL; loc = loc->dw_loc_next) switch (loc->dw_loc_opc) { + case DW_OP_implicit_pointer: + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_implicit_pointer: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: @@ -26029,16 +26114,20 @@ prune_unused_types_walk_loc_descr (dw_lo case DW_OP_call2: case DW_OP_call4: case DW_OP_call_ref: + case DW_OP_const_type: case DW_OP_GNU_const_type: case DW_OP_GNU_parameter_ref: gcc_assert (loc->dw_loc_oprnd1.val_class == dw_val_class_die_ref); prune_unused_types_mark (loc->dw_loc_oprnd1.v.val_die_ref.die, 1); break; + case DW_OP_regval_type: + case DW_OP_deref_type: case DW_OP_GNU_regval_type: case DW_OP_GNU_deref_type: gcc_assert (loc->dw_loc_oprnd2.val_class == dw_val_class_die_ref); prune_unused_types_mark (loc->dw_loc_oprnd2.v.val_die_ref.die, 1); break; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: gcc_assert (loc->dw_loc_oprnd1.val_class == dw_val_class_loc); prune_unused_types_walk_loc_descr (loc->dw_loc_oprnd1.v.val_loc); @@ -26514,18 +26603,24 @@ mark_base_types (dw_loc_descr_ref loc) { switch (loc->dw_loc_opc) { + case DW_OP_regval_type: + case DW_OP_deref_type: case DW_OP_GNU_regval_type: case DW_OP_GNU_deref_type: base_type = loc->dw_loc_oprnd2.v.val_die_ref.die; break; + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: if (loc->dw_loc_oprnd1.val_class == dw_val_class_unsigned_const) continue; /* FALLTHRU */ + case DW_OP_const_type: case DW_OP_GNU_const_type: base_type = loc->dw_loc_oprnd1.v.val_die_ref.die; break; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: mark_base_types (loc->dw_loc_oprnd1.v.val_loc); continue; @@ -26670,7 +26765,7 @@ resolve_one_addr (rtx *addr) /* For STRING_CST, return SYMBOL_REF of its constant pool entry, if possible, and create DW_TAG_dwarf_procedure that can be referenced - from DW_OP_GNU_implicit_pointer if the string hasn't been seen yet. */ + from DW_OP_implicit_pointer if the string hasn't been seen yet. */ static rtx string_cst_pool_decl (tree t) @@ -26712,7 +26807,7 @@ string_cst_pool_decl (tree t) a DW_OP_addr followed by DW_OP_stack_value, either at the start of exprloc or after DW_OP_{,bit_}piece, and val_addr can't be resolved. Replace it (both DW_OP_addr and DW_OP_stack_value) - with DW_OP_GNU_implicit_pointer if possible + with DW_OP_implicit_pointer if possible and return true, if unsuccessful, return false. */ static bool @@ -26751,7 +26846,7 @@ optimize_one_addr_into_implicit_ptr (dw_ if (ref && (get_AT (ref, DW_AT_location) || get_AT (ref, DW_AT_const_value))) { - loc->dw_loc_opc = DW_OP_GNU_implicit_pointer; + loc->dw_loc_opc = dwarf_op (DW_OP_implicit_pointer); loc->dw_loc_oprnd1.val_class = dw_val_class_die_ref; loc->dw_loc_oprnd1.val_entry = NULL; loc->dw_loc_oprnd1.v.val_die_ref.die = ref; @@ -26784,7 +26879,7 @@ resolve_addr_in_expr (dw_loc_descr_ref l || prev->dw_loc_opc == DW_OP_bit_piece) && loc->dw_loc_next && loc->dw_loc_next->dw_loc_opc == DW_OP_stack_value - && !dwarf_strict + && (!dwarf_strict || dwarf_version >= 5) && optimize_one_addr_into_implicit_ptr (loc)) break; return false; @@ -26827,6 +26922,7 @@ resolve_addr_in_expr (dw_loc_descr_ref l && !resolve_one_addr (&loc->dw_loc_oprnd2.v.val_addr)) return false; break; + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: case DW_OP_GNU_parameter_ref: if (loc->dw_loc_oprnd1.val_class == dw_val_class_decl_ref) @@ -26840,17 +26936,25 @@ resolve_addr_in_expr (dw_loc_descr_ref l loc->dw_loc_oprnd1.v.val_die_ref.external = 0; } break; + case DW_OP_const_type: + case DW_OP_regval_type: + case DW_OP_deref_type: + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_const_type: case DW_OP_GNU_regval_type: case DW_OP_GNU_deref_type: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: while (loc->dw_loc_next - && loc->dw_loc_next->dw_loc_opc == DW_OP_GNU_convert) + && (loc->dw_loc_next->dw_loc_opc == DW_OP_convert + || loc->dw_loc_next->dw_loc_opc == DW_OP_GNU_convert)) { dw_die_ref base1, base2; unsigned enc1, enc2, size1, size2; - if (loc->dw_loc_opc == DW_OP_GNU_regval_type + if (loc->dw_loc_opc == DW_OP_regval_type + || loc->dw_loc_opc == DW_OP_deref_type + || loc->dw_loc_opc == DW_OP_GNU_regval_type || loc->dw_loc_opc == DW_OP_GNU_deref_type) base1 = loc->dw_loc_oprnd2.v.val_die_ref.die; else if (loc->dw_loc_oprnd1.val_class @@ -26874,9 +26978,11 @@ resolve_addr_in_expr (dw_loc_descr_ref l && loc != keep) || enc1 == enc2)) { - /* Optimize away next DW_OP_GNU_convert after + /* Optimize away next DW_OP_convert after adjusting LOC's base type die reference. */ - if (loc->dw_loc_opc == DW_OP_GNU_regval_type + if (loc->dw_loc_opc == DW_OP_regval_type + || loc->dw_loc_opc == DW_OP_deref_type + || loc->dw_loc_opc == DW_OP_GNU_regval_type || loc->dw_loc_opc == DW_OP_GNU_deref_type) loc->dw_loc_oprnd2.v.val_die_ref.die = base2; else @@ -26884,7 +26990,7 @@ resolve_addr_in_expr (dw_loc_descr_ref l loc->dw_loc_next = loc->dw_loc_next->dw_loc_next; continue; } - /* Don't change integer DW_OP_GNU_convert after e.g. floating + /* Don't change integer DW_OP_convert after e.g. floating point typed stack entry. */ else if (enc1 != DW_ATE_unsigned && enc1 != DW_ATE_signed) keep = loc->dw_loc_next; @@ -26901,7 +27007,7 @@ resolve_addr_in_expr (dw_loc_descr_ref l DW_OP_addr alone, which referred to DECL in DW_OP_addr's operand and DW_OP_addr couldn't be resolved. resolve_addr has already removed the DW_AT_location attribute. This function attempts to - add a new DW_AT_location attribute with DW_OP_GNU_implicit_pointer + add a new DW_AT_location attribute with DW_OP_implicit_pointer to it or DW_AT_const_value attribute, if possible. */ static void @@ -26923,13 +27029,13 @@ optimize_location_into_implicit_ptr (dw_ DW_AT_const_value instead. */ if (tree_add_const_value_attribute (die, init)) return; - if (dwarf_strict) + if (dwarf_strict && dwarf_version < 5) return; /* If init is ADDR_EXPR or POINTER_PLUS_EXPR of ADDR_EXPR, and ADDR_EXPR refers to a decl that has DW_AT_location or DW_AT_const_value (but isn't addressable, otherwise resolving the original DW_OP_addr wouldn't fail), see if - we can add DW_OP_GNU_implicit_pointer. */ + we can add DW_OP_implicit_pointer. */ STRIP_NOPS (init); if (TREE_CODE (init) == POINTER_PLUS_EXPR && tree_fits_shwi_p (TREE_OPERAND (init, 1))) @@ -26963,7 +27069,7 @@ optimize_location_into_implicit_ptr (dw_ || (!get_AT (ref, DW_AT_location) && !get_AT (ref, DW_AT_const_value))) return; - l = new_loc_descr (DW_OP_GNU_implicit_pointer, 0, offset); + l = new_loc_descr (dwarf_op (DW_OP_implicit_pointer), 0, offset); l->dw_loc_oprnd1.val_class = dw_val_class_die_ref; l->dw_loc_oprnd1.v.val_die_ref.die = ref; l->dw_loc_oprnd1.v.val_die_ref.external = 0; @@ -26986,6 +27092,7 @@ non_dwarf_expression (dw_loc_descr_ref l case DW_OP_regx: case DW_OP_implicit_value: case DW_OP_stack_value: + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: case DW_OP_GNU_parameter_ref: case DW_OP_piece: @@ -27475,12 +27582,16 @@ hash_loc_operands (dw_loc_descr_ref loc, inchash::add_rtx (val1->val_entry->addr.rtl, hstate); } break; + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: hstate.add_int (val2->v.val_int); break; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: hstate.add_object (val1->v.val_loc); break; + case DW_OP_regval_type: + case DW_OP_deref_type: case DW_OP_GNU_regval_type: case DW_OP_GNU_deref_type: { @@ -27493,6 +27604,8 @@ hash_loc_operands (dw_loc_descr_ref loc, hstate.add_object (encoding); } break; + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: if (val1->val_class == dw_val_class_unsigned_const) @@ -27501,6 +27614,7 @@ hash_loc_operands (dw_loc_descr_ref loc, break; } /* FALLTHRU */ + case DW_OP_const_type: case DW_OP_GNU_const_type: { unsigned int byte_size @@ -27509,7 +27623,8 @@ hash_loc_operands (dw_loc_descr_ref loc, = get_AT_unsigned (val1->v.val_die_ref.die, DW_AT_encoding); hstate.add_object (byte_size); hstate.add_object (encoding); - if (loc->dw_loc_opc != DW_OP_GNU_const_type) + if (loc->dw_loc_opc != DW_OP_const_type + && loc->dw_loc_opc != DW_OP_GNU_const_type) break; hstate.add_object (val2->val_class); switch (val2->val_class) @@ -27702,13 +27817,16 @@ compare_loc_operands (dw_loc_descr_ref x rtx ay1 = valy1->val_entry->addr.rtl; return rtx_equal_p (ax1, ay1); } + case DW_OP_implicit_pointer: case DW_OP_GNU_implicit_pointer: return valx1->val_class == dw_val_class_die_ref && valx1->val_class == valy1->val_class && valx1->v.val_die_ref.die == valy1->v.val_die_ref.die && valx2->v.val_int == valy2->v.val_int; + case DW_OP_entry_value: case DW_OP_GNU_entry_value: return compare_loc_operands (valx1->v.val_loc, valy1->v.val_loc); + case DW_OP_const_type: case DW_OP_GNU_const_type: if (valx1->v.val_die_ref.die != valy1->v.val_die_ref.die || valx2->val_class != valy2->val_class) @@ -27731,10 +27849,14 @@ compare_loc_operands (dw_loc_descr_ref x default: gcc_unreachable (); } + case DW_OP_regval_type: + case DW_OP_deref_type: case DW_OP_GNU_regval_type: case DW_OP_GNU_deref_type: return valx1->v.val_int == valy1->v.val_int && valx2->v.val_die_ref.die == valy2->v.val_die_ref.die; + case DW_OP_convert: + case DW_OP_reinterpret: case DW_OP_GNU_convert: case DW_OP_GNU_reinterpret: if (valx1->val_class != valy1->val_class) Jakub