from ouroboros.logger import Logger import random as rnd from tate_bilinear_pairing import eta, ecc from ouroboros.utils import inverse_of from ouroboros.utils import vrf_hash eta.init(369) ''' verify signature @param x: signed messaged @param y: signature @param pi: [inf, x, y] proof components @param pk: [inf, x, y] public key components of the prover @param g: group base ''' def verify(x, y, pi, pk_raw, g): gx = ecc.scalar_mult(x, g) rhs = eta.pairing(*ecc.scalar_mult(1,g)[1:], *pi[1:]) if not y == rhs: print(f"y: {y}, rhs: {rhs}") return False gxs = ecc.add(gx, pk_raw) lhs = eta.pairing(*gxs[1:], *pi[1:]) rhs = eta.pairing(*ecc.scalar_mult(1, g)[1:], *ecc.scalar_mult(1, g)[1:]) if not lhs==rhs: print(f"proposed {x}, {y}, {pi}, {pk_raw}, {g}") print(f"lhs: {lhs},\nrhs: {rhs}") return False return True class VRF(object): ''' verifiable random function implementation ''' def __init__(self, seed): self.log = Logger(self) self.order = ecc.order() #TODO use ecc to gen sk sk = vrf_hash(seed) % self.order g = ecc.gen() pk = ecc.scalar_mult(sk, g) # self.pk = pk self.sk = sk self.g=g ''' short signature without random oracle @param x: message to be signed @return y (the signature), pi (the proof) ''' def sign(self, x): pi = ecc.scalar_mult(inverse_of(x+self.sk, self.order), self.g) y = eta.pairing(*self.g[1:], *pi[1:]) self.log.highlight(f"signing slot {x}\nsigma {y}\nproof {pi}\npk {self.pk} \nbase {self.g}") return (y, pi) def update(self, pk, sk, g): self.pk = pk self.sk = sk self.g = g ''' verify signature @param x: signed messaged @param y: signature @param pi: [inf, x, y] proof components ''' def verify(self, x, y, pi): gx = ecc.scalar_mult(x, self.g) rhs = eta.pairing(*ecc.scalar_mult(1,self.g)[1:], *pi[1:]) if not y == rhs: print(f"y: {y}, rhs: {rhs}") return False gxs = ecc.add(gx, self.pk) lhs = eta.pairing(*gxs[1:], *pi[1:]) rhs = eta.pairing(*ecc.scalar_mult(1, self.g)[1:], *ecc.scalar_mult(1, self.g)[1:]) if not lhs==rhs: print(f"proposed {x}, {y}, {pi}, {self.pk}, {self.g}") print(f"lhs: {lhs},\nrhs: {rhs}") return False return True