From: dfranke Date: Mon, 10 May 2010 17:10:53 +0000 (+0000) Subject: gcc/fortran/: X-Git-Url: http://git.sourceforge.jp/view?a=commitdiff_plain;ds=sidebyside;h=d7dbc78793abdbdb03100fda50c3881e13cae023;p=pf3gnuchains%2Fgcc-fork.git gcc/fortran/: 2010-05-10 Daniel Franke PR fortran/27866 PR fortran/35003 PR fortran/42809 * intrinsic.c (gfc_convert_type_warn): Be more discriminative about conversion warnings. gcc/testsuite/: 2010-05-08 Daniel Franke PR fortran/27866 PR fortran/35003 PR fortran/42809 * gfortran.dg/array_constructor_type_17.f03: Updated match string. * gfortran.dg/warn_conversion.f90: New. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@159238 138bc75d-0d04-0410-961f-82ee72b054a4 --- diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index d168a3b44aa..af70b8c67a6 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,11 @@ +2010-05-10 Daniel Franke + + PR fortran/27866 + PR fortran/35003 + PR fortran/42809 + * intrinsic.c (gfc_convert_type_warn): Be more dicsriminative + about conversion warnings. + 2010-05-10 Janus Weil PR fortran/44044 diff --git a/gcc/fortran/intrinsic.c b/gcc/fortran/intrinsic.c index e8041eb9b9a..07867541be0 100644 --- a/gcc/fortran/intrinsic.c +++ b/gcc/fortran/intrinsic.c @@ -4016,8 +4016,40 @@ gfc_convert_type_warn (gfc_expr *expr, gfc_typespec *ts, int eflag, int wflag) 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; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index de216a3876f..f54d9c4a898 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,11 @@ +2010-05-08 Daniel Franke + + PR fortran/27866 + PR fortran/35003 + PR fortran/42809 + * gfortran.dg/array_constructor_type_17.f03: Updated match string. + * gfortran.dg/warn_conversion.f90: New. + 2010-05-10 Michael Matz * gcc.dg/vect/fast-math-vect-reduc-8.c: New test. diff --git a/gcc/testsuite/gfortran.dg/array_constructor_type_17.f03 b/gcc/testsuite/gfortran.dg/array_constructor_type_17.f03 index 365d43e3f75..f8f15f9eba1 100644 --- a/gcc/testsuite/gfortran.dg/array_constructor_type_17.f03 +++ b/gcc/testsuite/gfortran.dg/array_constructor_type_17.f03 @@ -8,5 +8,5 @@ PROGRAM test IMPLICIT NONE INTEGER(KIND=4) :: arr(1) - arr = (/ INTEGER(KIND=4) :: HUGE(0_8) /) ! { dg-warning "Conversion from" } + arr = (/ INTEGER(KIND=4) :: HUGE(0_8) /) ! { dg-warning "conversion from" } END PROGRAM test diff --git a/gcc/testsuite/gfortran.dg/warn_conversion.f90 b/gcc/testsuite/gfortran.dg/warn_conversion.f90 new file mode 100644 index 00000000000..f658b655cae --- /dev/null +++ b/gcc/testsuite/gfortran.dg/warn_conversion.f90 @@ -0,0 +1,62 @@ +! { dg-do "compile" } +! { dg-options "-Wconversion" } + +! +! PR fortran/27866 -improve -Wconversion +! +SUBROUTINE pr27866 + double precision :: d + real :: r + d = 4d99 + r = d ! { dg-warning "conversion" } +END SUBROUTINE + +SUBROUTINE pr27866c4 + real(kind=4) :: a + real(kind=8) :: b + integer(kind=1) :: i1 + integer(kind=4) :: i4 + i4 = 2.3 ! { dg-warning "conversion" } + i1 = 500 ! { dg-error "overflow" } + ! { dg-warning "conversion" "" { target *-*-* } 20 } + a = 2**26-1 ! assignment INTEGER(4) to REAL(4) - no warning + b = 1d999 ! { dg-error "overflow" } + + a = i4 ! assignment INTEGER(4) to REAL(4) - no warning + b = i4 ! assignment INTEGER(4) to REAL(8) - no warning + i1 = i4 ! { dg-warning "conversion" } + a = b ! { dg-warning "conversion" } +END SUBROUTINE + + +! +! PR fortran/35003 - spurious warning with -Wconversion +! Contributed by Brian Barnes +! +SUBROUTINE pr35003 + IMPLICIT NONE + integer(8) :: i, n + n = 1_8 + + do i = 1_8,n + enddo +END SUBROUTINE + + +! +! PR fortran/42809 - Too much noise with -Wconversion +! Contributed by Harald Anlauf +! +SUBROUTINE pr42809 + implicit none + integer, parameter :: sp = kind (1.0) + integer, parameter :: dp = kind (1.d0) + real(sp) :: s + real(dp) :: d + complex(dp) :: z + + s = 0 ! assignment INTEGER(4) to REAL(4) - no warning + d = s ! assignment REAL((8)) to REAL(4) - no warning + z = (0, 1) ! conversion INTEGER(4) to REAL(4), + ! assignment COMPLEX(4) to COMPLEX(8) - no warning +END SUBROUTINE