/* computing of $(-t^2 +u*s -t*p -p^2)^3$ * The algorithm is by J.Beuchat et.al, in the paper of "Algorithms and Arithmetic Operators for Computing * the $eta_T$ Pairing in Characteristic Three", algorithm 4 in the appendix */ static void algorithm4a(element_t S, element_t t, element_t u) { field_ptr f = FIELD(t); element_t e1, c0, c1, m0, v0, v2; element_init(e1, f); element_init(c0, f); element_init(c1, f); element_init(m0, f); element_init(v0, f); element_init(v2, f); element_set1(e1); element_cubic(c0, t); // c0 == t^3 element_cubic(c1, u); element_neg(c1, c1); // c1 == -u^3 element_mul(m0, c0, c0); // m0 == c0^2 element_neg(v0, m0); // v0 == -c0^2 element_sub(v0, v0, c0); // v0 == -c0^2 -c0 element_sub(v0, v0, e1); // v0 == -c0^2 -c0 -1 element_set1(v2); element_sub(v2, v2, c0); // v2 == 1 -c0 // v1 == c1 // S == [[v0, v1], [v2, f3m.zero()], [f3m.two(), f3m.zero()]] element_set(ITEM(S,0,0), v0); element_set(ITEM(S,0,1), c1); element_set(ITEM(S,1,0), v2); element_set0(ITEM(S,1,1)); element_neg(ITEM(S,2,0), e1); element_set0(ITEM(S,2,1)); element_clear(e1); element_clear(c0); element_clear(c1); element_clear(m0); element_clear(v0); element_clear(v2); }
/* $e<- a*b$ */ static void gf32m_mult(element_t e, element_t a, element_t b) { element_ptr a0 = GF32M(a)->_0, a1 = GF32M(a)->_1, b0 = GF32M(b)->_0, b1 = GF32M(b)->_1, e0 = GF32M(e)->_0, e1 = GF32M(e)->_1; field_ptr base = BASE(a); element_t a0b0, a1b1, t0, t1, c1; element_init(a0b0, base); element_init(a1b1, base); element_init(t0, base); element_init(t1, base); element_init(c1, base); element_mul(a0b0, a0, b0); element_mul(a1b1, a1, b1); element_add(t0, a1, a0); element_add(t1, b1, b0); element_mul(c1, t0, t1); // c1 == (a1+a0)*(b1+b0) element_sub(c1, c1, a1b1); element_sub(c1, c1, a0b0); element_ptr c0 = a0b0; element_sub(c0, c0, a1b1); // c0 == a0*b0 - a1*b1 element_set(e0, c0); element_set(e1, c1); element_clear(a0b0); element_clear(a1b1); element_clear(t0); element_clear(t1); element_clear(c1); }
static void gf33m_assign(element_t e, element_t a) { element_ptr a0 = GF33M(a)->_0, a1 = GF33M(a)->_1, a2 = GF33M(a)->_2, e0 = GF33M(e)->_0, e1 = GF33M(e)->_1, e2 = GF33M(e)->_2; element_set(e0, a0); element_set(e1, a1); element_set(e2, a2); }
// The final powering, where we standardize the coset representative. static void cc_tatepower(element_ptr out, element_ptr in, pairing_t pairing) { pptr p = pairing->data; #define qpower(sign) { \ polymod_const_mul(e2, inre[1], p->xpowq); \ element_set(e0re, e2); \ polymod_const_mul(e2, inre[2], p->xpowq2); \ element_add(e0re, e0re, e2); \ element_add(e0re0, e0re0, inre[0]); \ \ if (sign > 0) { \ polymod_const_mul(e2, inim[1], p->xpowq); \ element_set(e0im, e2); \ polymod_const_mul(e2, inim[2], p->xpowq2); \ element_add(e0im, e0im, e2); \ element_add(e0im0, e0im0, inim[0]); \ } else { \ polymod_const_mul(e2, inim[1], p->xpowq); \ element_neg(e0im, e2); \ polymod_const_mul(e2, inim[2], p->xpowq2); \ element_sub(e0im, e0im, e2); \ element_sub(e0im0, e0im0, inim[0]); \ } \ } if (p->k == 6) { // See thesis, section 6.9, "The Final Powering", which gives a formula // for the first step of the final powering when Fq6 has been implemented // as a quadratic extension on top of a cubic extension. element_t e0, e2, e3; element_init(e0, p->Fqk); element_init(e2, p->Fqd); element_init(e3, p->Fqk); element_ptr e0re = element_x(e0); element_ptr e0im = element_y(e0); element_ptr e0re0 = ((element_t *) e0re->data)[0]; element_ptr e0im0 = ((element_t *) e0im->data)[0]; element_t *inre = element_x(in)->data; element_t *inim = element_y(in)->data; // Expressions in the formula are similar, hence the following function. qpower(1); element_set(e3, e0); element_set(e0re, element_x(in)); element_neg(e0im, element_y(in)); element_mul(e3, e3, e0); qpower(-1); element_mul(e0, e0, in); element_invert(e0, e0); element_mul(in, e3, e0); element_set(e0, in); // We use Lucas sequences to complete the final powering. lucas_even(out, e0, pairing->phikonr); element_clear(e0); element_clear(e2); element_clear(e3); } else { element_pow_mpz(out, in, p->tateexp); } #undef qpower }
static void point_add(element_t c, element_t a, element_t b) { point_ptr p1 = DATA(a), p2 = DATA(b), p3 = DATA(c); int inf1 = p1->isinf, inf2 = p2->isinf; element_ptr x1 = p1->x, y1 = p1->y, x2 = p2->x, y2 = p2->y; field_ptr f = FIELD(x1); if (inf1) { point_set(c, b); return; } if (inf2) { point_set(c, a); return; } element_t v0, v1, v2, v3, v4, ny2; element_init(v0, f); element_init(v1, f); element_init(v2, f); element_init(v3, f); element_init(v4, f); element_init(ny2, f); if (!element_cmp(x1, x2)) { // x1 == x2 element_neg(ny2, y2); // ny2 == -y2 if (!element_cmp(y1, ny2)) { p3->isinf = 1; goto end; } if (!element_cmp(y1, y2)) { // y1 == y2 element_invert(v0, y1); // v0 == y1^{-1} element_mul(v1, v0, v0); // v1 == [y1^{-1}]^2 element_add(p3->x, v1, x1); // v1 == [y1^{-1}]^2 + x1 element_cubic(v2, v0); // v2 == [y1^{-1}]^3 element_add(v2, v2, y1); // v2 == [y1^{-1}]^3 + y1 element_neg(p3->y, v2); // p3 == -([y1^{-1}]^3 + y1) p3->isinf = 0; goto end; } } // $P1 \ne \pm P2$ element_sub(v0, x2, x1); // v0 == x2-x1 element_invert(v1, v0); // v1 == (x2-x1)^{-1} element_sub(v0, y2, y1); // v0 == y2-y1 element_mul(v2, v0, v1); // v2 == (y2-y1)/(x2-x1) element_mul(v3, v2, v2); // v3 == [(y2-y1)/(x2-x1)]^2 element_cubic(v4, v2); // v4 == [(y2-y1)/(x2-x1)]^3 element_add(v0, x1, x2); // v0 == x1+x2 element_sub(v3, v3, v0); // v3 == [(y2-y1)/(x2-x1)]^2 - (x1+x2) element_add(v0, y1, y2); // v0 == y1+y2 element_sub(v4, v0, v4); // v4 == (y1+y2) - [(y2-y1)/(x2-x1)]^3 p3->isinf = 0; element_set(p3->x, v3); element_set(p3->y, v4); end: element_clear(v0); element_clear(v1); element_clear(v2); element_clear(v3); element_clear(v4); element_clear(ny2); }
//c_iとk_iをペアリングする関数 //¬記号で別々の処理する //(v_i - x_t)も必要→とりあえず置いておこう……→一応できた? Element *pairing_c_k(EC_PAIRING p, rho_i *rho, EC_POINT *c, EC_POINT *k, mpz_t *alpha_i) { int i; Element *result; result = (Element*)malloc(sizeof(Element)); Element egg, tempegg1, tempegg2; element_init(egg, p->g3); element_init(tempegg1, p->g3); element_init(tempegg2, p->g3); element_init(*result, p->g3); mpz_t temp1; mpz_init(temp1); mpz_t temp2; mpz_init(temp2); mpz_t order; mpz_init(order); mpz_set(order, *pairing_get_order(p)); element_set_one(*result); if (alpha_i == NULL && rho == NULL) { //e(c_0, k_0) for (i = 0; i < 5; i++) { pairing_map(tempegg1, c[i], k[i], p); element_mul(tempegg2, tempegg1, *result); element_set(*result, tempegg2); } } else if (mpz_cmp_ui(*alpha_i, 0) == 0) {//return 1 } else if (rho->is_negated == FALSE) { for (i = 0; i < 7; i++) { pairing_map(tempegg1, c[i], k[i], p); element_mul(tempegg2, tempegg1, *result); element_set(*result, tempegg2); } element_pow(tempegg1, *result, *alpha_i); element_set(*result, tempegg1); } else { //is_negated == TRUE for (i = 0; i < 7; i++) { pairing_map(tempegg1, c[i], k[i], p); element_mul(tempegg2, tempegg1, *result); element_set(*result, tempegg2); } mpz_set_ui(temp1, rho->v_t[0]); //v_i - x_t mpz_invert(temp2, temp1, order); mpz_mul(temp1, temp2, *alpha_i); // alpha_i / (v_i - x_t) mpz_mod(*alpha_i, temp1, order); element_pow(tempegg1, *result, *alpha_i); element_set(*result, tempegg1); } mpz_clear(order); mpz_clear(temp2); mpz_clear(temp1); element_clear(egg); element_clear(tempegg1); element_clear(tempegg2); return result; }
void point_set_xy(EC_POINT p, const Element x, const Element y) { element_set(p->x, x); element_set(p->y, y); element_set_one(p->z); p->isinfinity = FALSE; }
static void point_set(element_t e, element_t a) { point_ptr r = DATA(e), p = DATA(a); r->isinf = p->isinf; if (!p->isinf) { element_set(r->x, p->x); element_set(r->y, p->y); } }
/* $c <- a*b$ */ static void gf33m_mult(element_t e, element_t a, element_t b) { element_ptr a0 = GF33M(a)->_0, a1 = GF33M(a)->_1, a2 = GF33M(a)->_2, b0 = GF33M(b)->_0, b1 = GF33M(b)->_1, b2 = GF33M(b)->_2, e0 = GF33M(e)->_0, e1 = GF33M(e)->_1, e2 = GF33M(e)->_2; field_ptr base = BASE(e); element_t t0, t1, c1, a0b0, a1b1, a2b2; element_init(t0, base); element_init(t1, base); element_init(c1, base); element_init(a0b0, base); element_init(a1b1, base); element_init(a2b2, base); element_mul(a0b0, a0, b0); element_mul(a1b1, a1, b1); element_mul(a2b2, a2, b2); element_ptr d0 = a0b0; element_add(t0, a1, a0); element_add(t1, b1, b0); element_t d1; element_init(d1, base); element_mul(d1, t0, t1); element_sub(d1, d1, a1b1); element_sub(d1, d1, a0b0); element_add(t0, a2, a0); element_add(t1, b2, b0); element_t d2; element_init(d2, base); element_mul(d2, t0, t1); element_add(d2, d2, a1b1); element_sub(d2, d2, a2b2); element_sub(d2, d2, a0b0); element_add(t0, a2, a1); element_add(t1, b2, b1); element_t d3; element_init(d3, base); element_mul(d3, t0, t1); element_sub(d3, d3, a2b2); element_sub(d3, d3, a1b1); element_ptr d4 = a2b2; element_add(t0, d0, d3); element_ptr c0 = t0; element_add(c1, d1, d3); element_add(c1, c1, d4); element_add(t1, d2, d4); element_ptr c2 = t1; element_set(e0, c0); element_set(e1, c1); element_set(e2, c2); element_clear(t0); element_clear(t1); element_clear(c1); element_clear(a0b0); element_clear(a1b1); element_clear(a2b2); element_clear(d1); element_clear(d2); element_clear(d3); }
/* $e <- a^{-1}$ */ static void gf33m_invert(element_t e, element_t a) { element_ptr a0 = GF33M(a)->_0, a1 = GF33M(a)->_1, a2 = GF33M(a)->_2, e0 = GF33M(e)->_0, e1 = GF33M(e)->_1, e2 = GF33M(e)->_2; field_ptr base = BASE(e); element_t a02, a12, a22; element_init(a02, base); element_init(a12, base); element_init(a22, base); element_mul(a02, a0, a0); element_mul(a12, a1, a1); element_mul(a22, a2, a2); element_t v0; element_init(v0, base); element_sub(v0, a0, a2); // v0 == a0-a2 element_t delta; element_init(delta, base); element_mul(delta, v0, a02); // delta = (a0-a2)*(a0^2), free element_sub(v0, a1, a0); // v0 == a1-a0 element_t c0; element_init(c0, base); element_mul(c0, v0, a12); // c0 == (a1-a0)*(a1^2) element_add(delta, delta, c0); // delta = (a0-a2)*(a0^2) + (a1-a0)*(a1^2) element_sub(v0, a2, v0); // v0 == a2-(a1-a0) = a0-a1+a2 element_t c1; element_init(c1, base); element_mul(c1, v0, a22); // c1 == (a0-a1+a2)*(a2^2) element_add(delta, delta, c1); // delta = (a0-a2)*(a0^2) + (a1-a0)*(a1^2) + (a0-a1+a2)*(a2^2) element_invert(delta, delta); // delta = [(a0-a2)*(a0^2) + (a1-a0)*(a1^2) + (a0-a1+a2)*(a2^2)] ^ {-1} element_add(v0, a02, a22); // v0 == a0^2+a2^2 element_t c2; element_init(c2, base); element_mul(c2, a0, a2); // c2 == a0*a2 element_sub(c0, v0, c2); // c0 == a0^2+a2^2-a0*a2 element_add(v0, a1, a2); // v0 == a1+a2 element_t c3; element_init(c3, base); element_mul(c3, a1, v0); // c3 == a1*(a1+a2) element_sub(c0, c0, c3); // c0 == a0^2+a2^2-a0*a2-a1*(a1+a2) element_mul(c0, c0, delta); // c0 *= delta element_mul(c1, a0, a1); // c1 == a0*a1 element_sub(c1, a22, c1); // c1 == a2^2-a0*a1 element_mul(c1, c1, delta); // c1 *= delta element_sub(c2, a12, c2); // c2 == a1^2-a0*a2 element_sub(c2, c2, a22); // c2 == a1^2-a0*a2-a2^2 element_mul(c2, c2, delta); // c2 *= delta element_set(e0, c0); element_set(e1, c1); element_set(e2, c2); element_clear(a02); element_clear(a12); element_clear(a22); element_clear(v0); element_clear(delta); element_clear(c0); element_clear(c1); element_clear(c2); element_clear(c3); }
static void sn_add(element_t c, element_t a, element_t b) { point_ptr r = c->data; point_ptr p = a->data; point_ptr q = b->data; if (p->inf_flag) { sn_set(c, b); return; } if (q->inf_flag) { sn_set(c, a); return; } if (!element_cmp(p->x, q->x)) { if (!element_cmp(p->y, q->y)) { if (element_is0(p->y)) { r->inf_flag = 1; return; } else { sn_double_no_check(r, p); return; } } //points are inverses of each other r->inf_flag = 1; return; } else { element_t lambda, e0, e1; element_init(lambda, p->x->field); element_init(e0, p->x->field); element_init(e1, p->x->field); //lambda = (y2-y1)/(x2-x1) element_sub(e0, q->x, p->x); element_invert(e0, e0); element_sub(lambda, q->y, p->y); element_mul(lambda, lambda, e0); //x3 = lambda^2 - x1 - x2 - 1 element_square(e0, lambda); element_sub(e0, e0, p->x); element_sub(e0, e0, q->x); element_set1(e1); element_sub(e0, e0, e1); //y3 = (x1-x3)lambda - y1 element_sub(e1, p->x, e0); element_mul(e1, e1, lambda); element_sub(e1, e1, p->y); element_set(r->x, e0); element_set(r->y, e1); r->inf_flag = 0; element_clear(lambda); element_clear(e0); element_clear(e1); } }
//-------------------------------------------------- // square root in extended Fp //-------------------------------------------------- int bn254_fp2_sqrt(Element z, const Element x) { mpz_t _v; int m, r, i; field_precomp_sqrt_p ps; Element *t = field(z)->tmp; if (!element_is_sqr(x)) { return FALSE; } ps = ((field_precomp_p)(field(x)->precomp))->ps; element_set(t[0], ps->n_v); // t0 = n^v r = ps->e; // r = e mpz_init_set(_v, ps->v); mpz_sub_ui(_v, _v, 1); mpz_tdiv_q_2exp(_v, _v, 1); element_pow(t[1], x, _v); // t1 = x^{(v-1)/2} element_sqr(t[2], t[1]); element_mul(t[2], t[2], x); // t2 = x*t1^2 element_mul(t[1], x, t[1]); // t1 = x*t1 mpz_clear(_v); while (!element_is_one(t[2])) { m = 0; element_set(t[3], t[2]); do { element_sqr(t[3], t[3]); m++; } while (!element_is_one(t[3]) && m < r); r = r - m - 1; element_set(t[3], t[0]); for (i = 1; i <= r; i++) { element_sqr(t[3], t[3]); } // t3 = t2^{r-m-1} element_sqr(t[0], t[3]); // t0 = t3^2 r = m; element_mul(t[1], t[1], t[3]);// t1 = t1*t3 element_mul(t[2], t[2], t[0]);// t2 = t2*t0 } element_set(z, t[1]); return TRUE; }
static void sn_set(element_ptr c, element_ptr a) { point_ptr r = c->data, p = a->data; if (p->inf_flag) { r->inf_flag = 1; return; } r->inf_flag = 0; element_set(r->x, p->x); element_set(r->y, p->y); }
static void curve_mul(element_ptr c, element_ptr a, element_ptr b) { curve_data_ptr cdp = (curve_data_ptr)a->field->data; point_ptr r = (point_ptr)c->data, p = (point_ptr)a->data, q = (point_ptr)b->data; if (p->inf_flag) { curve_set(c, b); return; } if (q->inf_flag) { curve_set(c, a); return; } if (!element_cmp(p->x, q->x)) { if (!element_cmp(p->y, q->y)) { if (element_is0(p->y)) { r->inf_flag = 1; return; } else { double_no_check(r, p, cdp->a); return; } } //points are inverses of each other r->inf_flag = 1; return; } else { element_t lambda, e0, e1; element_init(lambda, cdp->field); element_init(e0, cdp->field); element_init(e1, cdp->field); //lambda = (y2-y1)/(x2-x1) element_sub(e0, q->x, p->x); element_invert(e0, e0); element_sub(lambda, q->y, p->y); element_mul(lambda, lambda, e0); //x3 = lambda^2 - x1 - x2 element_square(e0, lambda); element_sub(e0, e0, p->x); element_sub(e0, e0, q->x); //y3 = (x1-x3)lambda - y1 element_sub(e1, p->x, e0); element_mul(e1, e1, lambda); element_sub(e1, e1, p->y); element_set(r->x, e0); element_set(r->y, e1); r->inf_flag = 0; element_clear(lambda); element_clear(e0); element_clear(e1); } }
void miller(element_t z, element_t PR, element_t R, element_t P, element_t Q) { int m = mpz_sizeinbase(order, 2) - 2; element_t Z; element_t z1; element_t x1; element_init_same_as(Z, PR); element_set(Z, P); element_set1(z); element_init_same_as(z1, z); element_init_same_as(x1, z); do_vert(x1, PR, Q); element_printf("vert(P+R) %B\n", x1); do_line(z1, P, R, Q); element_printf("line(P,R) %B\n", z1); element_div(x1, x1, z1); element_printf("x1 %B\n", x1); element_set(z, x1); for (;;) { printf("iteration %d: %d\n", m, mpz_tstbit(order,m)); element_square(z, z); element_printf("squared: %B\n", z); do_tangent(z1, Z, Q); element_mul(z, z, z1); element_double(Z, Z); do_vert(z1, Z, Q); element_div(z, z, z1); element_printf("pre-if: %B\n", z); if (mpz_tstbit(order, m)) { element_mul(z, z, x1); do_vert(z1, P, Q); element_mul(z, z, z1); element_printf("done %B\n", z); /* do_line(z1, Z, P, Q); element_mul(z, z, z1); element_add(Z, Z, P); do_vert(z1, Z, Q); element_div(z, z, z1); */ } if (!m) break; m--; } element_clear(x1); element_clear(z1); }
static void record(element_t asum, element_t bsum, element_t snark, darray_t hole, mpz_t counter) { snapshot_ptr ss = pbc_malloc(sizeof(struct snapshot_s)); element_init_same_as(ss->a, asum); element_init_same_as(ss->b, bsum); element_init_same_as(ss->snark, snark); element_set(ss->a, asum); element_set(ss->b, bsum); element_set(ss->snark, snark); darray_append(hole, ss); element_printf("snark %Zd: %B\n", counter, snark); }
/* $e <- a^3$ */ static void gf32m_cubic(element_t e, element_t a) { element_ptr a0 = GF32M(a)->_0, a1 = GF32M(a)->_1, e0 = GF32M(e)->_0, e1 = GF32M(e)->_1; field_ptr base = BASE(a); element_t c0, c1; element_init(c0, base); element_init(c1, base); element_cubic(c0, a0); element_cubic(c1, a1); element_neg(c1, c1); // c1 == -(a1^3) element_set(e0, c0); element_set(e1, c1); element_clear(c0); element_clear(c1); }
// USER JOIN PHASE 4 - user key generation (Join) int xsgs_user_join_phase4(XSGS_PUBLIC_KEY* gpk, XSGS_USER_DB_ENTRY* udbe, XSGS_JOIN_PHASE3* jpd3, XSGS_JOIN_PHASE4* jpd4, char* upk_pem_filename) { int ret; pairing_ptr pairing = gpk->pairing; field_ptr Fp = pairing->Zr; DWORD msg_len = element_length_in_bytes(udbe->UCert.A); BYTE* msg = (BYTE*) malloc(msg_len); element_to_bytes(msg, udbe->UCert.A); /* TODO Verify_PK_CA(cert_user) */ ret = xsgs_rsa_verify(upk_pem_filename, msg, msg_len, jpd3->S.sig, jpd3->S.len); free(msg); udbe->S.len = jpd3->S.len; udbe->S.sig = (BYTE*) malloc(udbe->S.len); memcpy(udbe->S.sig, jpd3->S.sig, udbe->S.len); element_init(jpd4->x, Fp); element_set(jpd4->x, udbe->UCert.x); return ret; }
static void fi_sqrt(element_ptr n, element_ptr e) { eptr p = e->data; eptr r = n->data; element_t e0, e1, e2; // If (a+bi)^2 = x+yi then 2a^2 = x +- sqrt(x^2 + y^2) // where we choose the sign so that a exists, and 2ab = y. // Thus 2b^2 = - (x -+ sqrt(x^2 + y^2)). element_init(e0, p->x->field); element_init(e1, e0->field); element_init(e2, e0->field); element_square(e0, p->x); element_square(e1, p->y); element_add(e0, e0, e1); element_sqrt(e0, e0); // e0 = sqrt(x^2 + y^2) element_add(e1, p->x, e0); element_set_si(e2, 2); element_invert(e2, e2); element_mul(e1, e1, e2); // e1 = (x + sqrt(x^2 + y^2))/2 if (!element_is_sqr(e1)) { element_sub(e1, e1, e0); // e1 should be a square. } element_sqrt(e0, e1); element_add(e1, e0, e0); element_invert(e1, e1); element_mul(r->y, p->y, e1); element_set(r->x, e0); element_clear(e0); element_clear(e1); element_clear(e2); }
void CipherText::compute_node(element_t& v, Node* node){//v amounts to s if(node->getType() == LEAF){ Leaf* leaf = (Leaf*)node; leaf->compute(&v, this->pub, this->p); // printf("leaf: %d, %d, computed\n", leaf->getK(), leaf->getNum()); } else if (node->getType() == INTERNAL_NODE){ InternalNode* internalNode = (InternalNode*)node; int num = internalNode->getNum(); int k = internalNode->getK(); Node** sons = internalNode->getSons();//?? // printf("internal Node: %d, %d\n", k, num); element_t* ys = (element_t*)malloc(sizeof(element_t) * (num + 1)); element_init_Zr(ys[0], *(this->p)); element_set(ys[0], v); //set ys[0] to v computePoints(ys, k, num); //compute other num point, int i = 1; for (i = 1; i <= num; i++){ compute_node(ys[i], sons[i - 1]); } } }
/* computing $c <- U^M, M=(3^{3m}-1)*(3^m+1)*(3^m+1-\mu*b*3^{(m+1)//2})$ * This is the algorithm 8 in the paper above. */ static void algorithm8(element_t c, element_t u) { field_ptr f6 = FIELD(u), f = FIELD(ITEM(u,0,0)); params *p = (params *) f->data; element_t v, w; element_init(v, f6); element_init(w, f6); algorithm6(v, u); algorithm7(v, v); element_set(w, v); int i; for (i = 0; i < (p->m + 1) / 2; i++) element_cubic(w, w); algorithm7(v, v); if (p->m % 12 == 1 || p->m % 12 == 11) { // w <= w^{-\mu*b} element_ptr e; e = ITEM(w,0,1); element_neg(e, e); e = ITEM(w,1,1); element_neg(e, e); e = ITEM(w,2,1); element_neg(e, e); } element_mul(c, v, w); element_clear(v); element_clear(w); }
static val_ptr eval_elem(tree_ptr t) { // TODO: Write element_clone(), or at least element_new(). element_ptr e = (element_ptr)pbc_malloc(sizeof(*e)); element_init_same_as(e, t->elem); element_set(e, t->elem); return val_new_element(e); }
void millertate(element_t z, element_t P, element_t Q) { element_t Z; element_t z0; element_init_same_as(Z, P); element_init_same_as(z0, z); element_set(Z, P); do_tangent(z, Z, Q); element_double(Z, Z); do_vert(z0, Z, Q); element_div(z, z, z0); element_printf("presquare: z = %B\n", z); element_square(z, z); element_printf("square: z = %B\n", z); do_tangent(z0, Z, Q); element_mul(z, z, z0); element_clear(z0); element_clear(Z); }
//Called in file encryption function to generate C0,C1,C0',C1' and EK //returns CT,EK void EK_CT_generate(char *gamma, int *shared_users, int num_users, unsigned char *pps, ct CT, element_t EK, char *t_str) { global_broadcast_params_t gbs; element_t t; int j; //Global Setup of gbs params setup_global_broadcast_params(&gbs, pps); element_set_str(gbs->gamma, gamma, PBC_CONVERT_BASE); //it is important to set user gamma here else a random value will be used //pick a random value of t from Zr element_init_Zr(t, gbs->pairing); element_random(t); element_snprint(t_str,MAX_ELEMENT_LEN,t); //compute C0=g^t element_init(CT->OC0, gbs->pairing->G1); element_pow_zn(CT->OC0, gbs->g, t); //compute C1=(g^gamma)x(g[num_users+1-j]) for j in all shared users element_init(CT->OC1, gbs->pairing->G1); element_pow_zn(CT->OC1, gbs->g, gbs->gamma); //at this step C1 = g^gamma = v as given in paper for(j=0;j<num_users;j++) element_mul(CT->OC1, CT->OC1, gbs->gs[(gbs->num_users)-shared_users[j]]); element_pow_zn(CT->OC1, CT->OC1, t); //Duplicate C0'=C0 element_init(CT->C0, gbs->pairing->G1); element_set(CT->C0,CT->OC0); //Duplicate C1'=C1 element_init(CT->C1, gbs->pairing->G1); element_set(CT->C1,CT->OC1); //COMPUTE EK = e(g[n], g[1])^(t) element_init(EK, gbs->pairing->GT); element_pairing(EK, gbs->gs[0],gbs->gs[gbs->num_users-1]); //at this step EK = e(g[1],g[n]) element_pow_zn(EK,EK,t); //EK = e(g[1],g[n])^t //free the memory for global broadcast params element_clear(t); FreeGBP(gbs); return; }
static void fi_square(element_ptr n, element_ptr a) { eptr p = a->data; eptr r = n->data; element_t e0, e1; element_init(e0, p->x->field); element_init(e1, e0->field); // Re(n) = x^2 - y^2 = (x+y)(x-y) element_add(e0, p->x, p->y); element_sub(e1, p->x, p->y); element_mul(e0, e0, e1); // Im(n) = 2xy element_mul(e1, p->x, p->y); element_add(e1, e1, e1); element_set(r->x, e0); element_set(r->y, e1); element_clear(e0); element_clear(e1); }
void bn254_fp2_pow(Element z, const Element x, const mpz_t exp) { long t, i; Element c; element_init(c, field(z)); element_set(c, x); t = (long)mpz_sizeinbase(exp, 2); for (i = t - 2; i >= 0; i--) { element_sqr(c, c); if (mpz_tstbit(exp, i)) { element_mul(c, c, x); } } element_set(z, c); element_clear(c); }
static void curve_invert(element_ptr c, element_ptr a) { point_ptr r = (point_ptr)c->data, p = (point_ptr)a->data; if (p->inf_flag) { r->inf_flag = 1; return; } r->inf_flag = 0; element_set(r->x, p->x); element_neg(r->y, p->y); }
/* doing multiplication in GF(3^m) * The function sets $e == a*b \in GF(3^m)$ */ static void gf3m_mult(element_t e, element_ptr a, element_t b) { params *p = PARAM(a); element_t aa, t, c; element_init(aa, a->field); element_set(aa, a); a = aa; // clone $a$ element_init(t, a->field); element_init(c, a->field); unsigned i; for (i = 0; i < p->m; i++) { unsigned v = gf3m_get(b, i); gf3m_f1(t, v, a); /* t == b[i]*a in GF(3^m) */ gf3m_add(c, c, t); /* c += b[i]*a in GF(3^m) */ gf3m_f2(a); /* a == a*x in GF(3^m) */ } element_set(e, c); element_clear(t); element_clear(c); element_clear(aa); }
static val_ptr run_item(val_ptr v[]) { mpz_t z; mpz_init(z); element_to_mpz(z, v[1]->elem); int i = mpz_get_si(z); mpz_clear(z); element_ptr a = element_item(v[0]->elem, i); element_ptr e = (element_ptr)pbc_malloc(sizeof(*e)); element_init_same_as(e, a); element_set(e, a); return val_new_element(e); }
static void fq_square(element_ptr n, element_ptr a) { eptr p = a->data; eptr r = n->data; element_ptr nqr = fq_nqr(n->field); element_t e0, e1; element_init(e0, p->x->field); element_init(e1, e0->field); element_square(e0, p->x); element_square(e1, p->y); element_mul(e1, e1, nqr); element_add(e0, e0, e1); element_mul(e1, p->x, p->y); //TODO: which is faster? //element_add(e1, e1, e1); element_double(e1, e1); element_set(r->x, e0); element_set(r->y, e1); element_clear(e0); element_clear(e1); }