^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) /* Software floating-point emulation.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) Basic eight-word fraction declaration and manipulation.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) Copyright (C) 1997,1998,1999 Free Software Foundation, Inc.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) This file is part of the GNU C Library.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) Contributed by Richard Henderson (rth@cygnus.com),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) Jakub Jelinek (jj@ultra.linux.cz) and
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) Peter Maydell (pmaydell@chiark.greenend.org.uk).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) The GNU C Library is free software; you can redistribute it and/or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) modify it under the terms of the GNU Library General Public License as
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) published by the Free Software Foundation; either version 2 of the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) License, or (at your option) any later version.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) The GNU C Library is distributed in the hope that it will be useful,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) but WITHOUT ANY WARRANTY; without even the implied warranty of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) Library General Public License for more details.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) You should have received a copy of the GNU Library General Public
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) License along with the GNU C Library; see the file COPYING.LIB. If
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) not, write to the Free Software Foundation, Inc.,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #ifndef __MATH_EMU_OP_8_H__
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #define __MATH_EMU_OP_8_H__
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) /* We need just a few things from here for op-4, if we ever need some
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) other macros, they can be added. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #define _FP_FRAC_DECL_8(X) _FP_W_TYPE X##_f[8]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define _FP_FRAC_HIGH_8(X) (X##_f[7])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) #define _FP_FRAC_LOW_8(X) (X##_f[0])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #define _FP_FRAC_WORD_8(X,w) (X##_f[w])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) #define _FP_FRAC_SLL_8(X,N) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) do { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) _FP_I_TYPE _up, _down, _skip, _i; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) _skip = (N) / _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) _up = (N) % _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) _down = _FP_W_TYPE_SIZE - _up; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) if (!_up) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) for (_i = 7; _i >= _skip; --_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) X##_f[_i] = X##_f[_i-_skip]; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) else \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) for (_i = 7; _i > _skip; --_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) X##_f[_i] = X##_f[_i-_skip] << _up \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) | X##_f[_i-_skip-1] >> _down; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) X##_f[_i--] = X##_f[0] << _up; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) } \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) for (; _i >= 0; --_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) X##_f[_i] = 0; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) } while (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) #define _FP_FRAC_SRL_8(X,N) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) do { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) _FP_I_TYPE _up, _down, _skip, _i; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) _skip = (N) / _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) _down = (N) % _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) _up = _FP_W_TYPE_SIZE - _down; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) if (!_down) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) for (_i = 0; _i <= 7-_skip; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) X##_f[_i] = X##_f[_i+_skip]; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) else \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) for (_i = 0; _i < 7-_skip; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) X##_f[_i] = X##_f[_i+_skip] >> _down \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) | X##_f[_i+_skip+1] << _up; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) X##_f[_i++] = X##_f[7] >> _down; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) } \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) for (; _i < 8; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) X##_f[_i] = 0; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) } while (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) /* Right shift with sticky-lsb.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) * What this actually means is that we do a standard right-shift,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) * but that if any of the bits that fall off the right hand side
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * were one then we always set the LSbit.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) #define _FP_FRAC_SRS_8(X,N,size) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) do { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) _FP_I_TYPE _up, _down, _skip, _i; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) _FP_W_TYPE _s; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) _skip = (N) / _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) _down = (N) % _FP_W_TYPE_SIZE; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) _up = _FP_W_TYPE_SIZE - _down; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) for (_s = _i = 0; _i < _skip; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) _s |= X##_f[_i]; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) _s |= X##_f[_i] << _up; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) /* s is now != 0 if we want to set the LSbit */ \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) if (!_down) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) for (_i = 0; _i <= 7-_skip; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) X##_f[_i] = X##_f[_i+_skip]; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) else \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) { \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) for (_i = 0; _i < 7-_skip; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) X##_f[_i] = X##_f[_i+_skip] >> _down \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) | X##_f[_i+_skip+1] << _up; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) X##_f[_i++] = X##_f[7] >> _down; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) } \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) for (; _i < 8; ++_i) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) X##_f[_i] = 0; \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) /* don't fix the LSB until the very end when we're sure f[0] is stable */ \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) X##_f[0] |= (_s != 0); \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) } while (0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) #endif