UNPKG

@dedis/kyber

Version:

A typescript implementation of Kyber interfaces

211 lines (210 loc) 6.26 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; var __importStar = (this && this.__importStar) || function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; result["default"] = mod; return result; }; Object.defineProperty(exports, "__esModule", { value: true }); const gfp_1 = __importDefault(require("./gfp")); const gfp2_1 = __importStar(require("./gfp2")); /** * Group field of size p^6 * This object acts as an immutable and then any modification will instantiate * a new object. */ class GfP6 { constructor(x, y, z) { this.x = x || gfp2_1.default.zero(); this.y = y || gfp2_1.default.zero(); this.z = z || gfp2_1.default.zero(); } /** * Get the addition identity for this group field * @returns the element */ static zero() { return GfP6.ZERO; } /** * Get the multiplication identity for this group field * @returns the element */ static one() { return GfP6.ONE; } /** * Get the x value of the group field element * @returns the x element */ getX() { return this.x; } /** * Get the y value of the group field element * @returns the y element */ getY() { return this.y; } /** * Get the z value of the group field element * @returns the z element */ getZ() { return this.z; } /** * Check if the element is zero * @returns true when zero, false otherwise */ isZero() { return this.x.isZero() && this.y.isZero() && this.z.isZero(); } /** * Check if the element is one * @returns true when one, false otherwise */ isOne() { return this.x.isZero() && this.y.isZero() && this.z.isOne(); } /** * Get the negative of the element * @returns the new element */ neg() { const x = this.x.negative(); const y = this.y.negative(); const z = this.z.negative(); return new GfP6(x, y, z); } frobenius() { const x = this.x.conjugate().mul(gfp2_1.xiTo2PMinus2Over3); const y = this.y.conjugate().mul(gfp2_1.xiToPMinus1Over3); const z = this.z.conjugate(); return new GfP6(x, y, z); } frobeniusP2() { const x = this.x.mulScalar(new gfp_1.default(gfp2_1.xiTo2PSquaredMinus2Over3)); const y = this.y.mulScalar(new gfp_1.default(gfp2_1.xiToPSquaredMinus1Over3)); return new GfP6(x, y, this.z); } /** * Add b to the current element * @param b the element to add * @returns the new element */ add(b) { const x = this.x.add(b.x); const y = this.y.add(b.y); const z = this.z.add(b.z); return new GfP6(x, y, z); } /** * Subtract b to the current element * @param b the element to subtract * @returns the new element */ sub(b) { const x = this.x.sub(b.x); const y = this.y.sub(b.y); const z = this.z.sub(b.z); return new GfP6(x, y, z); } /** * Multiply the current element by b * @param b the element to multiply with * @returns the new element */ mul(b) { const v0 = this.z.mul(b.z); const v1 = this.y.mul(b.y); const v2 = this.x.mul(b.x); let t0 = this.x.add(this.y); let t1 = b.x.add(b.y); let tz = t0.mul(t1); tz = tz.sub(v1).sub(v2).mulXi().add(v0); t0 = this.y.add(this.z); t1 = b.y.add(b.z); let ty = t0.mul(t1); t0 = v2.mulXi(); ty = ty.sub(v0).sub(v1).add(t0); t0 = this.x.add(this.z); t1 = b.x.add(b.z); let tx = t0.mul(t1); tx = tx.sub(v0).add(v1).sub(v2); return new GfP6(tx, ty, tz); } /** * Multiply the current element by a scalar * @param b the scalar * @returns the new element */ mulScalar(b) { const x = this.x.mul(b); const y = this.y.mul(b); const z = this.z.mul(b); return new GfP6(x, y, z); } /** * Multiply the current element by a GFp element * @param b the GFp element * @returns the new element */ mulGfP(b) { const x = this.x.mulScalar(b); const y = this.y.mulScalar(b); const z = this.z.mulScalar(b); return new GfP6(x, y, z); } mulTau() { const tz = this.x.mulXi(); return new GfP6(this.y, this.z, tz); } /** * Get the square of the current element * @returns the new element */ square() { const v0 = this.z.square(); const v1 = this.y.square(); const v2 = this.x.square(); const c0 = this.x.add(this.y).square().sub(v1).sub(v2).mulXi().add(v0); const c1 = this.y.add(this.z).square().sub(v0).sub(v1).add(v2.mulXi()); const c2 = this.x.add(this.z).square().sub(v0).add(v1).sub(v2); return new GfP6(c2, c1, c0); } /** * Get the inverse of the element * @returns the new element */ invert() { const A = this.z.square().sub(this.x.mul(this.y).mulXi()); const B = this.x.square().mulXi().sub(this.y.mul(this.z)); const C = this.y.square().sub(this.x.mul(this.z)); const F = C.mul(this.y).mulXi().add(A.mul(this.z)).add(B.mul(this.x).mulXi()).invert(); return new GfP6(C.mul(F), B.mul(F), A.mul(F)); } /** * Check the equality with the other object * @param o the other object * @returns true when both are equal, false otherwise */ equals(o) { return this.x.equals(o.x) && this.y.equals(o.y) && this.z.equals(o.z); } /** * Get the string representation of the element * @returns a string representation */ toString() { return `(${this.x.toString()}, ${this.y.toString()}, ${this.z.toString()})`; } } GfP6.ZERO = new GfP6(); GfP6.ONE = new GfP6(gfp2_1.default.zero(), gfp2_1.default.zero(), gfp2_1.default.one()); exports.default = GfP6;