[PATCH] Fix PR34081/C++ ICE in s390_function_value

Andreas Krebbel Andreas.Krebbel@de.ibm.com
Mon Nov 26 18:04:00 GMT 2007


> I would suggest we change the name of the parameter to ABSTRACT_P, and
> then use PROCESSING_TEMPLATE_DECL in the front end to initialize that.
> As further cleanups (not required as part of the patch) we could attempt
> the "struct function" split for ABSTRACT_P and/or remove the use of
> current_function_returns_struct from the C++ front-end.

Done with the attached patch.

Bootstrapped on s390x and x86_64.
No testsuite regressions.
New testcase is fixed on s390x.

OK for mainline?

2007-11-26  Andreas Krebbel  <krebbel1@de.ibm.com>

	PR 34081/C++
	* c-decl.c (store_parm_decls): Pass 'false' for the new
	allocate_struct_function parameter.
	* cgraphunit.c (cgraph_build_static_cdtor): Likewise.
	* tree-parloops.c (create_loop_fn): Likewise.
	* function.c (push_function_context_to, push_struct_function,
	init_function_start): Likewise.
	(allocate_struct_function): Add boolean parameter.
	* tree.h (allocate_struct_function): Add boolean parameter.

2007-11-26  Andreas Krebbel  <krebbel1@de.ibm.com>

	PR 34081/C++
	* decl.c (start_preparsed_function): Pass 
	processing_template_decl for the new allocate_struct_function
	parameter.

2007-11-26  Andreas Krebbel  <krebbel1@de.ibm.com>

	PR 34081/C++
	* g++.dg/template/dependent-expr6.C: New testcase.

2007-11-26  Andreas Krebbel  <krebbel1@de.ibm.com>

        PR 34081/C++
        * trans.c (Subprogram_Body_to_gnu, Compilation_Unit_to_gnu):
        Pass 'false' for the new allocate_struct_function parameter.
        * utils.c (build_function_stub): Likewise.

... and so on for the ada, java and treelang front ends.


