Embedded Artistry libc
C Standard Library Support for Bare-metal Systems
strtopdd.c File Reference
#include "gdtoaimp.h"
Include dependency graph for strtopdd.c:

Go to the source code of this file.

Functions

int strtopdd (CONST char *s, char **sp, double *dd)
 

Function Documentation

◆ strtopdd()

int strtopdd ( CONST char *  s,
char **  sp,
double *  dd 
)

Definition at line 40 of file strtopdd.c.

42 {
43 #ifdef Sudden_Underflow
44  static FPI fpi = {106, 1 - 1023, 2046 - 1023 - 106 + 1, 1, 1};
45 #else
46  static FPI fpi = {106, 1 - 1023 - 53 + 1, 2046 - 1023 - 106 + 1, 1, 0};
47 #endif
48  ULong bits[4];
49  Long exp;
50  int i, j, rv;
51  typedef union
52  {
53  double d[2];
54  ULong L[4];
55  } U2;
56  U2* u;
57 
58  rv = strtodg(s, sp, &fpi, &exp, bits);
59  u = (U2*)dd;
60  switch(rv & STRTOG_Retmask)
61  {
62  case STRTOG_NoNumber:
63  case STRTOG_Zero:
64  u->d[0] = u->d[1] = 0.;
65  break;
66 
67  case STRTOG_Normal:
68  u->L[_1] = (bits[1] >> 21 | bits[2] << 11) & 0xffffffffL;
69  u->L[_0] =
70  bits[2] >> 21 | (bits[3] << 11 & 0xfffff) | (unsigned)((exp + 0x3ff + 105) << 20);
71  exp += 0x3ff + 52;
72  if(bits[1] &= 0x1fffff)
73  {
74  i = hi0bits(bits[1]) - 11;
75  if(i >= exp)
76  {
77  i = exp - 1;
78  exp = 0;
79  }
80  else
81  {
82  {
83  exp -= i;
84  }
85  }
86  if(i > 0)
87  {
88  bits[1] = bits[1] << i | bits[0] >> (32 - i);
89  bits[0] = bits[0] << i & 0xffffffffL;
90  }
91  }
92  else if(bits[0])
93  {
94  i = hi0bits(bits[0]) + 21;
95  if(i >= exp)
96  {
97  i = exp - 1;
98  exp = 0;
99  }
100  else
101  {
102  {
103  exp -= i;
104  }
105  }
106  if(i < 32)
107  {
108  bits[1] = bits[0] >> (32 - i);
109  bits[0] = bits[0] << i & 0xffffffffL;
110  }
111  else
112  {
113  bits[1] = bits[0] << (i - 32);
114  bits[0] = 0;
115  }
116  }
117  else
118  {
119  u->L[2] = u->L[3] = 0;
120  break;
121  }
122  u->L[2 + _1] = bits[0];
123  u->L[2 + _0] = (bits[1] & 0xfffff) | (unsigned)(exp << 20);
124  break;
125 
126  case STRTOG_Denormal:
127  if(bits[3])
128  {
129  {
130  goto nearly_normal;
131  }
132  }
133  if(bits[2])
134  {
135  {
136  goto partly_normal;
137  }
138  }
139  if(bits[1] & 0xffe00000)
140  {
141  {
142  goto hardly_normal;
143  }
144  }
145  /* completely denormal */
146  u->L[2] = u->L[3] = 0;
147  u->L[_1] = bits[0];
148  u->L[_0] = bits[1];
149  break;
150 
151  nearly_normal:
152  i = hi0bits(bits[3]) - 11; /* i >= 12 */
153  j = 32 - i;
154  u->L[_0] = ((bits[3] << i | bits[2] >> j) & 0xfffff) | (unsigned)((65 - i) << 20);
155  u->L[_1] = (bits[2] << i | bits[1] >> j) & 0xffffffffL;
156  u->L[2 + _0] = bits[1] & (1L << j) - 1;
157  u->L[2 + _1] = bits[0];
158  break;
159 
160  partly_normal:
161  i = hi0bits(bits[2]) - 11;
162  if(i < 0)
163  {
164  j = -i;
165  i += 32;
166  u->L[_0] = (bits[2] >> j & 0xfffff) | (unsigned)((33 + j) << 20);
167  u->L[_1] = (bits[2] << i | bits[1] >> j) & 0xffffffffL;
168  u->L[2 + _0] = bits[1] & (1L << j) - 1;
169  u->L[2 + _1] = bits[0];
170  break;
171  }
172  if(i == 0)
173  {
174  u->L[_0] = (bits[2] & 0xfffff) | 33 << 20;
175  u->L[_1] = bits[1];
176  u->L[2 + _0] = 0;
177  u->L[2 + _1] = bits[0];
178  break;
179  }
180  j = 32 - i;
181  u->L[_0] = ((bits[2] << i | bits[1] >> j) & 0xfffff) | (unsigned)((j + 1) << 20);
182  u->L[_1] = (bits[1] << i | bits[0] >> j) & 0xffffffffL;
183  u->L[2 + _0] = 0;
184  u->L[2 + _1] = bits[0] & (1L << j) - 1;
185  break;
186 
187  hardly_normal:
188  j = 11 - hi0bits(bits[1]);
189  i = 32 - j;
190  u->L[_0] = (bits[1] >> j & 0xfffff) | (unsigned)((j + 1) << 20);
191  u->L[_1] = (bits[1] << i | bits[0] >> j) & 0xffffffffL;
192  u->L[2 + _0] = 0;
193  u->L[2 + _1] = bits[0] & (1L << j) - 1;
194  break;
195 
196  case STRTOG_Infinite:
197  u->L[_0] = u->L[2 + _0] = 0x7ff00000;
198  u->L[_1] = u->L[2 + _1] = 0;
199  break;
200 
201  case STRTOG_NaN:
202  u->L[0] = u->L[2] = d_QNAN0;
203  u->L[1] = u->L[3] = d_QNAN1;
204  }
205  if(rv & STRTOG_Neg)
206  {
207  u->L[_0] |= 0x80000000L;
208  u->L[2 + _0] |= 0x80000000L;
209  }
210  return rv;
211 }
#define hi0bits(x)
Definition: gdtoaimp.h:525
unsigned Long ULong
Definition: gdtoa.h:41
Definition: gdtoa.h:86
#define Long
Definition: gdtoa.h:38
int strtodg(CONST char *s00, char **se, FPI *fpi, Long *exp, ULong *bits)
Definition: strtodg.c:443

References hi0bits, Long, strtodg(), STRTOG_Denormal, STRTOG_Infinite, STRTOG_NaN, STRTOG_Neg, STRTOG_NoNumber, STRTOG_Normal, STRTOG_Retmask, and STRTOG_Zero.