19
FEAL APPENDIX FOR KATAGAITAI CTF TECHTALK CSAW CTF 2014 QUALS - CRYPT0 300 YOU0708@YOKARO-MON

FEAL - CSAW CTF 2014 Quals Crypto300

Embed Size (px)

Citation preview

Page 1: FEAL - CSAW CTF 2014 Quals Crypto300

FEAL

APPENDIX FOR KATAGAITAI CTF TECHTALK CSAW CTF 2014 QUALS - CRYPT0 300

YOU0708@YOKARO-MON

Page 2: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

NOTICE

▸ This material is an appendix for katagaitai CTF TechTalk

▸ https://atnd.org/events/71810

▸ An modified version was used in katagaitai CTF

▸ Encryption key (SUBKEY) is fixed hex strings

Page 3: FEAL - CSAW CTF 2014 Quals Crypto300

FEAL 4.3

CSAW CTF 2014 QUALS CRYPT0 300 FEAL

Page 4: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

FEAL 4.3

▸ Feal 4.3 is used for the question

You must first solve a puzzle, a sha1 sum ending in 16 bit's set to 1, it must be of length 21 bytes, starting with PkExU2wOJRG/XBDB

Welcome to feal 4.3Please decrypt: edcf27af7821cc71615f329e78d1f65e

Page 5: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

FBOX IN FEAL 4.3

▸ Feal 4.3 uses “rot 3” in fBox

▸ Differential values are not same with Feal 4

Page 6: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

DIFFERENTIAL VALUEIn [1]: import array

In [2]: %pastedef rot3(x): return ((x<<3)|(x>>5))&0xffdef gBox(a,b,mode): return rot3((a+b+mode)%256)def fBox(plain):(snip.)

In [3]: x1 = array.array("B", "80800000".decode("hex"))

In [4]: fBox(x1)Out[4]: [10, 64, 8, 68]

In [5]: x2 = array.array("B", "00000000".decode("hex"))

In [6]: fBox(x2)Out[6]: [10, 64, 8, 64]

In [7]: for a, b in zip(fBox(x1), fBox(x2)): print a ^ b, ....: 0 0 0 4 ΔY = 0x00000004

Page 7: FEAL - CSAW CTF 2014 Quals Crypto300

BREAKING FEAL 4.3

CSAW CTF 2014 QUALS CRYPT0 300 FEAL

Page 8: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K3 FEALの最終ラウンドの差分解析49

0x02000000

key

f

出力差分(ΔC1)

ΔC1+ΔC2入力差分(ΔX1) 入力差分(ΔX2)

出力差分(ΔC2)

f(C1+C2+key)+f(C1’+C2’+key)

この値は?

ΔC1 = f(C1+C2+key)+f(C1’+C2’+key)+0x02000000

0x00000004

0x00000004

Page 9: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K3k3 = Noneif k3 == None: print "[*] start k3 attack" p1, p2, c1, c2, dc1, dc2, dcL, dcR = get_dataset(f, n, array.array(“B”,"8080000080800000".decode("hex")))

for k3 in xrange(65536): k3 = array.array("B", "%04x"%k3) for i in xrange(n): if dcL[i] != list_xor( list_xor( fBox(list_xor(dc1[i], k3)), fBox(list_xor(dc2[i], k3))), array("B", “00000004”.decode("hex")) ): break else: print "[*] found k3: %s" % "".join(map(chr, k3)) break else: print "[!] could not find k3" return

SUBKEY is hex string

Multiple candidates will be find if you use few plainest sets

Page 10: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K2

0x02000000

key

f

出力差分(ΔC1)

ΔC1+ΔC2入力差分(ΔX1) 入力差分(ΔX2)

出力差分(ΔC2)

f(C1+C2+key)+f(C1’+C2’+key)

この値は?

ΔC1 = f(C1+C2+key)+f(C1’+C2’+key)+0x02000000

0x80800000

0x80800000

It can be calculated from encrypted value and k3

It can be calculated from encrypted value and k3

Page 11: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K2for i in xrange(n): c1L = list_xor(c1[i][:4], c1[i][4:]) c1R = list_xor(c1[i][:4], fBox(list_xor(k3, list_xor(c1[i][4:], c1[i][:4])))) c2L = list_xor(c2[i][:4], c2[i][4:]) c2R = list_xor(c2[i][:4], fBox(list_xor(k3, list_xor(c2[i][4:], c2[i][:4])))) c1[i] = c1L + c1R c2[i] = c2L + c2R dcL[i] = list_xor(c1L, c2L)

for k2 in xrange(65536): k2 = array.array("B", "%04x"%k2) for i in xrange(n): if dcL[i] != list_xor( list_xor( fBox(list_xor(c1[i][4:], k2)), fBox(list_xor(c2[i][4:], k2))), array("B", "80800000".decode("hex"))): break else: print "[*] found k2: %s" % "".join(map(chr, k2)) breakelse: print "[!] could not find k2" return

