1 /* Floating point exceptions */ 2 /* 3 Copyright (C) 2004-2017,2018 John E. Davis 4 5 This file is part of the S-Lang Library. 6 7 The S-Lang Library is free software; you can redistribute it and/or 8 modify it under the terms of the GNU General Public License as 9 published by the Free Software Foundation; either version 2 of the 10 License, or (at your option) any later version. 11 12 The S-Lang Library is distributed in the hope that it will be useful, 13 but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 General Public License for more details. 16 17 You should have received a copy of the GNU General Public License 18 along with this library; if not, write to the Free Software 19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, 20 USA. 21 */ 22 23 #include "slinclud.h" 24 25 #include <float.h> 26 #include <math.h> 27 28 #ifdef HAVE_FLOATINGPOINT_H 29 # include <floatingpoint.h> 30 #endif 31 32 #ifdef HAVE_FENV_H 33 # include <fenv.h> 34 #endif 35 36 #ifdef HAVE_IEEEFP_H 37 # include <ieeefp.h> 38 #endif 39 40 #include "slang.h" 41 #include "_slang.h" 42 43 #ifdef HAVE_FECLEAREXCEPT 44 # define CLEAR_FP_EXCEPTION (void)feclearexcept(FE_ALL_EXCEPT); 45 # define GET_FP_EXCEPTION fetestexcept(FE_ALL_EXCEPT) 46 # ifndef FE_DIVBYZERO 47 # define FE_DIVBYZERO 0 48 # endif 49 # ifndef FE_INVALID 50 # define FE_INVALID 0 51 # endif 52 # ifndef FE_OVERFLOW 53 # define FE_OVERFLOW 0 54 # endif 55 # ifndef FE_UNDERFLOW 56 # define FE_UNDERFLOW 0 57 # endif 58 # ifndef FE_INEXACT 59 # define FE_INEXACT 0 60 # endif 61 # define SYS_FE_DIVBYZERO FE_DIVBYZERO 62 # define SYS_FE_INVALID FE_INVALID 63 # define SYS_FE_OVERFLOW FE_OVERFLOW 64 # define SYS_FE_UNDERFLOW FE_UNDERFLOW 65 # define SYS_FE_INEXACT FE_INEXACT 66 #else 67 # ifdef HAVE_FPSETSTICKY 68 # define CLEAR_FP_EXCEPTION (void)fpsetsticky(0) 69 # define GET_FP_EXCEPTION fpgetsticky() 70 # define SYS_FE_DIVBYZERO FP_X_DZ 71 # define SYS_FE_INVALID FP_X_INV 72 # define SYS_FE_OVERFLOW FP_X_OFL 73 # define SYS_FE_UNDERFLOW FP_X_UFL 74 # define SYS_FE_INEXACT FP_X_IMP 75 # else 76 /* ??? */ 77 # define CLEAR_FP_EXCEPTION (void)0 78 # define GET_FP_EXCEPTION (0) 79 # define SYS_FE_DIVBYZERO 0 80 # define SYS_FE_INVALID 0 81 # define SYS_FE_OVERFLOW 0 82 # define SYS_FE_UNDERFLOW 0 83 # define SYS_FE_INEXACT 0 84 # endif 85 #endif 86 SLfpu_clear_except_bits(void)87void SLfpu_clear_except_bits (void) 88 { 89 CLEAR_FP_EXCEPTION; 90 } 91 SLfpu_test_except_bits(unsigned int bits)92unsigned int SLfpu_test_except_bits (unsigned int bits) 93 { 94 unsigned int rbits; 95 unsigned long sysbits; 96 97 sysbits = GET_FP_EXCEPTION; 98 99 rbits = 0; 100 if (sysbits & SYS_FE_DIVBYZERO) rbits |= SL_FE_DIVBYZERO; 101 if (sysbits & SYS_FE_INVALID) rbits |= SL_FE_INVALID; 102 if (sysbits & SYS_FE_OVERFLOW) rbits |= SL_FE_OVERFLOW; 103 if (sysbits & SYS_FE_UNDERFLOW) rbits |= SL_FE_UNDERFLOW; 104 if (sysbits & SYS_FE_INEXACT) rbits |= SL_FE_INEXACT; 105 106 return rbits & bits; 107 } 108