1 | /* Manipulation of the bit representation of 'long double' quantities. |
---|---|

2 | Copyright (C) 2001-2022 Free Software Foundation, Inc. |

3 | This file is part of the GNU C Library. |

4 | |

5 | The GNU C Library is free software; you can redistribute it and/or |

6 | modify it under the terms of the GNU Lesser General Public |

7 | License as published by the Free Software Foundation; either |

8 | version 2.1 of the License, or (at your option) any later version. |

9 | |

10 | The GNU C Library is distributed in the hope that it will be useful, |

11 | but WITHOUT ANY WARRANTY; without even the implied warranty of |

12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |

13 | Lesser General Public License for more details. |

14 | |

15 | You should have received a copy of the GNU Lesser General Public |

16 | License along with the GNU C Library; if not, see |

17 | <https://www.gnu.org/licenses/>. */ |

18 | |

19 | #ifndef _MATH_LDBL_H_ |

20 | #define _MATH_LDBL_H_ 1 |

21 | |

22 | #include <stdint.h> |

23 | |

24 | /* A union which permits us to convert between a long double and |

25 | three 32 bit ints. */ |

26 | |

27 | typedef union |

28 | { |

29 | long double value; |

30 | struct |

31 | { |

32 | uint32_t lsw; |

33 | uint32_t msw; |

34 | int sign_exponent:16; |

35 | unsigned int empty1:16; |

36 | unsigned int empty0:32; |

37 | } parts; |

38 | } ieee_long_double_shape_type; |

39 | |

40 | /* Get three 32 bit ints from a double. */ |

41 | |

42 | #define GET_LDOUBLE_WORDS(exp,ix0,ix1,d) \ |

43 | do { \ |

44 | ieee_long_double_shape_type ew_u; \ |

45 | ew_u.value = (d); \ |

46 | (exp) = ew_u.parts.sign_exponent; \ |

47 | (ix0) = ew_u.parts.msw; \ |

48 | (ix1) = ew_u.parts.lsw; \ |

49 | } while (0) |

50 | |

51 | /* Set a double from two 32 bit ints. */ |

52 | |

53 | #define SET_LDOUBLE_WORDS(d,exp,ix0,ix1) \ |

54 | do { \ |

55 | ieee_long_double_shape_type iw_u; \ |

56 | iw_u.parts.sign_exponent = (exp); \ |

57 | iw_u.parts.msw = (ix0); \ |

58 | iw_u.parts.lsw = (ix1); \ |

59 | (d) = iw_u.value; \ |

60 | } while (0) |

61 | |

62 | /* Get the more significant 32 bits of a long double mantissa. */ |

63 | |

64 | #define GET_LDOUBLE_MSW(v,d) \ |

65 | do { \ |

66 | ieee_long_double_shape_type sh_u; \ |

67 | sh_u.value = (d); \ |

68 | (v) = sh_u.parts.msw; \ |

69 | } while (0) |

70 | |

71 | /* Set the more significant 32 bits of a long double mantissa from an int. */ |

72 | |

73 | #define SET_LDOUBLE_MSW(d,v) \ |

74 | do { \ |

75 | ieee_long_double_shape_type sh_u; \ |

76 | sh_u.value = (d); \ |

77 | sh_u.parts.msw = (v); \ |

78 | (d) = sh_u.value; \ |

79 | } while (0) |

80 | |

81 | /* Get int from the exponent of a long double. */ |

82 | |

83 | #define GET_LDOUBLE_EXP(exp,d) \ |

84 | do { \ |

85 | ieee_long_double_shape_type ge_u; \ |

86 | ge_u.value = (d); \ |

87 | (exp) = ge_u.parts.sign_exponent; \ |

88 | } while (0) |

89 | |

90 | /* Set exponent of a long double from an int. */ |

91 | |

92 | #define SET_LDOUBLE_EXP(d,exp) \ |

93 | do { \ |

94 | ieee_long_double_shape_type se_u; \ |

95 | se_u.value = (d); \ |

96 | se_u.parts.sign_exponent = (exp); \ |

97 | (d) = se_u.value; \ |

98 | } while (0) |

99 | |

100 | #endif /* math_ldbl.h */ |

101 |