ciphers.py 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132
  1. import abc
  2. import nacl.bindings
  3. from .key_schedule import tls_sha256, tls_sha384
  4. from Crypto.Cipher import AES
  5. from Crypto.Util import Counter
  6. from Crypto.Util.number import long_to_bytes, bytes_to_long
  7. from Utils import *
  8. # GF(2^128) defined by 1 + a + a^2 + a^7 + a^128
  9. # Please note the MSB is x0 and LSB is x127
  10. def gf_2_128_mul(x, y):
  11. assert x < (1 << 128)
  12. assert y < (1 << 128)
  13. res = 0
  14. for i in range(127, -1, -1):
  15. res ^= x * ((y >> i) & 1) # branchless
  16. x = (x >> 1) ^ ((x & 1) * 0xE1000000000000000000000000000000)
  17. assert res < 1 << 128
  18. return res
  19. class InvalidInputException(Exception):
  20. def __init__(self, msg):
  21. self.msg = msg
  22. def __str__(self):
  23. return str(self.msg)
  24. class InvalidTagException(Exception):
  25. def __str__(self):
  26. return 'The authenticaiton tag is invalid.'
  27. class TLS_AEAD_Cipher(abc.ABC):
  28. NONCE_LEN = 12
  29. @property
  30. @abc.abstractmethod
  31. def KEY_LEN(self):
  32. ""
  33. @property
  34. @abc.abstractmethod
  35. def MAC_LEN(self):
  36. ""
  37. @property
  38. @abc.abstractmethod
  39. def tls_hash(self):
  40. ""
  41. @abc.abstractmethod
  42. def cipher(self):
  43. ""
  44. def __init__(self, secret):
  45. self.reset(secret)
  46. def reset(self, secret):
  47. self.secret = secret
  48. self.key = self.tls_hash.derive_key(self.secret, self.KEY_LEN)
  49. print("\n\tkey\t\t", self.key.hex())
  50. iv = self.tls_hash.derive_iv(self.secret, self.NONCE_LEN)
  51. self.ivhex = iv
  52. self.iv = int.from_bytes(iv, "big")
  53. print("\n\tiv\t\t", iv.hex())
  54. self.sequence_number = 0
  55. def next_application_traffic_secret(self):
  56. return self.tls_hash.hkdf_expand_label(
  57. self.secret, b"traffic upd", b"", self.tls_hash.hash_len
  58. )
  59. def update_traffic_secret(self):
  60. self.reset(self.next_application_traffic_secret())
  61. def verify_data(self, msg):
  62. return self.tls_hash.verify_data(self.secret, msg)
  63. def get_nonce(self):
  64. nonce = self.sequence_number ^ self.iv
  65. nonce = nonce.to_bytes(self.NONCE_LEN, "big")
  66. simplePrint("IV", self.iv)
  67. simplePrint("Key", self.key.hex())
  68. simplePrint("nonce", nonce.hex())
  69. simplePrint("sequence_number", self.sequence_number)
  70. self.sequence_number += 1
  71. return nonce
  72. def decrypt(self, ciphertext, associated_data):
  73. cipher = self.cipher()
  74. simplePrint("ciphertext",
  75. ciphertext[: -self.MAC_LEN].tobytes().hex())
  76. simplePrint("Tag",
  77. ciphertext[-self.MAC_LEN:].tobytes().hex())
  78. simplePrint("associated_data",
  79. associated_data.tobytes().hex())
  80. cipher.update(associated_data)
  81. return cipher.decrypt_and_verify(
  82. ciphertext[: -self.MAC_LEN], ciphertext[-self.MAC_LEN:]
  83. )
  84. def encrypt(self, plaintext, associated_data):
  85. cipher = self.cipher()
  86. self.update2(associated_data, cipher)
  87. ciphertext, tag = cipher.encrypt_and_digest(plaintext)
  88. return ciphertext + tag
  89. def update2(self, associated_data, cipher):
  90. cipher.update(associated_data)
  91. def tls_ciphertext(self, plaintext):
  92. head = b"\x17\x03\x03" + \
  93. (len(plaintext) + self.MAC_LEN).to_bytes(2, "big")
  94. return head + self.encrypt(plaintext, head)
  95. class TLS_AES_128_GCM_SHA256(TLS_AEAD_Cipher):
  96. KEY_LEN = 16
  97. MAC_LEN = 16
  98. tls_hash = tls_sha256
  99. def cipher(self):
  100. return AES.new(
  101. self.key, AES.MODE_GCM, nonce=self.get_nonce(), mac_len=self.MAC_LEN
  102. )