On 07/11/2011 08:16 PM, Daniel Carrera wrote:
This patch improves support for the ALLOCATE statement when using the
coarray library. Specifically, it adds support for the stat= and
errmsg= attributes:
Thanks for the patch - and sorry for the slow review.
Some comments below.
Index: gcc/fortran/trans-stmt.c
===================================================================
+ /* ERRMSG= */
+ errmsg = null_pointer_node;
+ errlen = build_int_cst (gfc_charlen_type_node, 0);
+ if (code->expr2)
+ {
[...]
+ errlen = gfc_get_expr_charlen (code->expr2);
+ errmsg = gfc_build_addr_expr (pchar_type_node, se.expr);
+ }
While build_int_cst is not terribly expensive, it also does not come for
free (cf. tree.c); thus, please move the code from before the "if" into
an "else".
+ /* GOTO destinations. */
+ label_errmsg = gfc_build_label_decl (NULL_TREE);
+ label_finish = gfc_build_label_decl (NULL_TREE);
There seems to be a goto missing. For
integer, allocatable :: AA, BB[:], CC
integer :: stat
allocate(CC, AA, stat=stat)
one gets (-fdump-tree-original):
cc = D.1563; /* end of allocation of "CC". */
if (stat.0 != 0) goto L.1;
if ((logical(kind=4)) __builtin_expect (aa != 0B, 0))
....
else
/* Allocate "AA". */
If you try
allocate(BB[*], AA, stat=stat)
instead you do not get the "if (stat.0 != 0) goto L.1;"
Or in English: Assuming one has stat=variable: If you do not have
coarrays, as soon as one allocation fails, one jumps at the end of the
block and the "stat" variable contains a nonzero value.
If the coarray allocation fails, one continues with other allocations
and thus may end up with "stat == 0" although (at least) one (coarray)
allocation has failed.
+ if (status != NULL_TREE)
+ gfc_add_expr_to_block (block,
+ fold_build2_loc (input_location, MODIFY_EXPR, status_type,
+ status, build_int_cst (status_type, 0)));
Indent is wrong (should be two spaces, is more as a left over from
removing the { ... }).
+ This function follows the following pseudo-code:
[...]
+ newmem = _caf_register ( size, regtype, NULL,&stat, NULL, NULL);
+ if (newmem == NULL)
+ {
+ if (!stat requested)
+ runtime_error ("Allocation would exceed memory limit");
+ }
+ return newmem;
The "if (newmem == NULL) part is not present in the patch - an error is
already printed in _caf_register and thus the check has been removed.
However, the comment has not been updated.
Additionally, you could replace the last two NULLs by errmsg/errmsg_len.
+gfc_allocate_using_lib (stmtblock_t * block, tree size, tree status,
+ tree errmsg, tree errlen)
[...]
+ /* Set the optional status variable to zero. */
+ if (status != NULL_TREE)
+ gfc_add_expr_to_block (block,
+ fold_build2_loc (input_location, MODIFY_EXPR, status_type,
+ status, build_int_cst (status_type, 0)));
[...]
+ gfc_add_modify (block, res,
+ fold_convert (prvoid_type_node,
+ build_call_expr_loc (input_location,
+ gfor_fndecl_caf_register, 6,
The "stat" variable is already set in the registering function - no need
to set it to zero before the call.
Tobias