void G2::restore(char *bytes) { int i,j,n=(1<<WINDOW_SIZE); int bytes_per_big=(MIRACL/8)*(get_mip()->nib-1); int len=n*2*bytes_per_big; Big x,y,B; if (mtable!=NULL) return; mtable=new ECn[1<<WINDOW_SIZE]; B=getB(); B=-B; ecurve((Big)-3,B,get_modulus(),MR_PROJECTIVE); // move to twist for (i=j=0;i<n;i++) { x=from_binary(bytes_per_big,&bytes[j]); j+=bytes_per_big; y=from_binary(bytes_per_big,&bytes[j]); j+=bytes_per_big; mtable[i].set(x,y); } B=-B; ecurve((Big)-3,B,get_modulus(),MR_PROJECTIVE); // move back delete [] bytes; }
void PFC::random(G1& w) { Big x0; if (RNG==NULL) x0=rand(get_modulus()); else x0=strong_rand(RNG,get_modulus()); while (!w.g.set(x0,x0)) x0+=1; w.g*=(*cof); }
Big H1(char *string) { // Hash a zero-terminated string to a number < modulus Big h,p; char s[HASH_LEN]; int i,j; sha256 sh; shs256_init(&sh); for (i=0;;i++) { if (string[i]==0) break; shs256_process(&sh,string[i]); } shs256_hash(&sh,s); p=get_modulus(); h=1; j=0; i=1; forever { h*=256; if (j==HASH_LEN) {h+=i++; j=0;} else h+=s[j++]; if (h>=p) break; } h%=p; return h; }
Big PFC::hash_to_group(char *buffer, int len) { Big h,p; char s[HASH_LEN]; int i,j; sha256 sh; shs256_init(&sh); for (i=0; i < len; i++) { shs256_process(&sh,buffer[i]); } shs256_hash(&sh,s); p=get_modulus(); h=1; j=0; i=1; forever { h*=256; if (j==HASH_LEN) {h+=i++; j=0;} else h+=(unsigned char)s[j++]; if (h>=p) break; } h%=p; return h % (*ord); }
ostream& operator<<(ostream& s,const Poly& p) { BOOL first=TRUE; ZZn a; term *ptr=p.start; if (ptr==NULL) { s << "0"; return s; } while (ptr!=NULL) { a=ptr->an; if ((Big)a<get_modulus()/2) { if (!first) s << " + "; } else { a=(-a); s << " - "; } if (ptr->n==0) cout << a; else { if (a!=(ZZn)1) s << a << "*x"; else s << "x"; if (ptr->n!=1) s << "^" << ptr->n; } first=FALSE; ptr=ptr->next; } return s; }
void PFC::random(G1& w) { Big x0=rand(get_modulus()); while (!w.g.set(x0,x0)) x0+=1; w.g*=(*cof); }
Poly factor(const Poly& f,int d) { Poly c,u,h,g=f; Big r,p=get_modulus(); while (degree(g) > d) { // random monic polynomial u.clear(); u.addterm((ZZn)1,2*d-1); for (int i=2*d-2;i>=0;i--) { r=rand(p); u.addterm((ZZn)r,i); } r=(pow(p,d)-1)/2; c=pow(u,r,g); c.addterm((ZZn)(-1),0); h=gcd(c,g); if (degree(h)==0 || degree(h)==degree(g)) continue; if (2*degree(h)>degree(g)) g=g/h; else g=h; } return g; }
void get_modulus(zz_pX& pi_1, zz_pX& pi_2, zz_pX& a, int p, int d1, int d2) { get_modulus(pi_1, p, d1); get_modulus(pi_2, p, d1*d2); // find alpha zz_pE::init(pi_2); zz_pEX pi; conv(pi, pi_1); zz_pE zero; FindRoot(zero, pi); a = rep(zero); }
int main(int argc, char **argv) { zz_pX pi_1, pi_2, a; get_modulus(pi_1, pi_2, a, 5, 2, 2); long q = to_long(zz_pE::cardinality()); cout << "q = " << q << endl; cout << "pi_1 = " << pi_1 << endl; cout << "pi_2 = " << pi_2 << endl; cout << "a = " << a << endl; }
GT PFC::final_exp(const GT& z) { GT y; Big p; ZZn2 res; res=z.g; p=get_modulus(); // get p res=conj(res)/res; res=pow(res,(p+1)/(*ord)); // raise to power of (p^2-1)/q y.g=res; return y; }
void set_frobenius_constant(ZZn2 &X) { Big p=get_modulus(); switch (get_mip()->pmod8) { case 5: X.set((Big)0,(Big)1); // = (sqrt(-2)^(p-1)/2 break; case 3: // = (1+sqrt(-1))^(p-1)/2 X.set((Big)1,(Big)1); break; case 7: X.set((Big)2,(Big)1); // = (2+sqrt(-1))^(p-1)/2 default: break; } X=pow(X,(p-1)/3); }
void init_NTL_ff(int p, int d, int precompute_inverses, int precompute_square_roots, int precompute_legendre_char, int precompute_pth_frobenius_map) { zz_pX pi; get_modulus(pi, p, d); zz_pE::init(pi); // make sure size of finite field fits in a long assert(zz_pE::cardinality().WideSinglePrecision()); zz_pEExtraContext c(precompute_inverses, precompute_square_roots, precompute_legendre_char, precompute_pth_frobenius_map); c.restore(); }
ostream& operator<<(ostream& s,const Ps_ZZn& p) { BOOL first=TRUE; ZZn a; term_ps_zzn *ptr=p.start; int pw; if (ptr==NULL) { s << "0"; return s; } while (ptr!=NULL) { a=ptr->an; if (a.iszero()) { ptr=ptr->next; continue; } if ((Big)a < get_modulus()/2) { a=(-a); s << " - "; } else if (!first) s << " + "; first=FALSE; pw=ptr->n*p.pwr-p.offset; if (pw==0) { s << a; ptr=ptr->next; continue; } if (a==(ZZn)1) s << "x"; else s << a << "*x"; if (pw!=1) s << "^" << pw; ptr=ptr->next; } return s; }
ostream& operator<<(ostream& s,const PolyXY& p) { BOOL first=TRUE; ZZn a; termXY *ptr=p.start; if (ptr==NULL) { s << "0"; return s; } while (ptr!=NULL) { a=ptr->an; if ((Big)a<get_modulus()/2) { if (!first) s << " + "; } else { a=(-a); s << " - "; } if (ptr->nx==0 && ptr->ny==0) s << a; else { if (a!=(ZZn)1) s << a << "*"; if (ptr->nx!=0) { s << "x"; if (ptr->nx!=1) s << "^" << ptr->nx; } if (ptr->ny!=0) { if (ptr->nx!=0) s << "."; s << "y"; if (ptr->ny!=1) s << "^" << ptr->ny; } } first=FALSE; ptr=ptr->next; } return s; }
void set_frobenius_constant(ZZn &X) { // Note X=NR^[(p-13)/18]; Big p=get_modulus(); X=pow((ZZn)NR,(p-13)/18); }