]>
Commit | Line | Data |
---|---|---|
1 | /* Software floating-point emulation. | |
2 | Definitions for IEEE Double Precision | |
3 | Copyright (C) 1997-2014 Free Software Foundation, Inc. | |
4 | This file is part of the GNU C Library. | |
5 | Contributed by Richard Henderson (rth@cygnus.com), | |
6 | Jakub Jelinek (jj@ultra.linux.cz), | |
7 | David S. Miller (davem@redhat.com) and | |
8 | Peter Maydell (pmaydell@chiark.greenend.org.uk). | |
9 | ||
10 | The GNU C Library is free software; you can redistribute it and/or | |
11 | modify it under the terms of the GNU Lesser General Public | |
12 | License as published by the Free Software Foundation; either | |
13 | version 2.1 of the License, or (at your option) any later version. | |
14 | ||
15 | In addition to the permissions in the GNU Lesser General Public | |
16 | License, the Free Software Foundation gives you unlimited | |
17 | permission to link the compiled version of this file into | |
18 | combinations with other programs, and to distribute those | |
19 | combinations without any restriction coming from the use of this | |
20 | file. (The Lesser General Public License restrictions do apply in | |
21 | other respects; for example, they cover modification of the file, | |
22 | and distribution when not linked into a combine executable.) | |
23 | ||
24 | The GNU C Library is distributed in the hope that it will be useful, | |
25 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
26 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
27 | Lesser General Public License for more details. | |
28 | ||
29 | You should have received a copy of the GNU Lesser General Public | |
30 | License along with the GNU C Library; if not, see | |
31 | <http://www.gnu.org/licenses/>. */ | |
32 | ||
33 | #if _FP_W_TYPE_SIZE < 32 | |
34 | # error "Here's a nickel kid. Go buy yourself a real computer." | |
35 | #endif | |
36 | ||
37 | #if _FP_W_TYPE_SIZE < 64 | |
38 | # define _FP_FRACTBITS_D (2 * _FP_W_TYPE_SIZE) | |
39 | # define _FP_FRACTBITS_DW_D (4 * _FP_W_TYPE_SIZE) | |
40 | #else | |
41 | # define _FP_FRACTBITS_D _FP_W_TYPE_SIZE | |
42 | # define _FP_FRACTBITS_DW_D (2 * _FP_W_TYPE_SIZE) | |
43 | #endif | |
44 | ||
45 | #define _FP_FRACBITS_D 53 | |
46 | #define _FP_FRACXBITS_D (_FP_FRACTBITS_D - _FP_FRACBITS_D) | |
47 | #define _FP_WFRACBITS_D (_FP_WORKBITS + _FP_FRACBITS_D) | |
48 | #define _FP_WFRACXBITS_D (_FP_FRACTBITS_D - _FP_WFRACBITS_D) | |
49 | #define _FP_EXPBITS_D 11 | |
50 | #define _FP_EXPBIAS_D 1023 | |
51 | #define _FP_EXPMAX_D 2047 | |
52 | ||
53 | #define _FP_QNANBIT_D \ | |
54 | ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-2) % _FP_W_TYPE_SIZE) | |
55 | #define _FP_QNANBIT_SH_D \ | |
56 | ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-2+_FP_WORKBITS) % _FP_W_TYPE_SIZE) | |
57 | #define _FP_IMPLBIT_D \ | |
58 | ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-1) % _FP_W_TYPE_SIZE) | |
59 | #define _FP_IMPLBIT_SH_D \ | |
60 | ((_FP_W_TYPE) 1 << (_FP_FRACBITS_D-1+_FP_WORKBITS) % _FP_W_TYPE_SIZE) | |
61 | #define _FP_OVERFLOW_D \ | |
62 | ((_FP_W_TYPE) 1 << _FP_WFRACBITS_D % _FP_W_TYPE_SIZE) | |
63 | ||
64 | #define _FP_WFRACBITS_DW_D (2 * _FP_WFRACBITS_D) | |
65 | #define _FP_WFRACXBITS_DW_D (_FP_FRACTBITS_DW_D - _FP_WFRACBITS_DW_D) | |
66 | #define _FP_HIGHBIT_DW_D \ | |
67 | ((_FP_W_TYPE) 1 << (_FP_WFRACBITS_DW_D - 1) % _FP_W_TYPE_SIZE) | |
68 | ||
69 | typedef float DFtype __attribute__ ((mode (DF))); | |
70 | ||
71 | #if _FP_W_TYPE_SIZE < 64 | |
72 | ||
73 | union _FP_UNION_D | |
74 | { | |
75 | DFtype flt; | |
76 | struct _FP_STRUCT_LAYOUT | |
77 | { | |
78 | # if __BYTE_ORDER == __BIG_ENDIAN | |
79 | unsigned sign : 1; | |
80 | unsigned exp : _FP_EXPBITS_D; | |
81 | unsigned frac1 : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0) - _FP_W_TYPE_SIZE; | |
82 | unsigned frac0 : _FP_W_TYPE_SIZE; | |
83 | # else | |
84 | unsigned frac0 : _FP_W_TYPE_SIZE; | |
85 | unsigned frac1 : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0) - _FP_W_TYPE_SIZE; | |
86 | unsigned exp : _FP_EXPBITS_D; | |
87 | unsigned sign : 1; | |
88 | # endif | |
89 | } bits __attribute__ ((packed)); | |
90 | }; | |
91 | ||
92 | # define FP_DECL_D(X) _FP_DECL (2, X) | |
93 | # define FP_UNPACK_RAW_D(X, val) _FP_UNPACK_RAW_2 (D, X, val) | |
94 | # define FP_UNPACK_RAW_DP(X, val) _FP_UNPACK_RAW_2_P (D, X, val) | |
95 | # define FP_PACK_RAW_D(val, X) _FP_PACK_RAW_2 (D, val, X) | |
96 | # define FP_PACK_RAW_DP(val, X) \ | |
97 | do \ | |
98 | { \ | |
99 | if (!FP_INHIBIT_RESULTS) \ | |
100 | _FP_PACK_RAW_2_P (D, val, X); \ | |
101 | } \ | |
102 | while (0) | |
103 | ||
104 | # define FP_UNPACK_D(X, val) \ | |
105 | do \ | |
106 | { \ | |
107 | _FP_UNPACK_RAW_2 (D, X, val); \ | |
108 | _FP_UNPACK_CANONICAL (D, 2, X); \ | |
109 | } \ | |
110 | while (0) | |
111 | ||
112 | # define FP_UNPACK_DP(X, val) \ | |
113 | do \ | |
114 | { \ | |
115 | _FP_UNPACK_RAW_2_P (D, X, val); \ | |
116 | _FP_UNPACK_CANONICAL (D, 2, X); \ | |
117 | } \ | |
118 | while (0) | |
119 | ||
120 | # define FP_UNPACK_SEMIRAW_D(X, val) \ | |
121 | do \ | |
122 | { \ | |
123 | _FP_UNPACK_RAW_2 (D, X, val); \ | |
124 | _FP_UNPACK_SEMIRAW (D, 2, X); \ | |
125 | } \ | |
126 | while (0) | |
127 | ||
128 | # define FP_UNPACK_SEMIRAW_DP(X, val) \ | |
129 | do \ | |
130 | { \ | |
131 | _FP_UNPACK_RAW_2_P (D, X, val); \ | |
132 | _FP_UNPACK_SEMIRAW (D, 2, X); \ | |
133 | } \ | |
134 | while (0) | |
135 | ||
136 | # define FP_PACK_D(val, X) \ | |
137 | do \ | |
138 | { \ | |
139 | _FP_PACK_CANONICAL (D, 2, X); \ | |
140 | _FP_PACK_RAW_2 (D, val, X); \ | |
141 | } \ | |
142 | while (0) | |
143 | ||
144 | # define FP_PACK_DP(val, X) \ | |
145 | do \ | |
146 | { \ | |
147 | _FP_PACK_CANONICAL (D, 2, X); \ | |
148 | if (!FP_INHIBIT_RESULTS) \ | |
149 | _FP_PACK_RAW_2_P (D, val, X); \ | |
150 | } \ | |
151 | while (0) | |
152 | ||
153 | # define FP_PACK_SEMIRAW_D(val, X) \ | |
154 | do \ | |
155 | { \ | |
156 | _FP_PACK_SEMIRAW (D, 2, X); \ | |
157 | _FP_PACK_RAW_2 (D, val, X); \ | |
158 | } \ | |
159 | while (0) | |
160 | ||
161 | # define FP_PACK_SEMIRAW_DP(val, X) \ | |
162 | do \ | |
163 | { \ | |
164 | _FP_PACK_SEMIRAW (D, 2, X); \ | |
165 | if (!FP_INHIBIT_RESULTS) \ | |
166 | _FP_PACK_RAW_2_P (D, val, X); \ | |
167 | } \ | |
168 | while (0) | |
169 | ||
170 | # define FP_ISSIGNAN_D(X) _FP_ISSIGNAN (D, 2, X) | |
171 | # define FP_NEG_D(R, X) _FP_NEG (D, 2, R, X) | |
172 | # define FP_ADD_D(R, X, Y) _FP_ADD (D, 2, R, X, Y) | |
173 | # define FP_SUB_D(R, X, Y) _FP_SUB (D, 2, R, X, Y) | |
174 | # define FP_MUL_D(R, X, Y) _FP_MUL (D, 2, R, X, Y) | |
175 | # define FP_DIV_D(R, X, Y) _FP_DIV (D, 2, R, X, Y) | |
176 | # define FP_SQRT_D(R, X) _FP_SQRT (D, 2, R, X) | |
177 | # define _FP_SQRT_MEAT_D(R, S, T, X, Q) _FP_SQRT_MEAT_2 (R, S, T, X, Q) | |
178 | # define FP_FMA_D(R, X, Y, Z) _FP_FMA (D, 2, 4, R, X, Y, Z) | |
179 | ||
180 | # define FP_CMP_D(r, X, Y, un) _FP_CMP (D, 2, r, X, Y, un) | |
181 | # define FP_CMP_EQ_D(r, X, Y) _FP_CMP_EQ (D, 2, r, X, Y) | |
182 | # define FP_CMP_UNORD_D(r, X, Y) _FP_CMP_UNORD (D, 2, r, X, Y) | |
183 | ||
184 | # define FP_TO_INT_D(r, X, rsz, rsg) _FP_TO_INT (D, 2, r, X, rsz, rsg) | |
185 | # define FP_FROM_INT_D(X, r, rs, rt) _FP_FROM_INT (D, 2, X, r, rs, rt) | |
186 | ||
187 | # define _FP_FRAC_HIGH_D(X) _FP_FRAC_HIGH_2 (X) | |
188 | # define _FP_FRAC_HIGH_RAW_D(X) _FP_FRAC_HIGH_2 (X) | |
189 | ||
190 | # define _FP_FRAC_HIGH_DW_D(X) _FP_FRAC_HIGH_4 (X) | |
191 | ||
192 | #else | |
193 | ||
194 | union _FP_UNION_D | |
195 | { | |
196 | DFtype flt; | |
197 | struct _FP_STRUCT_LAYOUT | |
198 | { | |
199 | # if __BYTE_ORDER == __BIG_ENDIAN | |
200 | unsigned sign : 1; | |
201 | unsigned exp : _FP_EXPBITS_D; | |
202 | _FP_W_TYPE frac : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0); | |
203 | # else | |
204 | _FP_W_TYPE frac : _FP_FRACBITS_D - (_FP_IMPLBIT_D != 0); | |
205 | unsigned exp : _FP_EXPBITS_D; | |
206 | unsigned sign : 1; | |
207 | # endif | |
208 | } bits __attribute__ ((packed)); | |
209 | }; | |
210 | ||
211 | # define FP_DECL_D(X) _FP_DECL (1, X) | |
212 | # define FP_UNPACK_RAW_D(X, val) _FP_UNPACK_RAW_1 (D, X, val) | |
213 | # define FP_UNPACK_RAW_DP(X, val) _FP_UNPACK_RAW_1_P (D, X, val) | |
214 | # define FP_PACK_RAW_D(val, X) _FP_PACK_RAW_1 (D, val, X) | |
215 | # define FP_PACK_RAW_DP(val, X) \ | |
216 | do \ | |
217 | { \ | |
218 | if (!FP_INHIBIT_RESULTS) \ | |
219 | _FP_PACK_RAW_1_P (D, val, X); \ | |
220 | } \ | |
221 | while (0) | |
222 | ||
223 | # define FP_UNPACK_D(X, val) \ | |
224 | do \ | |
225 | { \ | |
226 | _FP_UNPACK_RAW_1 (D, X, val); \ | |
227 | _FP_UNPACK_CANONICAL (D, 1, X); \ | |
228 | } \ | |
229 | while (0) | |
230 | ||
231 | # define FP_UNPACK_DP(X, val) \ | |
232 | do \ | |
233 | { \ | |
234 | _FP_UNPACK_RAW_1_P (D, X, val); \ | |
235 | _FP_UNPACK_CANONICAL (D, 1, X); \ | |
236 | } \ | |
237 | while (0) | |
238 | ||
239 | # define FP_UNPACK_SEMIRAW_D(X, val) \ | |
240 | do \ | |
241 | { \ | |
242 | _FP_UNPACK_RAW_1 (D, X, val); \ | |
243 | _FP_UNPACK_SEMIRAW (D, 1, X); \ | |
244 | } \ | |
245 | while (0) | |
246 | ||
247 | # define FP_UNPACK_SEMIRAW_DP(X, val) \ | |
248 | do \ | |
249 | { \ | |
250 | _FP_UNPACK_RAW_1_P (D, X, val); \ | |
251 | _FP_UNPACK_SEMIRAW (D, 1, X); \ | |
252 | } \ | |
253 | while (0) | |
254 | ||
255 | # define FP_PACK_D(val, X) \ | |
256 | do \ | |
257 | { \ | |
258 | _FP_PACK_CANONICAL (D, 1, X); \ | |
259 | _FP_PACK_RAW_1 (D, val, X); \ | |
260 | } \ | |
261 | while (0) | |
262 | ||
263 | # define FP_PACK_DP(val, X) \ | |
264 | do \ | |
265 | { \ | |
266 | _FP_PACK_CANONICAL (D, 1, X); \ | |
267 | if (!FP_INHIBIT_RESULTS) \ | |
268 | _FP_PACK_RAW_1_P (D, val, X); \ | |
269 | } \ | |
270 | while (0) | |
271 | ||
272 | # define FP_PACK_SEMIRAW_D(val, X) \ | |
273 | do \ | |
274 | { \ | |
275 | _FP_PACK_SEMIRAW (D, 1, X); \ | |
276 | _FP_PACK_RAW_1 (D, val, X); \ | |
277 | } \ | |
278 | while (0) | |
279 | ||
280 | # define FP_PACK_SEMIRAW_DP(val, X) \ | |
281 | do \ | |
282 | { \ | |
283 | _FP_PACK_SEMIRAW (D, 1, X); \ | |
284 | if (!FP_INHIBIT_RESULTS) \ | |
285 | _FP_PACK_RAW_1_P (D, val, X); \ | |
286 | } \ | |
287 | while (0) | |
288 | ||
289 | # define FP_ISSIGNAN_D(X) _FP_ISSIGNAN (D, 1, X) | |
290 | # define FP_NEG_D(R, X) _FP_NEG (D, 1, R, X) | |
291 | # define FP_ADD_D(R, X, Y) _FP_ADD (D, 1, R, X, Y) | |
292 | # define FP_SUB_D(R, X, Y) _FP_SUB (D, 1, R, X, Y) | |
293 | # define FP_MUL_D(R, X, Y) _FP_MUL (D, 1, R, X, Y) | |
294 | # define FP_DIV_D(R, X, Y) _FP_DIV (D, 1, R, X, Y) | |
295 | # define FP_SQRT_D(R, X) _FP_SQRT (D, 1, R, X) | |
296 | # define _FP_SQRT_MEAT_D(R, S, T, X, Q) _FP_SQRT_MEAT_1 (R, S, T, X, Q) | |
297 | # define FP_FMA_D(R, X, Y, Z) _FP_FMA (D, 1, 2, R, X, Y, Z) | |
298 | ||
299 | /* The implementation of _FP_MUL_D and _FP_DIV_D should be chosen by | |
300 | the target machine. */ | |
301 | ||
302 | # define FP_CMP_D(r, X, Y, un) _FP_CMP (D, 1, r, X, Y, un) | |
303 | # define FP_CMP_EQ_D(r, X, Y) _FP_CMP_EQ (D, 1, r, X, Y) | |
304 | # define FP_CMP_UNORD_D(r, X, Y) _FP_CMP_UNORD (D, 1, r, X, Y) | |
305 | ||
306 | # define FP_TO_INT_D(r, X, rsz, rsg) _FP_TO_INT (D, 1, r, X, rsz, rsg) | |
307 | # define FP_FROM_INT_D(X, r, rs, rt) _FP_FROM_INT (D, 1, X, r, rs, rt) | |
308 | ||
309 | # define _FP_FRAC_HIGH_D(X) _FP_FRAC_HIGH_1 (X) | |
310 | # define _FP_FRAC_HIGH_RAW_D(X) _FP_FRAC_HIGH_1 (X) | |
311 | ||
312 | # define _FP_FRAC_HIGH_DW_D(X) _FP_FRAC_HIGH_2 (X) | |
313 | ||
314 | #endif /* W_TYPE_SIZE < 64 */ |