From patchwork Sun Aug 21 11:21:23 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Thomas Koenig X-Patchwork-Id: 110827 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) by ozlabs.org (Postfix) with SMTP id 5ACACB6F71 for ; Sun, 21 Aug 2011 21:21:47 +1000 (EST) Received: (qmail 6948 invoked by alias); 21 Aug 2011 11:21:43 -0000 Received: (qmail 6932 invoked by uid 22791); 21 Aug 2011 11:21:42 -0000 X-SWARE-Spam-Status: No, hits=-1.6 required=5.0 tests=AWL, BAYES_00, RCVD_IN_DNSWL_NONE, RP_MATCHES_RCVD, TW_PL X-Spam-Check-By: sourceware.org Received: from cc-smtpout2.netcologne.de (HELO cc-smtpout2.netcologne.de) (89.1.8.212) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Sun, 21 Aug 2011 11:21:27 +0000 Received: from cc-smtpin2.netcologne.de (cc-smtpin2.netcologne.de [89.1.8.202]) by cc-smtpout2.netcologne.de (Postfix) with ESMTP id 2CE4D12384; Sun, 21 Aug 2011 13:21:26 +0200 (CEST) Received: from [192.168.0.197] (xdsl-78-35-158-50.netcologne.de [78.35.158.50]) by cc-smtpin2.netcologne.de (Postfix) with ESMTPSA id D91B411E82; Sun, 21 Aug 2011 13:21:23 +0200 (CEST) Message-ID: <4E50EA33.3040400@netcologne.de> Date: Sun, 21 Aug 2011 13:21:23 +0200 From: Thomas Koenig User-Agent: Mozilla/5.0 (X11; U; Linux x86_64; de; rv:1.9.2.17) Gecko/20110414 SUSE/3.1.10 Thunderbird/3.1.10 MIME-Version: 1.0 To: Tobias Burnus CC: gcc patches , gfortran Subject: Re: [patch, fortran] PR 47659 - extend conversion warnings to assignments References: <4E47EB84.6080006@netcologne.de> <4E48360C.6080809@net-b.de> <4E495C2C.4010502@netcologne.de> <4E4C0000.9000500@net-b.de> In-Reply-To: <4E4C0000.9000500@net-b.de> Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Hello everybody, now that I have found a little time, here is an updated version of the patch, which incorporates Tobias' suggestions. Regression-tested. OK for trunk? Thomas 2011-08-21 Thomas Koenig PR fortran/47659 * expr.c (gfc_check_assign): Check for type conversions when the right-hand side is a constant REAL/COMPLEX contstant the left-hand side is also REAL/COMPLEX. Don't warn when a narrowing conversion for REAL does not change the value of the constant. 2011-08-21 Thomas Koenig PR fortran/47659 * gfortran.dg/warn_conversion_2.f90: Also warn about conversion of a constant resulting from simplification. * gfortran.dg/warn_conversion_3.f90: New test. ! { dg-do compile } ! { dg-options "-Wconversion -Wconversion-extra" } ! PR 47659 - warning about conversions on assignment ! Based on test cases by Thomas Henlich and Tobias Burnus. program main double precision d1, d2 complex(8), parameter :: z = cmplx (0.5, 0.5) ! { dg-warning "Conversion" } real :: r1, r2 r1 = 2.3d0 ! { dg-warning "Change of value in conversion" } r2 = 2.5d0 ! No warning because the value does not change d1 = .13 ! { dg-warning "Conversion" } d2 = .13d0 d1 = z ! { dg-warning "change of value in conversion" } end program main Index: fortran/expr.c =================================================================== --- fortran/expr.c (Revision 177746) +++ fortran/expr.c (Arbeitskopie) @@ -3190,6 +3190,53 @@ } } + /* Warn about type-changing conversions for REAL or COMPLEX constants. + If lvalue and rvalue are mixed REAL and complex, gfc_compare_types + will warn anyway, so there is no need to to so here. */ + + if (rvalue->expr_type == EXPR_CONSTANT && lvalue->ts.type == rvalue->ts.type + && (lvalue->ts.type == BT_REAL || lvalue->ts.type == BT_COMPLEX)) + { + if (lvalue->ts.kind < rvalue->ts.kind && gfc_option.gfc_warn_conversion) + { + /* As a special bonus, don't warn about REAL rvalues which are not + changed by the conversion if -Wconversion is specified. */ + if (rvalue->ts.type == BT_REAL && mpfr_number_p (rvalue->value.real)) + { + /* Calculate the difference between the constant and the rounded + value and check it against zero. */ + mpfr_t rv, diff; + gfc_set_model_kind (lvalue->ts.kind); + mpfr_init (rv); + gfc_set_model_kind (rvalue->ts.kind); + mpfr_init (diff); + + mpfr_set (rv, rvalue->value.real, GFC_RND_MODE); + mpfr_sub (diff, rv, rvalue->value.real, GFC_RND_MODE); + + if (!mpfr_zero_p (diff)) + gfc_warning ("Change of value in conversion from " + " %s to %s at %L", gfc_typename (&rvalue->ts), + gfc_typename (&lvalue->ts), &rvalue->where); + + mpfr_clear (rv); + mpfr_clear (diff); + } + else + gfc_warning ("Possible change of value in conversion from %s " + "to %s at %L",gfc_typename (&rvalue->ts), + gfc_typename (&lvalue->ts), &rvalue->where); + + } + else if (gfc_option.warn_conversion_extra + && lvalue->ts.kind > rvalue->ts.kind) + { + gfc_warning ("Conversion from %s to %s at %L", + gfc_typename (&rvalue->ts), + gfc_typename (&lvalue->ts), &rvalue->where); + } + } + if (gfc_compare_types (&lvalue->ts, &rvalue->ts)) return SUCCESS; Index: testsuite/gfortran.dg/warn_conversion_2.f90 =================================================================== --- testsuite/gfortran.dg/warn_conversion_2.f90 (Revision 177746) +++ testsuite/gfortran.dg/warn_conversion_2.f90 (Arbeitskopie) @@ -7,5 +7,5 @@ x = 2.0 sqrt2 = sqrt(x) ! { dg-warning "Conversion" } - sqrt2 = sqrt(2.0) ! no warning; simplified to a constant and range checked + sqrt2 = sqrt(2.0) ! { dg-warning "Conversion" } end