Function verifyBatch [src]

Verify several signatures in a single operation, much faster than verifying signatures one-by-one

Prototype

pub fn verifyBatch(comptime count: usize, signature_batch: [count]BatchElement) (SignatureVerificationError || IdentityElementError || WeakPublicKeyError || EncodingError || NonCanonicalError)!void

Parameters

count: usizesignature_batch: [count]BatchElement

Source

pub fn verifyBatch(comptime count: usize, signature_batch: [count]BatchElement) (SignatureVerificationError || IdentityElementError || WeakPublicKeyError || EncodingError || NonCanonicalError)!void { var r_batch: [count]CompressedScalar = undefined; var s_batch: [count]CompressedScalar = undefined; var a_batch: [count]Curve = undefined; var expected_r_batch: [count]Curve = undefined; for (signature_batch, 0..) |signature, i| { const r = signature.sig.r; const s = signature.sig.s; try Curve.scalar.rejectNonCanonical(s); const a = try Curve.fromBytes(signature.public_key.bytes); try a.rejectIdentity(); try Curve.rejectNonCanonical(r); const expected_r = try Curve.fromBytes(r); try expected_r.rejectIdentity(); expected_r_batch[i] = expected_r; r_batch[i] = r; s_batch[i] = s; a_batch[i] = a; } var hram_batch: [count]Curve.scalar.CompressedScalar = undefined; for (signature_batch, 0..) |signature, i| { var h = Sha512.init(.{}); h.update(&r_batch[i]); h.update(&signature.public_key.bytes); h.update(signature.msg); var hram64: [Sha512.digest_length]u8 = undefined; h.final(&hram64); hram_batch[i] = Curve.scalar.reduce64(hram64); } var z_batch: [count]Curve.scalar.CompressedScalar = undefined; for (&z_batch) |*z| { crypto.random.bytes(z[0..16]); @memset(z[16..], 0); } var zs_sum = Curve.scalar.zero; for (z_batch, 0..) |z, i| { const zs = Curve.scalar.mul(z, s_batch[i]); zs_sum = Curve.scalar.add(zs_sum, zs); } zs_sum = Curve.scalar.mul8(zs_sum); var zhs: [count]Curve.scalar.CompressedScalar = undefined; for (z_batch, 0..) |z, i| { zhs[i] = Curve.scalar.mul(z, hram_batch[i]); } const zr = (try Curve.mulMulti(count, expected_r_batch, z_batch)).clearCofactor(); const zah = (try Curve.mulMulti(count, a_batch, zhs)).clearCofactor(); const zsb = try Curve.basePoint.mulPublic(zs_sum); if (zr.add(zah).sub(zsb).rejectIdentity()) |_| { return error.SignatureVerificationFailed; } else |_| {} }