summaryrefslogtreecommitdiffstats
path: root/private/windbg/lib/mantold.c
diff options
context:
space:
mode:
Diffstat (limited to 'private/windbg/lib/mantold.c')
-rw-r--r--private/windbg/lib/mantold.c184
1 files changed, 184 insertions, 0 deletions
diff --git a/private/windbg/lib/mantold.c b/private/windbg/lib/mantold.c
new file mode 100644
index 000000000..05dc6db7c
--- /dev/null
+++ b/private/windbg/lib/mantold.c
@@ -0,0 +1,184 @@
+/***
+*mantold.c - conversion of a decimal mantissa to _ULDBL12
+*
+* Copyright (c) 1991-1991, Microsoft Corporation. All rights reserved.
+*
+*Purpose:
+* Conversion of a decimal mantissa into _ULDBL12 format (i.e. long
+* double with two additional bytes of significand)
+*
+*Revision History:
+* 7-17-91 GDP Initial version (ported from assembly)
+* 05-26-92 GWK Windbg srcs
+*
+*******************************************************************************/
+
+#include "cv.h"
+
+
+
+
+
+
+/***
+*int __addl(u_long x, u_long y, u_long *sum) - u_long addition
+*
+*Purpose: add two u_long numbers and return carry
+*
+*Entry: u_long x, u_long y : the numbers to be added
+* u_long *sum : where to store the result
+*
+*Exit: *sum receives the value of x+y
+* the value of the carry is returned
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+int __addl(u_long x, u_long y, u_long *sum)
+{
+ u_long r;
+ int carry=0;
+ r = x+y;
+ if (r < x || r < y)
+ carry++;
+ *sum = r;
+ return carry;
+}
+
+
+
+
+
+
+/***
+*void __add_12(_ULDBL12 *x, _ULDBL12 *y) - _ULDBL12 addition
+*
+*Purpose: add two _ULDBL12 numbers. The numbers are added
+* as 12-byte integers. Overflow is ignored.
+*
+*Entry: x,y: pointers to the operands
+*
+*Exit: *x receives the sum
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+void __add_12(_ULDBL12 *x, _ULDBL12 *y)
+{
+ int c0,c1,c2;
+ c0 = __addl(*UL_LO_12(x),*UL_LO_12(y),UL_LO_12(x));
+ if (c0) {
+ c1 = __addl(*UL_MED_12(x),(u_long)1,UL_MED_12(x));
+ if (c1) {
+ (*UL_HI_12(x))++;
+ }
+ }
+ c2 = __addl(*UL_MED_12(x),*UL_MED_12(y),UL_MED_12(x));
+ if (c2) {
+ (*UL_HI_12(x))++;
+ }
+ /* ignore next carry -- assume no overflow will occur */
+ (void) __addl(*UL_HI_12(x),*UL_HI_12(y),UL_HI_12(x));
+}
+
+
+
+
+
+/***
+*void __shl_12(_ULDBL12 *x) - _ULDBL12 shift left
+*void __shr_12(_ULDBL12 *x) - _ULDBL12 shift right
+*
+*Purpose: Shift a _ULDBL12 number one bit to the left (right). The number
+* is shifted as a 12-byte integer. The MSB is lost.
+*
+*Entry: x: a pointer to the operand
+*
+*Exit: *x is shifted one bit to the left (or right)
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+void __shl_12(_ULDBL12 *p)
+{
+ u_long c0,c1;
+
+ c0 = *UL_LO_12(p) & MSB_ULONG ? 1: 0;
+ c1 = *UL_MED_12(p) & MSB_ULONG ? 1: 0;
+ *UL_LO_12(p) <<= 1;
+ *UL_MED_12(p) = *UL_MED_12(p)<<1 | c0;
+ *UL_HI_12(p) = *UL_HI_12(p)<<1 | c1;
+}
+
+void __shr_12(_ULDBL12 *p)
+{
+ u_long c2,c1;
+ c2 = *UL_HI_12(p) & 0x1 ? MSB_ULONG: 0;
+ c1 = *UL_MED_12(p) & 0x1 ? MSB_ULONG: 0;
+ *UL_HI_12(p) >>= 1;
+ *UL_MED_12(p) = *UL_MED_12(p)>>1 | c2;
+ *UL_LO_12(p) = *UL_LO_12(p)>>1 | c1;
+}
+
+
+
+
+
+
+/***
+*void __mtold12(char *manptr,unsigned manlen,_ULDBL12 *ld12) -
+* convert a mantissa into a _ULDBL12
+*
+*Purpose: convert a mantissa into a _ULDBL12. The mantissa is
+* in the form of an array of manlen BCD digits and is
+* considered to be an integer.
+*
+*Entry: manptr: the array containing the packed BCD digits of the mantissa
+* manlen: the size of the array
+* ld12: a pointer to the long double where the result will be stored
+*
+*Exit:
+* ld12 gets the result of the conversion
+*
+*Exceptions:
+*
+*******************************************************************************/
+
+void __mtold12(char *manptr,
+ unsigned manlen,
+ _ULDBL12 *ld12)
+{
+ _ULDBL12 tmp;
+ u_short expn = LD_BIASM1+80;
+
+ *UL_LO_12(ld12) = 0;
+ *UL_MED_12(ld12) = 0;
+ *UL_HI_12(ld12) = 0;
+ for (;manlen>0;manlen--,manptr++){
+ tmp = *ld12;
+ __shl_12(ld12);
+ __shl_12(ld12);
+ __add_12(ld12,&tmp);
+ __shl_12(ld12); /* multiply by 10 */
+ *UL_LO_12(&tmp) = (u_long)*manptr;
+ *UL_MED_12(&tmp) = 0;
+ *UL_HI_12(&tmp) = 0;
+ __add_12(ld12,&tmp);
+ }
+
+ /* normalize mantissa -- first shift word by word */
+ while (*UL_HI_12(ld12) == 0) {
+ *UL_HI_12(ld12) = *UL_MED_12(ld12) >> 16;
+ *UL_MED_12(ld12) = *UL_MED_12(ld12) << 16 | *UL_LO_12(ld12) >> 16;
+ (*UL_LO_12(ld12)) <<= 16;
+ expn -= 16;
+ }
+ while ((*UL_HI_12(ld12) & 0x8000) == 0) {
+ __shl_12(ld12);
+ expn--;
+ }
+ *U_EXP_12(ld12) = expn;
+}