?? md5.h
字號:
/************************************************************************/
void NN_Decode (NN_DIGIT *a, unsigned int digits, unsigned char *b, unsigned int len)
{
NN_DIGIT t;
int j;
unsigned int i, u;
for (i = 0, j = len - 1; i < digits && j >= 0; i++) {
t = 0;
for (u = 0; j >= 0 && u < NN_DIGIT_BITS; j--, u += 8)
t |= ((NN_DIGIT)b[j]) << u;
a[i] = t;
}
for (; i < digits; i++)
a[i] = 0;
}
void NN_Encode (unsigned char *a, unsigned int len, NN_DIGIT *b, unsigned int digits)
{
NN_DIGIT t;
int j;
unsigned int i, u;
for (i = 0, j = len - 1; i < digits && j >= 0; i++) {
t = b[i];
for (u = 0; j >= 0 && u < NN_DIGIT_BITS; j--, u += 8)
a[j] = (unsigned char)(t >> u);
}
for (; j >= 0; j--)
a[j] = 0;
}
unsigned int NN_Digits ( NN_DIGIT *a, unsigned int digits)
{
int i;
for (i = digits - 1; i >= 0; i--)
if (a[i])
break;
return (i + 1);
}
int NN_Cmp (NN_DIGIT *a, NN_DIGIT *b, unsigned int digits)
{
int i;
for (i = digits - 1; i >= 0; i--) {
if (a[i] > b[i])
return (1);
if (a[i] < b[i])
return (-1);
}
return (0);
}
int NN_Zero (NN_DIGIT *a, unsigned int digits)
{
unsigned int i;
for (i = 0; i < digits; i++)
if (a[i])
return (0);
return (1);
}
static unsigned int NN_DigitBits (NN_DIGIT a)
{
unsigned int i;
for (i = 0; i < NN_DIGIT_BITS; i++, a >>= 1)
if (a == 0)
break;
return (i);
}
unsigned int NN_Bits (NN_DIGIT *a, unsigned int digits)
{
if ((digits = NN_Digits (a, digits)) == 0)
return (0);
return ((digits - 1) * NN_DIGIT_BITS + NN_DigitBits (a[digits-1]));
}
void NN_AssignZero (NN_DIGIT *a, unsigned int digits)
{
unsigned int i;
for (i = 0; i < digits; i++)
a[i] = 0;
}
void NN_DigitMult (NN_DIGIT a[2], NN_DIGIT b, NN_DIGIT c);
static NN_DIGIT NN_AddDigitMult (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT c, NN_DIGIT *d, unsigned int digits)
{
NN_DIGIT carry, t[2];
unsigned int i;
if (c == 0)
return (0);
carry = 0;
for (i = 0; i < digits; i++) {
NN_DigitMult (t, c, d[i]);
if ((a[i] = b[i] + carry) < carry)
carry = 1;
else
carry = 0;
if ((a[i] += t[0]) < t[0])
carry++;
carry += t[1];
}
return (carry);
}
void NN_Assign (NN_DIGIT *a, NN_DIGIT *b, unsigned int digits)
{
unsigned int i;
for (i = 0; i < digits; i++)
a[i] = b[i];
}
void NN_Mult (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int digits)
{
NN_DIGIT t[2*MAX_NN_DIGITS];
unsigned int bDigits, cDigits, i;
NN_AssignZero (t, 2 * digits);
bDigits = NN_Digits (b, digits);
cDigits = NN_Digits (c, digits);
for (i = 0; i < bDigits; i++)
t[i+cDigits] += NN_AddDigitMult (&t[i], &t[i], b[i], c, cDigits);
NN_Assign (a, t, 2 * digits);
R_memset ((POINTER)t, 0, sizeof (t));
}
void NN_Div (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int cDigits, NN_DIGIT *d, unsigned int dDigits);
void NN_Mod (NN_DIGIT *a, NN_DIGIT *b, unsigned int bDigits, NN_DIGIT *c, unsigned int cDigits)
{
NN_DIGIT t[2 * MAX_NN_DIGITS];
NN_Div (t, a, b, bDigits, c, cDigits);
R_memset ((POINTER)t, 0, sizeof (t));
}
void NN_ModMult (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, NN_DIGIT *d, unsigned int digits)
{
NN_DIGIT t[2*MAX_NN_DIGITS];
NN_Mult (t, b, c, digits);
NN_Mod (a, t, 2 * digits, d, digits);
R_memset ((POINTER)t, 0, sizeof (t));
}
void NN_ModExp (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int cDigits, NN_DIGIT *d, unsigned int dDigits)
{
NN_DIGIT bPower[3][MAX_NN_DIGITS], ci, t[MAX_NN_DIGITS];
int i;
unsigned int ciBits, j, s;
NN_Assign (bPower[0], b, dDigits);
NN_ModMult (bPower[1], bPower[0], b, d, dDigits);
NN_ModMult (bPower[2], bPower[1], b, d, dDigits);
NN_ASSIGN_DIGIT (t, 1, dDigits);
cDigits = NN_Digits (c, cDigits);
for (i = cDigits - 1; i >= 0; i--) {
ci = c[i];
ciBits = NN_DIGIT_BITS;
if (i == (int)(cDigits - 1)) {
while (! DIGIT_2MSB (ci)) {
ci <<= 2;
ciBits -= 2;
}
}
for (j = 0; j < ciBits; j += 2, ci <<= 2) {
NN_ModMult (t, t, t, d, dDigits);
NN_ModMult (t, t, t, d, dDigits);
if ((s = DIGIT_2MSB (ci)) != 0)
NN_ModMult (t, t, bPower[s-1], d, dDigits);
}
}
NN_Assign (a, t, dDigits);
R_memset ((POINTER)bPower, 0, sizeof (bPower));
R_memset ((POINTER)t, 0, sizeof (t));
}
void NN_Assign2Exp (NN_DIGIT *a, unsigned int b, unsigned int digits)
{
NN_AssignZero (a, digits);
if (b >= digits * NN_DIGIT_BITS)
return;
a[b / NN_DIGIT_BITS] = (NN_DIGIT)1 << (b % NN_DIGIT_BITS);
}
NN_DIGIT NN_Sub (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int digits)
{
NN_DIGIT ai, borrow;
unsigned int i;
borrow = 0;
for (i = 0; i < digits; i++) {
if ((ai = b[i] - borrow) > (MAX_NN_DIGIT - borrow))
ai = MAX_NN_DIGIT - c[i];
else if ((ai -= c[i]) > (MAX_NN_DIGIT - c[i]))
borrow = 1;
else
borrow = 0;
a[i] = ai;
}
return (borrow);
}
void NN_Gcd (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int digits)
{
NN_DIGIT t[MAX_NN_DIGITS], u[MAX_NN_DIGITS], v[MAX_NN_DIGITS];
NN_Assign (u, b, digits);
NN_Assign (v, c, digits);
while (! NN_Zero (v, digits)) {
NN_Mod (t, u, digits, v, digits);
NN_Assign (u, v, digits);
NN_Assign (v, t, digits);
}
NN_Assign (a, u, digits);
/* Zeroize potentially sensitive information.
*/
R_memset ((POINTER)t, 0, sizeof (t));
R_memset ((POINTER)u, 0, sizeof (u));
R_memset ((POINTER)v, 0, sizeof (v));
}
NN_DIGIT NN_LShift (NN_DIGIT *a, NN_DIGIT *b, unsigned int c, unsigned int digits)
{
NN_DIGIT bi, carry;
unsigned int i, t;
if (c >= NN_DIGIT_BITS)
return (0);
t = NN_DIGIT_BITS - c;
carry = 0;
for (i = 0; i < digits; i++) {
bi = b[i];
a[i] = (bi << c) | carry;
carry = c ? (bi >> t) : 0;
}
return (carry);
}
NN_DIGIT NN_RShift (NN_DIGIT *a, NN_DIGIT *b, unsigned int c, unsigned int digits)
{
NN_DIGIT bi, carry;
int i;
unsigned int t;
if (c >= NN_DIGIT_BITS)
return (0);
t = NN_DIGIT_BITS - c;
carry = 0;
for (i = digits - 1; i >= 0; i--) {
bi = b[i];
a[i] = (bi >> c) | carry;
carry = c ? (bi << t) : 0;
}
return (carry);
}
static NN_DIGIT NN_SubDigitMult (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT c, NN_DIGIT *d, unsigned int digits)
{
NN_DIGIT borrow, t[2];
unsigned int i;
if (c == 0)
return (0);
borrow = 0;
for (i = 0; i < digits; i++) {
NN_DigitMult (t, c, d[i]);
if ((a[i] = b[i] - borrow) > (MAX_NN_DIGIT - borrow))
borrow = 1;
else
borrow = 0;
if ((a[i] -= t[0]) > (MAX_NN_DIGIT - t[0]))
borrow++;
borrow += t[1];
}
return (borrow);
}
void NN_DigitDiv (NN_DIGIT *a, NN_DIGIT b[2], NN_DIGIT c)
{
NN_DIGIT t[2], u, v;
NN_HALF_DIGIT aHigh, aLow, cHigh, cLow;
cHigh = (NN_HALF_DIGIT)HIGH_HALF (c);
cLow = (NN_HALF_DIGIT)LOW_HALF (c);
t[0] = b[0];
t[1] = b[1];
if (cHigh == MAX_NN_HALF_DIGIT)
aHigh = (NN_HALF_DIGIT)HIGH_HALF (t[1]);
else
aHigh = (NN_HALF_DIGIT)(t[1] / (cHigh + 1));
u = (NN_DIGIT)aHigh * (NN_DIGIT)cLow;
v = (NN_DIGIT)aHigh * (NN_DIGIT)cHigh;
if ((t[0] -= TO_HIGH_HALF (u)) > (MAX_NN_DIGIT - TO_HIGH_HALF (u)))
t[1]--;
t[1] -= HIGH_HALF (u);
t[1] -= v;
while ((t[1] > cHigh) ||
((t[1] == cHigh) && (t[0] >= TO_HIGH_HALF (cLow)))) {
if ((t[0] -= TO_HIGH_HALF (cLow)) > MAX_NN_DIGIT - TO_HIGH_HALF (cLow))
t[1]--;
t[1] -= cHigh;
aHigh++;
}
if (cHigh == MAX_NN_HALF_DIGIT)
aLow = (NN_HALF_DIGIT)LOW_HALF (t[1]);
else
aLow =
(NN_HALF_DIGIT)((TO_HIGH_HALF (t[1]) + HIGH_HALF (t[0])) / (cHigh + 1));
u = (NN_DIGIT)aLow * (NN_DIGIT)cLow;
v = (NN_DIGIT)aLow * (NN_DIGIT)cHigh;
if ((t[0] -= u) > (MAX_NN_DIGIT - u))
t[1]--;
if ((t[0] -= TO_HIGH_HALF (v)) > (MAX_NN_DIGIT - TO_HIGH_HALF (v)))
t[1]--;
t[1] -= HIGH_HALF (v);
while ((t[1] > 0) || ((t[1] == 0) && t[0] >= c)) {
if ((t[0] -= c) > (MAX_NN_DIGIT - c))
t[1]--;
aLow++;
}
*a = TO_HIGH_HALF (aHigh) + aLow;
}
NN_DIGIT NN_Add (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int digits)
{
NN_DIGIT ai, carry;
unsigned int i;
carry = 0;
for (i = 0; i < digits; i++) {
if ((ai = b[i] + carry) < carry)
ai = c[i];
else if ((ai += c[i]) < c[i])
carry = 1;
else
carry = 0;
a[i] = ai;
}
return (carry);
}
void NN_Div (NN_DIGIT *a, NN_DIGIT *b, NN_DIGIT *c, unsigned int cDigits, NN_DIGIT *d, unsigned int dDigits)
{
NN_DIGIT ai, cc[2*MAX_NN_DIGITS+1], dd[MAX_NN_DIGITS], t;
int i;
unsigned int ddDigits, shift;
ddDigits = NN_Digits (d, dDigits);
if (ddDigits == 0)
return;
shift = NN_DIGIT_BITS - NN_DigitBits (d[ddDigits-1]);
NN_AssignZero (cc, ddDigits);
cc[
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -