1/* tfma -- test file for mpc_fma. 2 3Copyright (C) 2011, 2012, 2013 INRIA 4 5This file is part of GNU MPC. 6 7GNU MPC is free software; you can redistribute it and/or modify it under 8the terms of the GNU Lesser General Public License as published by the 9Free Software Foundation; either version 3 of the License, or (at your 10option) any later version. 11 12GNU MPC is distributed in the hope that it will be useful, but WITHOUT ANY 13WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for 15more details. 16 17You should have received a copy of the GNU Lesser General Public License 18along with this program. If not, see http://www.gnu.org/licenses/ . 19*/ 20 21#include "mpc-tests.h" 22 23static void 24cmpfma (mpc_srcptr a, mpc_srcptr b, mpc_srcptr c, mpc_rnd_t rnd) 25 /* computes a*b+c with the naive and fast functions using the rounding 26 mode rnd and compares the results and return values. 27 In our current test suite, all input precisions are the same, and we 28 use this precision also for the result. 29 */ 30{ 31 mpc_t z, t; 32 int inex_z, inex_t; 33 34 mpc_init2 (z, MPC_MAX_PREC (a)); 35 mpc_init2 (t, MPC_MAX_PREC (a)); 36 37 inex_z = mpc_fma_naive (z, a, b, c, rnd); 38 inex_t = mpc_fma (t, a, b, c, rnd); 39 40 if (mpc_cmp (z, t) != 0 || inex_z != inex_t) { 41 fprintf (stderr, "fma_naive and fma differ for rnd=(%s,%s)\n", 42 mpfr_print_rnd_mode(MPC_RND_RE(rnd)), 43 mpfr_print_rnd_mode(MPC_RND_IM(rnd))); 44 MPC_OUT (a); 45 MPC_OUT (b); 46 MPC_OUT (c); 47 MPC_OUT (z); 48 MPC_OUT (t); 49 if (inex_z != inex_t) { 50 fprintf (stderr, "inex_re (z): %s\n", MPC_INEX_STR (inex_z)); 51 fprintf (stderr, "inex_re (t): %s\n", MPC_INEX_STR (inex_t)); 52 } 53 exit (1); 54 } 55 56 mpc_clear (z); 57 mpc_clear (t); 58} 59 60 61static void 62check_random (void) 63{ 64 mpfr_prec_t prec; 65 int rnd_re, rnd_im; 66 mpc_t a, b, c; 67 68 mpc_init2 (a, 1000); 69 mpc_init2 (b, 1000); 70 mpc_init2 (c, 1000); 71 72 for (prec = 2; prec < 1000; prec = (mpfr_prec_t) (prec * 1.1 + 1)) { 73 mpc_set_prec (a, prec); 74 mpc_set_prec (b, prec); 75 mpc_set_prec (c, prec); 76 77 test_default_random (a, -1024, 1024, 128, 0); 78 test_default_random (b, -1024, 1024, 128, 0); 79 test_default_random (c, -1024, 1024, 128, 0); 80 81 for (rnd_re = 0; rnd_re < 4; rnd_re ++) 82 for (rnd_im = 0; rnd_im < 4; rnd_im ++) 83 cmpfma (a, b, c, MPC_RND (rnd_re, rnd_im)); 84 } 85 86 mpc_clear (a); 87 mpc_clear (b); 88 mpc_clear (c); 89} 90 91#define MPC_FUNCTION_CALL \ 92 P[0].mpc_inex = \ 93 mpc_fma (P[1].mpc, P[2].mpc, P[3].mpc, P[4].mpc, P[5].mpc_rnd) 94#define MPC_FUNCTION_CALL_REUSE_OP1 \ 95 P[0].mpc_inex = \ 96 mpc_fma (P[1].mpc, P[1].mpc, P[3].mpc, P[4].mpc, P[5].mpc_rnd) 97#define MPC_FUNCTION_CALL_REUSE_OP2 \ 98 P[0].mpc_inex = \ 99 mpc_fma (P[1].mpc, P[2].mpc, P[1].mpc, P[4].mpc, P[5].mpc_rnd) 100#define MPC_FUNCTION_CALL_REUSE_OP3 \ 101 P[0].mpc_inex = \ 102 mpc_fma (P[1].mpc, P[2].mpc, P[3].mpc, P[1].mpc, P[5].mpc_rnd) 103 104#include "data_check.tpl" 105#include "tgeneric.tpl" 106 107int 108main (void) 109{ 110 test_start (); 111 112 check_random (); /* Remove it? */ 113 114 data_check_template ("fma.dsc", "fma.dat"); 115 116 tgeneric_template ("fma.dsc", 2, 1024, 1, 256); 117 118 test_end (); 119 120 return 0; 121} 122