1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
|
/***************************************************************
__MPU_REAL.H
This file contains declarations of functions for
REAL arithmetic operations.
PART OF : MPU - library .
USAGE : Internal only .
NOTE : Include "libmpu.h" before this FILE .
Copyright (C) 2000 - 2024 by Andrew V.Kosteltsev.
All Rights Reserved.
***************************************************************/
#ifndef __MPU_REAL_H
#define __MPU_REAL_H
#ifdef __cplusplus
extern "C" {
#endif
/***************************************************************
Internal exploded e-type data structure of a real number
(a EMUSHORT is BITS_PER_EMUSHORT bits):
EMUSHORT ei[NP];
IF MPU_WORD_ORDER_BIG_ENDIAN = 1 (m68k, PowerPC)
ei[0] - high EMUSHORT partion,
ei[NP-1] - low EMUSHORT partion.
- that is ---------------------------------------
pointer -> [high EMUSHORT partion] :0 part
[ . . . ] :1 part
.
.
.
[low EMUSHORT partion] :NP-1 part
-------------------------------------------------
ELSE IF MPU_WORD_ORDER_BIG_ENDIAN = 0 (i386, Alpha)
ei[0] - low EMUSHORT partion.
ei[NP-1] - high EMUSHORT partion,
- that is ---------------------------------------
part 0: [low EMUSHORT partion] <- pointer
part 1: [ . . . ]
.
.
.
part NP-1: [high EMUSHORT partion]
-------------------------------------------------
===============================================================
index:
MPU_WORD_ORDER_BIG_ENDIAN = 0
[nS+nE+2]|[nS+nE+1]...[nS+2]| [nS+1]|[nS], . . . , [1]| [0].
MPU_WORD_ORDER_BIG_ENDIAN = 1
[0]|[1], . . . , [nE]| [nE+1]|[nE+2], ...,[nE+nS+1]|[nE+nS+2].
|--------|------. . .-------|-------|---------. . .-------|---------|
| sign | Exponent | hgw | Significand | lgw |
|--------|------. . .-------|-------|---------. . .-------|---------|
size: 1 nE 1 nS 1
hgw - hight guard word (always zero after normalization);
lgw - low guard word (0x8000... bit is rounding place);
sign - знак числа ( '+' - 0x0000...; '-' - 0xffff... );
Exponent - смещенный порядок;
Significand - мантисса;
Общее количество слов - nE + nS + 3;
Бит целой (1.) - явный.
СТАРШИЙ БИТ ЭКСПОНЕНТЫ НЕ ИСПОЛЬЗУЕТСЯ.
***************************************************************/
/***************************************************************
NOTE:
Количество порций вещественного числа во внутреннем
формате не должно превышать максимального значения
EMUSHORT (unsigned int), которому соответствует тип
__mpu_uint32_t.
NOTE:
Это ограничение связано с ограничением количества
бит мантиссы вещественного числа во внутреннем формате.
SEE: ei_normalize() in this file.
NOTE:
В случае программных моделей ILP32, LP64, LLP64 мы
всегда можем иметь 32-битный EMUSHORT, что позволяет
в качестве возвращаемого значения функции ei_normalize()
использовать переменные типа __mpu_int32_t или int.
***************************************************************/
/***************************************************************
External exploded e-type data structure of a real number
(a EMUPART is BITS_PER_EMUPART bits):
===============================================================
index:
MPU_WORD_ORDER_BIG_ENDIAN = 0
[nPx-1], . . . ,[nSx]| [nSx-1], . . ., [0].
MPU_WORD_ORDER_BIG_ENDIAN = 1
[0], . . . , [nEx-1]| [nEx], . . ., [nPx-1].
|--------. . .-------|-------------------. . .--------------------|
| Exponent | Significand |
|--------. . .-------|-------------------. . .--------------------|
^Sign bit ^(1.- implicit)
size: nEx nSx.
Exponent - смещенный порядок;
Significand - мантисса;
Общее количество слов - nEx + nSx;
Бит целой (1.) - неявный.
***************************************************************/
/* Следующее не верно для real32 & real64 */
/***************************************************************
Количество бит выделяемое на Sign и Exponent в
external e-type data struct.
n - number of bits in external e-type data struct.
***************************************************************/
#define NEBITS(nb) ((__mpu_int32_t)(internal_ne(nb)*BITS_PER_EMUSHORT))
/***************************************************************
Количество бит выделяемое на Significand в
external e-type data struct.
n - number of bits in external e-type data struct.
***************************************************************/
#define NSBITS(nb) ((__mpu_int32_t)(internal_ns(nb)*BITS_PER_EMUSHORT))
/***********************************************************
Количество EMUSHORT порций в Internal e-type data struct.
NOTE for real128 и более:
InternalNP = InternalNE + InternalNS + 3(Sign, hgw, lgw).
ExternalNE = InternalNE.
ExternalNS = InternalNS.
ExternalNP = InternalNE + InternalNS.
***********************************************************/
extern int internal_ne( int nb );
extern int internal_ns( int nb );
extern int internal_np( int nb );
extern void ei_cleaz ( EMUSHORT *ei, int nb );
extern void ei_cleazs ( EMUSHORT *ei, int nb );
extern void ei_ind ( EMUSHORT *ei, int nb );
extern int ei_isind ( EMUSHORT *ei, int nb );
extern void e_ind ( EMUSHORT *ee, int nb );
extern int e_isind ( EMUSHORT *ee, int nb );
extern void ei_nan ( EMUSHORT *ei, unsigned sign, int nb );
extern int ei_isnans ( EMUSHORT *ei, int nb );
extern void e_nan ( EMUSHORT *ee, unsigned sign, int nb );
extern int e_isnans ( EMUSHORT *ee, int nb );
extern void ei_nanmax ( EMUSHORT *ei, unsigned sign, int nb );
extern int ei_isnanmax ( EMUSHORT *ei, int nb );
extern void e_nanmax ( EMUSHORT *ee, unsigned sign, int nb );
extern int e_isnanmax ( EMUSHORT *ee, int nb );
extern void ei_nanmin ( EMUSHORT *ei, unsigned sign, int nb );
extern int ei_isnanmin ( EMUSHORT *ei, int nb );
extern void e_nanmin ( EMUSHORT *ee, unsigned sign, int nb );
extern int e_isnanmin ( EMUSHORT *ee, int nb );
extern void ei_infin ( EMUSHORT *ei, unsigned sign, int nb );
extern int ei_isinfin ( EMUSHORT *ei, int nb );
extern void e_infin ( EMUSHORT *ee, unsigned sign, int nb );
extern int e_isinfin ( EMUSHORT *ee, int nb );
extern void e_realmin ( EMUSHORT *ee, unsigned sign, int nb );
extern void e_realmax ( EMUSHORT *ee, unsigned sign, int nb );
extern void ei_signull ( EMUSHORT *ei, unsigned sign, int nb );
extern int ei_issignull ( EMUSHORT *ei, int nb );
extern void e_signull ( EMUSHORT *ee, unsigned sign, int nb );
extern int e_issignull ( EMUSHORT *ee, int nb );
extern void ei_neg ( EMUSHORT *ei, int nb );
extern int ei_isneg ( EMUSHORT *ei, int nb );
extern void e_neg ( EMUSHORT *ee, int nb );
extern int e_isneg ( EMUSHORT *ee, int nb );
extern void ei_abs ( EMUSHORT *ei, int nb );
extern void e_abs ( EMUSHORT *ee, int nb );
/***************************************************************
Functions for LONG INTEGER NUMBERS:
*/
/*
SIGNED COMPARE TWO SIGNED INTEGER NUMBER
if( a > b ) return( 1);
if( a == b ) return( 0);
if( a < b ) return( -1);
*/
extern int ei_cmpe ( EMUSHORT *a, EMUSHORT *b, int np );
/*
SIGNED COMPARE A with ZERO
if( a > 0 ) return( 1);
if( a == 0 ) return( 0);
if( a < 0 ) return( -1);
*/
extern int ei_cmp0e ( EMUSHORT *a, int np );
/* КОПИРОВАНИЕ БОЛЬШЕГО В МЕНЬШЕЕ (npa < npb) */
extern void ei_cpye_pack ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* КОПИРОВАНИЕ МЕНЬШЕГО В БОЛЬШЕЕ (npa >= npb) */
extern void ei_cpye_unpack ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* COPY UNSIGNED INTEGER NUMBER */
extern void ei_cpye ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* КОНВЕРТИРОВАНИЕ МЕНЬШЕГО В БОЛЬШЕЕ (npa >= npb) */
extern void ei_cvte_unpack ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* КОНВЕРТИРОВАНИЕ БОЛЬШЕГО В МЕНЬШЕЕ (npa < npb) */
extern void ei_cvte_pack ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* CONVERT SIGNED INTEGER NUMBER */
extern void ei_cvte ( EMUSHORT *a, EMUSHORT *b, int npa, int npb );
/* ADD INTEGER NUMBER */
extern void ei_adde ( EMUSHORT *c, EMUSHORT *a, EMUSHORT *b, int np );
/* INCrement INTEGER NUMBER */
extern void ei_ince ( EMUSHORT *c, EMUSHORT *a, int np );
/* SUB INTEGER NUMBER */
extern void ei_sube ( EMUSHORT *c, EMUSHORT *a, EMUSHORT *b, int np );
/* DECrement INTEGER NUMBER */
extern void ei_dece ( EMUSHORT *c, EMUSHORT *a, int np );
/* NEGATE Signed INTEGER NUMBER */
extern void ei_nege ( EMUSHORT *c, EMUSHORT *a, int np );
/* ADD INTEGER NUMBER */
extern void ei_ande ( EMUSHORT *c, EMUSHORT *a, EMUSHORT *b, int np );
/******************
СДВИГИ на b bits
******************/
/* SHIFT RIGHT */
extern void ei_shrn ( EMUSHORT *c, EMUSHORT *a, unsigned b, int np );
/* SHIFT LEFT */
extern void ei_shln ( EMUSHORT *c, EMUSHORT *a, unsigned b, int np );
/*
End of Functions for LONG INTEGER NUMBERS.
***************************************************************/
extern void ei_shdown ( EMUSHORT *ei, unsigned sc, int nb );
extern void ei_shup ( EMUSHORT *ei, unsigned sc, int nb );
extern int ei_shift ( EMUSHORT *ei, int sc, int nb );
extern __mpu_int32_t
ei_normalize ( EMUSHORT *ei, int nb );
extern void unpack ( EMUSHORT *ei, EMUSHORT *ee, int nb );
extern int ei_cmpm ( EMUSHORT *ai, EMUSHORT *bi, int nb );
extern void ei_addm ( EMUSHORT *ci, EMUSHORT *ai, EMUSHORT *bi, int nb );
extern void ei_subm ( EMUSHORT *ci, EMUSHORT *ai, EMUSHORT *bi, int nb );
extern int ei_divm ( EMUSHORT *quoti, EMUSHORT *numi, EMUSHORT *deni, int nb );
extern int ei_mulm ( EMUSHORT *prodi, EMUSHORT *numi, EMUSHORT *muli, int nb );
/***************************************************************
ROUNDOFF parameter register control.
= == = = =
регистр управления параметрами ОКРУГЛЕНИЯ.
***************************************************************/
#define NSBITS_DEFAULT 96 /* = NSBITS( NBR_128 ); */
extern int rndprc;
extern void ei_mdenorm ( EMUSHORT *si, int lost, int subflag, EMUSHORT *exp, int rcontrol, int nb );
extern void pack ( EMUSHORT *ee, EMUSHORT *ei, int nb );
extern void ei_copy ( EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_copyzlgw ( EMUSHORT *eia, EMUSHORT *eib, int nb );
extern int ei_cmp ( EMUSHORT *ai, EMUSHORT *bi, int nb );
extern void ei_convert ( EMUSHORT *eia, EMUSHORT *eib, int nba, int nbb );
extern void ei_add ( EMUSHORT *eic, EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_sub ( EMUSHORT *eic, EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_div ( EMUSHORT *eic, EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_mul ( EMUSHORT *eic, EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_ltor ( EMUSHORT *ei, EMUSHORT *lp, int nb, int nlp );
extern void ei_ultor ( EMUSHORT *ei, EMUSHORT *lp, int nb, int nlp );
extern void ei_rtoul_frac ( EMUSHORT *lp, EMUSHORT *frac, EMUSHORT *ei, int nlp, int nb );
extern void ei_rtol_frac ( EMUSHORT *lp, EMUSHORT *frac, EMUSHORT *ei, int nlp, int nb );
/***************************************************************
GENERATORS OF CONSTANT:
*/
extern void _gen_zero ( EMUSHORT *eia, int nb );
extern void _gen_half ( EMUSHORT *eia, int nb );
extern void _gen_one ( EMUSHORT *eia, int nb );
extern void _gen_two ( EMUSHORT *eia, int nb );
extern void _gen_ten ( EMUSHORT *eia, int nb );
extern void _gen_mten ( EMUSHORT *eia, int nb );
extern void _gen_32 ( EMUSHORT *eia, int nb );
/*
END GENERATORS OF CONSTANT.
***************************************************************/
extern void ei_remain ( EMUSHORT *eic, EMUSHORT *eiquot, EMUSHORT *eia, EMUSHORT *eib, int nb );
extern void ei_floor ( EMUSHORT *eic, EMUSHORT *eia, int nb );
extern void ei_ceil ( EMUSHORT *eic, EMUSHORT *eia, int nb );
extern void ei_round ( EMUSHORT *eic, EMUSHORT *eia, int nb );
extern void ei_frexp ( EMUSHORT *eis, EMUSHORT *lpexp, EMUSHORT *eia, int nlp, int nb );
extern void ei_ldexp ( EMUSHORT *eic, EMUSHORT *lppwr2, EMUSHORT *eia, int nlp, int nb );
extern void ei_logb ( EMUSHORT *lpbase2, EMUSHORT *eia, int nlp, int nb );
extern void ei_sqrt ( EMUSHORT *eic, EMUSHORT *eia, int nb );
#ifdef __cplusplus
} /* ... extern "C" */
#endif
#endif /* __MPU_REAL_H */
|