Message ID | 20160807135234.7dd4c7fc@vepi2 |
---|---|
State | New |
Headers | show |
To prevent further confusion: The patch-file pr72698_1.patch is for trunk and the gcc-6-branch, the pr72698_v5_1.patch is for gcc-5-branch. Sorry for not pointing that out immediately. - Andre On Sun, 7 Aug 2016 13:52:34 +0200 Andre Vehreschild <vehre@gmx.de> wrote: > Hi all, > > attached patch fixes the ICE caused by a zero-sized string. Assigning > that string to a temporary variable obviously did not work out. The > patch fixes this by checking for zero-sized strings in SOURCE= and not > producing the code to assign "nothing" to the temporary > variable and later to the allocated memory. The version for gcc-5 had > to be adapted slightly, because the version of the ALLOCATE() > implementation is way behind. > > Bootstrapped and regtested on x86_64-linux-gnu/F23. Ok for trunk, > gcc-6 and gcc-5? > > Regards, > Andre
Am 07.08.2016 um 13:52 schrieb Andre Vehreschild: Hi Andre, > attached patch fixes the ICE caused by a zero-sized string. Assigning > that string to a temporary variable obviously did not work out. The > patch fixes this by checking for zero-sized strings in SOURCE= and not > producing the code to assign "nothing" to the temporary > variable and later to the allocated memory. The version for gcc-5 had > to be adapted slightly, because the version of the ALLOCATE() > implementation is way behind. > > Bootstrapped and regtested on x86_64-linux-gnu/F23. Ok for trunk, gcc-6 > and gcc-5? Looks good. With the test case, you might consider changing that into a runtime test to make sure that the correct result is obtained. So, OK with that change. Regards Thomas
diff --git a/gcc/fortran/trans-stmt.c b/gcc/fortran/trans-stmt.c index 6e4e2a7..5884e7a 100644 --- a/gcc/fortran/trans-stmt.c +++ b/gcc/fortran/trans-stmt.c @@ -5448,9 +5448,19 @@ gfc_trans_allocate (gfc_code * code) } gfc_add_block_to_block (&block, &se.pre); gfc_add_block_to_block (&post, &se.post); + + /* Special case when string in expr3 is zero. */ + if (code->expr3->ts.type == BT_CHARACTER + && integer_zerop (se.string_length)) + { + gfc_init_se (&se, NULL); + temp_var_needed = false; + expr3_len = integer_zero_node; + e3_is = E3_MOLD; + } /* Prevent aliasing, i.e., se.expr may be already a variable declaration. */ - if (se.expr != NULL_TREE && temp_var_needed) + else if (se.expr != NULL_TREE && temp_var_needed) { tree var, desc; tmp = GFC_DESCRIPTOR_TYPE_P (TREE_TYPE (se.expr)) || is_coarray ? @@ -5679,11 +5689,8 @@ gfc_trans_allocate (gfc_code * code) gcc_assert (expr3_esize); expr3_esize = fold_convert (sizetype, expr3_esize); if (e3_is == E3_MOLD) - { - /* The expr3 is no longer valid after this point. */ - expr3 = NULL_TREE; - e3_is = E3_UNSET; - } + /* The expr3 is no longer valid after this point. */ + expr3 = NULL_TREE; } else if (code->ext.alloc.ts.type != BT_UNKNOWN) { @@ -6012,7 +6019,7 @@ gfc_trans_allocate (gfc_code * code) fold_convert (TREE_TYPE (al_len), integer_zero_node)); } - if (code->expr3 && !code->expr3->mold) + if (code->expr3 && !code->expr3->mold && e3_is != E3_MOLD) { /* Initialization via SOURCE block (or static default initializer). Classes need some special handling, so catch them first. */ diff --git a/gcc/testsuite/gfortran.dg/allocate_with_source_20.f03 b/gcc/testsuite/gfortran.dg/allocate_with_source_20.f03 new file mode 100644 index 0000000..c145267 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/allocate_with_source_20.f03 @@ -0,0 +1,20 @@ +! { dg-do compile } + +! Check that PR72698 is fixed. +! Contributed by Gerhard Steinmetz + +module m +contains + integer function f() + f = 4 + end +end +program p + use m + character(3), parameter :: c = 'abc' + character(:), allocatable :: z + allocate (z, source=repeat(c(2:1), f())) + print *, len(z), ' >>' // z // '<<' +end + +