af15e0698b
git-svn-id: svn://10.65.10.50/trunk@4679 c028cbd2-c16b-5b4b-a496-9718f37d4682
208 lines
4.9 KiB
C
Executable File
208 lines
4.9 KiB
C
Executable File
/* c4bcd.c (c)Copyright Sequiter Software Inc., 1988-1996. All rights reserved. */
|
|
/* binary digit is: xxxx xxxx xxxx xx01 */
|
|
/* sig dig |||| |||| */
|
|
/* |||| ||always 01 */
|
|
/* |length */
|
|
/* sign */
|
|
|
|
#include "d4all.h"
|
|
|
|
#ifdef __TURBOC__
|
|
#pragma hdrstop
|
|
#endif /* __TUROBC__ */
|
|
|
|
#ifdef S4MDX
|
|
|
|
/* MDX */
|
|
int S4CALL c4bcdCmp( S4CMP_PARM aPtr, S4CMP_PARM bPtr, size_t dummyLen )
|
|
{
|
|
int aSign, bSign, aLen, bLen, aSigDig, bSigDig, compareLen, rc ;
|
|
|
|
if ( ((C4BCD *)aPtr)->digitInfo & 0x80 ) /* get digit sign */
|
|
aSign = -1 ;
|
|
else
|
|
aSign = 1 ;
|
|
|
|
if ( ((C4BCD *)bPtr)->digitInfo & 0x80 )
|
|
bSign = -1 ;
|
|
else
|
|
bSign = 1 ;
|
|
|
|
if ( aSign != bSign )
|
|
return aSign ;
|
|
|
|
aLen = ( (((C4BCD *)aPtr)->digitInfo >> 2) & 0x1F ) ; /* get digit length */
|
|
bLen = ( (((C4BCD *)bPtr)->digitInfo >> 2) & 0x1F ) ;
|
|
|
|
if ( aLen == 0 )
|
|
aSigDig = 0 ;
|
|
else
|
|
aSigDig = ((C4BCD *)aPtr)->sigDig ; /* get digit significant digit */
|
|
|
|
if ( bLen == 0 )
|
|
bSigDig = 0 ;
|
|
else
|
|
bSigDig = ((C4BCD *)bPtr)->sigDig ;
|
|
|
|
if ( aSigDig != bSigDig )
|
|
{
|
|
if ( aSigDig < bSigDig )
|
|
return -aSign ;
|
|
else
|
|
return aSign ;
|
|
}
|
|
|
|
compareLen = (aLen < bLen) ? bLen : aLen ; /* Use Max */
|
|
|
|
compareLen = (compareLen+1)/2 ;
|
|
|
|
rc = c4memcmp( ((C4BCD *)aPtr)->bcd, ((C4BCD *)bPtr)->bcd, compareLen ) ;
|
|
if ( aSign < 0 ) return -rc ;
|
|
|
|
return rc ;
|
|
}
|
|
|
|
/* MDX */
|
|
void c4bcdFromA( char *result, const char *inputPtr, const int inputPtrLen )
|
|
{
|
|
char *ptr ;
|
|
unsigned len ;
|
|
int n, lastPos, pos, isBeforeDec, zeroCount ;
|
|
|
|
memset( result, 0, sizeof(C4BCD) ) ;
|
|
|
|
lastPos = inputPtrLen - 1 ;
|
|
pos = 0 ;
|
|
for ( ; pos <= lastPos; pos++ )
|
|
if ( inputPtr[pos] != ' ' ) break ;
|
|
|
|
if ( pos <= lastPos )
|
|
{
|
|
if ( inputPtr[pos] == '-' )
|
|
{
|
|
((C4BCD *)result)->digitInfo=(unsigned char)((int)((C4BCD *)result)->digitInfo | 0x80) ;
|
|
pos++ ;
|
|
}
|
|
else
|
|
{
|
|
if ( inputPtr[pos] == '+' ) pos++ ;
|
|
}
|
|
}
|
|
|
|
for ( ; pos <= lastPos; pos++ )
|
|
if ( inputPtr[pos] != ' ' && inputPtr[pos] != '0' ) break ;
|
|
|
|
isBeforeDec = 1 ;
|
|
|
|
((C4BCD *)result)->sigDig = 0x34 ;
|
|
if ( pos <= lastPos )
|
|
if ( inputPtr[pos] == '.' )
|
|
{
|
|
isBeforeDec = 0 ;
|
|
pos++ ;
|
|
for ( ; pos <= lastPos; pos++ )
|
|
{
|
|
if ( inputPtr[pos] != '0' ) break ;
|
|
((C4BCD *)result)->sigDig-- ;
|
|
}
|
|
}
|
|
|
|
ptr = (char *) ((C4BCD *)result)->bcd ; ;
|
|
zeroCount = 0 ;
|
|
|
|
for ( n=0; pos <= lastPos; pos++ )
|
|
{
|
|
if ( inputPtr[pos] >= '0' && inputPtr[pos] <= '9' )
|
|
{
|
|
if ( inputPtr[pos] == '0' )
|
|
zeroCount++ ;
|
|
else
|
|
zeroCount = 0 ;
|
|
if ( n >= 20 ) break ;
|
|
if ( n & 1 )
|
|
*ptr++ |= inputPtr[pos] - '0' ;
|
|
else
|
|
*ptr += (unsigned char)( (unsigned char)((unsigned char)inputPtr[pos] - (unsigned char)'0') << 4 ) ;
|
|
}
|
|
else
|
|
{
|
|
if ( inputPtr[pos] != '.' || ! isBeforeDec )
|
|
break ;
|
|
|
|
isBeforeDec = 0 ;
|
|
continue ;
|
|
}
|
|
if ( isBeforeDec )
|
|
((C4BCD *)result)->sigDig++ ;
|
|
|
|
n++ ;
|
|
}
|
|
/* 'always one' bit filled */
|
|
((C4BCD *)result)->digitInfo = (unsigned char)( ((C4BCD *)result)->digitInfo | 0x1 ) ;
|
|
|
|
#ifdef E4MISC
|
|
if ( n - zeroCount < 0 )
|
|
{
|
|
error4( 0, e4info, E95105 ) ;
|
|
return ;
|
|
}
|
|
#endif
|
|
|
|
len = n - zeroCount ;
|
|
if (len > 31)
|
|
len = 31 ;
|
|
|
|
((C4BCD *)result)->digitInfo = (unsigned char)( ((C4BCD *)result)->digitInfo | (len << 2) ) ;
|
|
|
|
if ( len == 0 )
|
|
((C4BCD *)result)->digitInfo = (unsigned char)( ((C4BCD *)result)->digitInfo & 0x7F ) ;
|
|
}
|
|
|
|
/* MDX */
|
|
void c4bcdFromD( char *result, const double doub )
|
|
{
|
|
char tempStr[258], *ptr ;
|
|
int sign, dec, len, pos ;
|
|
|
|
#ifdef S4NO_ECVT
|
|
ptr = f4ecvt( doub, E4ACCURACY_DIGITS, &dec, &sign ) ;
|
|
#else
|
|
ptr = ecvt( doub, E4ACCURACY_DIGITS, &dec, &sign ) ;
|
|
#endif
|
|
|
|
if ( sign )
|
|
{
|
|
pos = 1 ;
|
|
tempStr[0] = '-' ;
|
|
}
|
|
else
|
|
pos = 0 ;
|
|
|
|
if ( dec < 0 )
|
|
{
|
|
dec = -dec ;
|
|
len = dec+1+pos ;
|
|
memcpy( tempStr+len, ptr, E4ACCURACY_DIGITS ) ;
|
|
memset( tempStr+pos, '0', len-pos ) ;
|
|
tempStr[pos] = '.' ;
|
|
|
|
c4bcdFromA( result, tempStr, E4ACCURACY_DIGITS + len ) ;
|
|
}
|
|
else
|
|
{
|
|
memcpy( tempStr+pos, ptr, dec ) ;
|
|
pos += dec ;
|
|
if ( dec < E4ACCURACY_DIGITS )
|
|
{
|
|
tempStr[pos++] = '.' ;
|
|
|
|
len = E4ACCURACY_DIGITS - dec ;
|
|
memcpy( tempStr+pos, ptr+dec, len ) ;
|
|
pos += len ;
|
|
}
|
|
c4bcdFromA( result, tempStr, pos ) ;
|
|
}
|
|
}
|
|
|
|
#endif /* S4MDX */
|