atof-ieee.c revision 60484
1/* atof_ieee.c - turn a Flonum into an IEEE floating point number
2   Copyright (C) 1987, 92, 93, 94, 95, 96, 97, 98, 99, 2000
3   Free Software Foundation, Inc.
4
5   This file is part of GAS, the GNU Assembler.
6
7   GAS is free software; you can redistribute it and/or modify
8   it under the terms of the GNU General Public License as published by
9   the Free Software Foundation; either version 2, or (at your option)
10   any later version.
11
12   GAS is distributed in the hope that it will be useful,
13   but WITHOUT ANY WARRANTY; without even the implied warranty of
14   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15   GNU General Public License for more details.
16
17   You should have received a copy of the GNU General Public License
18   along with GAS; see the file COPYING.  If not, write to the Free
19   Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20   02111-1307, USA.  */
21
22#include "as.h"
23
24/* Flonums returned here.  */
25extern FLONUM_TYPE generic_floating_point_number;
26
27static int next_bits PARAMS ((int));
28static void unget_bits PARAMS ((int));
29static void make_invalid_floating_point_number PARAMS ((LITTLENUM_TYPE *));
30
31extern const char EXP_CHARS[];
32/* Precision in LittleNums. */
33/* Don't count the gap in the m68k extended precision format.  */
34#define MAX_PRECISION (5)
35#define F_PRECISION (2)
36#define D_PRECISION (4)
37#define X_PRECISION (5)
38#define P_PRECISION (5)
39
40/* Length in LittleNums of guard bits. */
41#define GUARD (2)
42
43static const unsigned long mask[] =
44{
45  0x00000000,
46  0x00000001,
47  0x00000003,
48  0x00000007,
49  0x0000000f,
50  0x0000001f,
51  0x0000003f,
52  0x0000007f,
53  0x000000ff,
54  0x000001ff,
55  0x000003ff,
56  0x000007ff,
57  0x00000fff,
58  0x00001fff,
59  0x00003fff,
60  0x00007fff,
61  0x0000ffff,
62  0x0001ffff,
63  0x0003ffff,
64  0x0007ffff,
65  0x000fffff,
66  0x001fffff,
67  0x003fffff,
68  0x007fffff,
69  0x00ffffff,
70  0x01ffffff,
71  0x03ffffff,
72  0x07ffffff,
73  0x0fffffff,
74  0x1fffffff,
75  0x3fffffff,
76  0x7fffffff,
77  0xffffffff,
78};
79
80
81static int bits_left_in_littlenum;
82static int littlenums_left;
83static LITTLENUM_TYPE *littlenum_pointer;
84
85static int
86next_bits (number_of_bits)
87     int number_of_bits;
88{
89  int return_value;
90
91  if (!littlenums_left)
92    return (0);
93  if (number_of_bits >= bits_left_in_littlenum)
94    {
95      return_value = mask[bits_left_in_littlenum] & *littlenum_pointer;
96      number_of_bits -= bits_left_in_littlenum;
97      return_value <<= number_of_bits;
98
99      if (--littlenums_left)
100	{
101	  bits_left_in_littlenum = LITTLENUM_NUMBER_OF_BITS - number_of_bits;
102	  --littlenum_pointer;
103	  return_value |= (*littlenum_pointer >> bits_left_in_littlenum) & mask[number_of_bits];
104	}
105    }
106  else
107    {
108      bits_left_in_littlenum -= number_of_bits;
109      return_value = mask[number_of_bits] & (*littlenum_pointer >> bits_left_in_littlenum);
110    }
111  return (return_value);
112}
113
114/* Num had better be less than LITTLENUM_NUMBER_OF_BITS */
115static void
116unget_bits (num)
117     int num;
118{
119  if (!littlenums_left)
120    {
121      ++littlenum_pointer;
122      ++littlenums_left;
123      bits_left_in_littlenum = num;
124    }
125  else if (bits_left_in_littlenum + num > LITTLENUM_NUMBER_OF_BITS)
126    {
127      bits_left_in_littlenum = num - (LITTLENUM_NUMBER_OF_BITS - bits_left_in_littlenum);
128      ++littlenum_pointer;
129      ++littlenums_left;
130    }
131  else
132    bits_left_in_littlenum += num;
133}
134
135static void
136make_invalid_floating_point_number (words)
137     LITTLENUM_TYPE *words;
138{
139  as_bad (_("cannot create floating-point number"));
140  words[0] = (LITTLENUM_TYPE) ((unsigned) -1) >> 1; /* Zero the leftmost bit */
141  words[1] = (LITTLENUM_TYPE) -1;
142  words[2] = (LITTLENUM_TYPE) -1;
143  words[3] = (LITTLENUM_TYPE) -1;
144  words[4] = (LITTLENUM_TYPE) -1;
145  words[5] = (LITTLENUM_TYPE) -1;
146}
147
148/************************************************************************\
149 *	Warning: this returns 16-bit LITTLENUMs. It is up to the caller	*
150 *	to figure out any alignment problems and to conspire for the	*
151 *	bytes/word to be emitted in the right order. Bigendians beware!	*
152 *									*
153\************************************************************************/
154
155/* Note that atof-ieee always has X and P precisions enabled.  it is up
156   to md_atof to filter them out if the target machine does not support
157   them.  */
158
159/* Returns pointer past text consumed. */
160char *
161atof_ieee (str, what_kind, words)
162     char *str;			/* Text to convert to binary. */
163     int what_kind;		/* 'd', 'f', 'g', 'h' */
164     LITTLENUM_TYPE *words;	/* Build the binary here. */
165{
166  /* Extra bits for zeroed low-order bits.  The 1st MAX_PRECISION are
167     zeroed, the last contain flonum bits. */
168  static LITTLENUM_TYPE bits[MAX_PRECISION + MAX_PRECISION + GUARD];
169  char *return_value;
170  /* Number of 16-bit words in the format. */
171  int precision;
172  long exponent_bits;
173  FLONUM_TYPE save_gen_flonum;
174
175  /* We have to save the generic_floating_point_number because it
176     contains storage allocation about the array of LITTLENUMs where
177     the value is actually stored.  We will allocate our own array of
178     littlenums below, but have to restore the global one on exit.  */
179  save_gen_flonum = generic_floating_point_number;
180
181  return_value = str;
182  generic_floating_point_number.low = bits + MAX_PRECISION;
183  generic_floating_point_number.high = NULL;
184  generic_floating_point_number.leader = NULL;
185  generic_floating_point_number.exponent = 0;
186  generic_floating_point_number.sign = '\0';
187
188  /* Use more LittleNums than seems necessary: the highest flonum may
189     have 15 leading 0 bits, so could be useless. */
190
191  memset (bits, '\0', sizeof (LITTLENUM_TYPE) * MAX_PRECISION);
192
193  switch (what_kind)
194    {
195    case 'f':
196    case 'F':
197    case 's':
198    case 'S':
199      precision = F_PRECISION;
200      exponent_bits = 8;
201      break;
202
203    case 'd':
204    case 'D':
205    case 'r':
206    case 'R':
207      precision = D_PRECISION;
208      exponent_bits = 11;
209      break;
210
211    case 'x':
212    case 'X':
213    case 'e':
214    case 'E':
215      precision = X_PRECISION;
216      exponent_bits = 15;
217      break;
218
219    case 'p':
220    case 'P':
221
222      precision = P_PRECISION;
223      exponent_bits = -1;
224      break;
225
226    default:
227      make_invalid_floating_point_number (words);
228      return (NULL);
229    }
230
231  generic_floating_point_number.high
232    = generic_floating_point_number.low + precision - 1 + GUARD;
233
234  if (atof_generic (&return_value, ".", EXP_CHARS,
235		    &generic_floating_point_number))
236    {
237      make_invalid_floating_point_number (words);
238      return (NULL);
239    }
240  gen_to_words (words, precision, exponent_bits);
241
242  /* Restore the generic_floating_point_number's storage alloc (and
243     everything else).  */
244  generic_floating_point_number = save_gen_flonum;
245
246  return return_value;
247}
248
249/* Turn generic_floating_point_number into a real float/double/extended.  */
250int
251gen_to_words (words, precision, exponent_bits)
252     LITTLENUM_TYPE *words;
253     int precision;
254     long exponent_bits;
255{
256  int return_value = 0;
257
258  long exponent_1;
259  long exponent_2;
260  long exponent_3;
261  long exponent_4;
262  int exponent_skippage;
263  LITTLENUM_TYPE word1;
264  LITTLENUM_TYPE *lp;
265  LITTLENUM_TYPE *words_end;
266
267  words_end = words + precision;
268#ifdef TC_M68K
269  if (precision == X_PRECISION)
270    /* On the m68k the extended precision format has a gap of 16 bits
271       between the exponent and the mantissa.  */
272    words_end++;
273#endif
274
275  if (generic_floating_point_number.low > generic_floating_point_number.leader)
276    {
277      /* 0.0e0 seen. */
278      if (generic_floating_point_number.sign == '+')
279	words[0] = 0x0000;
280      else
281	words[0] = 0x8000;
282      memset (&words[1], '\0',
283	      (words_end - words - 1) * sizeof (LITTLENUM_TYPE));
284      return (return_value);
285    }
286
287  /* NaN:  Do the right thing */
288  if (generic_floating_point_number.sign == 0)
289    {
290      if (precision == F_PRECISION)
291	{
292	  words[0] = 0x7fff;
293	  words[1] = 0xffff;
294	}
295      else if (precision == X_PRECISION)
296	{
297#ifdef TC_M68K
298	  words[0] = 0x7fff;
299	  words[1] = 0;
300	  words[2] = 0xffff;
301	  words[3] = 0xffff;
302	  words[4] = 0xffff;
303	  words[5] = 0xffff;
304#else /* ! TC_M68K */
305#ifdef TC_I386
306	  words[0] = 0xffff;
307	  words[1] = 0xc000;
308	  words[2] = 0;
309	  words[3] = 0;
310	  words[4] = 0;
311#else /* ! TC_I386 */
312	  abort ();
313#endif /* ! TC_I386 */
314#endif /* ! TC_M68K */
315	}
316      else
317	{
318	  words[0] = 0x7fff;
319	  words[1] = 0xffff;
320	  words[2] = 0xffff;
321	  words[3] = 0xffff;
322	}
323      return return_value;
324    }
325  else if (generic_floating_point_number.sign == 'P')
326    {
327      /* +INF:  Do the right thing */
328      if (precision == F_PRECISION)
329	{
330	  words[0] = 0x7f80;
331	  words[1] = 0;
332	}
333      else if (precision == X_PRECISION)
334	{
335#ifdef TC_M68K
336	  words[0] = 0x7fff;
337	  words[1] = 0;
338	  words[2] = 0;
339	  words[3] = 0;
340	  words[4] = 0;
341	  words[5] = 0;
342#else /* ! TC_M68K */
343#ifdef TC_I386
344	  words[0] = 0x7fff;
345	  words[1] = 0x8000;
346	  words[2] = 0;
347	  words[3] = 0;
348	  words[4] = 0;
349#else /* ! TC_I386 */
350	  abort ();
351#endif /* ! TC_I386 */
352#endif /* ! TC_M68K */
353	}
354      else
355	{
356	  words[0] = 0x7ff0;
357	  words[1] = 0;
358	  words[2] = 0;
359	  words[3] = 0;
360	}
361      return (return_value);
362    }
363  else if (generic_floating_point_number.sign == 'N')
364    {
365      /* Negative INF */
366      if (precision == F_PRECISION)
367	{
368	  words[0] = 0xff80;
369	  words[1] = 0x0;
370	}
371      else if (precision == X_PRECISION)
372	{
373#ifdef TC_M68K
374	  words[0] = 0xffff;
375	  words[1] = 0;
376	  words[2] = 0;
377	  words[3] = 0;
378	  words[4] = 0;
379	  words[5] = 0;
380#else /* ! TC_M68K */
381#ifdef TC_I386
382	  words[0] = 0xffff;
383	  words[1] = 0x8000;
384	  words[2] = 0;
385	  words[3] = 0;
386	  words[4] = 0;
387#else /* ! TC_I386 */
388	  abort ();
389#endif /* ! TC_I386 */
390#endif /* ! TC_M68K */
391	}
392      else
393	{
394	  words[0] = 0xfff0;
395	  words[1] = 0x0;
396	  words[2] = 0x0;
397	  words[3] = 0x0;
398	}
399      return (return_value);
400    }
401  /*
402   * The floating point formats we support have:
403   * Bit 15 is sign bit.
404   * Bits 14:n are excess-whatever exponent.
405   * Bits n-1:0 (if any) are most significant bits of fraction.
406   * Bits 15:0 of the next word(s) are the next most significant bits.
407   *
408   * So we need: number of bits of exponent, number of bits of
409   * mantissa.
410   */
411  bits_left_in_littlenum = LITTLENUM_NUMBER_OF_BITS;
412  littlenum_pointer = generic_floating_point_number.leader;
413  littlenums_left = (1
414		     + generic_floating_point_number.leader
415		     - generic_floating_point_number.low);
416  /* Seek (and forget) 1st significant bit */
417  for (exponent_skippage = 0; !next_bits (1); ++exponent_skippage);;
418  exponent_1 = (generic_floating_point_number.exponent
419		+ generic_floating_point_number.leader
420		+ 1
421		- generic_floating_point_number.low);
422  /* Radix LITTLENUM_RADIX, point just higher than
423     generic_floating_point_number.leader. */
424  exponent_2 = exponent_1 * LITTLENUM_NUMBER_OF_BITS;
425  /* Radix 2. */
426  exponent_3 = exponent_2 - exponent_skippage;
427  /* Forget leading zeros, forget 1st bit. */
428  exponent_4 = exponent_3 + ((1 << (exponent_bits - 1)) - 2);
429  /* Offset exponent. */
430
431  lp = words;
432
433  /* Word 1. Sign, exponent and perhaps high bits. */
434  word1 = ((generic_floating_point_number.sign == '+')
435	   ? 0
436	   : (1 << (LITTLENUM_NUMBER_OF_BITS - 1)));
437
438  /* Assume 2's complement integers. */
439  if (exponent_4 <= 0)
440    {
441      int prec_bits;
442      int num_bits;
443
444      unget_bits (1);
445      num_bits = -exponent_4;
446      prec_bits = LITTLENUM_NUMBER_OF_BITS * precision - (exponent_bits + 1 + num_bits);
447#ifdef TC_I386
448      if (precision == X_PRECISION && exponent_bits == 15)
449	{
450	  /* On the i386 a denormalized extended precision float is
451	     shifted down by one, effectively decreasing the exponent
452	     bias by one.  */
453	  prec_bits -= 1;
454	  num_bits += 1;
455	}
456#endif
457
458      if (num_bits >= LITTLENUM_NUMBER_OF_BITS - exponent_bits)
459	{
460	  /* Bigger than one littlenum */
461	  num_bits -= (LITTLENUM_NUMBER_OF_BITS - 1) - exponent_bits;
462	  *lp++ = word1;
463	  if (num_bits + exponent_bits + 1 > precision * LITTLENUM_NUMBER_OF_BITS)
464	    {
465	      /* Exponent overflow */
466	      make_invalid_floating_point_number (words);
467	      return (return_value);
468	    }
469#ifdef TC_M68K
470	  if (precision == X_PRECISION && exponent_bits == 15)
471	    *lp++ = 0;
472#endif
473	  while (num_bits >= LITTLENUM_NUMBER_OF_BITS)
474	    {
475	      num_bits -= LITTLENUM_NUMBER_OF_BITS;
476	      *lp++ = 0;
477	    }
478	  if (num_bits)
479	    *lp++ = next_bits (LITTLENUM_NUMBER_OF_BITS - (num_bits));
480	}
481      else
482	{
483	  if (precision == X_PRECISION && exponent_bits == 15)
484	    {
485	      *lp++ = word1;
486#ifdef TC_M68K
487	      *lp++ = 0;
488#endif
489	      *lp++ = next_bits (LITTLENUM_NUMBER_OF_BITS - num_bits);
490	    }
491	  else
492	    {
493	      word1 |= next_bits ((LITTLENUM_NUMBER_OF_BITS - 1) - (exponent_bits + num_bits));
494	      *lp++ = word1;
495	    }
496	}
497      while (lp < words_end)
498	*lp++ = next_bits (LITTLENUM_NUMBER_OF_BITS);
499
500      /* Round the mantissa up, but don't change the number */
501      if (next_bits (1))
502	{
503	  --lp;
504	  if (prec_bits >= LITTLENUM_NUMBER_OF_BITS)
505	    {
506	      int n = 0;
507	      int tmp_bits;
508
509	      n = 0;
510	      tmp_bits = prec_bits;
511	      while (tmp_bits > LITTLENUM_NUMBER_OF_BITS)
512		{
513		  if (lp[n] != (LITTLENUM_TYPE) - 1)
514		    break;
515		  --n;
516		  tmp_bits -= LITTLENUM_NUMBER_OF_BITS;
517		}
518	      if (tmp_bits > LITTLENUM_NUMBER_OF_BITS
519		  || (lp[n] & mask[tmp_bits]) != mask[tmp_bits]
520		  || (prec_bits != (precision * LITTLENUM_NUMBER_OF_BITS
521				    - exponent_bits - 1)
522#ifdef TC_I386
523		      /* An extended precision float with only the integer
524			 bit set would be invalid.  That must be converted
525			 to the smallest normalized number.  */
526		      && !(precision == X_PRECISION
527			   && prec_bits == (precision * LITTLENUM_NUMBER_OF_BITS
528					    - exponent_bits - 2))
529#endif
530		      ))
531		{
532		  unsigned long carry;
533
534		  for (carry = 1; carry && (lp >= words); lp--)
535		    {
536		      carry = *lp + carry;
537		      *lp = carry;
538		      carry >>= LITTLENUM_NUMBER_OF_BITS;
539		    }
540		}
541	      else
542		{
543		  /* This is an overflow of the denormal numbers.  We
544                     need to forget what we have produced, and instead
545                     generate the smallest normalized number.  */
546		  lp = words;
547		  word1 = ((generic_floating_point_number.sign == '+')
548			   ? 0
549			   : (1 << (LITTLENUM_NUMBER_OF_BITS - 1)));
550		  word1 |= (1
551			    << ((LITTLENUM_NUMBER_OF_BITS - 1)
552				- exponent_bits));
553		  *lp++ = word1;
554#ifdef TC_I386
555		  /* Set the integer bit in the extended precision format.
556		     This cannot happen on the m68k where the mantissa
557		     just overflows into the integer bit above.  */
558		  if (precision == X_PRECISION)
559		    *lp++ = 1 << (LITTLENUM_NUMBER_OF_BITS - 1);
560#endif
561		  while (lp < words_end)
562		    *lp++ = 0;
563		}
564	    }
565	  else
566	    *lp += 1;
567	}
568
569      return return_value;
570    }
571  else if ((unsigned long) exponent_4 >= mask[exponent_bits])
572    {
573      /*
574       * Exponent overflow. Lose immediately.
575       */
576
577      /*
578       * We leave return_value alone: admit we read the
579       * number, but return a floating exception
580       * because we can't encode the number.
581       */
582      make_invalid_floating_point_number (words);
583      return return_value;
584    }
585  else
586    {
587      word1 |= (exponent_4 << ((LITTLENUM_NUMBER_OF_BITS - 1) - exponent_bits))
588	| next_bits ((LITTLENUM_NUMBER_OF_BITS - 1) - exponent_bits);
589    }
590
591  *lp++ = word1;
592
593  /* X_PRECISION is special: on the 68k, it has 16 bits of zero in the
594     middle.  Either way, it is then followed by a 1 bit. */
595  if (exponent_bits == 15 && precision == X_PRECISION)
596    {
597#ifdef TC_M68K
598      *lp++ = 0;
599#endif
600      *lp++ = (1 << (LITTLENUM_NUMBER_OF_BITS - 1)
601	       | next_bits (LITTLENUM_NUMBER_OF_BITS - 1));
602    }
603
604  /* The rest of the words are just mantissa bits. */
605  while (lp < words_end)
606    *lp++ = next_bits (LITTLENUM_NUMBER_OF_BITS);
607
608  if (next_bits (1))
609    {
610      unsigned long carry;
611      /*
612       * Since the NEXT bit is a 1, round UP the mantissa.
613       * The cunning design of these hidden-1 floats permits
614       * us to let the mantissa overflow into the exponent, and
615       * it 'does the right thing'. However, we lose if the
616       * highest-order bit of the lowest-order word flips.
617       * Is that clear?
618       */
619
620      /* #if (sizeof(carry)) < ((sizeof(bits[0]) * BITS_PER_CHAR) + 2)
621	 Please allow at least 1 more bit in carry than is in a LITTLENUM.
622	 We need that extra bit to hold a carry during a LITTLENUM carry
623	 propagation. Another extra bit (kept 0) will assure us that we
624	 don't get a sticky sign bit after shifting right, and that
625	 permits us to propagate the carry without any masking of bits.
626	 #endif */
627      for (carry = 1, lp--; carry; lp--)
628	{
629	  carry = *lp + carry;
630	  *lp = carry;
631	  carry >>= LITTLENUM_NUMBER_OF_BITS;
632	  if (lp == words)
633	    break;
634	}
635      if (precision == X_PRECISION && exponent_bits == 15)
636	{
637	  /* Extended precision numbers have an explicit integer bit
638	     that we may have to restore.  */
639	  if (lp == words)
640	    {
641#ifdef TC_M68K
642	      /* On the m68k there is a gap of 16 bits.  We must
643		 explicitly propagate the carry into the exponent. */
644	      words[0] += words[1];
645	      words[1] = 0;
646	      lp++;
647#endif
648	      /* Put back the integer bit.  */
649	      lp[1] |= 1 << (LITTLENUM_NUMBER_OF_BITS - 1);
650	    }
651 	}
652      if ((word1 ^ *words) & (1 << (LITTLENUM_NUMBER_OF_BITS - 1)))
653	{
654	  /* We leave return_value alone: admit we read the
655	   * number, but return a floating exception
656	   * because we can't encode the number.
657	   */
658	  *words &= ~(1 << (LITTLENUM_NUMBER_OF_BITS - 1));
659	  /* make_invalid_floating_point_number (words); */
660	  /* return return_value; */
661	}
662    }
663  return (return_value);
664}
665
666#if 0 /* unused */
667/* This routine is a real kludge.  Someone really should do it better,
668   but I'm too lazy, and I don't understand this stuff all too well
669   anyway. (JF)  */
670static void
671int_to_gen (x)
672     long x;
673{
674  char buf[20];
675  char *bufp;
676
677  sprintf (buf, "%ld", x);
678  bufp = &buf[0];
679  if (atof_generic (&bufp, ".", EXP_CHARS, &generic_floating_point_number))
680    as_bad (_("Error converting number to floating point (Exponent overflow?)"));
681}
682#endif
683
684#ifdef TEST
685char *
686print_gen (gen)
687     FLONUM_TYPE *gen;
688{
689  FLONUM_TYPE f;
690  LITTLENUM_TYPE arr[10];
691  double dv;
692  float fv;
693  static char sbuf[40];
694
695  if (gen)
696    {
697      f = generic_floating_point_number;
698      generic_floating_point_number = *gen;
699    }
700  gen_to_words (&arr[0], 4, 11);
701  memcpy (&dv, &arr[0], sizeof (double));
702  sprintf (sbuf, "%x %x %x %x %.14G   ", arr[0], arr[1], arr[2], arr[3], dv);
703  gen_to_words (&arr[0], 2, 8);
704  memcpy (&fv, &arr[0], sizeof (float));
705  sprintf (sbuf + strlen (sbuf), "%x %x %.12g\n", arr[0], arr[1], fv);
706
707  if (gen)
708    {
709      generic_floating_point_number = f;
710    }
711
712  return (sbuf);
713}
714
715#endif
716
717/* end of atof-ieee.c */
718