/* Build up a list of intrinsic subroutines and functions for the
name-resolution stage.
- Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
+ Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008,
+ 2009, 2010
Free Software Foundation, Inc.
Contributed by Andy Vaught & Katherine Holcomb
/* Namespace to hold the resolved symbols for intrinsic subroutines. */
static gfc_namespace *gfc_intrinsic_namespace;
-int gfc_init_expr = 0;
+bool gfc_init_expr_flag = false;
/* Pointers to an intrinsic function and its argument names that are being
checked. */
/* See if this intrinsic is allowed in the current standard. */
if (gfc_check_intrinsic_standard (isym, &symstd, false, loc) == FAILURE)
{
- if (sym->attr.proc == PROC_UNKNOWN)
- {
- if (gfc_option.warn_intrinsics_std)
- gfc_warning_now ("The intrinsic '%s' at %L is not included in the"
- " selected standard but %s and '%s' will be"
- " treated as if declared EXTERNAL. Use an"
- " appropriate -std=* option or define"
- " -fall-intrinsics to allow this intrinsic.",
- sym->name, &loc, symstd, sym->name);
- gfc_add_external (&sym->attr, &loc);
- }
+ if (sym->attr.proc == PROC_UNKNOWN
+ && gfc_option.warn_intrinsics_std)
+ gfc_warning_now ("The intrinsic '%s' at %L is not included in the"
+ " selected standard but %s and '%s' will be"
+ " treated as if declared EXTERNAL. Use an"
+ " appropriate -std=* option or define"
+ " -fall-intrinsics to allow this intrinsic.",
+ sym->name, &loc, symstd, sym->name);
return false;
}
while (g->name != NULL)
{
- gcc_assert (g->id == id);
-
g->next = g + 1;
g->specific = 1;
g++;
*y = "y", *sz = "size", *sta = "string_a", *stb = "string_b",
*z = "z", *ln = "len", *ut = "unit", *han = "handler",
*num = "number", *tm = "time", *nm = "name", *md = "mode",
- *vl = "values", *p1 = "path1", *p2 = "path2", *com = "command";
+ *vl = "values", *p1 = "path1", *p2 = "path2", *com = "command",
+ *ca = "coarray", *sub = "sub";
int di, dr, dd, dl, dc, dz, ii;
make_generic ("achar", GFC_ISYM_ACHAR, GFC_STD_F95);
add_sym_1 ("acos", GFC_ISYM_ACOS, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_acos, gfc_resolve_acos,
+ gfc_check_fn_rc2008, gfc_simplify_acos, gfc_resolve_acos,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dacos", GFC_ISYM_ACOS, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
make_generic ("acos", GFC_ISYM_ACOS, GFC_STD_F77);
add_sym_1 ("acosh", GFC_ISYM_ACOSH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr,
- GFC_STD_F2008, gfc_check_fn_r, gfc_simplify_acosh,
+ GFC_STD_F2008, gfc_check_fn_rc2008, gfc_simplify_acosh,
gfc_resolve_acosh, x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dacosh", GFC_ISYM_ACOSH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_GNU,
make_generic ("aint", GFC_ISYM_AINT, GFC_STD_F77);
add_sym_2 ("all", GFC_ISYM_ALL, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_LOGICAL, dl, GFC_STD_F95,
- gfc_check_all_any, NULL, gfc_resolve_all,
+ gfc_check_all_any, gfc_simplify_all, gfc_resolve_all,
msk, BT_LOGICAL, dl, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL);
make_generic ("all", GFC_ISYM_ALL, GFC_STD_F95);
make_generic ("anint", GFC_ISYM_ANINT, GFC_STD_F77);
add_sym_2 ("any", GFC_ISYM_ANY, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_LOGICAL, dl, GFC_STD_F95,
- gfc_check_all_any, NULL, gfc_resolve_any,
+ gfc_check_all_any, gfc_simplify_any, gfc_resolve_any,
msk, BT_LOGICAL, dl, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL);
make_generic ("any", GFC_ISYM_ANY, GFC_STD_F95);
add_sym_1 ("asin", GFC_ISYM_ASIN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_asin, gfc_resolve_asin,
+ gfc_check_fn_rc2008, gfc_simplify_asin, gfc_resolve_asin,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dasin", GFC_ISYM_ASIN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
make_generic ("asin", GFC_ISYM_ASIN, GFC_STD_F77);
add_sym_1 ("asinh", GFC_ISYM_ASINH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr,
- GFC_STD_F2008, gfc_check_fn_r, gfc_simplify_asinh,
+ GFC_STD_F2008, gfc_check_fn_rc2008, gfc_simplify_asinh,
gfc_resolve_asinh, x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dasinh", GFC_ISYM_ASINH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_GNU,
make_generic ("associated", GFC_ISYM_ASSOCIATED, GFC_STD_F95);
add_sym_1 ("atan", GFC_ISYM_ATAN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_atan, gfc_resolve_atan,
+ gfc_check_fn_rc2008, gfc_simplify_atan, gfc_resolve_atan,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("datan", GFC_ISYM_ATAN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
gfc_check_fn_d, gfc_simplify_atan, gfc_resolve_atan,
x, BT_REAL, dd, REQUIRED);
+ /* Two-argument version of atan, equivalent to atan2. */
+ add_sym_2 ("atan", GFC_ISYM_ATAN2, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F2008,
+ gfc_check_atan_2, gfc_simplify_atan2, gfc_resolve_atan2,
+ y, BT_REAL, dr, REQUIRED, x, BT_REAL, dr, REQUIRED);
+
make_generic ("atan", GFC_ISYM_ATAN, GFC_STD_F77);
add_sym_1 ("atanh", GFC_ISYM_ATANH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr,
- GFC_STD_F2008, gfc_check_fn_r, gfc_simplify_atanh,
+ GFC_STD_F2008, gfc_check_fn_rc2008, gfc_simplify_atanh,
gfc_resolve_atanh, x, BT_REAL, dr, REQUIRED);
add_sym_1 ("datanh", GFC_ISYM_ATANH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_GNU,
make_generic ("cos", GFC_ISYM_COS, GFC_STD_F77);
add_sym_1 ("cosh", GFC_ISYM_COSH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_cosh, gfc_resolve_cosh,
+ gfc_check_fn_rc2008, gfc_simplify_cosh, gfc_resolve_cosh,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dcosh", GFC_ISYM_COSH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
add_sym_3 ("count", GFC_ISYM_COUNT, CLASS_TRANSFORMATIONAL, ACTUAL_NO,
BT_INTEGER, di, GFC_STD_F95,
- gfc_check_count, NULL, gfc_resolve_count,
+ gfc_check_count, gfc_simplify_count, gfc_resolve_count,
msk, BT_LOGICAL, dl, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL,
kind, BT_INTEGER, di, OPTIONAL);
make_generic ("exponent", GFC_ISYM_EXPONENT, GFC_STD_F95);
+ add_sym_2 ("extends_type_of", GFC_ISYM_EXTENDS_TYPE_OF, CLASS_INQUIRY,
+ ACTUAL_NO, BT_LOGICAL, dl, GFC_STD_F2003,
+ gfc_check_same_type_as, NULL, gfc_resolve_extends_type_of,
+ a, BT_UNKNOWN, 0, REQUIRED,
+ mo, BT_UNKNOWN, 0, REQUIRED);
+
add_sym_0 ("fdate", GFC_ISYM_FDATE, NO_CLASS, ACTUAL_NO, BT_CHARACTER, dc, GFC_STD_GNU,
NULL, NULL, gfc_resolve_fdate);
make_generic ("fput", GFC_ISYM_FPUT, GFC_STD_GNU);
- add_sym_1 ("gamma", GFC_ISYM_GAMMA, CLASS_ELEMENTAL, ACTUAL_NO, BT_REAL, dr,
+ add_sym_1 ("gamma", GFC_ISYM_TGAMMA, CLASS_ELEMENTAL, ACTUAL_NO, BT_REAL, dr,
GFC_STD_F2008, gfc_check_fn_r, gfc_simplify_gamma,
gfc_resolve_gamma, x, BT_REAL, dr, REQUIRED);
- add_sym_1 ("dgamma", GFC_ISYM_GAMMA, CLASS_ELEMENTAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_GNU,
+ add_sym_1 ("dgamma", GFC_ISYM_TGAMMA, CLASS_ELEMENTAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_GNU,
gfc_check_fn_d, gfc_simplify_gamma, gfc_resolve_gamma,
x, BT_REAL, dr, REQUIRED);
- make_generic ("gamma", GFC_ISYM_GAMMA, GFC_STD_F2008);
+ make_generic ("gamma", GFC_ISYM_TGAMMA, GFC_STD_F2008);
/* Unix IDs (g77 compatibility) */
add_sym_1 ("getcwd", GFC_ISYM_GETCWD, NO_CLASS, ACTUAL_NO, BT_INTEGER, di, GFC_STD_GNU,
make_generic ("ierrno", GFC_ISYM_IERRNO, GFC_STD_GNU);
+ add_sym_2 ("image_index", GFC_ISYM_IMAGE_INDEX, CLASS_INQUIRY, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F2008,
+ gfc_check_image_index, gfc_simplify_image_index, gfc_resolve_image_index,
+ ca, BT_REAL, dr, REQUIRED, sub, BT_INTEGER, ii, REQUIRED);
+
/* The resolution function for INDEX is called gfc_resolve_index_func
because the name gfc_resolve_index is already used in resolve.c. */
add_sym_4 ("index", GFC_ISYM_INDEX, CLASS_ELEMENTAL, ACTUAL_YES,
add_sym_1 ("is_iostat_end", GFC_ISYM_IS_IOSTAT_END,
CLASS_ELEMENTAL, ACTUAL_NO, BT_LOGICAL, dl, GFC_STD_F2003,
- gfc_check_i, NULL, NULL, i, BT_INTEGER, 0, REQUIRED);
+ gfc_check_i, gfc_simplify_is_iostat_end, NULL,
+ i, BT_INTEGER, 0, REQUIRED);
make_generic ("is_iostat_end", GFC_ISYM_IS_IOSTAT_END, GFC_STD_F2003);
add_sym_1 ("is_iostat_eor", GFC_ISYM_IS_IOSTAT_EOR,
CLASS_ELEMENTAL, ACTUAL_NO, BT_LOGICAL, dl, GFC_STD_F2003,
- gfc_check_i, NULL, NULL, i, BT_INTEGER, 0, REQUIRED);
+ gfc_check_i, gfc_simplify_is_iostat_eor, NULL,
+ i, BT_INTEGER, 0, REQUIRED);
make_generic ("is_iostat_eor", GFC_ISYM_IS_IOSTAT_EOR, GFC_STD_F2003);
- add_sym_1 ("isnan", GFC_ISYM_ISNAN, CLASS_ELEMENTAL, ACTUAL_NO, BT_LOGICAL,
- dl, GFC_STD_GNU, gfc_check_isnan, NULL, NULL,
+ add_sym_1 ("isnan", GFC_ISYM_ISNAN, CLASS_ELEMENTAL, ACTUAL_NO,
+ BT_LOGICAL, dl, GFC_STD_GNU,
+ gfc_check_isnan, gfc_simplify_isnan, NULL,
x, BT_REAL, 0, REQUIRED);
make_generic ("isnan", GFC_ISYM_ISNAN, GFC_STD_GNU);
make_generic ("lbound", GFC_ISYM_LBOUND, GFC_STD_F95);
+ add_sym_3 ("lcobound", GFC_ISYM_LCOBOUND, CLASS_INQUIRY, ACTUAL_NO,
+ BT_INTEGER, di, GFC_STD_F2008,
+ gfc_check_lcobound, gfc_simplify_lcobound, gfc_resolve_lcobound,
+ ca, BT_REAL, dr, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL,
+ kind, BT_INTEGER, di, OPTIONAL);
+
+ make_generic ("lcobound", GFC_ISYM_LCOBOUND, GFC_STD_F2008);
+
add_sym_1 ("leadz", GFC_ISYM_LEADZ, CLASS_ELEMENTAL, ACTUAL_NO,
BT_INTEGER, di, GFC_STD_F2008,
gfc_check_i, gfc_simplify_leadz, NULL,
make_generic ("null", GFC_ISYM_NULL, GFC_STD_F95);
+ add_sym_0 ("num_images", GFC_ISYM_NUMIMAGES, CLASS_INQUIRY, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F2008,
+ NULL, gfc_simplify_num_images, NULL);
+
add_sym_3 ("pack", GFC_ISYM_PACK, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
gfc_check_pack, gfc_simplify_pack, gfc_resolve_pack,
ar, BT_REAL, dr, REQUIRED, msk, BT_LOGICAL, dl, REQUIRED,
make_generic ("present", GFC_ISYM_PRESENT, GFC_STD_F95);
add_sym_3red ("product", GFC_ISYM_PRODUCT, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
- gfc_check_product_sum, NULL, gfc_resolve_product,
+ gfc_check_product_sum, gfc_simplify_product, gfc_resolve_product,
ar, BT_REAL, dr, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL,
msk, BT_LOGICAL, dl, OPTIONAL);
make_generic ("rrspacing", GFC_ISYM_RRSPACING, GFC_STD_F95);
+ add_sym_2 ("same_type_as", GFC_ISYM_SAME_TYPE_AS, CLASS_INQUIRY, ACTUAL_NO,
+ BT_LOGICAL, dl, GFC_STD_F2003,
+ gfc_check_same_type_as, NULL, NULL,
+ a, BT_UNKNOWN, 0, REQUIRED,
+ b, BT_UNKNOWN, 0, REQUIRED);
+
add_sym_2 ("scale", GFC_ISYM_SCALE, CLASS_ELEMENTAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
gfc_check_scale, gfc_simplify_scale, gfc_resolve_scale,
x, BT_REAL, dr, REQUIRED, i, BT_INTEGER, di, REQUIRED);
make_generic ("sin", GFC_ISYM_SIN, GFC_STD_F77);
add_sym_1 ("sinh", GFC_ISYM_SINH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_sinh, gfc_resolve_sinh,
+ gfc_check_fn_rc2008, gfc_simplify_sinh, gfc_resolve_sinh,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dsinh", GFC_ISYM_SINH,CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
make_generic ("spacing", GFC_ISYM_SPACING, GFC_STD_F95);
add_sym_3 ("spread", GFC_ISYM_SPREAD, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
- gfc_check_spread, NULL, gfc_resolve_spread,
+ gfc_check_spread, gfc_simplify_spread, gfc_resolve_spread,
src, BT_REAL, dr, REQUIRED, dm, BT_INTEGER, ii, REQUIRED,
ncopies, BT_INTEGER, di, REQUIRED);
make_generic ("stat", GFC_ISYM_STAT, GFC_STD_GNU);
add_sym_3red ("sum", GFC_ISYM_SUM, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
- gfc_check_product_sum, NULL, gfc_resolve_sum,
+ gfc_check_product_sum, gfc_simplify_sum, gfc_resolve_sum,
ar, BT_REAL, dr, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL,
msk, BT_LOGICAL, dl, OPTIONAL);
make_generic ("system", GFC_ISYM_SYSTEM, GFC_STD_GNU);
add_sym_1 ("tan", GFC_ISYM_TAN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_tan, gfc_resolve_tan,
+ gfc_check_fn_rc2008, gfc_simplify_tan, gfc_resolve_tan,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dtan", GFC_ISYM_TAN, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
make_generic ("tan", GFC_ISYM_TAN, GFC_STD_F77);
add_sym_1 ("tanh", GFC_ISYM_TANH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dr, GFC_STD_F77,
- gfc_check_fn_r, gfc_simplify_tanh, gfc_resolve_tanh,
+ gfc_check_fn_rc2008, gfc_simplify_tanh, gfc_resolve_tanh,
x, BT_REAL, dr, REQUIRED);
add_sym_1 ("dtanh", GFC_ISYM_TANH, CLASS_ELEMENTAL, ACTUAL_YES, BT_REAL, dd, GFC_STD_F77,
make_generic ("tanh", GFC_ISYM_TANH, GFC_STD_F77);
+ add_sym_2 ("this_image", GFC_ISYM_THIS_IMAGE, CLASS_INQUIRY, ACTUAL_NO, BT_INTEGER, di, GFC_STD_F2008,
+ gfc_check_this_image, gfc_simplify_this_image, gfc_resolve_this_image,
+ ca, BT_REAL, dr, OPTIONAL, dm, BT_INTEGER, ii, OPTIONAL);
+
add_sym_0 ("time", GFC_ISYM_TIME, NO_CLASS, ACTUAL_NO, BT_INTEGER, di, GFC_STD_GNU,
NULL, NULL, gfc_resolve_time);
make_generic ("ubound", GFC_ISYM_UBOUND, GFC_STD_F95);
+ add_sym_3 ("ucobound", GFC_ISYM_UCOBOUND, CLASS_INQUIRY, ACTUAL_NO,
+ BT_INTEGER, di, GFC_STD_F2008,
+ gfc_check_ucobound, gfc_simplify_ucobound, gfc_resolve_ucobound,
+ ca, BT_REAL, dr, REQUIRED, dm, BT_INTEGER, ii, OPTIONAL,
+ kind, BT_INTEGER, di, OPTIONAL);
+
+ make_generic ("ucobound", GFC_ISYM_UCOBOUND, GFC_STD_F2008);
+
/* g77 compatibility for UMASK. */
add_sym_1 ("umask", GFC_ISYM_UMASK, NO_CLASS, ACTUAL_NO, BT_INTEGER, di,
GFC_STD_GNU, gfc_check_umask, NULL, gfc_resolve_umask,
make_generic ("unlink", GFC_ISYM_UNLINK, GFC_STD_GNU);
add_sym_3 ("unpack", GFC_ISYM_UNPACK, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95,
- gfc_check_unpack, NULL, gfc_resolve_unpack,
+ gfc_check_unpack, gfc_simplify_unpack, gfc_resolve_unpack,
v, BT_REAL, dr, REQUIRED, msk, BT_LOGICAL, dl, REQUIRED,
f, BT_REAL, dr, REQUIRED);
if (f->actual != NULL)
{
- gfc_error ("Argument '%s' is appears twice in call to '%s' at %L",
+ gfc_error ("Argument '%s' appears twice in call to '%s' at %L",
f->name, name, where);
return FAILURE;
}
first_expr = arg->expr;
for ( ; arg && arg->expr; arg = arg->next, n++)
- {
- char buffer[80];
- snprintf (buffer, 80, "arguments '%s' and '%s' for intrinsic '%s'",
- gfc_current_intrinsic_arg[0], gfc_current_intrinsic_arg[n],
- gfc_current_intrinsic);
- if (gfc_check_conformance (buffer, first_expr, arg->expr) == FAILURE)
- return FAILURE;
- }
+ if (gfc_check_conformance (first_expr, arg->expr,
+ "arguments '%s' and '%s' for "
+ "intrinsic '%s'",
+ gfc_current_intrinsic_arg[0],
+ gfc_current_intrinsic_arg[n],
+ gfc_current_intrinsic) == FAILURE)
+ return FAILURE;
}
if (t == FAILURE)
if ((isym->id == GFC_ISYM_REAL || isym->id == GFC_ISYM_DBLE
|| isym->id == GFC_ISYM_CMPLX)
- && gfc_init_expr
+ && gfc_init_expr_flag
&& gfc_notify_std (GFC_STD_F2003, "Fortran 2003: Function '%s' "
"as initialization expression at %L", name,
&expr->where) == FAILURE)
(4) A reference to an elemental standard intrinsic function,
where each argument is an initialization expression */
- if (gfc_init_expr && isym->elemental && flag
+ if (gfc_init_expr_flag && isym->elemental && flag
&& gfc_notify_std (GFC_STD_F2003, "Fortran 2003: Elemental function "
"as initialization expression with non-integer/non-"
"character arguments at %L", &expr->where) == FAILURE)
gfc_warning_now ("Extension: Conversion from %s to %s at %L",
gfc_typename (&from_ts), gfc_typename (ts), &expr->where);
else if (wflag && gfc_option.warn_conversion)
- gfc_warning_now ("Conversion from %s to %s at %L",
- gfc_typename (&from_ts), gfc_typename (ts), &expr->where);
+ {
+ /* If the types are the same (but not LOGICAL), and if from-kind
+ is larger than to-kind, this may indicate a loss of precision.
+ The same holds for conversions from REAL to COMPLEX. */
+ if (((from_ts.type == ts->type && from_ts.type != BT_LOGICAL)
+ && from_ts.kind > ts->kind)
+ || ((from_ts.type == BT_REAL && ts->type == BT_COMPLEX)
+ && from_ts.kind > ts->kind))
+ gfc_warning_now ("Possible loss of precision in conversion "
+ "from %s to %s at %L", gfc_typename (&from_ts),
+ gfc_typename (ts), &expr->where);
+
+ /* If INTEGER is converted to REAL/COMPLEX, this is generally ok if
+ the kind of the INTEGER value is less or equal to the kind of the
+ REAL/COMPLEX one. Otherwise the value may not fit.
+ Assignment of an overly large integer constant also generates
+ an overflow error with range checking. */
+ else if (from_ts.type == BT_INTEGER
+ && (ts->type == BT_REAL || ts->type == BT_COMPLEX)
+ && from_ts.kind > ts->kind)
+ gfc_warning_now ("Possible loss of digits in conversion "
+ "from %s to %s at %L", gfc_typename (&from_ts),
+ gfc_typename (ts), &expr->where);
+
+ /* If REAL/COMPLEX is converted to INTEGER, or COMPLEX is converted
+ to REAL we almost certainly have a loss of digits, regardless of
+ the respective kinds. */
+ else if (((from_ts.type == BT_REAL || from_ts.type == BT_COMPLEX)
+ && ts->type == BT_INTEGER)
+ || (from_ts.type == BT_COMPLEX && ts->type == BT_REAL))
+ gfc_warning_now ("Likely loss of digits in conversion from"
+ "%s to %s at %L", gfc_typename (&from_ts),
+ gfc_typename (ts), &expr->where);
+ }
/* Insert a pre-resolved function call to the right function. */
old_where = expr->where;
new_expr->shape = gfc_copy_shape (shape, rank);
gfc_get_ha_sym_tree (sym->name, &new_expr->symtree);
+ new_expr->symtree->n.sym->result = new_expr->symtree->n.sym;
new_expr->symtree->n.sym->ts = *ts;
new_expr->symtree->n.sym->attr.flavor = FL_PROCEDURE;
new_expr->symtree->n.sym->attr.function = 1;
gfc_convert_chartype (gfc_expr *expr, gfc_typespec *ts)
{
gfc_intrinsic_sym *sym;
- gfc_typespec from_ts;
locus old_where;
gfc_expr *new_expr;
int rank;
mpz_t *shape;
gcc_assert (expr->ts.type == BT_CHARACTER && ts->type == BT_CHARACTER);
- from_ts = expr->ts; /* expr->ts gets clobbered */
sym = find_char_conv (&expr->ts, ts);
gcc_assert (sym);