X-Git-Url: https://git.distorted.org.uk/~mdw/catacomb-perl/blobdiff_plain/68e68e18c457d31c1c61bc08dd14a56e7e7ac21e..a1a90aaf554eb974e39e34b513747eb666180776:/ec.xs diff --git a/ec.xs b/ec.xs new file mode 100644 index 0000000..66314ce --- /dev/null +++ b/ec.xs @@ -0,0 +1,401 @@ +# ---?--- +# +# $Id$ +# +# Elliptic curves +# +# (c) 2001 Straylight/Edgeware +# + +#----- Licensing notice ----------------------------------------------------- +# +# This file is part of the Perl interface to Catacomb. +# +# Catacomb/Perl is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# Catacomb/Perl is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Catacomb/Perl; if not, write to the Free Software Foundation, +# Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + +MODULE = Catacomb PACKAGE = Catacomb::EC::Point PREFIX = ec_ + +EC_Point * +new(x = 0, y = 0, z = 0) + mp *x + mp *y + mp *z + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + if (x && y) { + RETVAL->x = MP_COPY(x); + RETVAL->y = MP_COPY(y); + if (z) + RETVAL->z = MP_COPY(z); + } + OUTPUT: + RETVAL + +bool +atinfp(p) + EC_Point *p + CODE: + RETVAL = EC_ATINF(p); + OUTPUT: + RETVAL + +mp * +x(p) + EC_Point *p + CODE: + RETVAL = p->x ? MP_COPY(p->x) : 0; + OUTPUT: + RETVAL + +mp * +y(p) + EC_Point *p + CODE: + RETVAL = p->y ? MP_COPY(p->y) : 0; + OUTPUT: + RETVAL + +mp * +z(p) + EC_Point *p + CODE: + RETVAL = p->z ? MP_COPY(p->z) : 0; + OUTPUT: + RETVAL + +SV * +DESTROY(p) + EC_Point *p + CODE: + EC_DESTROY(p); + DESTROY(p); + XSRETURN_YES; + +MODULE = Catacomb PACKAGE = Catacomb::EC::Curve PREFIX = ec_ + +EC_Curve * +ec_prime(me, f, a, b) + SV *me + Field *f + mp *a + mp *b + C_ARGS: + f, a, b + +EC_Curve * +ec_primeproj(me, f, a, b) + SV *me + Field *f + mp *a + mp *b + C_ARGS: + f, a, b + +EC_Curve * +ec_bin(me, f, a, b) + SV *me + Field *f + gf *a + gf *b + C_ARGS: + f, a, b + +EC_Curve * +ec_binproj(me, f, a, b) + SV *me + Field *f + gf *a + gf *b + C_ARGS: + f, a, b + +char * +name(c) + EC_Curve *c + CODE: + RETVAL = (char *)EC_NAME(c); + OUTPUT: + RETVAL + +bool +ec_samep(me, c) + EC_Curve *me + EC_Curve *c + +EC_Point * +find(c, x) + EC_Curve *c + mp *x + CODE: + RETVAL = CREATE(EC_Point); + if (!ec_find(c, RETVAL, x)) { + DESTROY(RETVAL); + RETVAL = 0; + } + OUTPUT: + RETVAL + +EC_Point * +rand(c, r = &rand_global) + EC_Curve *c + grand *r + CODE: + RETVAL = CREATE(EC_Point); + ec_rand(c, RETVAL, r); + OUTPUT: + RETVAL + +EC_Point * +neg(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_neg(c, RETVAL, p); + OUTPUT: + RETVAL + +EC_Point * +add(c, p, q) + EC_Curve *c + EC_Point *p + EC_Point *q + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_add(c, RETVAL, p, q); + OUTPUT: + RETVAL + +EC_Point * +sub(c, p, q) + EC_Curve *c + EC_Point *p + EC_Point *q + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_sub(c, RETVAL, p, q); + OUTPUT: + RETVAL + +EC_Point * +dbl(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_dbl(c, RETVAL, p); + OUTPUT: + RETVAL + +bool +ec_check(c, p) + EC_Curve *c + EC_Point *p + +EC_Point * +mul(c, p, x) + EC_Curve *c + EC_Point *p + mp *x + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_mul(c, RETVAL, p, x); + OUTPUT: + RETVAL + +EC_Point * +mmul(c, ...) + EC_Curve *c + PREINIT: + ec_mulfactor *v; + size_t i, j, n; + CODE: + if (items < 3 || !(items & 1)) { + croak("Usage: Catacomb::EC::Curve::mmul" + "(c, p_0, x_0, p_1, x_1, ..."); + } + n = (items - 1)/2; + v = xmalloc(n * sizeof(mp_expfactor)); + for (i = 1, j = 0; i < items; i += 2, j++) { + v[j].base = *(ec *)ptrfromsv(ST(i), "Catacomb::EC::Point", "p_i"); + v[j].exp = mp_fromsv(ST(i + 1), "x_i", "Catacomb::MP", 0, 0); + } + RETVAL = CREATE(RETVAL); + EC_CREATE(RETVAL); + ec_mmul(c, RETVAL, v, n); + xfree(v); + OUTPUT: + RETVAL + +EC_Point * +in(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_IN(c, RETVAL, p); + OUTPUT: + RETVAL + +EC_Point * +out(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_OUT(c, RETVAL, p); + OUTPUT: + RETVAL + +EC_Point * +fix(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_FIX(c, RETVAL, p); + OUTPUT: + RETVAL + +EC_Point * +ifind(c, x) + EC_Curve *c + mp *x + CODE: + RETVAL = CREATE(EC_Point); + if (!EC_FIND(c, RETVAL, x)) { + DESTROY(RETVAL); + RETVAL = 0; + } + OUTPUT: + RETVAL + +EC_Point * +ineg(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_NEG(c, RETVAL, p); + OUTPUT: + RETVAL + +EC_Point * +iadd(c, p, q) + EC_Curve *c + EC_Point *p + EC_Point *q + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_ADD(c, RETVAL, p, q); + OUTPUT: + RETVAL + +EC_Point * +isub(c, p, q) + EC_Curve *c + EC_Point *p + EC_Point *q + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_SUB(c, RETVAL, p, q); + OUTPUT: + RETVAL + +EC_Point * +idbl(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + EC_DBL(c, RETVAL, p); + OUTPUT: + RETVAL + +bool +icheck(c, p) + EC_Curve *c + EC_Point *p + CODE: + RETVAL = EC_CHECK(c, p); + OUTPUT: + RETVAL + +EC_Point * +imul(c, p, x) + EC_Curve *c + EC_Point *p + mp *x + CODE: + RETVAL = CREATE(EC_Point); + EC_CREATE(RETVAL); + ec_imul(c, RETVAL, p, x); + OUTPUT: + RETVAL + +EC_Point * +immul(c, ...) + EC_Curve *c + PREINIT: + ec_mulfactor *v; + size_t i, j, n; + CODE: + if (items < 3 || !(items & 1)) { + croak("Usage: Catacomb::EC::Curve::immul" + "(c, p_0, x_0, p_1, x_1, ..."); + } + n = (items - 1)/2; + v = xmalloc(n * sizeof(mp_expfactor)); + for (i = 1, j = 0; i < items; i += 2, j++) { + v[j].base = *(ec *)ptrfromsv(ST(i), "Catacomb::EC::Point", "p_i"); + v[j].exp = mp_fromsv(ST(i + 1), "x_i", "Catacomb::MP", 0, 0); + } + RETVAL = CREATE(RETVAL); + EC_CREATE(RETVAL); + ec_mmul(c, RETVAL, v, n); + xfree(v); + OUTPUT: + RETVAL + +void +getinfo(me, p) + char *p + PREINIT: + ec_info i; + const char *e; + EC_Point *pt; + PPCODE: + if ((e = ec_getinfo(&i, p)) != 0) + croak("bad curve spec: %s", e); + pt = CREATE(EC_Point); + *pt = i.g; + XPUSHs(RET(i.c, "Catacomb::EC::Curve")); + XPUSHs(RET(pt, "Catacomb::EC::Point")); + XPUSHs(RET(i.r, "Catacomb::MP")); + XPUSHs(RET(i.h, "Catacomb::MP")); +