version 1.2, 2000/08/21 08:31:24 |
version 1.6, 2018/03/29 01:32:51 |
|
|
* shall be made on your publication or presentation in any form of the |
* shall be made on your publication or presentation in any form of the |
* results obtained by use of the SOFTWARE. |
* results obtained by use of the SOFTWARE. |
* (4) In the event that you modify the SOFTWARE, you shall notify FLL by |
* (4) In the event that you modify the SOFTWARE, you shall notify FLL by |
* e-mail at risa-admin@flab.fujitsu.co.jp of the detailed specification |
* e-mail at risa-admin@sec.flab.fujitsu.co.jp of the detailed specification |
* for such modification or the source code of the modified part of the |
* for such modification or the source code of the modified part of the |
* SOFTWARE. |
* SOFTWARE. |
* |
* |
|
|
* DEVELOPER SHALL HAVE NO LIABILITY IN CONNECTION WITH THE USE, |
* DEVELOPER SHALL HAVE NO LIABILITY IN CONNECTION WITH THE USE, |
* PERFORMANCE OR NON-PERFORMANCE OF THE SOFTWARE. |
* PERFORMANCE OR NON-PERFORMANCE OF THE SOFTWARE. |
* |
* |
* $OpenXM: OpenXM_contrib2/asir2000/engine/D.c,v 1.1.1.1 1999/12/03 07:39:07 noro Exp $ |
* $OpenXM: OpenXM_contrib2/asir2000/engine/D.c,v 1.5 2002/03/15 02:52:10 noro Exp $ |
*/ |
*/ |
#include "ca.h" |
#include "ca.h" |
|
|
|
|
int hint; |
int hint; |
DCP *dcp; |
DCP *dcp; |
{ |
{ |
int n,np,bound,q; |
int n,np,bound,q; |
int i,j,k; |
int i,j,k; |
int *win; |
int *win; |
P g,factor,cofactor; |
P g,factor,cofactor; |
Q csum,csumt; |
Q csum,csumt; |
DCP dcf,dcf0; |
DCP dcf,dcf0; |
LUM *c; |
LUM *c; |
ML wlist; |
ML wlist; |
int z; |
int z; |
|
|
n = UDEG(f); np = list->n; bound = list->bound; q = list->mod; |
n = UDEG(f); np = list->n; bound = list->bound; q = list->mod; |
win = W_ALLOC(np+1); |
win = W_ALLOC(np+1); |
ucsump(f,&csum); mulq(csum,(Q)COEF(DC(f)),&csumt); csum = csumt; |
ucsump(f,&csum); mulq(csum,(Q)COEF(DC(f)),&csumt); csum = csumt; |
wlist = W_MLALLOC(np); wlist->n = list->n; |
wlist = W_MLALLOC(np); wlist->n = list->n; |
wlist->mod = list->mod; wlist->bound = list->bound; |
wlist->mod = list->mod; wlist->bound = list->bound; |
c = (LUM *)COEF(wlist); bcopy((char *)COEF(list),(char *)c,(int)(sizeof(LUM)*np)); |
c = (LUM *)COEF(wlist); bcopy((char *)COEF(list),(char *)c,(int)(sizeof(LUM)*np)); |
for ( g = f, k = 1, dcf = dcf0 = 0, win[0] = 1, --np, z = 0; ; ) { |
for ( g = f, k = 1, dcf = dcf0 = 0, win[0] = 1, --np, z = 0; ; ) { |
#if 0 |
#if 0 |
if ( !(++z % 10000) ) |
if ( !(++z % 10000) ) |
fprintf(stderr,"z=%d\n",z); |
fprintf(stderr,"z=%d\n",z); |
#endif |
#endif |
if ( degtest(k,win,wlist,hint) && |
if ( degtest(k,win,wlist,hint) && |
dtestmain(g,csum,wlist,k,win,&factor,&cofactor) ) { |
dtestmain(g,csum,wlist,k,win,&factor,&cofactor) ) { |
NEXTDC(dcf0,dcf); DEG(dcf) = ONE; COEF(dcf) = factor; |
NEXTDC(dcf0,dcf); DEG(dcf) = ONE; COEF(dcf) = factor; |
g = cofactor; |
g = cofactor; |
ucsump(g,&csum); mulq(csum,(Q)COEF(DC(g)),&csumt); csum = csumt; |
ucsump(g,&csum); mulq(csum,(Q)COEF(DC(g)),&csumt); csum = csumt; |
for ( i = 0; i < k - 1; i++ ) |
for ( i = 0; i < k - 1; i++ ) |
for ( j = win[i] + 1; j < win[i + 1]; j++ ) |
for ( j = win[i] + 1; j < win[i + 1]; j++ ) |
c[j-i-1] = c[j]; |
c[j-i-1] = c[j]; |
for ( j = win[k-1] + 1; j <= np; j++ ) |
for ( j = win[k-1] + 1; j <= np; j++ ) |
c[j-k] = c[j]; |
c[j-k] = c[j]; |
if ( ( np -= k ) < k ) |
if ( ( np -= k ) < k ) |
break; |
break; |
if ( np - win[0] + 1 < k ) |
if ( np - win[0] + 1 < k ) |
if ( ++k > np ) |
if ( ++k > np ) |
break; |
break; |
else |
else |
for ( i = 0; i < k; i++ ) |
for ( i = 0; i < k; i++ ) |
win[i] = i + 1; |
win[i] = i + 1; |
else |
else |
for ( i = 1; i < k; i++ ) |
for ( i = 1; i < k; i++ ) |
win[i] = win[0] + i; |
win[i] = win[0] + i; |
} else if ( !ncombi(1,np,k,win) ) |
} else if ( !ncombi(1,np,k,win) ) |
if ( k == np ) |
if ( k == np ) |
break; |
break; |
else |
else |
for ( i = 0, ++k; i < k; i++ ) |
for ( i = 0, ++k; i < k; i++ ) |
win[i] = i + 1; |
win[i] = i + 1; |
} |
} |
NEXTDC(dcf0,dcf); COEF(dcf) = g; |
NEXTDC(dcf0,dcf); COEF(dcf) = g; |
DEG(dcf) = ONE; NEXT(dcf) = 0;*dcp = dcf0; |
DEG(dcf) = ONE; NEXT(dcf) = 0;*dcp = dcf0; |
} |
} |
|
|
void dtestsql(f,list,dc,dcp) |
void dtestsql(f,list,dc,dcp) |
|
|
struct oDUM *dc; |
struct oDUM *dc; |
DCP *dcp; |
DCP *dcp; |
{ |
{ |
int j,n,m,b; |
int j,n,m,b; |
P t,s,fq,fr; |
P t,s,fq,fr; |
P *true; |
P *true; |
Q tq; |
Q tq; |
LUM *c; |
LUM *c; |
DCP dcr,dcr0; |
DCP dcr,dcr0; |
|
|
n = list->n; m = list->mod; b = list->bound; c = (LUM *)list->c; |
n = list->n; m = list->mod; b = list->bound; c = (LUM *)list->c; |
true = (P*)ALLOCA(n*sizeof(P)); |
true = (P*)ALLOCA(n*sizeof(P)); |
for ( j = 0; j < n; j++ ) { |
for ( j = 0; j < n; j++ ) { |
dtestsq(m,b,f,c[j],&t); |
dtestsq(m,b,f,c[j],&t); |
if ( t ) |
if ( t ) |
true[j] = t; |
true[j] = t; |
else { |
else { |
*dcp = 0; |
*dcp = 0; |
return; |
return; |
} |
} |
} |
} |
for ( t = f, j = 0; j < n; j++ ) { |
for ( t = f, j = 0; j < n; j++ ) { |
STOQ(dc[j].n,tq); pwrp(CO,true[j],tq,&s); udivpz(t,s,&fq,&fr); |
STOQ(dc[j].n,tq); pwrp(CO,true[j],tq,&s); udivpz(t,s,&fq,&fr); |
if ( fq && !fr ) |
if ( fq && !fr ) |
t = fq; |
t = fq; |
else { |
else { |
*dcp = 0; |
*dcp = 0; |
return; |
return; |
} |
} |
} |
} |
for ( j = 0, dcr = dcr0 = 0; j < n; j++ ) { |
for ( j = 0, dcr = dcr0 = 0; j < n; j++ ) { |
NEXTDC(dcr0,dcr); STOQ(dc[j].n,DEG(dcr)); COEF(dcr) = true[j]; |
NEXTDC(dcr0,dcr); STOQ(dc[j].n,DEG(dcr)); COEF(dcr) = true[j]; |
} |
} |
NEXT(dcr) = 0; *dcp = dcr0; |
NEXT(dcr) = 0; *dcp = dcr0; |
} |
} |
|
|
void dtestsq(q,bound,f,fl,g) |
void dtestsq(q,bound,f,fl,g) |
|
|
LUM fl; |
LUM fl; |
P *g; |
P *g; |
{ |
{ |
P lcf,t,fq,fr,s; |
P lcf,t,fq,fr,s; |
struct oML list; |
struct oML list; |
int in = 0; |
int in = 0; |
|
|
list.n = 1; |
list.n = 1; |
list.mod = q; |
list.mod = q; |
list.bound = bound; |
list.bound = bound; |
list.c[0] = (pointer)fl; |
list.c[0] = (pointer)fl; |
|
|
mullumarray(f,&list,1,&in,&t); mulp(CO,f,COEF(DC(f)),&lcf); |
mullumarray(f,&list,1,&in,&t); mulp(CO,f,COEF(DC(f)),&lcf); |
udivpz(lcf,t,&fq,&fr); |
udivpz(lcf,t,&fq,&fr); |
if( fq && !fr ) |
if( fq && !fr ) |
ptozp(t,1,(Q *)&s,g); |
ptozp(t,1,(Q *)&s,g); |
else |
else |
*g = 0; |
*g = 0; |
} |
} |
|
|
void dtestroot(m,b,f,fl,dc,dcp) |
void dtestroot(m,b,f,fl,dc,dcp) |
|
|
struct oDUM *dc; |
struct oDUM *dc; |
DCP *dcp; |
DCP *dcp; |
{ |
{ |
P t,s,u; |
P t,s,u; |
DCP dcr; |
DCP dcr; |
Q q; |
Q q; |
|
|
dtestroot1(m,b,f,fl,&t); |
dtestroot1(m,b,f,fl,&t); |
if ( !t ) { |
if ( !t ) { |
*dcp = 0; |
*dcp = 0; |
return; |
return; |
} |
} |
STOQ(dc[0].n,q); pwrp(CO,t,q,&s); subp(CO,s,f,&u); |
STOQ(dc[0].n,q); pwrp(CO,t,q,&s); subp(CO,s,f,&u); |
if ( u ) |
if ( u ) |
*dcp = 0; |
*dcp = 0; |
else { |
else { |
NEWDC(dcr); STOQ(dc[0].n,DEG(dcr)); |
NEWDC(dcr); STOQ(dc[0].n,DEG(dcr)); |
COEF(dcr) = t; NEXT(dcr) = 0; *dcp = dcr; |
COEF(dcr) = t; NEXT(dcr) = 0; *dcp = dcr; |
} |
} |
} |
} |
|
|
void dtestroot1(q,bound,f,fl,g) |
void dtestroot1(q,bound,f,fl,g) |
|
|
LUM fl; |
LUM fl; |
P *g; |
P *g; |
{ |
{ |
P fq,fr,t; |
P fq,fr,t; |
|
|
lumtop(VR(f),q,bound,fl,&t); udivpz(f,t,&fq,&fr); |
lumtop(VR(f),q,bound,fl,&t); udivpz(f,t,&fq,&fr); |
*g = (fq && !fr) ? t : 0; |
*g = (fq && !fr) ? t : 0; |
} |
} |
|
|
int dtestmain(g,csum,list,k,in,fp,cofp) |
int dtestmain(g,csum,list,k,in,fp,cofp) |
|
|
int *in; |
int *in; |
P *fp,*cofp; |
P *fp,*cofp; |
{ |
{ |
int mod; |
int mod; |
P fmul,lcg; |
P fmul,lcg; |
Q csumg; |
Q csumg; |
N nq,nr; |
N nq,nr; |
P fq,fr,t; |
P fq,fr,t; |
|
|
if (!ctest(g,list,k,in)) |
if (!ctest(g,list,k,in)) |
return 0; |
return 0; |
mod = list->mod; |
mod = list->mod; |
mullumarray(g,list,k,in,&fmul); mulp(CO,g,COEF(DC(g)),&lcg); |
mullumarray(g,list,k,in,&fmul); mulp(CO,g,COEF(DC(g)),&lcg); |
if ( csum ) { |
if ( csum ) { |
ucsump(fmul,&csumg); |
ucsump(fmul,&csumg); |
if ( csumg ) { |
if ( csumg ) { |
divn(NM(csum),NM(csumg),&nq,&nr); |
divn(NM(csum),NM(csumg),&nq,&nr); |
if ( nr ) |
if ( nr ) |
return 0; |
return 0; |
} |
} |
} |
} |
udivpz(lcg,fmul,&fq,&fr); |
udivpz(lcg,fmul,&fq,&fr); |
if ( fq && !fr ) { |
if ( fq && !fr ) { |
ptozp(fq,1,(Q *)&t,cofp); ptozp(fmul,1,(Q *)&t,fp); |
ptozp(fq,1,(Q *)&t,cofp); ptozp(fmul,1,(Q *)&t,fp); |
return 1; |
return 1; |
} else |
} else |
return 0; |
return 0; |
} |
} |
|
|
int degtest(k,win,list,hint) |
int degtest(k,win,list,hint) |
|
|
ML list; |
ML list; |
int hint; |
int hint; |
{ |
{ |
register int i,d; |
register int i,d; |
LUM *c; |
LUM *c; |
|
|
if ( hint == 1 ) |
if ( hint == 1 ) |
return 1; |
return 1; |
for ( c = (LUM*)list->c, i = 0, d = 0; i < k; i++ ) |
for ( c = (LUM*)list->c, i = 0, d = 0; i < k; i++ ) |
d += DEG(c[win[i]]); |
d += DEG(c[win[i]]); |
return !(d % hint); |
return !(d % hint); |
} |
} |
|
|
int ctest(g,list,k,in) |
int ctest(g,list,k,in) |
|
|
int k; |
int k; |
int *in; |
int *in; |
{ |
{ |
register int i; |
register int i; |
int q,bound; |
int q,bound; |
int *wm,*wm1,*tmpp; |
int *wm,*wm1,*tmpp; |
DCP dc; |
DCP dc; |
Q dvr; |
Q dvr; |
N lcn,cstn,dndn,dmyn,rn; |
N lcn,cstn,dndn,dmyn,rn; |
LUM *l; |
LUM *l; |
|
|
for ( dc = DC(g); dc && DEG(dc); dc = NEXT(dc) ); |
for ( dc = DC(g); dc && DEG(dc); dc = NEXT(dc) ); |
if ( dc ) |
if ( dc ) |
cstn = NM((Q)COEF(dc)); |
cstn = NM((Q)COEF(dc)); |
else |
else |
return 1; |
return 1; |
q = list->mod; bound = list->bound; |
q = list->mod; bound = list->bound; |
ntobn(q,NM((Q)COEF(DC(g))),&lcn);; |
ntobn(q,NM((Q)COEF(DC(g))),&lcn);; |
W_CALLOC(bound+1,int,wm); W_CALLOC(bound+1,int,wm1); |
W_CALLOC(bound+1,int,wm); W_CALLOC(bound+1,int,wm1); |
for ( i = 0; i < PL(lcn); i++ ) |
for ( i = 0; i < PL(lcn); i++ ) |
wm[i] = BD(lcn)[i]; |
wm[i] = BD(lcn)[i]; |
for ( i = 0, l = (LUM *)list->c; i < k; i++ ) { |
for ( i = 0, l = (LUM *)list->c; i < k; i++ ) { |
mulpadic(q,bound,wm,COEF(l[in[i]])[0],wm1); |
mulpadic(q,bound,wm,COEF(l[in[i]])[0],wm1); |
tmpp = wm; wm = wm1; wm1 = tmpp; |
tmpp = wm; wm = wm1; wm1 = tmpp; |
} |
} |
padictoq(q,bound,wm,&dvr); |
padictoq(q,bound,wm,&dvr); |
kmuln(NM((Q)COEF(DC(g))),cstn,&dndn); divn(dndn,NM(dvr),&dmyn,&rn); |
kmuln(NM((Q)COEF(DC(g))),cstn,&dndn); divn(dndn,NM(dvr),&dmyn,&rn); |
return rn ? 0 : 1; |
return rn ? 0 : 1; |
} |
} |
|
|
/* |
/* |
int ncombi(n0,n,k,c) |
int ncombi(n0,n,k,c) |
int n0,n,k,*c; |
int n0,n,k,*c; |
{ |
{ |
register int i,tmp; |
register int i,tmp; |
|
|
if ( !k ) |
if ( !k ) |
return 0; |
return 0; |
if ( !ncombi(c[1],n,k-1,c+1) ) { |
if ( !ncombi(c[1],n,k-1,c+1) ) { |
if ( c[0] + k > n ) |
if ( c[0] + k > n ) |
return 0; |
return 0; |
else { |
else { |
for ( i = 0, tmp = c[0]; i < k; i++ ) |
for ( i = 0, tmp = c[0]; i < k; i++ ) |
c[i] = tmp + i + 1; |
c[i] = tmp + i + 1; |
return 1; |
return 1; |
} |
} |
} else |
} else |
return 1; |
return 1; |
} |
} |
*/ |
*/ |
|
|
int ncombi(n0,n,k,c) |
int ncombi(n0,n,k,c) |
int n0,n,k,*c; |
int n0,n,k,*c; |
{ |
{ |
register int i,t; |
register int i,t; |
|
|
if ( !k ) |
if ( !k ) |
return 0; |
return 0; |
for ( i = k-1; i >= 0 && c[i] == n+i-(k-1); i-- ); |
for ( i = k-1; i >= 0 && c[i] == n+i-(k-1); i-- ); |
if ( i < 0 ) |
if ( i < 0 ) |
return 0; |
return 0; |
t = ++c[i++]; |
t = ++c[i++]; |
for ( t++ ; i < k; i++, t++ ) |
for ( t++ ; i < k; i++, t++ ) |
c[i] = t; |
c[i] = t; |
return 1; |
return 1; |
} |
} |
|
|
void nthrootn(number,n,root) |
void nthrootn(number,n,root) |
int n; |
int n; |
N number,*root; |
N number,*root; |
{ |
{ |
N s,t,u,pn,base,n1,n2,q,r,gcd,num; |
N s,t,u,pn,base,n1,n2,q,r,gcd,num; |
int sgn,index,p,i,tmp,tp,mlr,num0; |
int sgn,index,p,i,tmp,tp,mlr,num0; |
|
|
for ( i = 0; !(n % 2); n /= 2, i++ ); |
for ( i = 0; !(n % 2); n /= 2, i++ ); |
for ( index = 0, num = number; ; index++ ) { |
for ( index = 0, num = number; ; index++ ) { |
if ( n == 1 ) |
if ( n == 1 ) |
goto TAIL; |
goto TAIL; |
p = lprime[index]; |
p = get_lprime(index); |
if ( !p ) |
if ( !(num0 = rem(num,p)) ) |
error("nthrootn : lprime[] exhausted."); |
continue; |
if ( !(num0 = rem(num,p)) ) |
STON(n,n1); STON(p-1,n2); gcdn(n1,n2,&gcd); |
continue; |
if ( !UNIN(gcd) ) |
STON(n,n1); STON(p-1,n2); gcdn(n1,n2,&gcd); |
continue; |
if ( !UNIN(gcd) ) |
tp = pwrm(p,num0,invm(n,p-1)); STON(tp,s); |
continue; |
mlr = invm(dmb(p,n,pwrm(p,tp,n-1),&tmp),p); |
tp = pwrm(p,num0,invm(n,p-1)); STON(tp,s); |
STON(p,base); STON(p,pn); |
mlr = invm(dmb(p,n,pwrm(p,tp,n-1),&tmp),p); |
while ( 1 ) { |
STON(p,base); STON(p,pn); |
pwrn(s,n,&t); sgn = subn(num,t,&u); |
while ( 1 ) { |
if ( !u ) { |
pwrn(s,n,&t); sgn = subn(num,t,&u); |
num = s; |
if ( !u ) { |
break; |
num = s; |
} |
break; |
if ( sgn < 0 ) { |
} |
*root = 0; |
if ( sgn < 0 ) { |
return; |
*root = 0; |
} |
return; |
divn(u,base,&q,&r); |
} |
if ( r ) { |
divn(u,base,&q,&r); |
*root = 0; |
if ( r ) { |
return; |
*root = 0; |
} |
return; |
STON(dmb(p,mlr,rem(q,p),&tmp),t); |
} |
kmuln(t,base,&u); addn(u,s,&t); s = t; |
STON(dmb(p,mlr,rem(q,p),&tmp),t); |
kmuln(base,pn,&t); base = t; |
kmuln(t,base,&u); addn(u,s,&t); s = t; |
} |
kmuln(base,pn,&t); base = t; |
TAIL : |
} |
for ( ; i; i-- ) { |
TAIL : |
sqrtn(num,&t); |
for ( ; i; i-- ) { |
if ( !t ) { |
sqrtn(num,&t); |
*root = 0; |
if ( !t ) { |
return; |
*root = 0; |
} |
return; |
num = t; |
} |
} |
num = t; |
*root = num; |
} |
return; |
*root = num; |
} |
return; |
|
} |
|
} |
} |
|
|
void sqrtn(number,root) |
void sqrtn(number,root) |
N number,*root; |
N number,*root; |
{ |
{ |
N a,s,r,q; |
N a,s,r,q; |
int sgn; |
int sgn; |
|
|
for ( a = ONEN; ; ) { |
for ( a = ONEN; ; ) { |
divn(number,a,&q,&r); sgn = subn(q,a,&s); |
divn(number,a,&q,&r); sgn = subn(q,a,&s); |
if ( !s ) { |
if ( !s ) { |
*root = !r ? a : 0; |
*root = !r ? a : 0; |
return; |
return; |
} else if ( UNIN(s) ) { |
} else if ( UNIN(s) ) { |
*root = 0; |
*root = 0; |
return; |
return; |
} else { |
} else { |
divin(s,2,&q); |
divin(s,2,&q); |
if ( sgn > 0 ) |
if ( sgn > 0 ) |
addn(a,q,&r); |
addn(a,q,&r); |
else |
else |
subn(a,q,&r); |
subn(a,q,&r); |
a = r; |
a = r; |
} |
} |
} |
} |
} |
} |
|
|
void lumtop(v,mod,bound,f,g) |
void lumtop(v,mod,bound,f,g) |
|
|
LUM f; |
LUM f; |
P *g; |
P *g; |
{ |
{ |
DCP dc,dc0; |
DCP dc,dc0; |
int **l; |
int **l; |
int i; |
int i; |
Q q; |
Q q; |
|
|
for ( dc0 = NULL, i = DEG(f), l = COEF(f); i >= 0; i-- ) { |
for ( dc0 = NULL, i = DEG(f), l = COEF(f); i >= 0; i-- ) { |
padictoq(mod,bound,l[i],&q); |
padictoq(mod,bound,l[i],&q); |
if ( q ) { |
if ( q ) { |
NEXTDC(dc0,dc); |
NEXTDC(dc0,dc); |
if ( i ) |
if ( i ) |
STOQ(i,DEG(dc)); |
STOQ(i,DEG(dc)); |
else |
else |
DEG(dc) = 0; |
DEG(dc) = 0; |
COEF(dc) = (P)q; |
COEF(dc) = (P)q; |
} |
} |
} |
} |
if ( !dc0 ) |
if ( !dc0 ) |
*g = 0; |
*g = 0; |
else { |
else { |
NEXT(dc) = 0; MKP(v,dc0,*g); |
NEXT(dc) = 0; MKP(v,dc0,*g); |
} |
} |
} |
} |
|
|
void padictoq(mod,bound,p,qp) |
void padictoq(mod,bound,p,qp) |
int mod,bound,*p; |
int mod,bound,*p; |
Q *qp; |
Q *qp; |
{ |
{ |
register int h,i,t; |
register int h,i,t; |
int br,sgn; |
int br,sgn; |
unsigned int *ptr; |
unsigned int *ptr; |
N n,tn; |
N n,tn; |
int *c; |
int *c; |
|
|
c = W_ALLOC(bound); |
c = W_ALLOC(bound); |
for ( i = 0; i < bound; i++ ) |
for ( i = 0; i < bound; i++ ) |
c[i] = p[i]; |
c[i] = p[i]; |
h = (mod%2?(mod-1)/2:mod/2); i = bound - 1; |
h = (mod%2?(mod-1)/2:mod/2); i = bound - 1; |
while ( i >= 0 && c[i] == h ) i--; |
while ( i >= 0 && c[i] == h ) i--; |
if ( i == -1 || c[i] > h ) { |
if ( i == -1 || c[i] > h ) { |
for (i = 0, br = 0; i < bound; i++ ) |
for (i = 0, br = 0; i < bound; i++ ) |
if ( ( t = -(c[i] + br) ) < 0 ) { |
if ( ( t = -(c[i] + br) ) < 0 ) { |
c[i] = t + mod; br = 1; |
c[i] = t + mod; br = 1; |
} else { |
} else { |
c[i] = 0; br = 0; |
c[i] = 0; br = 0; |
} |
} |
sgn = -1; |
sgn = -1; |
} else |
} else |
sgn = 1; |
sgn = 1; |
for ( i = bound - 1; ( i >= 0 ) && ( c[i] == 0 ); i--); |
for ( i = bound - 1; ( i >= 0 ) && ( c[i] == 0 ); i--); |
if ( i == -1 ) |
if ( i == -1 ) |
*qp = 0; |
*qp = 0; |
else { |
else { |
n = NALLOC(i+1); PL(n) = i+1; |
n = NALLOC(i+1); PL(n) = i+1; |
for ( i = 0, ptr = BD(n); i < PL(n); i++ ) |
for ( i = 0, ptr = BD(n); i < PL(n); i++ ) |
ptr[i] = c[i]; |
ptr[i] = c[i]; |
bnton(mod,n,&tn); NTOQ(tn,sgn,*qp); |
bnton(mod,n,&tn); NTOQ(tn,sgn,*qp); |
} |
} |
} |
} |
|
|
|
void padictoq_unsigned(int,int,int *,Q *); |
|
|
|
void lumtop_unsigned(v,mod,bound,f,g) |
|
V v; |
|
int mod; |
|
int bound; |
|
LUM f; |
|
P *g; |
|
{ |
|
DCP dc,dc0; |
|
int **l; |
|
int i; |
|
Q q; |
|
|
|
for ( dc0 = NULL, i = DEG(f), l = COEF(f); i >= 0; i-- ) { |
|
padictoq_unsigned(mod,bound,l[i],&q); |
|
if ( q ) { |
|
NEXTDC(dc0,dc); |
|
if ( i ) |
|
STOQ(i,DEG(dc)); |
|
else |
|
DEG(dc) = 0; |
|
COEF(dc) = (P)q; |
|
} |
|
} |
|
if ( !dc0 ) |
|
*g = 0; |
|
else { |
|
NEXT(dc) = 0; MKP(v,dc0,*g); |
|
} |
|
} |
|
|
|
void padictoq_unsigned(mod,bound,p,qp) |
|
int mod,bound,*p; |
|
Q *qp; |
|
{ |
|
register int h,i,t; |
|
int br,sgn; |
|
unsigned int *ptr; |
|
N n,tn; |
|
int *c; |
|
|
|
c = W_ALLOC(bound); |
|
for ( i = 0; i < bound; i++ ) |
|
c[i] = p[i]; |
|
for ( i = bound - 1; ( i >= 0 ) && ( c[i] == 0 ); i--); |
|
if ( i == -1 ) |
|
*qp = 0; |
|
else { |
|
n = NALLOC(i+1); PL(n) = i+1; |
|
for ( i = 0, ptr = BD(n); i < PL(n); i++ ) |
|
ptr[i] = c[i]; |
|
bnton(mod,n,&tn); NTOQ(tn,1,*qp); |
|
} |
|
} |
|
|
void mullumarray(f,list,k,in,g) |
void mullumarray(f,list,k,in,g) |
P f; |
P f; |
ML list; |
ML list; |
|
|
int *in; |
int *in; |
P *g; |
P *g; |
{ |
{ |
int np,bound,q,n,i,u; |
int np,bound,q,n,i,u; |
int *tmpp; |
int *tmpp; |
LUM lclum,wb0,wb1,tlum; |
LUM lclum,wb0,wb1,tlum; |
LUM *l; |
LUM *l; |
N lc; |
N lc; |
|
|
n = UDEG(f); np = list->n; bound = list->bound; q = list->mod; |
n = UDEG(f); np = list->n; bound = list->bound; q = list->mod; |
W_LUMALLOC(n,bound,wb0); W_LUMALLOC(n,bound,wb1); |
W_LUMALLOC(n,bound,wb0); W_LUMALLOC(n,bound,wb1); |
W_LUMALLOC(0,bound,lclum); |
W_LUMALLOC(0,bound,lclum); |
ntobn(q,NM((Q)COEF(DC(f))),&lc); |
ntobn(q,NM((Q)COEF(DC(f))),&lc); |
for ( i = 0, tmpp = COEF(lclum)[0], u = MIN(bound,PL(lc)); |
for ( i = 0, tmpp = COEF(lclum)[0], u = MIN(bound,PL(lc)); |
i < u; i++ ) |
i < u; i++ ) |
tmpp[i] = BD(lc)[i]; |
tmpp[i] = BD(lc)[i]; |
l = (LUM *)list->c; |
l = (LUM *)list->c; |
mullum(q,bound,lclum,l[in[0]],wb0); |
mullum(q,bound,lclum,l[in[0]],wb0); |
for ( i = 1; i < k; i++ ) { |
for ( i = 1; i < k; i++ ) { |
mullum(q,bound,l[in[i]],wb0,wb1); |
mullum(q,bound,l[in[i]],wb0,wb1); |
tlum = wb0; wb0 = wb1; wb1 = tlum; |
tlum = wb0; wb0 = wb1; wb1 = tlum; |
} |
} |
lumtop(VR(f),q,bound,wb0,g); |
lumtop(VR(f),q,bound,wb0,g); |
} |
} |
|
|
void ucsump(f,s) |
void ucsump(f,s) |
P f; |
P f; |
Q *s; |
Q *s; |
{ |
{ |
Q t,u; |
Q t,u; |
DCP dc; |
DCP dc; |
|
|
for ( dc = DC(f), t = 0; dc; dc = NEXT(dc) ) { |
for ( dc = DC(f), t = 0; dc; dc = NEXT(dc) ) { |
addq((Q)COEF(dc),t,&u); t = u; |
addq((Q)COEF(dc),t,&u); t = u; |
} |
} |
*s = t; |
*s = t; |
} |
} |
|
|