xref: /csrg-svn/old/as.vax/bignum2.c (revision 5803)
1*5803Srrh /*
2*5803Srrh  *	Copyright (c) 1982 Regents of the University of California
3*5803Srrh  */
4*5803Srrh #ifndef lint
5*5803Srrh static char sccsid[] = "@(#)bignum2.c 4.1 02/14/82";
6*5803Srrh #endif not lint
7*5803Srrh 
8*5803Srrh #include <stdio.h>
9*5803Srrh #include "as.h"
10*5803Srrh Bignum	Znumber;			/* zero reference */
11*5803Srrh #define	MINEXP		-32768		/* never generate; reserved for id 0 */
12*5803Srrh 
13*5803Srrh Bignum intconvert(number, convto)
14*5803Srrh 	Bignum	number;
15*5803Srrh 	int	convto;
16*5803Srrh {
17*5803Srrh 	reg	int	i;
18*5803Srrh 	if (number.num_tag == convto)
19*5803Srrh 		return(number);
20*5803Srrh 	if (ty_nbyte[number.num_tag] > ty_nbyte[convto] && (passno == 2)){
21*5803Srrh 		yywarning("Conversion between %s and %s looses significance",
22*5803Srrh 			ty_string[number.num_tag],
23*5803Srrh 			ty_string[convto]);
24*5803Srrh 	}
25*5803Srrh 	for (i = ty_nbyte[convto]; i < ty_nbyte[TYPO]; i++)
26*5803Srrh 		number.num_uchar[i] = 0;
27*5803Srrh 	return(number);
28*5803Srrh }
29*5803Srrh 
30*5803Srrh #define	CONV(src, dst)	(((src) << TYPLG) + (dst))
31*5803Srrh 
32*5803Srrh Bignum floatconvert(number, convto)
33*5803Srrh 	Bignum	number;
34*5803Srrh 	int	convto;
35*5803Srrh {
36*5803Srrh 	reg	u_int	*bp;		/* r11 */
37*5803Srrh 		int	loss = 0;
38*5803Srrh 		int	gain = 0;
39*5803Srrh 		int	mixs = 0;
40*5803Srrh 		Ovf	ovf;
41*5803Srrh 
42*5803Srrh 	if (number.num_tag == convto)
43*5803Srrh 		return(number);
44*5803Srrh 	bp = &number.num_uint[0];
45*5803Srrh #ifdef lint
46*5803Srrh 	*bp = *bp;
47*5803Srrh #endif lint
48*5803Srrh 
49*5803Srrh 	switch(CONV(number.num_tag, convto)){
50*5803Srrh 
51*5803Srrh 	case CONV(TYPF, TYPD):	asm("cvtfd (r11), (r11)"); break;
52*5803Srrh 	case CONV(TYPF, TYPG):	mixs++; break;
53*5803Srrh 	case CONV(TYPF, TYPH):	mixs++; break;
54*5803Srrh 
55*5803Srrh 	case CONV(TYPD, TYPF):	asm("cvtdf (r11), (r11)"); break;
56*5803Srrh 	case CONV(TYPD, TYPG):	mixs++; break;
57*5803Srrh 	case CONV(TYPD, TYPH):	mixs++; break;
58*5803Srrh 
59*5803Srrh 	case CONV(TYPG, TYPF):	mixs++; break;
60*5803Srrh 	case CONV(TYPG, TYPD):	mixs++; break;
61*5803Srrh 	case CONV(TYPG, TYPH):	mixs++; break;
62*5803Srrh 
63*5803Srrh 	case CONV(TYPH, TYPF):	mixs++; break;
64*5803Srrh 	case CONV(TYPH, TYPD):	mixs++; break;
65*5803Srrh 	case CONV(TYPH, TYPG):	mixs++; break;
66*5803Srrh 	default:	panic("Bad floating point conversion?");
67*5803Srrh 	}
68*5803Srrh 	if ((gain || mixs || loss) && (passno == 2)){
69*5803Srrh 		yywarning("Converting from %s to %s: %s ",
70*5803Srrh 			ty_string[number.num_tag],
71*5803Srrh 			ty_string[convto],
72*5803Srrh 			gain ? "gains significance" :
73*5803Srrh 			(loss ? "looses significance" : "mixs exponent formats")
74*5803Srrh 		);
75*5803Srrh 	}
76*5803Srrh 	if (mixs){
77*5803Srrh 		number = bignumconvert(number, convto, &ovf);
78*5803Srrh 		if (ovf && passno == 2){
79*5803Srrh 			yywarning("Floating conversion over/underflowed\n");
80*5803Srrh 		}
81*5803Srrh 	} else {
82*5803Srrh 		number.num_tag = convto;
83*5803Srrh 	}
84*5803Srrh 	return(number);
85*5803Srrh }
86*5803Srrh 
87*5803Srrh /*
88*5803Srrh  *	Convert a big number between various representations
89*5803Srrh  */
90*5803Srrh Bignum bignumconvert(number, toconv, ovfp)
91*5803Srrh 	Bignum	number;
92*5803Srrh 	int	toconv;
93*5803Srrh 	Ovf	*ovfp;
94*5803Srrh {
95*5803Srrh 	int	tag;
96*5803Srrh 
97*5803Srrh 	*ovfp = 0;
98*5803Srrh 	tag = number.num_tag;
99*5803Srrh 	if (tag == toconv)
100*5803Srrh 		return(number);
101*5803Srrh 	if (tag == TYPUNPACKED){
102*5803Srrh 		return(bignumpack(number, toconv, ovfp));
103*5803Srrh 	}
104*5803Srrh 	if (toconv == TYPUNPACKED){
105*5803Srrh 		return(bignumunpack(number, ovfp));
106*5803Srrh 	}
107*5803Srrh 	return(bignumpack(bignumunpack(number, ovfp), toconv, ovfp));
108*5803Srrh }
109*5803Srrh 
110*5803Srrh Bignum bignumunpack(Packed, ovfp)
111*5803Srrh 	Bignum	Packed;
112*5803Srrh 		Ovf	*ovfp;
113*5803Srrh {
114*5803Srrh 		Bignum	Mantissa;
115*5803Srrh 		Bignum	Enumber;
116*5803Srrh 	reg	int	i;
117*5803Srrh 		int	j;
118*5803Srrh 		int	k;
119*5803Srrh 	reg	struct	ty_bigdesc	*p;
120*5803Srrh 	reg	chptr	packed;
121*5803Srrh 	reg	chptr	mantissa;
122*5803Srrh 	reg	chptr	enumber;
123*5803Srrh 		u_short	exponent;
124*5803Srrh 		int	sign;
125*5803Srrh 		int	mask;
126*5803Srrh 
127*5803Srrh 	p = &ty_bigdesc[Packed.num_tag];
128*5803Srrh 
129*5803Srrh 	*ovfp = 0;
130*5803Srrh 	Mantissa = Znumber;
131*5803Srrh 	sign = 0;
132*5803Srrh 	exponent = 0;
133*5803Srrh 	mantissa = CH_FIELD(Mantissa);
134*5803Srrh 	enumber = CH_FIELD(Enumber);
135*5803Srrh 	packed = CH_FIELD(Packed);
136*5803Srrh 
137*5803Srrh 	if (isclear(packed)){
138*5803Srrh 		Mantissa.num_tag = TYPUNPACKED;
139*5803Srrh 		Mantissa.num_exponent = MINEXP;
140*5803Srrh 		return(Mantissa);
141*5803Srrh 	}
142*5803Srrh 	/*
143*5803Srrh 	 *	map the packed number into the mantissa, using
144*5803Srrh 	 *	the unpacking map
145*5803Srrh 	 */
146*5803Srrh 	mapnumber(mantissa, packed, 16, p->b_upmmap);
147*5803Srrh 	/*
148*5803Srrh 	 *	perform the mantissa shifting.
149*5803Srrh 	 *	This may appear to overflow; all that is lost
150*5803Srrh 	 *	is low order bits of the exponent.
151*5803Srrh 	 */
152*5803Srrh 	(void)numshift(p->b_mlshift, mantissa, mantissa);
153*5803Srrh 	/*
154*5803Srrh 	 *	handle sign and exponent
155*5803Srrh 	 */
156*5803Srrh 	switch(Packed.num_tag){
157*5803Srrh 	case TYPB:
158*5803Srrh 	case TYPW:
159*5803Srrh 	case TYPL:
160*5803Srrh 	case TYPO:
161*5803Srrh 	case TYPQ:
162*5803Srrh 		sign = 0;
163*5803Srrh 		exponent = p->b_eexcess;
164*5803Srrh 		if (mantissa[HOC] & SIGNBIT){
165*5803Srrh 			sign = -1;
166*5803Srrh 			*ovfp |= numnegate(mantissa, mantissa);
167*5803Srrh 		}
168*5803Srrh 		/*
169*5803Srrh 		 *	Normalize the packed by left shifting,
170*5803Srrh 		 *	adjusting the exponent as we go.
171*5803Srrh 		 *	Do a binary weighted left shift for some speed.
172*5803Srrh 		 */
173*5803Srrh 		k = 0;
174*5803Srrh 		for (j = 4; j >= 0; --j){
175*5803Srrh 			i = 1 << j;	/* 16, 8, 4, 2, 1 */
176*5803Srrh 			while(1){
177*5803Srrh 				if (k >= p->b_msigbits)
178*5803Srrh 					break;
179*5803Srrh 				mask = ONES(i) << (CH_BITS - i);
180*5803Srrh 				if (mantissa[HOC] & mask)
181*5803Srrh 					break;
182*5803Srrh 				(void)numshift(i, mantissa, mantissa);
183*5803Srrh 				k += i;
184*5803Srrh 				exponent -= i;
185*5803Srrh 			}
186*5803Srrh 		}
187*5803Srrh 		assert(mantissa[HOC] & SIGNBIT, "integer <<ing");
188*5803Srrh 		/*
189*5803Srrh 		 *	now, kick the most significant bit off the top
190*5803Srrh 		 */
191*5803Srrh 		(void)numshift(1, mantissa, mantissa);
192*5803Srrh 		break;
193*5803Srrh 	default:
194*5803Srrh 		/*
195*5803Srrh 		 *	map the exponent into the local area.
196*5803Srrh 		 */
197*5803Srrh 		Enumber = Znumber;
198*5803Srrh 		mapnumber(enumber, packed, 2, p->b_upemap);
199*5803Srrh 		/*
200*5803Srrh 		 *	Extract the exponent, and get rid
201*5803Srrh 		 *	of the sign bit
202*5803Srrh 		 */
203*5803Srrh 		exponent = Enumber.num_ushort[0] & ONES(15);
204*5803Srrh 		/*
205*5803Srrh 		 *	shift the exponent, and get rid of high order
206*5803Srrh 		 *	trash
207*5803Srrh 		 */
208*5803Srrh 		exponent >>= p->b_ershift;
209*5803Srrh 		exponent &= ONES(p->b_esigbits);
210*5803Srrh 		/*
211*5803Srrh 		 *	un excess the exponent
212*5803Srrh 		 */
213*5803Srrh 		exponent -= p->b_eexcess;
214*5803Srrh 		/*
215*5803Srrh 		 *	extract and extend the sign bit
216*5803Srrh 		 */
217*5803Srrh 		sign = (Enumber.num_ushort[0] & ~ONES(15)) ? -1 : 0;
218*5803Srrh 	}
219*5803Srrh 	/*
220*5803Srrh 	 *	Assemble the pieces, and return the number
221*5803Srrh 	 */
222*5803Srrh 	Mantissa.num_tag = TYPUNPACKED;
223*5803Srrh 	Mantissa.num_sign = sign;
224*5803Srrh 	Mantissa.num_exponent = exponent;
225*5803Srrh 	return(Mantissa);
226*5803Srrh }
227*5803Srrh 
228*5803Srrh Bignum bignumpack(Unpacked, toconv, ovfp)
229*5803Srrh 	Bignum	Unpacked;
230*5803Srrh 	int	toconv;
231*5803Srrh 	Ovf	*ovfp;
232*5803Srrh {
233*5803Srrh 	Bignum	Back;
234*5803Srrh 	Bignum	Enumber;
235*5803Srrh 	Bignum	Temp;
236*5803Srrh 
237*5803Srrh 		short	exponent;
238*5803Srrh 		char	sign;
239*5803Srrh 	reg	struct	ty_bigdesc	*p;
240*5803Srrh 	reg	chptr	back;
241*5803Srrh 	reg	chptr	enumber;
242*5803Srrh 	reg	chptr	temp;
243*5803Srrh 	reg	chptr	unpacked;
244*5803Srrh 
245*5803Srrh 		int	i,j;
246*5803Srrh 
247*5803Srrh 	if (Unpacked.num_tag != TYPUNPACKED)
248*5803Srrh 		panic("Argument to bignumpack is not unpacked");
249*5803Srrh 
250*5803Srrh 	*ovfp = 0;
251*5803Srrh 	Back = Znumber;
252*5803Srrh 	Temp = Znumber;
253*5803Srrh 	Back.num_tag = toconv;
254*5803Srrh 
255*5803Srrh 	back = CH_FIELD(Back);
256*5803Srrh 	temp = CH_FIELD(Temp);
257*5803Srrh 	enumber = CH_FIELD(Enumber);
258*5803Srrh 	unpacked = CH_FIELD(Unpacked);
259*5803Srrh 	p = &ty_bigdesc[toconv];
260*5803Srrh 
261*5803Srrh 	exponent = Unpacked.num_exponent;
262*5803Srrh 	sign = Unpacked.num_sign;
263*5803Srrh 	if (exponent == MINEXP)
264*5803Srrh 		return(Back);	/* identically zero */
265*5803Srrh 
266*5803Srrh 	switch(toconv){
267*5803Srrh 	case TYPB:
268*5803Srrh 	case TYPW:
269*5803Srrh 	case TYPL:
270*5803Srrh 	case TYPQ:
271*5803Srrh 	case TYPO:
272*5803Srrh 		/*
273*5803Srrh 		 *	Put back in the assumed high order fraction
274*5803Srrh 		 *	bit that is always a 1.
275*5803Srrh 		 */
276*5803Srrh 		(void)numshift(-1, temp, unpacked);
277*5803Srrh 		temp[HOC] |= SIGNBIT;
278*5803Srrh 		if (exponent > p->b_eexcess){
279*5803Srrh 			/*
280*5803Srrh 			 *	Construct the largest positive integer
281*5803Srrh 			 */
282*5803Srrh 			(void)numclear(temp);
283*5803Srrh 			(void)num1comp(temp, temp);
284*5803Srrh 			temp[HOC] &= ~SIGNBIT;
285*5803Srrh 			sign = sign;
286*5803Srrh 			*ovfp |= OVF_OVERFLOW;
287*5803Srrh 		} else
288*5803Srrh 		if (exponent <= 0){
289*5803Srrh 			/*
290*5803Srrh 			 *	chop the temp; underflow to integer 0
291*5803Srrh 			 */
292*5803Srrh 			(void)numclear(temp);
293*5803Srrh 			sign = 0;
294*5803Srrh 			*ovfp |= OVF_UNDERFLOW;
295*5803Srrh 		} else {
296*5803Srrh 			/*
297*5803Srrh 			 *	denormalize the temp.
298*5803Srrh 			 *	This will again chop, by shifting
299*5803Srrh 			 *	bits off the right end into oblivion.
300*5803Srrh 			 */
301*5803Srrh 			for (j = 4; j >= 0; --j){
302*5803Srrh 				i = 1 << j;	/* 16, 8, 4, 2, 1 */
303*5803Srrh 				while(exponent + i <= p->b_eexcess){
304*5803Srrh 					numshift(-i, temp, temp);
305*5803Srrh 					exponent += i;
306*5803Srrh 				}
307*5803Srrh 			}
308*5803Srrh 		}
309*5803Srrh 		/*
310*5803Srrh 		 *	negate the temp if the sign is set
311*5803Srrh 		 */
312*5803Srrh 		if (sign)
313*5803Srrh 			*ovfp |= numnegate(temp, temp);
314*5803Srrh 		/*
315*5803Srrh 		 *	Stuff the temp number into the return area
316*5803Srrh 		 */
317*5803Srrh 		mapnumber(back, temp, 16, p->b_pmmap);
318*5803Srrh 		return(Back);
319*5803Srrh 	default:
320*5803Srrh 		/*
321*5803Srrh 		 *	Shift the mantissa to the right, filling in zeroes on
322*5803Srrh 		 *	the left.  This aligns the least significant bit
323*5803Srrh 		 *	on the bottom of a byte, something that upround
324*5803Srrh 		 *	will use.
325*5803Srrh 		 *	Put the result into a temporary.
326*5803Srrh 		 *	Even though the shift may be zero, there
327*5803Srrh 		 *	is still a copy involved here.
328*5803Srrh 		 */
329*5803Srrh 		(void)numshift(-(p->b_mlshift), temp, unpacked);
330*5803Srrh 		/*
331*5803Srrh 		 *	Perform the rounding by adding in 0.5 ulp's
332*5803Srrh 		 */
333*5803Srrh 		exponent = upround(&Temp, p, exponent);
334*5803Srrh 		/*
335*5803Srrh 		 *	Do a range check on the exponent, in preparation
336*5803Srrh 		 *	to stuffing it in.
337*5803Srrh 		 */
338*5803Srrh 		if ((short)(exponent + p->b_eexcess) == 0){
339*5803Srrh 			/*
340*5803Srrh 			 *	Sorry, no gradual underflow on the
341*5803Srrh 			 *	VAX.  Chop this beasty totally to zero
342*5803Srrh 			 */
343*5803Srrh 			goto zeroret;
344*5803Srrh 		} else
345*5803Srrh 		if ((short)(exponent + p->b_eexcess) < 0){
346*5803Srrh 			/*
347*5803Srrh 			 *	True underflow will happen;
348*5803Srrh 			 *	Chop everything to positive zero
349*5803Srrh 			 */
350*5803Srrh 		  zeroret:
351*5803Srrh 			(void)numclear(temp);
352*5803Srrh 			exponent = 0;
353*5803Srrh 			sign = 0;	/* avoid reserved operand! */
354*5803Srrh 			*ovfp |= OVF_UNDERFLOW;
355*5803Srrh 		} else
356*5803Srrh 		if ((unsigned)(exponent + p->b_eexcess)
357*5803Srrh 		    >= (unsigned)(1 << p->b_esigbits)){
358*5803Srrh 			/*
359*5803Srrh 			 *	Construct the largest magnitude possible
360*5803Srrh 			 *	floating point unpacked: 0.{1}111111111
361*5803Srrh 			 */
362*5803Srrh 			(void)numclear(temp);
363*5803Srrh 			(void)num1comp(temp, temp);
364*5803Srrh 			exponent = ONES(p->b_esigbits);
365*5803Srrh 			sign = sign;
366*5803Srrh 			*ovfp |= OVF_OVERFLOW;
367*5803Srrh 		} else {
368*5803Srrh 			/*
369*5803Srrh 			 *	The exponent will fit.
370*5803Srrh 			 *	Bias it up, and the common code will stuff it.
371*5803Srrh 			 */
372*5803Srrh 			exponent += p->b_eexcess;
373*5803Srrh 		}
374*5803Srrh 		exponent <<= p->b_ershift;
375*5803Srrh 		/*
376*5803Srrh 		 *	mask out trash for the sign, and put in the sign.
377*5803Srrh 		 */
378*5803Srrh 		exponent &= ONES(15);
379*5803Srrh 		if (sign)
380*5803Srrh 			exponent |= ~ONES(15);
381*5803Srrh 		Enumber.num_ushort[0] = exponent;
382*5803Srrh 		/*
383*5803Srrh 		 *	Map the unpacked exponent into the value going back
384*5803Srrh 		 */
385*5803Srrh 		mapnumber(back, enumber, 2, p->b_pemap);
386*5803Srrh 		/*
387*5803Srrh 		 *	Stuff the unpacked mantissa into the return area
388*5803Srrh 		 */
389*5803Srrh 		mapnumber(back, temp, 16, p->b_pmmap);
390*5803Srrh 		return(Back);
391*5803Srrh 	}
392*5803Srrh 	/*NOTREACHED*/
393*5803Srrh }
394*5803Srrh 
395*5803Srrh mapnumber(chp1, chp2, nbytes, themap)
396*5803Srrh 		chptr	chp1, chp2;
397*5803Srrh 		int	nbytes;
398*5803Srrh 		char	*themap;
399*5803Srrh {
400*5803Srrh 	reg	int	i;
401*5803Srrh 	reg	u_char	*p1, *p2;
402*5803Srrh 
403*5803Srrh 	p1 = (u_char *)chp1;
404*5803Srrh 	p2 = (u_char *)chp2;
405*5803Srrh 	for (i = 0; i < nbytes; i++){
406*5803Srrh 		switch(themap[i]){
407*5803Srrh 		case NOTAKE:
408*5803Srrh 			break;
409*5803Srrh 		default:
410*5803Srrh 			p1[themap[i]] |= p2[i];
411*5803Srrh 			break;
412*5803Srrh 		}
413*5803Srrh 	}
414*5803Srrh }
415*5803Srrh 
416*5803Srrh #define	UPSHIFT	2
417*5803Srrh /*
418*5803Srrh  *	round in 1/2 ulp in the number, possibly modifying
419*5803Srrh  *	the binary exponent if there was total carry out.
420*5803Srrh  *	Return the modified exponent
421*5803Srrh  */
422*5803Srrh int upround(numberp, p, exponent)
423*5803Srrh 	reg	Bignum	*numberp;
424*5803Srrh 	reg	struct	ty_bigdesc	*p;
425*5803Srrh 		int	exponent;
426*5803Srrh {
427*5803Srrh 	reg	u_char	*bytep;
428*5803Srrh 		int	nbytes;
429*5803Srrh 		int	byteindex;
430*5803Srrh 		int	hofractionbit;
431*5803Srrh 		int	ovffractionbit;
432*5803Srrh 	reg	int	ovfbitindex;
433*5803Srrh 	reg	chptr	number;
434*5803Srrh 	static	Bignum	ulp;
435*5803Srrh 
436*5803Srrh 	/*
437*5803Srrh 	 *	Find out the byte index of the byte containing the ulp
438*5803Srrh 	 */
439*5803Srrh 	number = CH_FIELD(numberp[0]);
440*5803Srrh 	bytep = numberp->num_uchar;
441*5803Srrh 
442*5803Srrh 	nbytes = (p->b_msigbits - 1) + p->b_mlshift;
443*5803Srrh 	assert((nbytes % 8) == 0, "mantissa sig bits");
444*5803Srrh 	nbytes /= 8;
445*5803Srrh 	byteindex = 15 - nbytes;
446*5803Srrh 	assert(byteindex >= 0, "ulp in outer space");
447*5803Srrh 	/*
448*5803Srrh 	 *	Shift the number to the right by two places,
449*5803Srrh 	 *	so that we can do full arithmetic without overflowing
450*5803Srrh 	 *	to the left.
451*5803Srrh 	 */
452*5803Srrh 	numshift(-UPSHIFT, number, number);
453*5803Srrh 	/*
454*5803Srrh 	 *	Construct the missing high order fraction bit
455*5803Srrh 	 */
456*5803Srrh 	ovfbitindex = 8 - (p->b_mlshift + UPSHIFT);
457*5803Srrh 	assert(ovfbitindex >= 0, "Shifted byte 15 into byte 14");
458*5803Srrh 	hofractionbit = (0x01 << ovfbitindex);
459*5803Srrh 	ovffractionbit = (0x02 << ovfbitindex);
460*5803Srrh 	bytep[15] |= hofractionbit;
461*5803Srrh 	/*
462*5803Srrh 	 *	construct the unit in the last place, and it
463*5803Srrh 	 *	to the fraction
464*5803Srrh 	 */
465*5803Srrh 	ulp.num_uchar[byteindex] |= (0x80 >> UPSHIFT);
466*5803Srrh 	numaddv(number, number, CH_FIELD(ulp));
467*5803Srrh 	ulp.num_uchar[byteindex] &= ~(0x80 >> UPSHIFT);
468*5803Srrh 	/*
469*5803Srrh 	 *	Check if there was an overflow,
470*5803Srrh 	 *	and adjust by shifting.
471*5803Srrh 	 *	Also, bring the number back into canonical
472*5803Srrh 	 *	unpacked form by left shifting by two to undeo
473*5803Srrh 	 *	what we did before.
474*5803Srrh 	 */
475*5803Srrh 	if (bytep[15] & ovffractionbit){
476*5803Srrh 		exponent += 1;
477*5803Srrh 		numshift(UPSHIFT - 1, number, number);
478*5803Srrh 	} else {
479*5803Srrh 		numshift(UPSHIFT, number, number);
480*5803Srrh 	}
481*5803Srrh 	/*
482*5803Srrh 	 *	Clear off trash in the unused bits of the high
483*5803Srrh 	 *	order byte of the number
484*5803Srrh 	 */
485*5803Srrh 	bytep[15] &= ONES(8 - p->b_mlshift);
486*5803Srrh 	return(exponent);
487*5803Srrh }
488*5803Srrh #ifdef DEBUG
489*5803Srrh bignumprint(number)
490*5803Srrh 	Bignum	number;
491*5803Srrh {
492*5803Srrh 	printf("Bignum: %s (exp: %d, sign: %d) 0x%08x%08x%08x%08x",
493*5803Srrh 		ty_string[number.num_tag],
494*5803Srrh 		number.num_exponent,
495*5803Srrh 		number.num_sign,
496*5803Srrh 		number.num_uint[3],
497*5803Srrh 		number.num_uint[2],
498*5803Srrh 		number.num_uint[1],
499*5803Srrh 		number.num_uint[0]);
500*5803Srrh 	switch(number.num_tag){
501*5803Srrh 	case TYPB:
502*5803Srrh 	case TYPW:
503*5803Srrh 	case TYPL:
504*5803Srrh 	case TYPQ:
505*5803Srrh 	case TYPO:
506*5803Srrh 	case TYPUNPACKED:
507*5803Srrh 		break;
508*5803Srrh 	case TYPF:
509*5803Srrh 		printf(" == %10.8e", number.num_num.numFf_float.Ff_value);
510*5803Srrh 		break;
511*5803Srrh 	case TYPD:
512*5803Srrh 		printf(" == %20.17e", number.num_num.numFd_float.Fd_value);
513*5803Srrh 		break;
514*5803Srrh 	case TYPG:
515*5803Srrh 	case TYPH:
516*5803Srrh 		break;
517*5803Srrh 	}
518*5803Srrh }
519*5803Srrh 
520*5803Srrh numprintovf(ovf)
521*5803Srrh 	Ovf	ovf;
522*5803Srrh {
523*5803Srrh 	int	i;
524*5803Srrh 	static struct	ovftab{
525*5803Srrh 		Ovf	which;
526*5803Srrh 		char	*print;
527*5803Srrh 	} ovftab[] = {
528*5803Srrh 		OVF_POSOVF,	"posovf",
529*5803Srrh 		OVF_MAXINT,	"maxint",
530*5803Srrh 		OVF_ADDV,	"addv",
531*5803Srrh 		OVF_LSHIFT,	"lshift",
532*5803Srrh 		OVF_F,		"F float",
533*5803Srrh 		OVF_D,		"D float",
534*5803Srrh 		OVF_G,		"G float",
535*5803Srrh 		OVF_H,		"H float",
536*5803Srrh 		OVF_OVERFLOW,	"cvt overflow",
537*5803Srrh 		OVF_UNDERFLOW,	"cvt underflow",
538*5803Srrh 		0,		0
539*5803Srrh 	};
540*5803Srrh 	for(i = 0; ovftab[i].which; i++){
541*5803Srrh 		if (ovf & ovftab[i].which)
542*5803Srrh 			printf("Overflow(%s) ", ovftab[i].print);
543*5803Srrh 	}
544*5803Srrh }
545*5803Srrh #endif DEBUG
546