PR 35681: Correct handling of "expressions" with ELEMENTAL subroutines
Daniel Kraft
d@domob.eu
Tue Oct 21 15:51:00 GMT 2008
Hi all,
I'm investigating PR 35681 at the moment; one of the problems there is
that a call to an ELEMENTAL subroutine like
CALL copy ((a((/ 2, 1 /))), a)
does not create a temporary value for the "expression" (parentheses!) in
the first actual argument; see the PR for details. The problem there is
that this expression is indeed handled and a temporary created, but this
all happens in gfc_conv_function_call inside the scalarization loop for
the ELEMENTAL call and thus only scalar temporaries are created one at a
time and not one array temporary, as it should be.
My first idea of handling this was to move the expression-evaluation for
function calls out of gfc_conv_function_call and thus out of the
ELEMENTAL scalarization; but I believe this would be a very intrusive
patch and difficult to get right; not to mention it is surely not the
thing we want for stage 3 and not really worth this trouble at the moment.
Currently there's already logic to handle temporaries (although for the
INTENT(OUT) arguments) if required for ELEMENTAL calls
(trans-stmt.c:gfc_conv_elemental_dependencies) and I tried to study the
code there, but unfortunatelly am not really an expert about trans-time
scalarization and all those ss/se things.
I also tried a naive patch re-using this logic for the temporaries for
INTRINSIC_PARENTHESES-expressions but failed because those seem not to
get an entry into loopse->ss->expr like EXPR_VARIABLE ones seem to do.
So my question is, is it possible (and relatively easy) to
"gfc_conv_expr" arbitrary expressions (like those not being
constants/variables or something like this, at the very least
parentheses expressions but they are probably too few) into array
temporaries and then modify the ss/se/code->ext.actual in such a way
that this temporary is used later when calling gfc_conv_function_call
using the ss and actual argument list of the call-statement instead of
converting it again?
Something along the lines of:
gfc_expr* e = some_actual_argument_of (code->ext.actual);
temp = create_temporary_array (); /* gfc_conv_create_array_temporary? */
add_modify_to_block (se.pre, temp, gfc_conv_expr (e));
/* Change ss/e somehow to refer to the temporary instead of the original
expression that would get converted again. */
gfc_conv_function_call (expr->symtree, code->ext.actual);
I hope I got it somewhat clear... Any pointer about where I can find
information on how this scalarization stuff really works and how I can
achieve this would be very appreciated!
Thanks,
Daniel
--
Done: Arc-Bar-Cav-Rog-Sam-Val-Wiz
To go: Hea-Kni-Mon-Pri-Ran-Tou
More information about the Fortran
mailing list