def verify(curve, hash, pub, message, sig): """ Verify given signature on message (hashed with given hash function). Public key is on the curve. Returns nothing on success, raises on error. """ r, s = sig error = ValueError('invalid signature') if r < 1 or r >= curve.n or s < 1 or s >= curve.n: raise error e = _hash_message(curve, hash, message) e, r, s = ec.modp(curve.n, e, r, s) w = 1 / s u1 = e * w u2 = r * w p1 = curve.base_mul(int(u1)) p2 = curve.point_mul(int(u2), pub) R = curve.point_add(p1, p2) if R.at_inf: raise error xr = curve.fe2i(R.x) v, = ec.modp(curve.n, xr) if v != r: raise error
def verify(curve, hash, pub, message, sig): """ Verify given signature on message (hashed with given hash function). Public key is on the curve. Returns nothing on success, raises on error. """ r, s = sig error = ValueError('invalid signature') if r < 1 or r >= curve.n or s < 1 or s >= curve.n or not curve.point_on_curve( pub): raise error # XXX: proper serialization of hash inputs #e = _hash_message(curve, hash, hex(curve.fe2i(pub.x)) + hex(r) + message) e = _hash_message(curve, hash, hex(r) + message) e, r, s = ec.modp(curve.n, e, r, s) p1 = curve.base_mul(int(s)) p2 = curve.point_mul(int(e), pub) R = curve.point_add(p1, p2) if R.at_inf: raise error xr = curve.fe2i(R.x) v, = ec.modp(curve.n, xr) if v != r: raise error
def sign(curve, hash, priv, message, nonce=None): """ Sign given message, hashing it with hash. Use the given private key (a scalar), on given curve. """ while True: if nonce == None: k, R = curve.generate_key() #k = 38642705407899615353112568654350726618181305661874559450207851549217158808738 #R = curve.base_mul(int(k)) #print "R: ", R else: k, R = nonce #print "nonce k:", k xr = curve.fe2i(R.x) pub = curve.fe2i(curve.base_mul(int(priv)).x) # XXX use tight serialization #e = _hash_message(curve, hash, hex(pub) + hex(xr) + message) e = _hash_message(curve, hash, hex(xr) + message) print "e: ", e e, d, k, xr = ec.modp(curve.n, e, priv, k, xr) # s = (k - e * d) if int(xr) != 0 and int(s) != 0: return int(xr), int(s)
def sign(curve, hash, priv, message): """ Sign given message, hashing it with hash. Use the given private key (a scalar), on given curve. """ e = _hash_message(curve, hash, message) while True: k, R = curve.generate_key() xr = curve.fe2i(R.x) e, d, k, xr = ec.modp(curve.n, e, priv, k, xr) s = (e + xr * d) / k if int(xr) != 0 and int(s) != 0: return int(xr), int(s)
def user_blind(curve, hash, pub, message, R): a = curve.rand_scalar() b = curve.rand_scalar() p1 = curve.base_mul(int(a)) p2 = curve.point_mul(int(b), pub) Rp = curve.point_add(R, p1) Rp = curve.point_add(Rp, p2) xrp = curve.fe2i(Rp.x) # XXX: properly serialize inputs to hash function # XXX: add public key into hash input ep = _hash_message(curve, hash, hex(xrp) + message) e = ec.modp(curve.n, ep - b)[0] return a, xrp, ep, e
def recover_candidate_pubkeys(curve, hash, message, sig): """ Recovers the two possible public keys corresponding to the signature on given message. """ r, s = sig e = _hash_message(curve, hash, message) Rp, Rn = curve.points_at_x(curve.i2fe(r)) r, = ec.modp(curve.n, r) rinv = 1 / r out = [] for R in (Rp, Rn): p = curve.point_mul(int(rinv), curve.point_sub(curve.point_mul(s, R), curve.base_mul(e))) out.append(p) return out
def recover_candidate_pubkeys(curve, hash, message, sig): """ Recovers the two possible public keys corresponding to the signature on given message. """ r, s = sig e = _hash_message(curve, hash, message) Rp, Rn = curve.points_at_x(curve.i2fe(r)) r, = ec.modp(curve.n, r) rinv = 1 / r out = [] for R in (Rp, Rn): p = curve.point_mul( int(rinv), curve.point_sub(curve.point_mul(s, R), curve.base_mul(e))) out.append(p) return out
def user_unblind(curve, s, a): # XXX: check s is consistent as sG ?= R + cX (ie signer didn't cheat) sp = ec.modp(curve.n, int(s)+int(a)) return int(sp[0])
def bank_sign(curve, k, e, priv): e, priv, k = ec.modp(curve.n, int(e), int(priv), int(k)) s = k - e*priv return s