[PATCH] Fix up typed DWARF stack support for POINTERS_EXTEND_UNSIGNED targets (PR debug/48853)
Jakub Jelinek
jakub@redhat.com
Thu May 5 09:22:00 GMT 2011
Hi!
My typed DWARF stack changes apparently broke ia64-hpux and H.J.'s out of
tree x32 target. There are several issues:
1) for SUBREG mem_loc_descriptor's 3rd argument was wrong, found by code
inspection
2) CONST/SYMBOL_REF/LABEL_REF when in MEM addresses on POINTERS_EXTEND_UNSIGNED
targets are often Pmode, which is unfortunately larger than DWARF2_ADDR_SIZE
and my conditional would just return NULL in that case instead of
emitting DW_OP_addr.
3) and, when mem_loc_descriptor is called from unwind code, Pmodes larger
than DWARF2_ADDR_SIZE would result in the new DW_OP_GNU_*_type etc. ops
which are not allowed in .eh_frame/.debug_frame
The following patch ought to fix that, bootstrapped/regtested on
x86_64-linux and i686-linux and Steve tested it on ia64-hpux and H.J. on his
port. Ok for trunk?
2011-05-05 Jakub Jelinek <jakub@redhat.com>
PR debug/48853
* dwarf2out.c (mem_loc_descriptor) <case SUBREG>: Pass mem_mode
instead of mode as 3rd argument to recursive call.
(mem_loc_descriptor) <case REG>: If POINTERS_EXTEND_UNSIGNED, don't
emit DW_OP_GNU_regval_type if mode is Pmode and mem_mode is not
VOIDmode.
(mem_loc_descriptor) <case SYMBOL_REF>: If POINTERS_EXTEND_UNSIGNED,
don't give up if mode is Pmode and mem_mode is not VOIDmode.
(mem_loc_descriptor) <case CONST_INT>: If POINTERS_EXTEND_UNSIGNED,
use int_loc_descriptor if mode is Pmode and mem_mode is not VOIDmode.
--- gcc/dwarf2out.c.jj 2011-05-04 10:14:08.000000000 +0200
+++ gcc/dwarf2out.c 2011-05-04 19:08:22.000000000 +0200
@@ -13883,7 +13883,7 @@ mem_loc_descriptor (rtx rtl, enum machin
mem_loc_result = mem_loc_descriptor (SUBREG_REG (rtl),
GET_MODE (SUBREG_REG (rtl)),
- mode, initialized);
+ mem_mode, initialized);
if (mem_loc_result == NULL)
break;
type_die = base_type_for_mode (mode, 0);
@@ -13906,7 +13906,13 @@ mem_loc_descriptor (rtx rtl, enum machin
case REG:
if (GET_MODE_CLASS (mode) != MODE_INT
- || GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE)
+ || (GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE
+#ifdef POINTERS_EXTEND_UNSIGNED
+ && (mode != Pmode
+ || GET_MODE_SIZE (ptr_mode) != DWARF2_ADDR_SIZE
+ || mem_mode == VOIDmode)
+#endif
+ ))
{
dw_die_ref type_die;
@@ -14049,9 +14055,18 @@ mem_loc_descriptor (rtx rtl, enum machin
pool. */
case CONST:
case SYMBOL_REF:
+ if (GET_MODE_CLASS (mode) != MODE_INT)
+ break;
+#ifndef POINTERS_EXTEND_UNSIGNED
+ if (GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE)
+ break;
+#else
if (GET_MODE_SIZE (mode) > DWARF2_ADDR_SIZE
- || GET_MODE_CLASS (mode) != MODE_INT)
+ && (mode != Pmode
+ || GET_MODE_SIZE (ptr_mode) != DWARF2_ADDR_SIZE
+ || mem_mode == VOIDmode))
break;
+#endif
if (GET_CODE (rtl) == SYMBOL_REF
&& SYMBOL_REF_TLS_MODEL (rtl) != TLS_MODEL_NONE)
{
@@ -14288,7 +14303,14 @@ mem_loc_descriptor (rtx rtl, enum machin
break;
case CONST_INT:
- if (GET_MODE_SIZE (mode) <= DWARF2_ADDR_SIZE)
+ if (GET_MODE_SIZE (mode) <= DWARF2_ADDR_SIZE
+#ifdef POINTERS_EXTEND_UNSIGNED
+ || (mode == Pmode
+ && GET_MODE_SIZE (ptr_mode) == DWARF2_ADDR_SIZE
+ && mem_mode != VOIDmode
+ && trunc_int_for_mode (INTVAL (rtl), ptr_mode) == INTVAL (rtl))
+#endif
+ )
{
mem_loc_result = int_loc_descriptor (INTVAL (rtl));
break;
Jakub
More information about the Gcc-patches
mailing list