Calculate ΔC1, ΔC2 using k3

Page 12: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K1

▸ You must re-generate plaintext sets to change result after fBox

FEALの差分解析41

� 次の差分を持つ平文ペアを入力する� 0x8080000080800000

� 同じ鍵で暗号化されているため鍵の入力差分は0

0x80800000 0x80800000

0x80800000

0

0x02000000

ここの差分は不明

0

ΔC1 is fixed value It means: k1 can not be calculated

Page 13: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K1

▸ e.g. ΔX = 0x0000000040000000

FEALの差分解析41

� 次の差分を持つ平文ペアを入力する� 0x8080000080800000

� 同じ鍵で暗号化されているため鍵の入力差分は0

0x80800000 0x80800000

0x80800000

0

0x02000000

ここの差分は不明

0

0x00000000 0x40000000

0x40000000????

????

ΔX1 = 0x40000000

Page 14: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K1

0x02000000

key

f

出力差分(ΔC1)

ΔC1+ΔC2入力差分(ΔX1) 入力差分(ΔX2)

出力差分(ΔC2)

f(C1+C2+key)+f(C1’+C2’+key)

この値は?

ΔC1 = f(C1+C2+key)+f(C1’+C2’+key)+0x02000000

0x40000000

0x40000000

It can be calculated from encrypted value and k3

It can be calculated from encrypted value, k3, and k2

Page 15: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K1p1, p2, c1, c2, dc1, dc2, dcL, dcR = get_dataset(f, n, array.array("B","0000000040000000".decode("hex")))for i in xrange(n): c1L = list_xor(c1[i][:4], c1[i][4:]) c1R = list_xor(c1[i][:4], fBox(list_xor(k3, list_xor(c1[i][4:], c1[i][:4])))) c2L = list_xor(c2[i][:4], c2[i][4:]) c2R = list_xor(c2[i][:4], fBox(list_xor(k3, list_xor(c2[i][4:], c2[i][:4])))) c1[i] = c1L + c1R c2[i] = c2L + c2R dcL[i] = list_xor(c1L, c2L) c1L = c1[i][4:] c1R = list_xor(c1[i][:4], fBox(list_xor(k2, c1[i][4:]))) c2L = c2[i][4:] c2R = list_xor(c2[i][:4], fBox(list_xor(k2, c2[i][4:]))) c1[i] = c1L + c1R c2[i] = c2L + c2R dcL[i] = list_xor(c1L, c2L)

for k1 in xrange(65536): k1 = array.array("B", "%04x"%k1) for i in xrange(n): if dcL[i] != list_xor( list_xor( fBox(list_xor(c1[i][4:], k2)), fBox(list_xor(c2[i][4:], k2))), array("B", "80800000".decode("hex"))):

Page 16: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K0

▸ e.g. ΔX = 0x0000000040000000

FEALの差分解析41

� 次の差分を持つ平文ペアを入力する� 0x8080000080800000

� 同じ鍵で暗号化されているため鍵の入力差分は0

0x80800000 0x80800000

0x80800000

0

0x02000000

ここの差分は不明

0

0x00000000 0x40000000

0x0400000????

????

ΔX1 = 0x00000000

Page 17: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K0for i in xrange(n): c1L = c1[i][4:] c1R = list_xor(c1[i][:4], fBox(list_xor(k1, c1[i][4:]))) c2L = c2[i][4:] c2R = list_xor(c2[i][:4], fBox(list_xor(k1, c2[i][4:]))) c1[i] = c1L + c1R c2[i] = c2L + c2R dcL[i] = list_xor(c1L, c2L)

for k0 in xrange(65536): k0 = array.array("B", "%04x"%k0) for i in xrange(n): if dcL[i] != list_xor(fBox(list_xor(c1[i][4:], k0)), fBox(list_xor(c2[i][4:], k0))): break else: print "[*] found k0: %s" % "".join(map(chr, k0)) breakelse: print "[!] could not find k0" return

Page 18: FEAL - CSAW CTF 2014 Quals Crypto300

CSAW CTF 2014 QUALS - CRYPT0 300: FEAL

K4, K5, FLAG

k4 = list_xor(list_xor(fBox(list_xor(k0, c1[0][4:])), c1[0][:4]), p1[0][:4])print "[*] found k4: %s" % "".join(map(chr, k4))

k5 = list_xor(list_xor(list_xor(p1[0][:4], k4), c1[0][4:]), p1[0][4:])print "[*] found k5: %s" % "".join(map(chr, k5))

k = [k0, k1, k2, k3, k4, k5]print "[*] got encryption key:", k

flag = "".join(map(chr, feal.decrypt(array("B", flag1), k))) + "".join(map(chr, feal.decrypt(array("B", flag2), k)))print "[*] the flag is:", flag

Page 19: FEAL - CSAW CTF 2014 Quals Crypto300

THANK YOU!

CSAW CTF 2014 QUALS CRYPT0 300 FEAL