/******************************************************************************
* *
* N-WORD ADD *
* 04/19/10 (dkc) *
* *
******************************************************************************/
unsigned int carry(unsigned int a, unsigned int b, unsigned int sum);
void addn(unsigned int *a, unsigned int *b, unsigned int n) {
unsigned int i,s;
unsigned int c[2048];
if (n>2048)
return;
for (i=n-1; i>0; i--) {
s=*(a+i)+*(b+i);
c[i]=carry(*(a+i),*(b+i),s);
*(b+i)=s;
}
*b=*a+*b;
for (i=n-2; i>0; i--) {
s=*(b+i)+c[i+1];
c[i]+=carry(*(b+i),c[i+1],s);
*(b+i)=s;
}
*b=*b+c[1];
return;
}
/******************************************************************************
* *
* N-WORD SUBTRACT *
* 04/19/10 (dkc) *
* *
******************************************************************************/
unsigned int carry(unsigned int a, unsigned int b, unsigned int sum);
void subn(unsigned int *a, unsigned int *b, unsigned int n) {
unsigned int i,s,d;
unsigned int c[2048];
if (n>2048)
return;
for (i=0; i<n; i++) {
s=*(b+i);
*(b+i)=~s;
}
d=1;
for (i=n-1; i>0; i--) {
s=*(b+i)+d;
d=carry(*(b+i),d,s);
*(b+i)=s;
}
*b=*b+d;
for (i=n-1; i>0; i--) {
s=*(a+i)+*(b+i);
c[i]=carry(*(a+i),*(b+i),s);
*(b+i)=s;
}
*b=*a+*b;
for (i=n-2; i>0; i--) {
s=*(b+i)+c[i+1];
c[i]+=carry(*(b+i),c[i+1],s);
*(b+i)=s;
}
*b=*b+c[1];
return;
}
/*****************************************************************************/
/* */
/* N-WORD RIGHT SHIFT */
/* 04/02/10 (dkc) */
/* */
/*****************************************************************************/
void shiftn(unsigned int *a, unsigned int *b, unsigned int shift, unsigned
int n) {
unsigned int i;
for (i=0; i<n; i++)
*(b+i)=*(a+i);
while (shift>31) {
for (i=n-1; i>0; i--)
*(b+i)=*(b+i-1);
*b=0;
shift=shift-32;
}
if (shift==0)
return;
for (i=n-1; i>0; i--)
*(b+i)=(*(b+i)>>shift)|(*(b+i-1)<<(32-shift));
*b=*b>>shift;
return;
}
/*****************************************************************************/
/* */
/* N-WORD LEFT SHIFT */
/* 10/16/09 (dkc) */
/* */
/*****************************************************************************/
void lshiftn(unsigned int *a, unsigned int *b, unsigned int shift, unsigned
int n) {
unsigned int i;
for (i=0; i<n; i++)
*(b+i)=*(a+i);
while (shift>31) {
for (i=0; i<n-1; i++)
*(b+i)=*(b+i+1);
*(b+n-1)=0;
shift=shift-32;
}
if (shift==0)
return;
for (i=0; i<n-1; i++)
*(b+i)=(*(b+i)<<shift)|(*(b+i+1)>>(32-shift));
*(b+n-1)=*(b+n-1)<<shift;
return;
}
/******************************************************************************
* *
* N-WORD NORMALIZATION *
* 04/03/10 (dkc) *
* *
******************************************************************************/
unsigned int normn(unsigned int *a, unsigned int n) {
unsigned int i,shift,mask;
i=0;
while ((*(a+i)==0)&&(i<n))
i=i+1;
shift=32*i;
if (i==n)
return shift;
mask=0x80000000;
while ((*(a+i)&mask)==0) {
shift=shift+1;
mask=mask>>1;
}
return shift;
}
/******************************************************************************
* *
* N-WORD "OR" *
* 04/02/10 (dkc) *
* *
******************************************************************************/
unsigned int orn(unsigned int *a, unsigned int n) {
unsigned int i,b;
b=*a;
for (i=1; i<n; i++)
b=b|*(a+i);
return b;
}
/******************************************************************************
* *
* N-WORD COPY *
* 04/02/10 (dkc) *
* *
******************************************************************************/
void copyn(unsigned int *a, unsigned int *b, unsigned int n) {
unsigned int i;
for (i=0; i<n; i++)
*(b+i)=*(a+i);
return;
}
/******************************************************************************
* *
* N-WORD CLEAR (AND SET OF LAST WORD) *
* 04/02/10 (dkc) *
* *
******************************************************************************/
void setn(unsigned int *a, unsigned int b, unsigned int n) {
unsigned int i;
for (i=0; i<n-1; i++)
*(a+i)=0;
*(a+n-1)=b;
return;
}