diff options
author | mikael <mikael@138bc75d-0d04-0410-961f-82ee72b054a4> | 2012-08-14 16:45:55 +0000 |
---|---|---|
committer | mikael <mikael@138bc75d-0d04-0410-961f-82ee72b054a4> | 2012-08-14 16:45:55 +0000 |
commit | 6fe2a89d24424512af1d4474c2741481f92dd1cb (patch) | |
tree | 5c06ec0e03bb0ba229ec6bc79ac71362f4c78f3c /gcc/fortran/trans-expr.c | |
parent | a63bcd97bbf68ea5df42a289da3ca5e1b5e471ab (diff) | |
download | gcc-6fe2a89d24424512af1d4474c2741481f92dd1cb.tar.gz |
fortran/
PR fortran/47586
* trans-expr.c (expr_is_variable): Handle regular, procedure pointer,
and typebound functions returning a data pointer.
testsuite/
PR fortran/47586
* gfortran.dg/typebound_proc_20.f90: Enable runtime test.
* gfortran.dg/typebound_proc_27.f03: New test.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@190394 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/fortran/trans-expr.c')
-rw-r--r-- | gcc/fortran/trans-expr.c | 45 |
1 files changed, 45 insertions, 0 deletions
diff --git a/gcc/fortran/trans-expr.c b/gcc/fortran/trans-expr.c index 53fdf45c400..4f7d02620ad 100644 --- a/gcc/fortran/trans-expr.c +++ b/gcc/fortran/trans-expr.c @@ -6961,6 +6961,8 @@ static bool expr_is_variable (gfc_expr *expr) { gfc_expr *arg; + gfc_component *comp; + gfc_symbol *func_ifc; if (expr->expr_type == EXPR_VARIABLE) return true; @@ -6972,7 +6974,50 @@ expr_is_variable (gfc_expr *expr) return expr_is_variable (arg); } + /* A data-pointer-returning function should be considered as a variable + too. */ + if (expr->expr_type == EXPR_FUNCTION + && expr->ref == NULL) + { + if (expr->value.function.isym != NULL) + return false; + + if (expr->value.function.esym != NULL) + { + func_ifc = expr->value.function.esym; + goto found_ifc; + } + else + { + gcc_assert (expr->symtree); + func_ifc = expr->symtree->n.sym; + goto found_ifc; + } + + gcc_unreachable (); + } + + comp = gfc_get_proc_ptr_comp (expr); + if ((expr->expr_type == EXPR_PPC || expr->expr_type == EXPR_FUNCTION) + && comp) + { + func_ifc = comp->ts.interface; + goto found_ifc; + } + + if (expr->expr_type == EXPR_COMPCALL) + { + gcc_assert (!expr->value.compcall.tbp->is_generic); + func_ifc = expr->value.compcall.tbp->u.specific->n.sym; + goto found_ifc; + } + return false; + +found_ifc: + gcc_assert (func_ifc->attr.function + && func_ifc->result != NULL); + return func_ifc->result->attr.pointer; } |