| Index: nss/lib/freebl/mpi/mpi.c
|
| diff --git a/nss/lib/freebl/mpi/mpi.c b/nss/lib/freebl/mpi/mpi.c
|
| index 2a3719b88367d8924767822d4fdcb2bf2bcc97b2..84f9b97b63ea408c8a85ddd52b38b88ba12863f3 100644
|
| --- a/nss/lib/freebl/mpi/mpi.c
|
| +++ b/nss/lib/freebl/mpi/mpi.c
|
| @@ -1095,7 +1095,7 @@ mp_err mp_expt(mp_int *a, mp_int *b, mp_int *c)
|
| mp_int s, x;
|
| mp_err res;
|
| mp_digit d;
|
| - int dig, bit;
|
| + unsigned int dig, bit;
|
|
|
| ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);
|
|
|
| @@ -1470,7 +1470,7 @@ mp_err s_mp_exptmod(const mp_int *a, const mp_int *b, const mp_int *m, mp_int *c
|
| mp_int s, x, mu;
|
| mp_err res;
|
| mp_digit d;
|
| - int dig, bit;
|
| + unsigned int dig, bit;
|
|
|
| ARGCHK(a != NULL && b != NULL && c != NULL, MP_BADARG);
|
|
|
| @@ -2004,7 +2004,7 @@ mp_size mp_trailing_zeros(const mp_int *mp)
|
| {
|
| mp_digit d;
|
| mp_size n = 0;
|
| - int ix;
|
| + unsigned int ix;
|
|
|
| if (!mp || !MP_DIGITS(mp) || !mp_cmp_z(mp))
|
| return n;
|
| @@ -2916,8 +2916,7 @@ void s_mp_exch(mp_int *a, mp_int *b)
|
| mp_err s_mp_lshd(mp_int *mp, mp_size p)
|
| {
|
| mp_err res;
|
| - mp_size pos;
|
| - int ix;
|
| + unsigned int ix;
|
|
|
| if(p == 0)
|
| return MP_OKAY;
|
| @@ -2928,14 +2927,13 @@ mp_err s_mp_lshd(mp_int *mp, mp_size p)
|
| if((res = s_mp_pad(mp, USED(mp) + p)) != MP_OKAY)
|
| return res;
|
|
|
| - pos = USED(mp) - 1;
|
| -
|
| /* Shift all the significant figures over as needed */
|
| - for(ix = pos - p; ix >= 0; ix--)
|
| + for (ix = USED(mp) - p; ix-- > 0;) {
|
| DIGIT(mp, ix + p) = DIGIT(mp, ix);
|
| + }
|
|
|
| /* Fill the bottom digits with zeroes */
|
| - for(ix = 0; ix < p; ix++)
|
| + for(ix = 0; (mp_size)ix < p; ix++)
|
| DIGIT(mp, ix) = 0;
|
|
|
| return MP_OKAY;
|
| @@ -3046,7 +3044,7 @@ void s_mp_div_2(mp_int *mp)
|
| mp_err s_mp_mul_2(mp_int *mp)
|
| {
|
| mp_digit *pd;
|
| - int ix, used;
|
| + unsigned int ix, used;
|
| mp_digit kin = 0;
|
|
|
| /* Shift digits leftward by 1 bit */
|
| @@ -4192,6 +4190,7 @@ mp_err s_mp_div(mp_int *rem, /* i: dividend, o: remainder */
|
|
|
| MP_SIGN(rem) = ZPOS;
|
| MP_SIGN(div) = ZPOS;
|
| + MP_SIGN(&part) = ZPOS;
|
|
|
| /* A working temporary for division */
|
| MP_CHECKOK( mp_init_size(&t, MP_ALLOC(rem)));
|
| @@ -4199,8 +4198,6 @@ mp_err s_mp_div(mp_int *rem, /* i: dividend, o: remainder */
|
| /* Normalize to optimize guessing */
|
| MP_CHECKOK( s_mp_norm(rem, div, &d) );
|
|
|
| - part = *rem;
|
| -
|
| /* Perform the division itself...woo! */
|
| MP_USED(quot) = MP_ALLOC(quot);
|
|
|
| @@ -4209,11 +4206,15 @@ mp_err s_mp_div(mp_int *rem, /* i: dividend, o: remainder */
|
| while (MP_USED(rem) > MP_USED(div) || s_mp_cmp(rem, div) >= 0) {
|
| int i;
|
| int unusedRem;
|
| + int partExtended = 0; /* set to true if we need to extend part */
|
|
|
| unusedRem = MP_USED(rem) - MP_USED(div);
|
| MP_DIGITS(&part) = MP_DIGITS(rem) + unusedRem;
|
| MP_ALLOC(&part) = MP_ALLOC(rem) - unusedRem;
|
| MP_USED(&part) = MP_USED(div);
|
| +
|
| + /* We have now truncated the part of the remainder to the same length as
|
| + * the divisor. If part is smaller than div, extend part by one digit. */
|
| if (s_mp_cmp(&part, div) < 0) {
|
| -- unusedRem;
|
| #if MP_ARGCHK == 2
|
| @@ -4222,26 +4223,34 @@ mp_err s_mp_div(mp_int *rem, /* i: dividend, o: remainder */
|
| -- MP_DIGITS(&part);
|
| ++ MP_USED(&part);
|
| ++ MP_ALLOC(&part);
|
| + partExtended = 1;
|
| }
|
|
|
| /* Compute a guess for the next quotient digit */
|
| q_msd = MP_DIGIT(&part, MP_USED(&part) - 1);
|
| div_msd = MP_DIGIT(div, MP_USED(div) - 1);
|
| - if (q_msd >= div_msd) {
|
| + if (!partExtended) {
|
| + /* In this case, q_msd /= div_msd is always 1. First, since div_msd is
|
| + * normalized to have the high bit set, 2*div_msd > MP_DIGIT_MAX. Since
|
| + * we didn't extend part, q_msd >= div_msd. Therefore we know that
|
| + * div_msd <= q_msd <= MP_DIGIT_MAX < 2*div_msd. Dividing by div_msd we
|
| + * get 1 <= q_msd/div_msd < 2. So q_msd /= div_msd must be 1. */
|
| q_msd = 1;
|
| - } else if (MP_USED(&part) > 1) {
|
| + } else {
|
| #if !defined(MP_NO_MP_WORD) && !defined(MP_NO_DIV_WORD)
|
| q_msd = (q_msd << MP_DIGIT_BIT) | MP_DIGIT(&part, MP_USED(&part) - 2);
|
| q_msd /= div_msd;
|
| if (q_msd == RADIX)
|
| --q_msd;
|
| #else
|
| - mp_digit r;
|
| - MP_CHECKOK( s_mpv_div_2dx1d(q_msd, MP_DIGIT(&part, MP_USED(&part) - 2),
|
| - div_msd, &q_msd, &r) );
|
| + if (q_msd == div_msd) {
|
| + q_msd = MP_DIGIT_MAX;
|
| + } else {
|
| + mp_digit r;
|
| + MP_CHECKOK( s_mpv_div_2dx1d(q_msd, MP_DIGIT(&part, MP_USED(&part) - 2),
|
| + div_msd, &q_msd, &r) );
|
| + }
|
| #endif
|
| - } else {
|
| - q_msd = 0;
|
| }
|
| #if MP_ARGCHK == 2
|
| assert(q_msd > 0); /* This case should never occur any more. */
|
| @@ -4672,10 +4681,10 @@ mp_read_unsigned_octets(mp_int *mp, const unsigned char *str, mp_size len)
|
| /* }}} */
|
|
|
| /* {{{ mp_unsigned_octet_size(mp) */
|
| -int
|
| +unsigned int
|
| mp_unsigned_octet_size(const mp_int *mp)
|
| {
|
| - int bytes;
|
| + unsigned int bytes;
|
| int ix;
|
| mp_digit d = 0;
|
|
|
| @@ -4712,12 +4721,12 @@ mp_err
|
| mp_to_unsigned_octets(const mp_int *mp, unsigned char *str, mp_size maxlen)
|
| {
|
| int ix, pos = 0;
|
| - int bytes;
|
| + unsigned int bytes;
|
|
|
| ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);
|
|
|
| bytes = mp_unsigned_octet_size(mp);
|
| - ARGCHK(bytes >= 0 && bytes <= maxlen, MP_BADARG);
|
| + ARGCHK(bytes <= maxlen, MP_BADARG);
|
|
|
| /* Iterate over each digit... */
|
| for(ix = USED(mp) - 1; ix >= 0; ix--) {
|
| @@ -4744,12 +4753,12 @@ mp_err
|
| mp_to_signed_octets(const mp_int *mp, unsigned char *str, mp_size maxlen)
|
| {
|
| int ix, pos = 0;
|
| - int bytes;
|
| + unsigned int bytes;
|
|
|
| ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);
|
|
|
| bytes = mp_unsigned_octet_size(mp);
|
| - ARGCHK(bytes >= 0 && bytes <= maxlen, MP_BADARG);
|
| + ARGCHK(bytes <= maxlen, MP_BADARG);
|
|
|
| /* Iterate over each digit... */
|
| for(ix = USED(mp) - 1; ix >= 0; ix--) {
|
| @@ -4784,12 +4793,12 @@ mp_err
|
| mp_to_fixlen_octets(const mp_int *mp, unsigned char *str, mp_size length)
|
| {
|
| int ix, pos = 0;
|
| - int bytes;
|
| + unsigned int bytes;
|
|
|
| ARGCHK(mp != NULL && str != NULL && !SIGN(mp), MP_BADARG);
|
|
|
| bytes = mp_unsigned_octet_size(mp);
|
| - ARGCHK(bytes >= 0 && bytes <= length, MP_BADARG);
|
| + ARGCHK(bytes <= length, MP_BADARG);
|
|
|
| /* place any needed leading zeros */
|
| for (;length > bytes; --length) {
|
|
|