Skip to content

Instantly share code, notes, and snippets.

@theoremoon
Created March 27, 2022 05:52
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save theoremoon/8bcb9b87dcb1289cf13c9db4431db324 to your computer and use it in GitHub Desktop.
Save theoremoon/8bcb9b87dcb1289cf13c9db4431db324 to your computer and use it in GitHub Desktop.
AES-GCMを多項式で愚直に表すとわかりやすいね
from Crypto.Cipher import AES
import secrets
F = GF(2**128, name="a", modulus=x**128 + x**7 + x**2 + x + 1)
def to_poly(x):
bs = Integer(int.from_bytes(x, "big")).bits()[::-1]
return F([0] * (128 - len(bs)) + bs)
def to_bytes(x):
v = int(bin(x.integer_representation())[2:].zfill(128)[::-1], 2)
return v.to_bytes(128 // 8, "big")
def chunks(xs, n):
for i in range(0, len(xs), n):
yield xs[i:i+n]
def xor(xs, ys):
return bytes(x^^y for x, y in zip(xs, ys))
def aes_gcm(key, nonce, plaintext, additional):
# in this implementation, we support only fast pattern
assert len(nonce) == 12
assert len(plaintext) % 16 == 0
assert len(additional) % 16 == 0
aes = AES.new(key=key, mode=AES.MODE_ECB)
ctr = int.from_bytes(nonce + b"\x00\x00\x00\x01", "big")
H = to_poly(aes.encrypt(b"\0" * 16))
S = to_poly(aes.encrypt(int(ctr).to_bytes(16, "big")))
ctr += 1
t = 0
for a in chunks(additional, 16):
t = (t + to_poly(a))*H
cs = b""
for m in chunks(plaintext, 16):
k = aes.encrypt(int(ctr).to_bytes(16, "big"))
c = xor(m, k)
cs += c
t = (t + to_poly(c))*H
ctr += 1
L = to_poly(int((8*len(additional) << 64) + (8*len(cs))).to_bytes(16, "big"))
t = (t + L)*H
t = t + S
return cs, to_bytes(t)
key = secrets.token_bytes(16)
nonce = secrets.token_bytes(12)
additional = secrets.token_bytes(512)
plaintext = secrets.token_bytes(1024)
aes = AES.new(key=key, mode=AES.MODE_GCM, nonce=nonce)
aes.update(additional)
c1, t1 = aes.encrypt_and_digest(plaintext)
c2, t2 = aes_gcm(key, nonce, plaintext, additional)
assert c1 == c2
assert t1 == t2
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment