Skip to content

Instantly share code, notes, and snippets.

@swenson
Created March 31, 2015 22:14
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save swenson/4cf2156e1ea7259457f1 to your computer and use it in GitHub Desktop.
Save swenson/4cf2156e1ea7259457f1 to your computer and use it in GitHub Desktop.
Code samples from Modern Cryptanalysis by Christopher Swenson
# The number of bits in the S-box
sbits = 6
# Calculate the maximum value / differential
ssize = 2**6
# Generate the matrix of differences, starting
# at all zeros
count = []
for i in range(ssize):
count.append([0 for j in range(ssize)])
# Take every possible value for the first plaintext
for x1 in range(0, ssize):
# Calculate the corresponding ciphertext
y1 = s[x1]
# Now, for each possible differential
for dx in range(0, ssize):
# Calculate the other plaintext and ciphertext
x2 = x1 ^ dx
y2 = s[x2]
# Calculate the output differential
dy = y1 ^ y2
# Increment the count of the characteristic
# in the table corresponding to the two
# differentials
count[dx][dy] = count[dx][dy] + 1
# Import the random library
import random
# Seed it with a fixed value (for repeatability)
random.seed(12345)
# Set the number of rounds in the encryption function
rounds = 3
# Set the number of bits in a plaintext or ciphertext
bits = 36
# Set the plaintext differential
pdiff = 0x280000000L
# Set the number of pairs to generate
numpairs = 1000
# Store the plaintexts and ciphertexts
plaintext1 = []
plaintext2 = []
ciphertext1 = []
ciphertext2 = []
for i in range(0, numpairs):
# Create a random plaintext
r = random.randint(0, 2**bits)
# Create a paired plaintext with a fixed differential
r2 = r ^ pdiff
# Save them
plaintext1.append(r)
plaintext2.append(r2)
# Create the associated ciphertexts
# Assume that the encryption algorithm has already
# been defined
c = encrypt(r,rounds)
c2 = encrypt(r2,rounds)
ciphertext1.append(c)
ciphertext2.append(c2)
keys = 64 # number of keys we need to analyze
count = [0 for i in range(keys)] # count for each key
maxcount = -1 # best count found so far
maxkey = -1 # key for the best differential
cdiff = 2 # the ciphertext differential we are looking for
# Brute force the subkeys
for k1 in range(0,keys):
# Adjust the key to match up with the correct S-box
k = k1 << 18
# For each p/c pair
for j in range(numpairs):
c1 = ciphertext1[j]
c2 = ciphertext2[j]
# Calculate whatever needs to be done using
# key bits, storing the results as u1 and u2
v = mix(demux(apbox(c)), k)
u = asbox(v[3])
v2 = mix(demux(apbox(c2)), k)
u2 = asbox(v2[3])
# If the differential holds, increment count
if u1 ^ u2 == cdiff: count[k1] = count[k1] + 1
# If this was the best key so far, then save it
# Otherwise, ignore it for now
if count[k1] >= maxcount:
maxcount = count[k1]
maxkey = k1
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment