def new_xab(x, a, b): S = x[0] % 3 if S == 0: a = (a + 1) % N x = fast_add(x, G) elif S == 1: a = (a * 2) % N b = (b * 2) % N x = fast_add(x, x) elif S == 2: b = (b + 1) % N x = fast_add(x, Q) return x, a, b
async def handle_key_verification_phase(self): global own_address for participant in self.participants: share1 = participant.secret_share1 share2 = participant.secret_share2 if share1 is not None and share2 is not None: vlhs = bitcoin.fast_add( bitcoin.fast_multiply(bitcoin.G, share1), bitcoin.fast_multiply(G2, share2)) vrhs = functools.reduce( bitcoin.fast_add, (bitcoin.fast_multiply(ps, pow(own_address, k, bitcoin.N)) for k, ps in enumerate(participant.verification_points))) if vlhs != vrhs: # TODO: Produce complaints and continue instead of halting here raise ProtocolError('verification of shares failed') else: # TODO: Produce complaints and continue instead of halting here raise ProtocolError( 'missing share from address {:040x}'.format(address)) self.phase = ECDKGPhase.key_check db.Session.commit()
def generate_public_shares(poly1, poly2): if len(poly1) != len(poly2): raise ValueError('polynomial lengths must match ({} != {})'.format( len(poly1), len(poly2))) return (bitcoin.fast_add(bitcoin.fast_multiply(bitcoin.G, a), bitcoin.fast_multiply(G2, b)) for a, b in zip(poly1, poly2))
def get_kG(e, P, s=None): '''Use EC operation: kG = sG +eP. If s (signature) is not provided, it is generated randomly and returned. e - hash value, 32 bytes binary P - verification pubkey s - 32 bytes binary''' if not s: s = os.urandom(32) sG = btc.fast_multiply(btc.G,btc.decode(s,256)) eP = btc.fast_multiply(P,btc.decode(e,256)) return (btc.fast_add(sG, eP), s)
def get_kG(e, P, s=None): '''Use EC operation: kG = sG +eP. If s (signature) is not provided, it is generated randomly and returned. e - hash value, 32 bytes binary P - verification pubkey s - 32 bytes binary''' if not s: s = os.urandom(32) sG = btc.fast_multiply(btc.G, btc.decode(s, 256)) eP = btc.fast_multiply(P, btc.decode(e, 256)) return (btc.fast_add(sG, eP), s)
def ecdsa_raw_verify_one_to_one(msghash, vrs, sender_pub, receiver_priv): v, r, s = vrs w = bitcoin.inv(s, N) z = bitcoin.hash_to_int(msghash) u1, u2 = z * w % N, r * w % N receiver_pub = bitcoin.decode_pubkey(bitcoin.privtopub(receiver_priv)) receiver_sender_shared = bitcoin.fast_multiply( bitcoin.decode_pubkey(sender_pub), bitcoin.decode_privkey(receiver_priv)) u1Qr = bitcoin.fast_multiply(receiver_pub, u1) u2Qs = bitcoin.fast_multiply(receiver_sender_shared, u2) x, y = bitcoin.fast_add(u1Qr, u2Qs) return bool(r == x and (r % N) and (s % N))
async def handle_uninitialized_phase(self): for addr in networking.channels.keys(): self.get_or_create_participant_by_address(addr) # everyone should on agree on participants self.threshold = math.ceil(THRESHOLD_FACTOR * (len(self.participants) + 1)) spoly1 = random_polynomial(self.threshold) spoly2 = random_polynomial(self.threshold) self.secret_poly1 = spoly1 self.secret_poly2 = spoly2 self.encryption_key_part = bitcoin.fast_multiply( bitcoin.G, self.secret_poly1[0]) self.verification_points = tuple( bitcoin.fast_add(bitcoin.fast_multiply(bitcoin.G, a), bitcoin.fast_multiply(G2, b)) for a, b in zip(spoly1, spoly2)) self.phase = ECDKGPhase.key_distribution db.Session.commit()
#!/usr/bin/env python from bitcoin import fast_add, fast_multiply, G, hash_to_int, inv, N from hashlib import sha256 from random import SystemRandom # Generate secret key & the corresponding public key and address d = SystemRandom().randrange(1, N) Q = fast_multiply(G, d); # Choose a 2 random numbers a = SystemRandom().randrange(1, N) b = SystemRandom().randrange(1, N) # calculate a signature r = fast_add(fast_multiply(G, a), fast_multiply(Q, b))[0] s = r * inv(b, N) # Calculate the hash corresponding to the signature (r,s) h = a * r * inv(b, N) # calculate the hash of the message we want to sign z = hash_to_int(sha256('0xDEADBEEF').hexdigest()) # re-calculate s to sign z s_p = s * (z + d*r) * inv(h + d*r, N) # et voila w = inv(s_p, N) u1, u2 = z*w % N, r*w % N x, y = fast_add(fast_multiply(G, u1), fast_multiply(Q, u2))
def fast_substract(a, b): x1, y1 = a x2, y2 = b return fast_add((x1, y1), (x2, -y2))