Summary: | [4.8 Regression] [OOP] ICE in fold_convert_loc, at fold-const.c:2016 | ||
---|---|---|---|
Product: | gcc | Reporter: | Richard L Lozes <richard> |
Component: | fortran | Assignee: | janus |
Status: | RESOLVED FIXED | ||
Severity: | normal | CC: | jakub, janus |
Priority: | P4 | Keywords: | ice-on-valid-code |
Version: | 4.7.2 | ||
Target Milestone: | 4.8.0 | ||
Host: | Target: | ||
Build: | Known to work: | ||
Known to fail: | Last reconfirmed: | 2012-10-10 00:00:00 | |
Attachments: | Source code reproducing bug |
I get the ICE with 4.7.2, but the trunk gives pr54881.f90:140.24: call DestroyNode (theNode, lstatus ) 1 Error: Actual argument for 'thenode' must be a pointer at (1) which seems weird (AFAICT theNode is a pointer). While trying to reduce it, I found a version which also ICEs with trunk: implicit none type treeNode type(treeNode), pointer :: right => null() end type type(treeNode), pointer :: theNode print *, associated( RightOf(theNode) ) contains function RightOf( theNode ) class(treeNode), pointer :: RightOf type(treeNode), target, intent(in) :: theNode RightOf => theNode%right end function end Apparently, the ICE on the original test case was only prevented by the error message mentioned by Dominique. With 4.8 trunk one gets the following output: CompilerBug.f03:10:0: internal compiler error: in fold_convert_loc, at fold-const.c:1979 print *, associated( RightOf(theNode) ) ^ 0x8070d4 fold_convert_loc(unsigned int, tree_node*, tree_node*) /home/jweil/gcc48/trunk/gcc/fold-const.c:1979 0x654b90 gfc_conv_associated /home/jweil/gcc48/trunk/gcc/fortran/trans-intrinsic.c:5768 0x656501 gfc_conv_intrinsic_function(gfc_se*, gfc_expr*) /home/jweil/gcc48/trunk/gcc/fortran/trans-intrinsic.c:6303 0x639461 gfc_conv_function_expr /home/jweil/gcc48/trunk/gcc/fortran/trans-expr.c:5127 0x63b4e8 gfc_conv_expr(gfc_se*, gfc_expr*) /home/jweil/gcc48/trunk/gcc/fortran/trans-expr.c:5834 0x63b99c gfc_conv_expr_reference(gfc_se*, gfc_expr*) /home/jweil/gcc48/trunk/gcc/fortran/trans-expr.c:5963 0x65ecb5 gfc_trans_transfer(gfc_code*) /home/jweil/gcc48/trunk/gcc/fortran/trans-io.c:2246 0x5f99da trans_code /home/jweil/gcc48/trunk/gcc/fortran/trans.c:1510 0x5f9b37 gfc_trans_code_cond(gfc_code*, tree_node*) /home/jweil/gcc48/trunk/gcc/fortran/trans.c:1565 0x65dd2e build_dt /home/jweil/gcc48/trunk/gcc/fortran/trans-io.c:1831 0x65de0a gfc_trans_write(gfc_code*) /home/jweil/gcc48/trunk/gcc/fortran/trans-io.c:1870 0x5f9953 trans_code /home/jweil/gcc48/trunk/gcc/fortran/trans.c:1482 0x5f9b56 gfc_trans_code(gfc_code*) /home/jweil/gcc48/trunk/gcc/fortran/trans.c:1573 0x628ccb gfc_generate_function_code(gfc_namespace*) /home/jweil/gcc48/trunk/gcc/fortran/trans-decl.c:5353 0x5f9b9a gfc_generate_code(gfc_namespace*) /home/jweil/gcc48/trunk/gcc/fortran/trans.c:1590 0x59b241 translate_all_program_units /home/jweil/gcc48/trunk/gcc/fortran/parse.c:4467 0x59b8a7 gfc_parse_file() /home/jweil/gcc48/trunk/gcc/fortran/parse.c:4681 0x5e67f4 gfc_be_parse_file /home/jweil/gcc48/trunk/gcc/fortran/f95-lang.c:191 (In reply to comment #1) > > call DestroyNode (theNode, lstatus ) > 1 > Error: Actual argument for 'thenode' must be a pointer at (1) > > which seems weird (AFAICT theNode is a pointer). I agree that this error looks fishy. 'theNode' is clearly declared as POINTER, and the error only occurs if the call is inside a SELECT TYPE statement. Here is a reduced test case: implicit none type treeNode end type class(treeNode), pointer :: theNode logical :: lstatus select type( theNode ) class is (treeNode) call DestroyNode (theNode, lstatus ) end select contains subroutine DestroyNode( theNode, lstatus ) class(treeNode), pointer :: theNode logical, intent(out) :: lstatus end subroutine end Seems to be a regression on trunk. In summary, we have two bugs here: 1) The ICE in comment 2, which happens with all gfortran versions from 4.5 to trunk. 2) The error message in comment 3, which only happens with trunk (and therefore is a regression). (In reply to comment #4) > 1) The ICE in comment 2, which happens with all gfortran versions from 4.5 to > trunk. The ICE can be fixed by the following patch: Index: gcc/fortran/trans-intrinsic.c =================================================================== --- gcc/fortran/trans-intrinsic.c (revision 192159) +++ gcc/fortran/trans-intrinsic.c (working copy) @@ -5732,8 +5732,6 @@ gfc_conv_associated (gfc_se *se, gfc_expr *expr) gfc_init_se (&arg1se, NULL); gfc_init_se (&arg2se, NULL); arg1 = expr->value.function.actual; - if (arg1->expr->ts.type == BT_CLASS) - gfc_add_data_component (arg1->expr); arg2 = arg1->next; /* Check whether the expression is a scalar or not; we cannot use @@ -5755,7 +5753,10 @@ gfc_conv_associated (gfc_se *se, gfc_expr *expr) && arg1->expr->symtree->n.sym->attr.dummy) arg1se.expr = build_fold_indirect_ref_loc (input_location, arg1se.expr); - tmp2 = arg1se.expr; + if (arg1->expr->ts.type == BT_CLASS) + tmp2 = gfc_class_data_get (arg1se.expr); + else + tmp2 = arg1se.expr; } else { (In reply to comment #4) > 2) The error message in comment 3, which only happens with trunk (and therefore > is a regression). This can be fixed by the following: Index: gcc/fortran/match.c =================================================================== --- gcc/fortran/match.c (revision 192159) +++ gcc/fortran/match.c (working copy) @@ -5257,12 +5257,14 @@ select_class_set_tmp (gfc_typespec *ts) gfc_get_sym_tree (name, gfc_current_ns, &tmp, false); gfc_add_type (tmp->n.sym, ts, NULL); -/* Copy across the array spec to the selector. */ + tmp->n.sym->attr.pointer + = CLASS_DATA (select_type_stack->selector)->attr.class_pointer; + + /* Copy across the array spec to the selector. */ if (select_type_stack->selector->ts.type == BT_CLASS && (CLASS_DATA (select_type_stack->selector)->attr.dimension || CLASS_DATA (select_type_stack->selector)->attr.codimension)) { - tmp->n.sym->attr.pointer = 1; tmp->n.sym->attr.dimension = CLASS_DATA (select_type_stack->selector)->attr.dimension; tmp->n.sym->attr.codimension However, I really wonder what caused this regression. On a quick glance, the only patch concerning SELECT TYPE on trunk was the commit for PR41600. And I don't directly see how this would cause the regression. Here is a variant of the test case in comment 3, which for some strange reason fails also with 4.7: implicit none type treeNode end type class(treeNode), pointer :: theNode logical :: lstatus select type( theNode ) type is (treeNode) call DestroyNode (theNode, lstatus ) class is (treeNode) call DestroyNode (theNode, lstatus ) end select contains subroutine DestroyNode( theNode, lstatus ) type(treeNode), pointer :: theNode logical, intent(out) :: lstatus end subroutine end Author: janus Date: Mon Nov 26 10:30:12 2012 New Revision: 193809 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=193809 Log: 2012-11-26 Janus Weil <janus@gcc.gnu.org> PR fortran/54881 * match.c (select_derived_set_tmp,select_class_set_tmp): Removed and unified into ... (select_type_set_tmp): ... this one. Set POINTER argument according to selector. * trans-intrinsic.c (gfc_conv_associated): Use 'gfc_class_data_get' instead of 'gfc_add_data_component'. 2012-11-26 Janus Weil <janus@gcc.gnu.org> PR fortran/54881 * gfortran.dg/associated_6.f90: New. * gfortran.dg/select_type_30.f03: New. Added: trunk/gcc/testsuite/gfortran.dg/associated_6.f90 trunk/gcc/testsuite/gfortran.dg/select_type_30.f03 Modified: trunk/gcc/fortran/ChangeLog trunk/gcc/fortran/match.c trunk/gcc/fortran/trans-intrinsic.c trunk/gcc/testsuite/ChangeLog |
Created attachment 28406 [details] Source code reproducing bug ~/Tests> gfortran -Wall -fbounds-check -Wtabs -g -c ../Source/CompilerBug.f03 ../Source/CompilerBug.f03:124.22: integer*4 :: istat 1 Warning: Unused variable 'istat' declared at (1) ../Source/CompilerBug.f03: In function 'destroydnode': ../Source/CompilerBug.f03:129:0: internal compiler error: in fold_convert_loc, at fold-const.c:2016 Please submit a full bug report, ... ~/Tests> gfortran --version GNU Fortran (SUSE Linux) 4.7.2 20120920 [gcc-4_7-branch revision 191568] Copyright (C) 2012 Free Software Foundation, Inc. ~/Tests> gfortran -dumpmachine i586-suse-linux