dh.py 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647
  1. from openid import cryptutil
  2. def strxor(x, y):
  3. if len(x) != len(y):
  4. raise ValueError('Inputs to strxor must have the same length')
  5. if isinstance(x, str):
  6. x = x.encode("utf-8")
  7. if isinstance(y, str):
  8. y = y.encode("utf-8")
  9. return bytes([a ^ b for a, b in zip(x, y)])
  10. class DiffieHellman(object):
  11. DEFAULT_MOD = 155172898181473697471232257763715539915724801966915404479707795314057629378541917580651227423698188993727816152646631438561595825688188889951272158842675419950341258706556549803580104870537681476726513255747040765857479291291572334510643245094715007229621094194349783925984760375594985848253359305585439638443
  12. DEFAULT_GEN = 2
  13. def fromDefaults(cls):
  14. return cls(cls.DEFAULT_MOD, cls.DEFAULT_GEN)
  15. fromDefaults = classmethod(fromDefaults)
  16. def __init__(self, modulus, generator):
  17. self.modulus = int(modulus)
  18. self.generator = int(generator)
  19. self._setPrivate(cryptutil.randrange(1, modulus - 1))
  20. def _setPrivate(self, private):
  21. """This is here to make testing easier"""
  22. self.private = private
  23. self.public = pow(self.generator, self.private, self.modulus)
  24. def usingDefaultValues(self):
  25. return (self.modulus == self.DEFAULT_MOD and
  26. self.generator == self.DEFAULT_GEN)
  27. def getSharedSecret(self, composite):
  28. return pow(composite, self.private, self.modulus)
  29. def xorSecret(self, composite, secret, hash_func):
  30. dh_shared = self.getSharedSecret(composite)
  31. hashed_dh_shared = hash_func(cryptutil.longToBinary(dh_shared))
  32. return strxor(secret, hashed_dh_shared)