From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 16633 invoked by alias); 26 May 2016 18:00:23 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Received: (qmail 16567 invoked by uid 89); 26 May 2016 18:00:16 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=4.0 required=5.0 tests=AWL,BAYES_99,BAYES_999,KAM_ASCII_DIVIDERS,KAM_LAZY_DOMAIN_SECURITY,RP_MATCHES_RCVD autolearn=no version=3.3.2 spammy=nonexistent, Treat, affects, __builtin_ X-HELO: nikam.ms.mff.cuni.cz Received: from nikam.ms.mff.cuni.cz (HELO nikam.ms.mff.cuni.cz) (195.113.20.16) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES256-GCM-SHA384 encrypted) ESMTPS; Thu, 26 May 2016 17:59:55 +0000 Received: by nikam.ms.mff.cuni.cz (Postfix, from userid 16202) id CCB5C54582E; Thu, 26 May 2016 19:59:51 +0200 (CEST) Date: Fri, 27 May 2016 06:14:00 -0000 From: Jan Hubicka To: Uros Bizjak Cc: Joseph Myers , "gcc-patches@gcc.gnu.org" , Jan Hubicka Subject: Re: Add option for whether ceil etc. can raise "inexact", adjust x86 conditions Message-ID: <20160526175950.GA60285@kam.mff.cuni.cz> References: MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.21 (2010-09-15) X-SW-Source: 2016-05/txt/msg02138.txt.bz2 > > +ffp-int-builtin-inexact > > +Common Report Var(flag_fp_int_builtin_inexact) Optimization > > +Allow built-in functions ceil, floor, round, trunc to raise \"inexact\" exceptions. When adding new codegen option which affects the correctness, it is also necessary to update can_inline_edge_p and inline_call. (In general it would be great if we had fewer such flags and more stuff explicitly represented in IL. I am not sure how hard that would be here and if it is worth the effort.) Honza > > + > > ; Nonzero means don't put addresses of constant functions in registers. > > ; Used for compiling the Unix kernel, where strange substitutions are > > ; done on the assembly output. > > Index: gcc/config/i386/i386.md > > =================================================================== > > --- gcc/config/i386/i386.md (revision 236740) > > +++ gcc/config/i386/i386.md (working copy) > > @@ -15512,25 +15512,31 @@ > > [(set (match_operand:XF 0 "register_operand" "=f") > > (unspec:XF [(match_operand:XF 1 "register_operand" "0")] > > UNSPEC_FRNDINT))] > > - "TARGET_USE_FANCY_MATH_387 > > - && flag_unsafe_math_optimizations" > > + "TARGET_USE_FANCY_MATH_387" > > "frndint" > > [(set_attr "type" "fpspc") > > (set_attr "znver1_decode" "vector") > > (set_attr "mode" "XF")]) > > > > +(define_insn "rint2_frndint" > > + [(set (match_operand:MODEF 0 "register_operand" "=f") > > + (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "0")] > > + UNSPEC_FRNDINT))] > > + "TARGET_USE_FANCY_MATH_387" > > + "frndint" > > + [(set_attr "type" "fpspc") > > + (set_attr "znver1_decode" "vector") > > + (set_attr "mode" "")]) > > + > > (define_expand "rint2" > > [(use (match_operand:MODEF 0 "register_operand")) > > (use (match_operand:MODEF 1 "register_operand"))] > > "(TARGET_USE_FANCY_MATH_387 > > && (!(SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH) > > - || TARGET_MIX_SSE_I387) > > - && flag_unsafe_math_optimizations) > > - || (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH > > - && !flag_trapping_math)" > > + || TARGET_MIX_SSE_I387)) > > + || (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)" > > { > > - if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH > > - && !flag_trapping_math) > > + if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH) > > { > > if (TARGET_ROUND) > > emit_insn (gen_sse4_1_round2 > > @@ -15539,15 +15545,7 @@ > > ix86_expand_rint (operands[0], operands[1]); > > } > > else > > - { > > - rtx op0 = gen_reg_rtx (XFmode); > > - rtx op1 = gen_reg_rtx (XFmode); > > - > > - emit_insn (gen_extendxf2 (op1, operands[1])); > > - emit_insn (gen_rintxf2 (op0, op1)); > > - > > - emit_insn (gen_truncxf2_i387_noop (operands[0], op0)); > > - } > > + emit_insn (gen_rint2_frndint (operands[0], operands[1])); > > DONE; > > }) > > > > @@ -15770,13 +15768,13 @@ > > (UNSPEC_FIST_CEIL "CEIL")]) > > > > ;; Rounding mode control word calculation could clobber FLAGS_REG. > > -(define_insn_and_split "frndintxf2_" > > - [(set (match_operand:XF 0 "register_operand") > > - (unspec:XF [(match_operand:XF 1 "register_operand")] > > +(define_insn_and_split "frndint2_" > > + [(set (match_operand:X87MODEF 0 "register_operand") > > + (unspec:X87MODEF [(match_operand:X87MODEF 1 "register_operand")] > > FRNDINT_ROUNDING)) > > (clobber (reg:CC FLAGS_REG))] > > "TARGET_USE_FANCY_MATH_387 > > - && flag_unsafe_math_optimizations > > + && (flag_fp_int_builtin_inexact || !flag_trapping_math) > > && can_create_pseudo_p ()" > > "#" > > "&& 1" > > @@ -15787,26 +15785,26 @@ > > operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED); > > operands[3] = assign_386_stack_local (HImode, SLOT_CW_); > > > > - emit_insn (gen_frndintxf2__i387 (operands[0], operands[1], > > - operands[2], operands[3])); > > + emit_insn (gen_frndint2__i387 (operands[0], operands[1], > > + operands[2], operands[3])); > > DONE; > > } > > [(set_attr "type" "frndint") > > (set_attr "i387_cw" "") > > - (set_attr "mode" "XF")]) > > + (set_attr "mode" "")]) > > > > -(define_insn "frndintxf2__i387" > > - [(set (match_operand:XF 0 "register_operand" "=f") > > - (unspec:XF [(match_operand:XF 1 "register_operand" "0")] > > - FRNDINT_ROUNDING)) > > +(define_insn "frndint2__i387" > > + [(set (match_operand:X87MODEF 0 "register_operand" "=f") > > + (unspec:X87MODEF [(match_operand:X87MODEF 1 "register_operand" "0")] > > + FRNDINT_ROUNDING)) > > (use (match_operand:HI 2 "memory_operand" "m")) > > (use (match_operand:HI 3 "memory_operand" "m"))] > > "TARGET_USE_FANCY_MATH_387 > > - && flag_unsafe_math_optimizations" > > + && (flag_fp_int_builtin_inexact || !flag_trapping_math)" > > "fldcw\t%3\n\tfrndint\n\tfldcw\t%2" > > [(set_attr "type" "frndint") > > (set_attr "i387_cw" "") > > - (set_attr "mode" "XF")]) > > + (set_attr "mode" "")]) > > > > (define_expand "xf2" > > [(parallel [(set (match_operand:XF 0 "register_operand") > > @@ -15814,7 +15812,7 @@ > > FRNDINT_ROUNDING)) > > (clobber (reg:CC FLAGS_REG))])] > > "TARGET_USE_FANCY_MATH_387 > > - && flag_unsafe_math_optimizations") > > + && (flag_fp_int_builtin_inexact || !flag_trapping_math)") > > > > (define_expand "2" > > [(parallel [(set (match_operand:MODEF 0 "register_operand") > > @@ -15824,16 +15822,17 @@ > > "(TARGET_USE_FANCY_MATH_387 > > && (!(SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH) > > || TARGET_MIX_SSE_I387) > > - && flag_unsafe_math_optimizations) > > + && (flag_fp_int_builtin_inexact || !flag_trapping_math)) > > || (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH > > - && !flag_trapping_math)" > > + && (TARGET_ROUND || !flag_trapping_math || flag_fp_int_builtin_inexact))" > > { > > if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH > > - && !flag_trapping_math) > > + && (TARGET_ROUND || !flag_trapping_math || flag_fp_int_builtin_inexact)) > > { > > if (TARGET_ROUND) > > emit_insn (gen_sse4_1_round2 > > - (operands[0], operands[1], GEN_INT (ROUND_))); > > + (operands[0], operands[1], GEN_INT (ROUND_ > > + | ROUND_NO_EXC))); > > else if (TARGET_64BIT || (mode != DFmode)) > > { > > if (ROUND_ == ROUND_FLOOR) > > @@ -15858,16 +15857,7 @@ > > } > > } > > else > > - { > > - rtx op0, op1; > > - > > - op0 = gen_reg_rtx (XFmode); > > - op1 = gen_reg_rtx (XFmode); > > - emit_insn (gen_extendxf2 (op1, operands[1])); > > - emit_insn (gen_frndintxf2_ (op0, op1)); > > - > > - emit_insn (gen_truncxf2_i387_noop (operands[0], op0)); > > - } > > + emit_insn (gen_frndint2_ (operands[0], operands[1])); > > DONE; > > }) > > > > Index: gcc/doc/invoke.texi > > =================================================================== > > --- gcc/doc/invoke.texi (revision 236740) > > +++ gcc/doc/invoke.texi (working copy) > > @@ -370,9 +370,9 @@ Objective-C and Objective-C++ Dialects}. > > -flto-partition=@var{alg} -fmerge-all-constants @gol > > -fmerge-constants -fmodulo-sched -fmodulo-sched-allow-regmoves @gol > > -fmove-loop-invariants -fno-branch-count-reg @gol > > --fno-defer-pop -fno-function-cse -fno-guess-branch-probability @gol > > --fno-inline -fno-math-errno -fno-peephole -fno-peephole2 @gol > > --fno-sched-interblock -fno-sched-spec -fno-signed-zeros @gol > > +-fno-defer-pop -fno-fp-int-builtin-inexact -fno-function-cse @gol > > +-fno-guess-branch-probability -fno-inline -fno-math-errno -fno-peephole @gol > > +-fno-peephole2 -fno-sched-interblock -fno-sched-spec -fno-signed-zeros @gol > > -fno-toplevel-reorder -fno-trapping-math -fno-zero-initialized-in-bss @gol > > -fomit-frame-pointer -foptimize-sibling-calls @gol > > -fpartial-inlining -fpeel-loops -fpredictive-commoning @gol > > @@ -8531,6 +8531,24 @@ The default is @option{-fno-signaling-nans}. > > This option is experimental and does not currently guarantee to > > disable all GCC optimizations that affect signaling NaN behavior. > > > > +@item -fno-fp-int-builtin-inexact > > +@opindex fno-fp-int-builtin-inexact > > +Do not allow the built-in functions @code{ceil}, @code{floor}, > > +@code{round} and @code{trunc}, and their @code{float} and @code{long > > +double} variants, to generate code that raises the ``inexact'' > > +floating-point exception for noninteger arguments. ISO C99 and C11 > > +allow these functions to raise the ``inexact'' exception, but ISO/IEC > > +TS 18661-1:2014, the C bindings to IEEE 754-2008, does not allow these > > +functions to do so. > > + > > +The default is @option{-ffp-int-builtin-inexact}, allowing the > > +exception to be raised. This option does nothing unless > > +@option{-ftrapping-math} is in effect. > > + > > +Even if @option{-fno-fp-int-builtin-inexact} is used, if the functions > > +generate a call to a library function then the ``inexact'' exception > > +may be raised if the library implementation does not follow TS 18661. > > + > > @item -fsingle-precision-constant > > @opindex fsingle-precision-constant > > Treat floating-point constants as single precision instead of > > Index: gcc/testsuite/gcc.dg/torture/builtin-fp-int-inexact.c > > =================================================================== > > --- gcc/testsuite/gcc.dg/torture/builtin-fp-int-inexact.c (nonexistent) > > +++ gcc/testsuite/gcc.dg/torture/builtin-fp-int-inexact.c (working copy) > > @@ -0,0 +1,72 @@ > > +/* Test -fno-fp-int-builtin-inexact. */ > > +/* { dg-do run } */ > > +/* { dg-options "-fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target fenv_exceptions } */ > > + > > +#include > > + > > +/* Define functions locally to ensure that if the calls are not > > + expanded inline, failures do not occur because of libm raising > > + "inexact". */ > > + > > +#define LOCAL_FN(NAME, TYPE) \ > > + __attribute__ ((noinline, noclone)) TYPE \ > > + NAME (TYPE x) \ > > + { \ > > + return x; \ > > + } > > + > > +#define LOCAL_FNS(NAME) \ > > + LOCAL_FN (NAME, double) \ > > + LOCAL_FN (NAME ## f, float) \ > > + LOCAL_FN (NAME ## l, long double) > > + > > +LOCAL_FNS (ceil) > > +LOCAL_FNS (floor) > > +LOCAL_FNS (round) > > +LOCAL_FNS (trunc) > > + > > +extern void abort (void); > > +extern void exit (int); > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + if (fetestexcept (FE_INEXACT)) \ > > + abort (); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + TEST (__builtin_ ## FN ## l, long double); \ > > + } \ > > + while (0) > > + > > +static void > > +main_test (void) > > +{ > > + FN_TESTS (ceil); > > + FN_TESTS (floor); > > + FN_TESTS (round); > > + FN_TESTS (trunc); > > +} > > + > > +/* This file may be included by architecture-specific tests. */ > > + > > +#ifndef ARCH_MAIN > > + > > +int > > +main (void) > > +{ > > + main_test (); > > + exit (0); > > +} > > + > > +#endif > > Index: gcc/testsuite/gcc.target/i386/387-builtin-fp-int-inexact.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/387-builtin-fp-int-inexact.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/387-builtin-fp-int-inexact.c (working copy) > > @@ -0,0 +1,7 @@ > > +/* Test -fno-fp-int-builtin-inexact for 387. */ > > +/* { dg-do run } */ > > +/* { dg-options "-O2 -mfancy-math-387 -mfpmath=387 -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target fenv_exceptions } */ > > + > > +#include "../../gcc.dg/torture/builtin-fp-int-inexact.c" > > Index: gcc/testsuite/gcc.target/i386/387-rint-inline-1.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/387-rint-inline-1.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/387-rint-inline-1.c (working copy) > > @@ -0,0 +1,36 @@ > > +/* Test rint and related functions expanded inline for 387. All > > + should be expanded when spurious "inexact" allowed. */ > > +/* { dg-do compile } */ > > +/* { dg-options "-O2 -mfancy-math-387 -mfpmath=387 -ffp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + TEST (__builtin_ ## FN ## l, long double); \ > > + } \ > > + while (0) > > + > > +void > > +test (void) > > +{ > > + FN_TESTS (rint); > > + FN_TESTS (ceil); > > + FN_TESTS (floor); > > + FN_TESTS (trunc); > > +} > > + > > +/* { dg-final { scan-assembler-not "\[ \t\]rint" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]ceil" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]floor" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]trunc" } } */ > > Index: gcc/testsuite/gcc.target/i386/387-rint-inline-2.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/387-rint-inline-2.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/387-rint-inline-2.c (working copy) > > @@ -0,0 +1,30 @@ > > +/* Test rint and related functions expanded inline for 387. rint > > + should be expanded even when spurious "inexact" not allowed. */ > > +/* { dg-do compile } */ > > +/* { dg-options "-O2 -mfancy-math-387 -mfpmath=387 -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + TEST (__builtin_ ## FN ## l, long double); \ > > + } \ > > + while (0) > > + > > +void > > +test (void) > > +{ > > + FN_TESTS (rint); > > +} > > + > > +/* { dg-final { scan-assembler-not "\[ \t\]rint" } } */ > > Index: gcc/testsuite/gcc.target/i386/sse2-builtin-fp-int-inexact.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/sse2-builtin-fp-int-inexact.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/sse2-builtin-fp-int-inexact.c (working copy) > > @@ -0,0 +1,12 @@ > > +/* Test -fno-fp-int-builtin-inexact for SSE 2. */ > > +/* { dg-do run } */ > > +/* { dg-options "-O2 -msse2 -mfpmath=sse -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target fenv_exceptions } */ > > +/* { dg-require-effective-target sse2 } */ > > + > > +#include "sse2-check.h" > > + > > +#define main_test sse2_test > > +#define ARCH_MAIN > > +#include "../../gcc.dg/torture/builtin-fp-int-inexact.c" > > Index: gcc/testsuite/gcc.target/i386/sse2-rint-inline-1.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/sse2-rint-inline-1.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/sse2-rint-inline-1.c (working copy) > > @@ -0,0 +1,36 @@ > > +/* Test rint and related functions expanded inline for SSE2. All > > + should be expanded when spurious "inexact" allowed. */ > > +/* { dg-do compile } */ > > +/* { dg-options "-O2 -msse2 -mfpmath=sse -ffp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target sse2 } */ > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + } \ > > + while (0) > > + > > +void > > +test (void) > > +{ > > + FN_TESTS (rint); > > + FN_TESTS (ceil); > > + FN_TESTS (floor); > > + FN_TESTS (trunc); > > +} > > + > > +/* { dg-final { scan-assembler-not "\[ \t\]rint" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]ceil" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]floor" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]trunc" } } */ > > Index: gcc/testsuite/gcc.target/i386/sse2-rint-inline-2.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/sse2-rint-inline-2.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/sse2-rint-inline-2.c (working copy) > > @@ -0,0 +1,30 @@ > > +/* Test rint and related functions expanded inline for SSE2. rint > > + should be expanded even when spurious "inexact" not allowed. */ > > +/* { dg-do compile } */ > > +/* { dg-options "-O2 -msse2 -mfpmath=sse -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target sse2 } */ > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + } \ > > + while (0) > > + > > +void > > +test (void) > > +{ > > + FN_TESTS (rint); > > +} > > + > > +/* { dg-final { scan-assembler-not "\[ \t\]rint" } } */ > > Index: gcc/testsuite/gcc.target/i386/sse4_1-builtin-fp-int-inexact.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/sse4_1-builtin-fp-int-inexact.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/sse4_1-builtin-fp-int-inexact.c (working copy) > > @@ -0,0 +1,12 @@ > > +/* Test -fno-fp-int-builtin-inexact for SSE 4.1. */ > > +/* { dg-do run } */ > > +/* { dg-options "-O2 -msse4.1 -mfpmath=sse -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target fenv_exceptions } */ > > +/* { dg-require-effective-target sse4 } */ > > + > > +#include "sse4_1-check.h" > > + > > +#define main_test sse4_1_test > > +#define ARCH_MAIN > > +#include "../../gcc.dg/torture/builtin-fp-int-inexact.c" > > Index: gcc/testsuite/gcc.target/i386/sse4_1-rint-inline.c > > =================================================================== > > --- gcc/testsuite/gcc.target/i386/sse4_1-rint-inline.c (nonexistent) > > +++ gcc/testsuite/gcc.target/i386/sse4_1-rint-inline.c (working copy) > > @@ -0,0 +1,36 @@ > > +/* Test rint and related functions expanded inline for SSE4.1, even > > + when spurious "inexact" not allowed. */ > > +/* { dg-do compile } */ > > +/* { dg-options "-O2 -msse4.1 -mfpmath=sse -fno-fp-int-builtin-inexact" } */ > > +/* { dg-add-options c99_runtime } */ > > +/* { dg-require-effective-target sse4 } */ > > + > > +#define TEST(FN, TYPE) \ > > + do \ > > + { \ > > + volatile TYPE a = 1.5, b; \ > > + b = FN (a); \ > > + } \ > > + while (0) > > + > > +#define FN_TESTS(FN) \ > > + do \ > > + { \ > > + TEST (__builtin_ ## FN, double); \ > > + TEST (__builtin_ ## FN ## f, float); \ > > + } \ > > + while (0) > > + > > +void > > +test (void) > > +{ > > + FN_TESTS (rint); > > + FN_TESTS (ceil); > > + FN_TESTS (floor); > > + FN_TESTS (trunc); > > +} > > + > > +/* { dg-final { scan-assembler-not "\[ \t\]rint" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]ceil" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]floor" } } */ > > +/* { dg-final { scan-assembler-not "\[ \t\]trunc" } } */ > > > > -- > > Joseph S. Myers > > joseph@codesourcery.com