This is the mail archive of the
fortran@gcc.gnu.org
mailing list for the GNU Fortran project.
[Patch, Fortran] PR fortran/38887: Fix MVBITS with runtime zero-length array
- From: Daniel Kraft <d at domob dot eu>
- To: Fortran List <fortran at gcc dot gnu dot org>, gcc-patches <gcc-patches at gcc dot gnu dot org>
- Date: Wed, 21 Jan 2009 12:35:18 +0100
- Subject: [Patch, Fortran] PR fortran/38887: Fix MVBITS with runtime zero-length array
Hi all,
this "trivial" patch fixes PR 38887, where a call to MVBITS aborted at
runtime if the array was empty (but this not detected at runtime).
This regression was introduced by my wrong-code fix for MVBITS; prior to
it, elemental dependencies in the arguments to MVBITS were simply
ignored, leading to that wrong-code bug. Now,
gfc_conv_elemental_dependencies is called which in turn called
internal_unpack for copying the result back after the whole evaluation.
internal_unpack however aborted when its argument was empty.
I'm not completely sure why it was done that way, as the "ordinary"
unpack library function simply returns in this case; my patch changes
internal_unpack to do so, also. I believe this is the best solution and
should not hurt; my guess is that the abort() was introduced first
simply because it was (probably) not possible at that time that
internal_unpack could be called with empty arrays. Now it is, and
instead of generating runtime-check code for this and call
internal_unpack only if the array is not empty, this seems to be the
best solution. Comments on this welcome though, if someone can point me
out why the abort() was there!
I did exclude the regenerated files from the patch, hope this is ok.
Regression-testing on gnu/linux-x86-32 (but there shouldn't be any) at
the moment. Ok for trunk if no failures?
Cheers,
Daniel
--
Done: Arc-Bar-Cav-Rog-Sam-Tou-Val-Wiz
To go: Hea-Kni-Mon-Pri-Ran
2009-01-21 Daniel Kraft <d@domob.eu>
* trans-stmt.c (gfc_conv_elemental_dependencies): Cleaned up comment.
2009-01-21 Daniel Kraft <d@domob.eu>
PR fortran/38887
* runtime/in_unpack_generic.c (internal_unpack): Return instead of
abort when called with empty array.
* m4/in_unpack.m4: Ditto.
* generated/in_unpack_i1.c: Regenerated.
* generated/in_unpack_i2.c: Regenerated.
* generated/in_unpack_i4.c: Regenerated.
* generated/in_unpack_i8.c: Regenerated.
* generated/in_unpack_i16.c: Regenerated.
* generated/in_unpack_r4.c: Regenerated.
* generated/in_unpack_r8.c: Regenerated.
* generated/in_unpack_r10.c: Regenerated.
* generated/in_unpack_r16.c: Regenerated.
* generated/in_unpack_c4.c: Regenerated.
* generated/in_unpack_c8.c: Regenerated.
* generated/in_unpack_c10.c: Regenerated.
* generated/in_unpack_c16.c: Regenerated.
2009-01-21 Daniel Kraft <d@domob.eu>
PR fortran/38887
* gfortran.dg/mvbits_5.f90: New test.
Index: gcc/fortran/trans-stmt.c
===================================================================
--- gcc/fortran/trans-stmt.c (revision 143527)
+++ gcc/fortran/trans-stmt.c (working copy)
@@ -311,14 +311,11 @@ gfc_conv_elemental_dependencies (gfc_se
info->offset = gfc_create_var (gfc_array_index_type, NULL);
gfc_add_modify (&se->pre, info->offset, offset);
-
/* Copy the result back using unpack. */
tmp = build_call_expr (gfor_fndecl_in_unpack, 2, parmse.expr, data);
gfc_add_expr_to_block (&se->post, tmp);
- /* XXX: This is possibly not needed; but isn't it cleaner this way? */
gfc_add_block_to_block (&se->pre, &parmse.pre);
-
gfc_add_block_to_block (&se->post, &parmse.post);
gfc_add_block_to_block (&se->post, &temp_post);
}
Index: libgfortran/runtime/in_unpack_generic.c
===================================================================
--- libgfortran/runtime/in_unpack_generic.c (revision 143527)
+++ libgfortran/runtime/in_unpack_generic.c (working copy)
@@ -178,12 +178,12 @@ internal_unpack (gfc_array_char * d, con
stride[n] = d->dim[n].stride;
extent[n] = d->dim[n].ubound + 1 - d->dim[n].lbound;
if (extent[n] <= 0)
- abort ();
+ return;
if (dsize == stride[n])
- dsize *= extent[n];
+ dsize *= extent[n];
else
- dsize = 0;
+ dsize = 0;
}
src = s;
Index: libgfortran/m4/in_unpack.m4
===================================================================
--- libgfortran/m4/in_unpack.m4 (revision 143527)
+++ libgfortran/m4/in_unpack.m4 (working copy)
@@ -63,12 +63,12 @@ internal_unpack_'rtype_ccode` ('rtype` *
stride[n] = d->dim[n].stride;
extent[n] = d->dim[n].ubound + 1 - d->dim[n].lbound;
if (extent[n] <= 0)
- abort ();
+ return;
if (dsize == stride[n])
- dsize *= extent[n];
+ dsize *= extent[n];
else
- dsize = 0;
+ dsize = 0;
}
if (dsize != 0)
Index: gcc/testsuite/gfortran.dg/mvbits_5.f90
===================================================================
--- gcc/testsuite/gfortran.dg/mvbits_5.f90 (revision 0)
+++ gcc/testsuite/gfortran.dg/mvbits_5.f90 (revision 0)
@@ -0,0 +1,17 @@
+! { dg-do run }
+
+! PR fortran/38887
+! This aborted at runtime for the runtime zero-sized array arguments.
+
+! Contributed by Dick Hendrickson <dick.hendrickson@gmail.com>
+
+program try_ya0013
+ integer ida(9)
+ call ya0013(ida,1,5,6)
+end program
+
+SUBROUTINE YA0013(IDA,nf1,nf5,nf6)
+ INTEGER IDA(9)
+ IDA = 1
+ CALL MVBITS(IDA(NF5:NF1), 0, 1, IDA(NF6:NF1),2)
+END SUBROUTINE