1 /* 2 * wrappers.h - wrappers to modify output of MPFR/MPC test functions 3 * 4 * Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5 * See https://llvm.org/LICENSE.txt for license information. 6 * SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7 */ 8 9 typedef struct { 10 /* Structure type should be considered opaque outside wrappers.c, 11 * though we have to define it here so its size is known. */ 12 int nops; 13 int nresults; 14 mpfr_srcptr mpfr_ops[2]; 15 mpfr_ptr mpfr_result; 16 mpc_srcptr mpc_ops[2]; 17 mpc_ptr mpc_result; 18 const uint32 *ieee_ops[2]; 19 uint32 *ieee_result; 20 int size_ops[2]; 21 int size_result; 22 int need_regen; 23 } wrapperctx; 24 25 typedef void (*wrapperfunc)(wrapperctx *ctx); 26 #define MAXWRAPPERS 3 27 28 /* 29 * Functions for the test harness to call. 30 * 31 * When the test harness executes a test function, it should 32 * initialise a wrapperctx with wrapper_init, then provide all the 33 * operands and results in both mpfr/mpc and IEEE (+ extrabits) 34 * formats via wrapper_op_* and wrapper_result_*. Then it should run 35 * the function's wrappers using wrapper_run(), and if that returns 36 * true then the primary result has been rewritten in mpfr/mpc format 37 * and it should therefore retranslate into IEEE. 38 * 39 * 'size' in all prototypes below represents an FP type by giving the 40 * number of 32-bit words it requires, so 1=float and 2=double. Input 41 * operands will be that many words (or that many for both their real 42 * and imag parts); outputs will have one extra word for 'extrabits'. 43 * 44 * This system only applies at all to reference functions using 45 * mpfr/mpc. The seminumerical functions we implement in pure IEEE 46 * form are expected to handle all their own special cases correctly. 47 */ 48 49 void wrapper_init(wrapperctx *ctx); 50 51 /* Real operand. */ 52 void wrapper_op_real(wrapperctx *ctx, const mpfr_t r, 53 int size, const uint32 *ieee); 54 55 /* Complex operand. Real part starts at ieee[0], the imag part at ieee[2]. */ 56 void wrapper_op_complex(wrapperctx *ctx, const mpc_t c, 57 int size, const uint32 *ieee); 58 59 /* Real result. ieee contains size+1 words, as discussed above. */ 60 void wrapper_result_real(wrapperctx *ctx, mpfr_t r, 61 int size, uint32 *ieee); 62 63 /* Complex result. ieee contains size+1 words of real part starting at 64 * ieee[0], and another size+1 of imag part starting at ieee[4]. */ 65 void wrapper_result_complex(wrapperctx *ctx, mpc_t c, 66 int size, uint32 *ieee); 67 68 int wrapper_run(wrapperctx *ctx, wrapperfunc wrappers[MAXWRAPPERS]); 69 70 /* 71 * Functions for wrappers to call. 'op' indicates which operand is 72 * being requested: 0,1 means first and second, and -1 means the 73 * result. 74 */ 75 76 mpfr_srcptr wrapper_get_mpfr(wrapperctx *ctx, int op); 77 const uint32 *wrapper_get_ieee(wrapperctx *ctx, int op); 78 79 mpc_srcptr wrapper_get_mpc(wrapperctx *ctx, int op); 80 mpfr_srcptr wrapper_get_mpfr_r(wrapperctx *ctx, int op); 81 mpfr_srcptr wrapper_get_mpfr_i(wrapperctx *ctx, int op); 82 const uint32 *wrapper_get_ieee_r(wrapperctx *ctx, int op); 83 const uint32 *wrapper_get_ieee_i(wrapperctx *ctx, int op); 84 85 /* Query operand count + types */ 86 int wrapper_get_nops(wrapperctx *ctx); 87 int wrapper_get_size(wrapperctx *ctx, int op); 88 int wrapper_is_complex(wrapperctx *ctx, int op); 89 90 /* Change just the sign of the result. Only the top bit of 'sign' is used. */ 91 void wrapper_set_sign(wrapperctx *ctx, uint32 sign); 92 void wrapper_set_sign_r(wrapperctx *ctx, uint32 sign); 93 void wrapper_set_sign_i(wrapperctx *ctx, uint32 sign); 94 95 /* Set a result to NaN. */ 96 void wrapper_set_nan(wrapperctx *ctx); 97 void wrapper_set_nan_r(wrapperctx *ctx); 98 void wrapper_set_nan_i(wrapperctx *ctx); 99 100 /* Set a result to an integer value (converted to the appropriate 101 * float format). */ 102 void wrapper_set_int(wrapperctx *ctx, int val); 103 void wrapper_set_int_r(wrapperctx *ctx, int val); 104 void wrapper_set_int_i(wrapperctx *ctx, int val); 105 106 /* Set a result to a new MPFR float. */ 107 void wrapper_set_mpfr(wrapperctx *ctx, const mpfr_t val); 108 void wrapper_set_mpfr_r(wrapperctx *ctx, const mpfr_t val); 109 void wrapper_set_mpfr_i(wrapperctx *ctx, const mpfr_t val); 110 111 /* 112 * A universal wrapper called for _all_ functions, that doesn't have 113 * to be specified individually everywhere. 114 */ 115 void universal_wrapper(wrapperctx *ctx); 116