From: Eric Botcazou Date: Fri, 6 Jun 2014 08:13:24 +0000 (+0000) Subject: re PR debug/53927 (wrong value for DW_AT_static_link) X-Git-Tag: releases/gcc-5.1.0~7046 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=3fd48b121a654c914b2784334650d23095d938e4;p=thirdparty%2Fgcc.git re PR debug/53927 (wrong value for DW_AT_static_link) PR debug/53927 * function.c (instantiate_decls): Process the saved static chain. (expand_function_start): If not optimizing, save the static chain onto the stack. * tree-nested.c (convert_all_function_calls): Always create the static chain for nested functions if not optimizing. From-SVN: r211308 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 7cb049ca9b0b..e6cfb2d85150 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,12 @@ +2014-06-06 Eric Botcazou + + PR debug/53927 + * function.c (instantiate_decls): Process the saved static chain. + (expand_function_start): If not optimizing, save the static chain + onto the stack. + * tree-nested.c (convert_all_function_calls): Always create the static + chain for nested functions if not optimizing. + 2014-06-06 Eric Botcazou * tree-cfg.c (make_edges) : Put a location on the edge. diff --git a/gcc/function.c b/gcc/function.c index a85ad462a7d0..441289e84bc1 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -1877,6 +1877,11 @@ instantiate_decls (tree fndecl) } } + /* Process the saved static chain if it exists. */ + decl = DECL_STRUCT_FUNCTION (fndecl)->static_chain_decl; + if (decl && DECL_HAS_VALUE_EXPR_P (decl)) + instantiate_decl_rtl (DECL_RTL (DECL_VALUE_EXPR (decl))); + /* Now process all variables defined in the function or its subblocks. */ instantiate_decls_1 (DECL_INITIAL (fndecl)); @@ -4811,6 +4816,20 @@ expand_function_start (tree subr) if (MEM_P (chain) && reg_mentioned_p (arg_pointer_rtx, XEXP (chain, 0))) set_dst_reg_note (insn, REG_EQUIV, chain, local); + + /* If we aren't optimizing, save the static chain onto the stack. */ + if (!optimize) + { + tree saved_static_chain_decl + = build_decl (DECL_SOURCE_LOCATION (parm), VAR_DECL, + DECL_NAME (parm), TREE_TYPE (parm)); + rtx saved_static_chain_rtx + = assign_stack_local (Pmode, GET_MODE_SIZE (Pmode), 0); + SET_DECL_RTL (saved_static_chain_decl, saved_static_chain_rtx); + emit_move_insn (saved_static_chain_rtx, chain); + SET_DECL_VALUE_EXPR (parm, saved_static_chain_decl); + DECL_HAS_VALUE_EXPR_P (parm) = 1; + } } /* If the function receives a non-local goto, then store the diff --git a/gcc/tree-nested.c b/gcc/tree-nested.c index ba2cc7657098..85c6a03f7374 100644 --- a/gcc/tree-nested.c +++ b/gcc/tree-nested.c @@ -2220,11 +2220,21 @@ convert_all_function_calls (struct nesting_info *root) struct nesting_info *n; /* First, optimistically clear static_chain for all decls that haven't - used the static chain already for variable access. */ + used the static chain already for variable access. But always create + it if not optimizing. This makes it possible to reconstruct the static + nesting tree at run time and thus to resolve up-level references from + within the debugger. */ FOR_EACH_NEST_INFO (n, root) { tree decl = n->context; - if (!n->outer || (!n->chain_decl && !n->chain_field)) + if (!optimize) + { + if (n->inner) + (void) get_frame_type (n); + if (n->outer) + (void) get_chain_decl (n); + } + else if (!n->outer || (!n->chain_decl && !n->chain_field)) { DECL_STATIC_CHAIN (decl) = 0; if (dump_file && (dump_flags & TDF_DETAILS))