Hi all, this patches fixes PR60289 for allocating unlimited polymorphic entities retyping them to a char array. The patch depends on my former patch for pr60255 at:
https://gcc.gnu.org/ml/fortran/2014-12/msg00130.html because it needs the _len component introduced. I have extend Janus' patch given in the PR and added a testcase. This is the fifth version of the patch, where the previous hasn't gotten any comments, so I think it is well enough for commit. What do you think? Bootstraps and regtests ok on x86_64-linux-gnu. Depends on: https://gcc.gnu.org/ml/fortran/2014-12/msg00130.html Regards, Andre -- Andre Vehreschild * Kreuzherrenstr. 8 * 52062 Aachen Tel.: +49 241 9291018 * Email: [email protected]
pr60289_5.clog
Description: Binary data
diff --git a/gcc/fortran/resolve.c b/gcc/fortran/resolve.c
index 05a948b..6038dd5 100644
--- a/gcc/fortran/resolve.c
+++ b/gcc/fortran/resolve.c
@@ -6930,7 +6930,9 @@ resolve_allocate_expr (gfc_expr *e, gfc_code *code)
goto failure;
}
- if (code->ext.alloc.ts.type == BT_CHARACTER && !e->ts.deferred)
+ /* Check F08:C632. */
+ if (code->ext.alloc.ts.type == BT_CHARACTER && !e->ts.deferred
+ && !UNLIMITED_POLY (e))
{
int cmp = gfc_dep_compare_expr (e->ts.u.cl->length,
code->ext.alloc.ts.u.cl->length);
diff --git a/gcc/fortran/trans-stmt.c b/gcc/fortran/trans-stmt.c
index c560d05..82ecf31 100644
--- a/gcc/fortran/trans-stmt.c
+++ b/gcc/fortran/trans-stmt.c
@@ -5139,8 +5139,15 @@ gfc_trans_allocate (gfc_code * code)
gfc_add_block_to_block (&se.pre, &se_sz.pre);
se_sz.expr = gfc_evaluate_now (se_sz.expr, &se.pre);
gfc_add_block_to_block (&se.pre, &se_sz.post);
- /* Store the string length. */
- tmp = al->expr->ts.u.cl->backend_decl;
+ /* Store the string length. Get the backend_decl of the _len
+ component for that. */
+ if ((expr->symtree->n.sym->ts.type == BT_CLASS
+ || expr->symtree->n.sym->ts.type == BT_DERIVED)
+ && expr->ts.u.derived->attr.unlimited_polymorphic)
+ tmp = gfc_class_len_get (gfc_get_symbol_decl (
+ expr->symtree->n.sym));
+ else
+ tmp = al->expr->ts.u.cl->backend_decl;
gfc_add_modify (&se.pre, tmp, fold_convert (TREE_TYPE (tmp),
se_sz.expr));
tmp = TREE_TYPE (gfc_typenode_for_spec (&code->ext.alloc.ts));
diff --git a/gcc/testsuite/gfortran.dg/unlimited_polymorphic_21.f90 b/gcc/testsuite/gfortran.dg/unlimited_polymorphic_21.f90
new file mode 100644
index 0000000..18a66b0
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/unlimited_polymorphic_21.f90
@@ -0,0 +1,57 @@
+! { dg-do run }
+! Testing fix for PR fortran/60289
+! Contributed by: Andre Vehreschild <[email protected]>
+!
+program test
+ implicit none
+
+ class(*), pointer :: P
+ integer :: string_len = 10 *2
+
+ allocate(character(string_len)::P)
+
+ select type(P)
+ type is (character(*))
+ P ="some test string"
+ if (P .ne. "some test string") then
+ call abort ()
+ end if
+ if (len(P) .ne. 20) then
+ call abort ()
+ end if
+ if (len(P) .eq. len("some test string")) then
+ call abort ()
+ end if
+ class default
+ call abort ()
+ end select
+
+ deallocate(P)
+
+ ! Now for kind=4 chars.
+
+ allocate(character(len=20,kind=4)::P)
+
+ select type(P)
+ type is (character(len=*,kind=4))
+ P ="some test string"
+ if (P .ne. 4_"some test string") then
+ call abort ()
+ end if
+ if (len(P) .ne. 20) then
+ call abort ()
+ end if
+ if (len(P) .eq. len("some test string")) then
+ call abort ()
+ end if
+ type is (character(len=*,kind=1))
+ call abort ()
+ class default
+ call abort ()
+ end select
+
+ deallocate(P)
+
+
+end program test
+
