Skip to content

Instantly share code, notes, and snippets.

@mveytsman
Last active July 30, 2017 16:48
Show Gist options
  • Save mveytsman/7c911fbc1f02bbce2282402982bca71d to your computer and use it in GitHub Desktop.
Save mveytsman/7c911fbc1f02bbce2282402982bca71d to your computer and use it in GitHub Desktop.
Pedersen commitments
# An implementation of Pedersen Commitments.
# This is like tweeting out a hash of a statement you want to make but better.
# Why is it better?
# 1) If the universe of things you want to commit to is small, an attacker can just hash them to see which one you committed to.
# 2) I'm sure there are other nice security properties but I don't know them yet.
# Learning purposes only, DON'T USE THIS, I have no idea what I'm doing, etc etc
import random
rand = random.SystemRandom()
# First we need a big prime. This is the 1536bit prime from RFC 3526
# This is public
P = 0xFFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA237327FFFFFFFFFFFFFFFF
# We need two unrelated generators for it. These are relatively prime numbers such that for generator g, there exists an n such that g^n mod P = x for all x < P.
# Basically we pick two small primes. These are public.
G = 0x02 # This is the generator specified in RFC 3256
H = 0x05 # 5 is also prime!
def commit(v):
"""
Given some value v < P, `commit(v)` returns a "blinding factor" a, and a
number q. To prove that you know v at some later date, give out q freely
and then reveal a and v when you're ready.
"""
if (v < 1) or (v > P-1):
raise "v must be between 1 and P-1"
a = rand.randint(1,P-1)
# q is G^a + H^v % P
q = (pow(G,a,P) + pow(H,v,P)) % P
return (a, q)
def verify(q,a,v):
"""
Verifies that q is a Pedersen commitment for value v with blind a.
"""
return q == (pow(G,a,P) + pow(H,a,P)) % P
"""
In [1]: import pedersen
In [2]: v = 0xdeadbeef
In [3]: a,q = pedersen.commit(v)
In [4]: a
Out[4]: 572886087667195921199806285995771095595761163791581991562556496246915380093586028060001050408052346604030791781337965208391084426386231228122688227515143682143610988807392708877050508561235283431646376282660934953817442810927393998879356943229627857659850967439862745467380982333426187706138446635281392627233727928154739182286347884113062164145463938492123908344815746584221814234696869461608427361931445519753576702718116165642848685724983636130626855312546594L
In [5]: q
Out[5]: 884000484509887104867976009977333010760185180861460109143631803940704229710496940683914117211213225963758673510268007564978462795681549919508468312993836523169089579723800807788453923256960597329792526972052162609641731677071503925273703685075483806773164400288957443756943077673581226611830184579270812000580868688477766008516896806929421991120687392291421178357444812051040336366022979080950494074006576244023916032987748778156482329469195579793907702936636780L
In [6]: pedersen.verify(q,a,v)
Out[6]: True
"""
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment