changed: small changes in: UInt:: RclMoveAllWords, UInt::RcrMoveAllWords, UInt::SetBitInWord(),

UInt::FindLeadingBitInWord, UInt::SetBitInWord
fixed:   UInt::Div() didn't return a correct result when the divisor was equal 1
         there was an error in UInt::DivInt() - when the divisor was 1 it returned
         zero and the carry was set
         this error was from the beginning of the TTMath library


git-svn-id: svn://ttmath.org/publicrep/ttmath/trunk@103 e52654a7-88a9-db11-a3e9-0013d4bc506e
This commit is contained in:
Tomasz Sowa 2009-03-07 22:54:42 +00:00
parent 4aebe9aa18
commit 404727f3de
1 changed files with 20 additions and 20 deletions

View File

@ -1207,15 +1207,16 @@ private:
*/ */
void RclMoveAllWords(uint & rest_bits, uint & last_c, uint bits, uint c) void RclMoveAllWords(uint & rest_bits, uint & last_c, uint bits, uint c)
{ {
rest_bits = sint(bits % TTMATH_BITS_PER_UINT); rest_bits = bits % TTMATH_BITS_PER_UINT;
sint all_words = sint(bits / TTMATH_BITS_PER_UINT); uint all_words = bits / TTMATH_BITS_PER_UINT;
uint mask = ( c ) ? TTMATH_UINT_MAX_VALUE : 0; uint mask = ( c ) ? TTMATH_UINT_MAX_VALUE : 0;
if( all_words >= sint(value_size) ) if( all_words >= value_size )
{ {
if( all_words == value_size && rest_bits == 0 ) if( all_words == value_size && rest_bits == 0 )
last_c = table[0] & 1; last_c = table[0] & 1;
// else: last_c is default set to 0
// clearing // clearing
for(uint i = 0 ; i<value_size ; ++i) for(uint i = 0 ; i<value_size ; ++i)
@ -1296,15 +1297,16 @@ private:
*/ */
void RcrMoveAllWords(uint & rest_bits, uint & last_c, uint bits, uint c) void RcrMoveAllWords(uint & rest_bits, uint & last_c, uint bits, uint c)
{ {
rest_bits = sint(bits % TTMATH_BITS_PER_UINT); rest_bits = bits % TTMATH_BITS_PER_UINT;
sint all_words = sint(bits / TTMATH_BITS_PER_UINT); uint all_words = bits / TTMATH_BITS_PER_UINT;
uint mask = c ? TTMATH_UINT_MAX_VALUE : 0; uint mask = ( c ) ? TTMATH_UINT_MAX_VALUE : 0;
if( all_words >= sint(value_size) ) if( all_words >= value_size )
{ {
if( all_words == value_size && rest_bits == 0 ) if( all_words == value_size && rest_bits == 0 )
last_c = (table[value_size-1] & TTMATH_UINT_HIGHEST_BIT) ? 1 : 0; last_c = (table[value_size-1] & TTMATH_UINT_HIGHEST_BIT) ? 1 : 0;
// else: last_c is default set to 0
// clearing // clearing
for(uint i = 0 ; i<value_size ; ++i) for(uint i = 0 ; i<value_size ; ++i)
@ -1436,9 +1438,9 @@ public:
push edx push edx
mov edx,-1 mov edx,-1
bsr eax,x bsr eax,[x]
cmovz eax,edx cmovz eax,edx
mov result, eax mov [result], eax
pop edx pop edx
pop eax pop eax
@ -1521,10 +1523,10 @@ public:
{ {
push ebx push ebx
push eax push eax
mov eax, value mov eax, [value]
mov ebx, bit mov ebx, [bit]
bts eax, ebx bts eax, ebx
mov value, eax mov [value], eax
pop eax pop eax
pop ebx pop ebx
} }
@ -1534,10 +1536,10 @@ public:
#ifdef __GNUC__ #ifdef __GNUC__
__asm__ __volatile__( __asm__ __volatile__(
"btsl %%ebx,%%eax \n" "btsl %2,%0 \n"
: "=a" (value) : "=R" (value)
: "0" (value), "b" (bit) : "0" (value), "R" (bit)
: "cc" ); : "cc" );
#endif #endif
@ -1656,7 +1658,7 @@ public:
this method never returns a carry this method never returns a carry
it is an auxiliary method for version two of the multiplication algorithm it is an auxiliary method for second version of the multiplication algorithm
*/ */
static void MulTwoWords(uint a, uint b, uint * result2, uint * result1) static void MulTwoWords(uint a, uint b, uint * result2, uint * result1)
{ {
@ -1664,7 +1666,7 @@ public:
we must use these temporary variables in order to inform the compilator we must use these temporary variables in order to inform the compilator
that value pointed with result1 and result2 has changed that value pointed with result1 and result2 has changed
this has no effect in visual studio but it's usefull when this has no effect in visual studio but it's useful when
using gcc and options like -Ox using gcc and options like -Ox
*/ */
register uint result1_; register uint result1_;
@ -2044,12 +2046,10 @@ public:
{ {
if( divisor == 1 ) if( divisor == 1 )
{ {
SetZero();
if( remainder ) if( remainder )
*remainder = 0; *remainder = 0;
return 1; return 0;
} }
UInt<value_size> dividend(*this); UInt<value_size> dividend(*this);