Index: gcc/ada/trans.c
===================================================================
*** gcc/ada/trans.c.orig	2007-11-21 10:48:54.000000000 +0100
--- gcc/ada/trans.c	2007-11-21 14:02:57.000000000 +0100
*************** Subprogram_Body_to_gnu (Node_Id gnat_nod
*** 1776,1782 ****
    Sloc_to_locus (Sloc (gnat_node), &DECL_SOURCE_LOCATION (gnu_subprog_decl));
  
    /* Initialize the information structure for the function.  */
!   allocate_struct_function (gnu_subprog_decl);
    DECL_STRUCT_FUNCTION (gnu_subprog_decl)->language
      = GGC_CNEW (struct language_function);
  
--- 1776,1782 ----
    Sloc_to_locus (Sloc (gnat_node), &DECL_SOURCE_LOCATION (gnu_subprog_decl));
  
    /* Initialize the information structure for the function.  */
!   allocate_struct_function (gnu_subprog_decl, false);
    DECL_STRUCT_FUNCTION (gnu_subprog_decl)->language
      = GGC_CNEW (struct language_function);
  
*************** Compilation_Unit_to_gnu (Node_Id gnat_no
*** 2914,2920 ****
    push_stack (&gnu_elab_proc_stack, NULL_TREE, gnu_elab_proc_decl);
  
    DECL_ELABORATION_PROC_P (gnu_elab_proc_decl) = 1;
!   allocate_struct_function (gnu_elab_proc_decl);
    Sloc_to_locus (Sloc (gnat_unit_entity), &cfun->function_end_locus);
    set_cfun (NULL);
  
--- 2914,2920 ----
    push_stack (&gnu_elab_proc_stack, NULL_TREE, gnu_elab_proc_decl);
  
    DECL_ELABORATION_PROC_P (gnu_elab_proc_decl) = 1;
!   allocate_struct_function (gnu_elab_proc_decl, false);
    Sloc_to_locus (Sloc (gnat_unit_entity), &cfun->function_end_locus);
    set_cfun (NULL);
  
Index: gcc/ada/utils.c
===================================================================
*** gcc/ada/utils.c.orig	2007-11-21 10:48:54.000000000 +0100
--- gcc/ada/utils.c	2007-11-21 14:02:57.000000000 +0100
*************** build_function_stub (tree gnu_subprog, E
*** 2983,2989 ****
  
    gnat_poplevel ();
  
!   allocate_struct_function (gnu_stub_decl);
    end_subprog_body (gnu_body);
  }
  
--- 2983,2989 ----
  
    gnat_poplevel ();
  
!   allocate_struct_function (gnu_stub_decl, false);
    end_subprog_body (gnu_body);
  }
  
Index: gcc/c-decl.c
===================================================================
*** gcc/c-decl.c.orig	2007-11-21 10:49:17.000000000 +0100
--- gcc/c-decl.c	2007-11-21 14:02:57.000000000 +0100
*************** store_parm_decls (void)
*** 6632,6638 ****
    gen_aux_info_record (fndecl, 1, 0, proto);
  
    /* Initialize the RTL code for the function.  */
!   allocate_struct_function (fndecl);
  
    /* Begin the statement tree for this function.  */
    DECL_SAVED_TREE (fndecl) = push_stmt_list ();
--- 6632,6638 ----
    gen_aux_info_record (fndecl, 1, 0, proto);
  
    /* Initialize the RTL code for the function.  */
!   allocate_struct_function (fndecl, false);
  
    /* Begin the statement tree for this function.  */
    DECL_SAVED_TREE (fndecl) = push_stmt_list ();
Index: gcc/cgraphunit.c
===================================================================
*** gcc/cgraphunit.c.orig	2007-11-21 10:49:17.000000000 +0100
--- gcc/cgraphunit.c	2007-11-21 14:02:57.000000000 +0100
*************** cgraph_build_static_cdtor (char which, t
*** 1481,1487 ****
    DECL_ARTIFICIAL (resdecl) = 1;
    DECL_RESULT (decl) = resdecl;
  
!   allocate_struct_function (decl);
  
    TREE_STATIC (decl) = 1;
    TREE_USED (decl) = 1;
--- 1481,1487 ----
    DECL_ARTIFICIAL (resdecl) = 1;
    DECL_RESULT (decl) = resdecl;
  
!   allocate_struct_function (decl, false);
  
    TREE_STATIC (decl) = 1;
    TREE_USED (decl) = 1;
Index: gcc/cp/decl.c
===================================================================
*** gcc/cp/decl.c.orig	2007-11-21 10:48:52.000000000 +0100
--- gcc/cp/decl.c	2007-11-26 09:48:16.000000000 +0100
*************** start_preparsed_function (tree decl1, tr
*** 11180,11186 ****
       CFUN set up, and our per-function variables initialized.
       FIXME factor out the non-RTL stuff.  */
    bl = current_binding_level;
!   allocate_struct_function (decl1);
    current_binding_level = bl;
  
    /* Even though we're inside a function body, we still don't want to
--- 11180,11186 ----
       CFUN set up, and our per-function variables initialized.
       FIXME factor out the non-RTL stuff.  */
    bl = current_binding_level;
!   allocate_struct_function (decl1, processing_template_decl);
    current_binding_level = bl;
  
    /* Even though we're inside a function body, we still don't want to
Index: gcc/function.c
===================================================================
*** gcc/function.c.orig	2007-11-21 10:49:17.000000000 +0100
--- gcc/function.c	2007-11-26 09:52:20.000000000 +0100
*************** push_function_context_to (tree context A
*** 247,253 ****
    struct function *p;
  
    if (cfun == 0)
!     allocate_struct_function (NULL);
    p = cfun;
  
    p->outer = outer_function_chain;
--- 247,253 ----
    struct function *p;
  
    if (cfun == 0)
!     allocate_struct_function (NULL, false);
    p = cfun;
  
    p->outer = outer_function_chain;
*************** get_next_funcdef_no (void) 
*** 3881,3890 ****
     directly into cfun and invoke the back end hook explicitly at the
     very end, rather than initializing a temporary and calling set_cfun
     on it.
! */
  
  void
! allocate_struct_function (tree fndecl)
  {
    tree result;
    tree fntype = fndecl ? TREE_TYPE (fndecl) : NULL_TREE;
--- 3881,3894 ----
     directly into cfun and invoke the back end hook explicitly at the
     very end, rather than initializing a temporary and calling set_cfun
     on it.
! 
!    ABSTRACT_P is true if this is a function that will never be seen by
!    the middle-end.  Such functions are front-end concepts (like C++
!    function templates) that do not correspond directly to functions
!    placed in object files.  */
  
  void
! allocate_struct_function (tree fndecl, bool abstract_p)
  {
    tree result;
    tree fntype = fndecl ? TREE_TYPE (fndecl) : NULL_TREE;
*************** allocate_struct_function (tree fndecl)
*** 3910,3916 ****
        cfun->decl = fndecl;
  
        result = DECL_RESULT (fndecl);
!       if (aggregate_value_p (result, fndecl))
  	{
  #ifdef PCC_STATIC_STRUCT_RETURN
  	  current_function_returns_pcc_struct = 1;
--- 3914,3920 ----
        cfun->decl = fndecl;
  
        result = DECL_RESULT (fndecl);
!       if (!abstract_p && aggregate_value_p (result, fndecl))
  	{
  #ifdef PCC_STATIC_STRUCT_RETURN
  	  current_function_returns_pcc_struct = 1;
*************** push_struct_function (tree fndecl)
*** 3943,3949 ****
    VEC_safe_push (function_p, heap, cfun_stack, cfun);
    if (fndecl)
      in_system_header = DECL_IN_SYSTEM_HEADER (fndecl);
!   allocate_struct_function (fndecl);
  }
  
  /* Reset cfun, and other non-struct-function variables to defaults as
--- 3947,3953 ----
    VEC_safe_push (function_p, heap, cfun_stack, cfun);
    if (fndecl)
      in_system_header = DECL_IN_SYSTEM_HEADER (fndecl);
!   allocate_struct_function (fndecl, false);
  }
  
  /* Reset cfun, and other non-struct-function variables to defaults as
*************** init_function_start (tree subr)
*** 3998,4004 ****
    if (subr && DECL_STRUCT_FUNCTION (subr))
      set_cfun (DECL_STRUCT_FUNCTION (subr));
    else
!     allocate_struct_function (subr);
    prepare_function_start ();
  
    /* Warn if this value is an aggregate type,
--- 4002,4008 ----
    if (subr && DECL_STRUCT_FUNCTION (subr))
      set_cfun (DECL_STRUCT_FUNCTION (subr));
    else
!     allocate_struct_function (subr, false);
    prepare_function_start ();
  
    /* Warn if this value is an aggregate type,
Index: gcc/java/decl.c
===================================================================
*** gcc/java/decl.c.orig	2007-11-21 10:47:25.000000000 +0100
--- gcc/java/decl.c	2007-11-21 14:02:57.000000000 +0100
*************** finish_method (tree fndecl)
*** 1850,1856 ****
    if (DECL_STRUCT_FUNCTION (fndecl))
      set_cfun (DECL_STRUCT_FUNCTION (fndecl));
    else
!     allocate_struct_function (fndecl);
  #ifdef USE_MAPPED_LOCATION
    cfun->function_end_locus = DECL_FUNCTION_LAST_LINE (fndecl);
  #else
--- 1850,1856 ----
    if (DECL_STRUCT_FUNCTION (fndecl))
      set_cfun (DECL_STRUCT_FUNCTION (fndecl));
    else
!     allocate_struct_function (fndecl, false);
  #ifdef USE_MAPPED_LOCATION
    cfun->function_end_locus = DECL_FUNCTION_LAST_LINE (fndecl);
  #else
Index: gcc/tree-parloops.c
===================================================================
*** gcc/tree-parloops.c.orig	2007-11-21 10:49:17.000000000 +0100
--- gcc/tree-parloops.c	2007-11-21 14:02:57.000000000 +0100
*************** create_loop_fn (void)
*** 1248,1254 ****
    TREE_USED (t) = 1;
    DECL_ARGUMENTS (decl) = t;
  
!   allocate_struct_function (decl);
  
    /* The call to allocate_struct_function clobbers CFUN, so we need to restore
       it.  */
--- 1248,1254 ----
    TREE_USED (t) = 1;
    DECL_ARGUMENTS (decl) = t;
  
!   allocate_struct_function (decl, false);
  
    /* The call to allocate_struct_function clobbers CFUN, so we need to restore
       it.  */
Index: gcc/tree.h
===================================================================
*** gcc/tree.h.orig	2007-11-21 10:49:17.000000000 +0100
--- gcc/tree.h	2007-11-21 14:02:57.000000000 +0100
*************** extern void expand_main_function (void);
*** 4935,4941 ****
  extern void init_dummy_function_start (void);
  extern void expand_dummy_function_end (void);
  extern unsigned int init_function_for_compilation (void);
! extern void allocate_struct_function (tree);
  extern void push_struct_function (tree fndecl);
  extern void init_function_start (tree);
  extern bool use_register_for_decl (const_tree);
--- 4935,4941 ----
  extern void init_dummy_function_start (void);
  extern void expand_dummy_function_end (void);
  extern unsigned int init_function_for_compilation (void);
! extern void allocate_struct_function (tree, bool);
  extern void push_struct_function (tree fndecl);
  extern void init_function_start (tree);
  extern bool use_register_for_decl (const_tree);
Index: gcc/treelang/treetree.c
===================================================================
*** gcc/treelang/treetree.c.orig	2007-11-21 10:47:25.000000000 +0100
--- gcc/treelang/treetree.c	2007-11-21 14:02:57.000000000 +0100
*************** tree_code_create_function_wrapup (locati
*** 457,463 ****
                                        BLOCK_VARS (block),
  			              stmts, block);
  
!   allocate_struct_function (fn_decl);
    cfun->function_end_locus = loc;
  
    /* Dump the original tree to a file.  */
--- 457,463 ----
                                        BLOCK_VARS (block),
  			              stmts, block);
  
!   allocate_struct_function (fn_decl, false);
    cfun->function_end_locus = loc;
  
    /* Dump the original tree to a file.  */
Index: gcc/testsuite/g++.dg/template/dependent-expr6.C
===================================================================
*** /dev/null	1970-01-01 00:00:00.000000000 +0000
--- gcc/testsuite/g++.dg/template/dependent-expr6.C	2007-11-21 14:02:57.000000000 +0100
***************
*** 0 ****
--- 1,21 ----
+ // { dg-do compile }
+ 
+ // Copyright 2007 Free Software Foundation
+ // Contributed by Andreas Krebbel <Andreas.Krebbel@de.ibm.com>
+ 
+ // PR C++ 34081 ICE
+ 
+ class Foo;
+ 
+ template < class Foo > class Bar
+ {
+   enum Status
+   { OK, NO };
+ 
+   enum Status getStatus ()
+   {
+     return status;
+   }
+ 
+   Status status;
+ };



More information about the Gcc-patches mailing list