gfortran.h (gfc_copy_formal_args_intr): Update prototype.

2014-06-12  Tobias Burnus  <burnus@net-b.de>

        * gfortran.h (gfc_copy_formal_args_intr): Update prototype.
        * symbol.c (gfc_copy_formal_args_intr): Handle the case
        that absent optional arguments should be ignored.
        * trans-intrinsic.c (gfc_get_symbol_for_expr): Ditto.
        (gfc_conv_intrinsic_funcall,
        conv_generic_with_optional_char_arg): Update call.
        * resolve.c (gfc_resolve_intrinsic): Ditto.

From-SVN: r211587
This commit is contained in:
Tobias Burnus 2014-06-12 20:35:00 +02:00 committed by Tobias Burnus
parent 551a6341d5
commit 8fdcb6a997
5 changed files with 38 additions and 8 deletions

View File

@ -1,3 +1,13 @@
2014-06-12 Tobias Burnus <burnus@net-b.de>
* gfortran.h (gfc_copy_formal_args_intr): Update prototype.
* symbol.c (gfc_copy_formal_args_intr): Handle the case
that absent optional arguments should be ignored.
* trans-intrinsic.c (gfc_get_symbol_for_expr): Ditto.
(gfc_conv_intrinsic_funcall,
conv_generic_with_optional_char_arg): Update call.
* resolve.c (gfc_resolve_intrinsic): Ditto.
2014-06-10 Dominique d'Humieres <dominiq@lps.ens.fr> 2014-06-10 Dominique d'Humieres <dominiq@lps.ens.fr>
Mikael Morin <mikael@gcc.gnu.org> Mikael Morin <mikael@gcc.gnu.org>

View File

@ -2785,7 +2785,8 @@ gfc_symbol* gfc_get_ultimate_derived_super_type (gfc_symbol*);
bool gfc_type_is_extension_of (gfc_symbol *, gfc_symbol *); bool gfc_type_is_extension_of (gfc_symbol *, gfc_symbol *);
bool gfc_type_compatible (gfc_typespec *, gfc_typespec *); bool gfc_type_compatible (gfc_typespec *, gfc_typespec *);
void gfc_copy_formal_args_intr (gfc_symbol *, gfc_intrinsic_sym *); void gfc_copy_formal_args_intr (gfc_symbol *, gfc_intrinsic_sym *,
gfc_actual_arglist *);
void gfc_free_finalizer (gfc_finalizer *el); /* Needed in resolve.c, too */ void gfc_free_finalizer (gfc_finalizer *el); /* Needed in resolve.c, too */

View File

@ -1674,7 +1674,7 @@ gfc_resolve_intrinsic (gfc_symbol *sym, locus *loc)
return false; return false;
} }
gfc_copy_formal_args_intr (sym, isym); gfc_copy_formal_args_intr (sym, isym, NULL);
sym->attr.pure = isym->pure; sym->attr.pure = isym->pure;
sym->attr.elemental = isym->elemental; sym->attr.elemental = isym->elemental;

View File

@ -4042,16 +4042,21 @@ add_proc_interface (gfc_symbol *sym, ifsrc source, gfc_formal_arglist *formal)
each arg is set according to the existing ones. This function is each arg is set according to the existing ones. This function is
used when creating procedure declaration variables from a procedure used when creating procedure declaration variables from a procedure
declaration statement (see match_proc_decl()) to create the formal declaration statement (see match_proc_decl()) to create the formal
args based on the args of a given named interface. */ args based on the args of a given named interface.
When an actual argument list is provided, skip the absent arguments.
To be used together with gfc_se->ignore_optional. */
void void
gfc_copy_formal_args_intr (gfc_symbol *dest, gfc_intrinsic_sym *src) gfc_copy_formal_args_intr (gfc_symbol *dest, gfc_intrinsic_sym *src,
gfc_actual_arglist *actual)
{ {
gfc_formal_arglist *head = NULL; gfc_formal_arglist *head = NULL;
gfc_formal_arglist *tail = NULL; gfc_formal_arglist *tail = NULL;
gfc_formal_arglist *formal_arg = NULL; gfc_formal_arglist *formal_arg = NULL;
gfc_intrinsic_arg *curr_arg = NULL; gfc_intrinsic_arg *curr_arg = NULL;
gfc_formal_arglist *formal_prev = NULL; gfc_formal_arglist *formal_prev = NULL;
gfc_actual_arglist *act_arg = actual;
/* Save current namespace so we can change it for formal args. */ /* Save current namespace so we can change it for formal args. */
gfc_namespace *parent_ns = gfc_current_ns; gfc_namespace *parent_ns = gfc_current_ns;
@ -4062,6 +4067,17 @@ gfc_copy_formal_args_intr (gfc_symbol *dest, gfc_intrinsic_sym *src)
for (curr_arg = src->formal; curr_arg; curr_arg = curr_arg->next) for (curr_arg = src->formal; curr_arg; curr_arg = curr_arg->next)
{ {
/* Skip absent arguments. */
if (actual)
{
gcc_assert (act_arg != NULL);
if (act_arg->expr == NULL)
{
act_arg = act_arg->next;
continue;
}
act_arg = act_arg->next;
}
formal_arg = gfc_get_formal_arglist (); formal_arg = gfc_get_formal_arglist ();
gfc_get_symbol (curr_arg->name, gfc_current_ns, &(formal_arg->sym)); gfc_get_symbol (curr_arg->name, gfc_current_ns, &(formal_arg->sym));

View File

@ -2371,7 +2371,7 @@ gfc_conv_intrinsic_minmax_char (gfc_se * se, gfc_expr * expr, int op)
has the generic name. */ has the generic name. */
static gfc_symbol * static gfc_symbol *
gfc_get_symbol_for_expr (gfc_expr * expr) gfc_get_symbol_for_expr (gfc_expr * expr, bool ignore_optional)
{ {
gfc_symbol *sym; gfc_symbol *sym;
@ -2394,7 +2394,9 @@ gfc_get_symbol_for_expr (gfc_expr * expr)
sym->as->rank = expr->rank; sym->as->rank = expr->rank;
} }
gfc_copy_formal_args_intr (sym, expr->value.function.isym); gfc_copy_formal_args_intr (sym, expr->value.function.isym,
ignore_optional ? expr->value.function.actual
: NULL);
return sym; return sym;
} }
@ -2413,7 +2415,7 @@ gfc_conv_intrinsic_funcall (gfc_se * se, gfc_expr * expr)
else else
gcc_assert (expr->rank == 0); gcc_assert (expr->rank == 0);
sym = gfc_get_symbol_for_expr (expr); sym = gfc_get_symbol_for_expr (expr, se->ignore_optional);
/* Calls to libgfortran_matmul need to be appended special arguments, /* Calls to libgfortran_matmul need to be appended special arguments,
to be able to call the BLAS ?gemm functions if required and possible. */ to be able to call the BLAS ?gemm functions if required and possible. */
@ -4584,7 +4586,8 @@ conv_generic_with_optional_char_arg (gfc_se* se, gfc_expr* expr,
} }
/* Build the call itself. */ /* Build the call itself. */
sym = gfc_get_symbol_for_expr (expr); gcc_assert (!se->ignore_optional);
sym = gfc_get_symbol_for_expr (expr, false);
gfc_conv_procedure_call (se, sym, expr->value.function.actual, expr, gfc_conv_procedure_call (se, sym, expr->value.function.actual, expr,
append_args); append_args);
gfc_free_symbol (sym); gfc_free_symbol (sym);