Skip to content

Commit

Permalink
Fix ElGamal encryption tests
Browse files Browse the repository at this point in the history
  • Loading branch information
jvdsn committed Jan 6, 2024
1 parent d2c3c23 commit 4f5510c
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 21 deletions.
14 changes: 8 additions & 6 deletions attacks/elgamal_encryption/nonce_reuse.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
def attack(p, m1, c1, d1, c2, d2):
def attack(p, m, c1, c2, c1_, c2_):
"""
Recovers a secret plaintext encrypted using the same nonce as a previous, known plaintext.
:param p: the prime used in the ElGamal scheme
:param m1: the known plaintext
:param m: the known plaintext
:param c1: the ciphertext of the known plaintext
:param d1: the ciphertext of the known plaintext
:param c2: the ciphertext of the secret plaintext
:param d2: the ciphertext of the secret plaintext
:param c2: the ciphertext of the known plaintext
:param c1_: the ciphertext of the secret plaintext
:param c2_: the ciphertext of the secret plaintext
:return: the secret plaintext
"""
return int(pow(d1, -1, p) * d2 * m1 % p)
s = c2 * pow(m, -1, p) % p
m_ = c2_ * pow(s, -1, p) % p
return int(m_)
31 changes: 16 additions & 15 deletions test/test_elgamal_encryption.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import os
import sys
from random import getrandbits
from random import randrange
from unittest import TestCase

Expand All @@ -19,31 +18,33 @@ def test_nonce_reuse(self):
# Safe prime.
p = 16902648776703029279
g = 3
d = randrange(1, p)
h = pow(g, d, p)
l = randrange(1, p)
s = pow(h, p, l)
c = pow(g, l, p)
m1 = getrandbits(p.bit_length())
d1 = m1 * s % p
m2 = getrandbits(p.bit_length())
d2 = m2 * s % p
m2_ = nonce_reuse.attack(p, m1, c, d1, c, d2)
self.assertIsInstance(m2_, int)
self.assertEqual(m2, m2_)
for _ in range(100):
x = randrange(1, p)
h = pow(g, x, p)
y = randrange(1, p)
s = pow(h, y, p)
m = randrange(1, p)
c1 = pow(g, y, p)
c2 = m * s % p
m_ = randrange(1, p)
c1_ = pow(g, y, p)
c2_ = m_ * s % p
m__ = nonce_reuse.attack(p, m, c1, c2, c1_, c2_)
self.assertIsInstance(m__, int)
self.assertEqual(m_, m__)

def test_unsafe_generator(self):
# Safe prime.
p = 16902648776703029279
# Unsafe generator, generates the entire group.
g = 7
for i in range(100):
for _ in range(100):
x = randrange(1, p)
h = pow(g, x, p)
y = randrange(1, p)
s = pow(h, y, p)
c1 = pow(g, y, p)
m = randrange(1, p)
c1 = pow(g, y, p)
c2 = m * s % p
k = unsafe_generator.attack(p, h, c1, c2)
self.assertIsInstance(k, int)
Expand Down

0 comments on commit 4f5510c

Please sign in to comment.