def __init__(self, logger): self.IK = X25519PrivateKey.generate() self.SPK = X25519PrivateKey.generate() self.OPK = X25519PrivateKey.generate() self.peer_keys = defaultdict(dict) self.sessions = defaultdict(lambda: SessionState.new()) self.logger = logger
def is_available(cls): try: X25519PrivateKey.generate() except UnsupportedAlgorithm: return False else: return True
def load_bob_keys() -> (X25519PrivateKey, X25519PrivateKey, X25519PrivateKey): # If existing, load the saved keys for bob. # If they do not already exists, generate new keys and save them. # Generate OPKb once and do not save it. # Returns 3 keys: # IK: X25519PrivateKey # SPKb: X25519PrivateKey # OPKb: X25519PrivateKey OPKb = X25519PrivateKey.generate() try: with open(path_keys_bob, 'rb') as f: lines = f.read() assert (len(lines) == 2 * key_length) IK_bytes = lines[:key_length] SPKb_bytes = lines[key_length:] IK = deserialize_private_key(IK_bytes) SPKb = deserialize_private_key(SPKb_bytes) print("Loaded saved keys.") except FileNotFoundError: print("No keys found. Creating new keys...") IK = X25519PrivateKey.generate() SPKb = X25519PrivateKey.generate() with open(path_keys_bob, 'wb') as f: for key in [IK, SPKb]: f.write(serialize_private_key(key)) print("Keys saved.") pass return (IK, SPKb, OPKb)
def __init__(self): self.IdentityPri = X25519PrivateKey.generate() self.IdentityPub = self.IdentityPri.public_key() self.SignedPri = X25519PrivateKey.generate() self.SignedPub = self.SignedPri.public_key() self.OneTimePri = X25519PrivateKey.generate() self.OneTimePub = self.OneTimePri.public_key() self.EphemeralPri = X25519PrivateKey.generate() self.EphemeralPub = self.EphemeralPri.public_key()
def test_x25519_unsupported(backend): with raises_unsupported_algorithm(_Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM): X25519PublicKey.from_public_bytes(b"0" * 32) with raises_unsupported_algorithm(_Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM): X25519PrivateKey.from_private_bytes(b"0" * 32) with raises_unsupported_algorithm(_Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM): X25519PrivateKey.generate()
def __init__ (self): # generate pre-key bundle # ideally, this is published to a server self.IK = X25519PrivateKey.generate () # identity key self.SPK = X25519PrivateKey.generate () # signed pre-key self.OPK = X25519PrivateKey.generate () # one time key # initiator - boolean to determine whether this client is initating a connection # helps with x3dh, i think ... self.init = False
def __init__(self, name): # generate Bob's keys self.__name = name # Identity self.__IPK = X25519PrivateKey.generate() # Pre signed key self.__SPK = X25519PrivateKey.generate() # One time pre key self.__OPK = X25519PrivateKey.generate() # Ephemeral key self.__EFK = X25519PrivateKey.generate()
def isCryptographyAdvanced(): """ Check if the cryptography library is present, and if it supports X25519, ChaCha20Poly1305 and such (v2.0 or later). """ try: from cryptography.hazmat.primitives.asymmetric.x25519 import X25519PrivateKey # noqa: E501 X25519PrivateKey.generate() except Exception: return False else: return True
def main(key_file, port): if key_file: private_key_text = open(key_file).readline().strip() private_key = X25519PrivateKey.from_private_bytes( bytes.fromhex(private_key_text)) else: private_key = X25519PrivateKey.generate() print( "Server public key: ", private_key.public_key().public_bytes(encoding=Encoding.Raw, format=PublicFormat.Raw).hex()) server_handler = pssst.PSSSTServer(private_key) with closing(socket.socket(socket.AF_INET, socket.SOCK_DGRAM)) as server_socket: server_socket.bind(('127.0.0.1', port)) while True: packet, client_addr = server_socket.recvfrom(2048) try: data, client_key, reply_handler = server_handler.unpack_request( packet) reply_packet = reply_handler(data) server_socket.sendto(reply_packet, client_addr) except pssst.PSSSTException as e: print("Server Exception: {}".format(e))
def test_public_bytes_bad_args(self, backend): key = X25519PrivateKey.generate().public_key() with pytest.raises(ValueError): key.public_bytes( None, serialization.PublicFormat.Raw # type: ignore[arg-type] )
def pack_x25519(self) -> bytes: private_key: X25519PrivateKey = X25519PrivateKey.generate() public_key: X25519PublicKey = private_key.public_key() self.private = private_key self.public = public_key.public_bytes(encoding=serialization.Encoding.Raw, format=serialization.PublicFormat.Raw) return self.public
def keygen_public(key_size, alg, hash_alg, curve): if alg == 'rsa': key_pair = RSA.generate(key_size) priv_key = key_pair.exportKey() pub_key = key_pair.publickey().exportKey() priv_key_dict = {'alg' : 'rsa', 'type' : 'private', 'size': key_size, 'hash' : hash_alg, 'key' : priv_key} pub_key_dict = {'alg' : 'rsa', 'type' : 'public', 'size': key_size, 'hash' : hash_alg, 'key' : pub_key} #return priv_key_dict, pub_key_dict return [priv_key_dict, pub_key_dict] elif alg == 'ECC': if curve == 'X25519': key_pair = X25519PrivateKey.generate() pub_key = key_pair.public_key().public_bytes() priv_key_dict = {'alg' : 'ecc', 'curve' : 'x25519', 'type' : 'private', 'hash' : hash_alg, 'key': key_pair} pub_key_dict = {'alg' : 'ecc', 'curve' : 'x25519', 'type' : 'public', 'hash' : hash_alg, 'key' : pub_key} elif curve == 'P-256': #SECP256r1 key_pair = ec.generate_private_key(ec.SECP256R1(), default_backend()) priv_key = key_pair.private_bytes(encoding=serialization.Encoding.PEM, format=serialization.PrivateFormat.PKCS8, encryption_algorithm=serializtion.NoEncryption) pub_key = key_pair.public_key().public_bytes(encoding=serialization.Encoding.PEM, format=serialization.PublicFormat.SubjectPublicKeyInfo) priv_key_dict = {'alg' : 'ecc', 'curve' : 'p256', 'type' : 'private', 'hash' : hash_alg, 'key': priv_key} pub_key_dict = {'alg' : 'ecc', 'curve' : 'p256', 'type' : 'public', 'hash' : hash_alg, 'key' : pub_key} return priv_key_dict, pub_key_dict else: print('SA_ERROR:', alg, 'not yet implemented.', flush = True)
def encrypt(self, plaintext): """ Encrypts information for the identity. :param plaintext: The plaintext to be encrypted as *bytes*. :returns: Ciphertext token as *bytes*. :raises: *KeyError* if the instance does not hold a public key. """ if self.pub != None: ephemeral_key = X25519PrivateKey.generate() ephemeral_pub_bytes = ephemeral_key.public_key().public_bytes( encoding=serialization.Encoding.Raw, format=serialization.PublicFormat.Raw) shared_key = ephemeral_key.exchange(self.pub) derived_key = derived_key = HKDF( algorithm=hashes.SHA256(), length=32, salt=self.get_salt(), info=self.get_context(), ).derive(shared_key) fernet = Fernet(base64.urlsafe_b64encode(derived_key)) ciphertext = base64.urlsafe_b64decode(fernet.encrypt(plaintext)) token = ephemeral_pub_bytes + ciphertext return token else: raise KeyError( "Encryption failed because identity does not hold a public key" )
def generate_public_private_key(): """ generate_public_private_key uses curve25519 to generate a public and private key pair """ private_key = X25519PrivateKey.generate() return private_key.public_key(), private_key
def __init__(self, test, src, port): super(VppWgInterface, self).__init__(test) self.port = port self.src = src self.private_key = X25519PrivateKey.generate() self.public_key = self.private_key.public_key()
def isCryptographyAdvanced(): """ Check if the cryptography module is present, and if it supports X25519, ChaCha20Poly1305 and such. Notes: - cryptography >= 2.0 is required - OpenSSL >= 1.1.0 is required """ try: from cryptography.hazmat.primitives.asymmetric.x25519 import X25519PrivateKey # noqa: E501 X25519PrivateKey.generate() except Exception: return False else: return True
def test_round_trip_private_serialization( self, encoding, fmt, encryption, passwd, load_func, backend ): key = X25519PrivateKey.generate() serialized = key.private_bytes(encoding, fmt, encryption) loaded_key = load_func(serialized, passwd, backend) assert isinstance(loaded_key, X25519PrivateKey)
def ecies_hkdf(self, enckey, plainkey): if isinstance(enckey, ecdsa.ECDSA256P1Public): newpk = ec.generate_private_key(ec.SECP256R1(), default_backend()) shared = newpk.exchange(ec.ECDH(), enckey._get_public()) else: newpk = X25519PrivateKey.generate() shared = newpk.exchange(enckey._get_public()) derived_key = HKDF(algorithm=hashes.SHA256(), length=48, salt=None, info=b'MCUBoot_ECIES_v1', backend=default_backend()).derive(shared) encryptor = Cipher(algorithms.AES(derived_key[:16]), modes.CTR(bytes([0] * 16)), backend=default_backend()).encryptor() cipherkey = encryptor.update(plainkey) + encryptor.finalize() mac = hmac.HMAC(derived_key[16:], hashes.SHA256(), backend=default_backend()) mac.update(cipherkey) ciphermac = mac.finalize() if isinstance(enckey, ecdsa.ECDSA256P1Public): pubk = newpk.public_key().public_bytes( encoding=Encoding.X962, format=PublicFormat.UncompressedPoint) else: pubk = newpk.public_key().public_bytes(encoding=Encoding.Raw, format=PublicFormat.Raw) return cipherkey, ciphermac, pubk
def modify(packet): pkt = dpkt.ip6.IP6(packet.get_payload()) if is_icmp_neighbour_message(pkt): packet.accept() return global client_id aes_key_text = pkt.data[:256] aes_key_text = asymmetrickeys.decrypt(aes_key_text) nonce = struct.unpack(">I", pkt.data[256:260])[0] public_ecdhe_key = pkt.data[260:292] ci = struct.unpack(">I", pkt.data[292:296])[0] aes_key = AESGCM(aes_key_text) decrypted_block = bytes( aes_key.decrypt(bytes(nonce), pkt.data[296:-288], '')) ip_b = decrypted_block[:16] # --- Header 2 header_2 = pkt.data[-288:] ecdhe = X25519PrivateKey.generate() shared_key = ecdhe.exchange( X25519PublicKey.from_public_bytes(public_ecdhe_key)) derived_key = HKDF(algorithm=hashes.SHA512(), length=32, info=None, salt=None, backend=default_backend()).derive(shared_key) key = AESGCM(derived_key) nonce = random.randint(0, 4294967295) encrypted_header = key.encrypt(bytes(nonce), header_2, '') signature = sign(ecdhe.public_key().public_bytes(), asymmetrickeys) header_2 = ecdhe.public_key().public_bytes() + signature + struct.pack( ">I", nonce) + encrypted_header + struct.pack(">I", client_id) client_id = client_id + 1 # Finalize packet pkt.data = decrypted_block[16:] + header_2 pkt.plen = len(pkt.data) pkt.dst = ip_b sockfd.sendto(bytes(pkt), (socket.inet_ntop(socket.AF_INET6, ip_b), 0)) packet.drop()
def accept(self): """Accept an incoming connection & initialize the encryption layer for that client Returns ------- returns (socket, addr) of the client """ clt, addr = super().accept() # Generate a private key server_key = X25519PrivateKey.generate() pubkey = server_key.public_key().public_bytes(encoding=Encoding.Raw, format=PublicFormat.Raw) data = clt.recv(32) # Receive client public Key clt.sendall(pubkey) # send public key to client public_key = X25519PublicKey.from_public_bytes(data) # get Shared key shared_key = server_key.exchange(public_key) shared_key = HKDF(algorithm=hashes.SHA256(), length=48, salt=None, info=b'handshake data', backend=default_backend()).derive(shared_key) encrypted_socket = wrap_socket(clt, False, handshaked=True) encrypted_socket.cipher = Cipher(algorithms.AES(shared_key[0:32]), modes.CBC(shared_key[32:]), backend=default_backend()) return encrypted_socket, addr
def generate_key( algorithm: CoseAlgorithms, key_ops: KeyOps, curve_type: CoseEllipticCurves = CoseEllipticCurves.X25519 ) -> 'OKP': """ Generate a random OKP COSE key object. :param algorithm: Specify the CoseAlgorithm to use. :param key_ops: Specify the key operation (KeyOps). :param curve_type: Specify curve, must be X25519 or X448. """ if curve_type == CoseEllipticCurves.X25519: private_key = X25519PrivateKey.generate() elif curve_type == CoseEllipticCurves.X448: private_key = X448PrivateKey.generate() else: raise CoseIllegalCurve( f"curve must be of type {CoseEllipticCurves.X25519} or {CoseEllipticCurves.X448}" ) encoding = Encoding(serialization.Encoding.Raw) private_format = PrivateFormat(serialization.PrivateFormat.Raw) public_format = PublicFormat(serialization.PublicFormat.Raw) encryption = serialization.NoEncryption() return OKP(alg=CoseAlgorithms(algorithm), key_ops=KeyOps(key_ops), crv=CoseEllipticCurves(curve_type), x=private_key.public_key().public_bytes( encoding, public_format), d=private_key.private_bytes(encoding, private_format, encryption))
def modify(packet): pkt = dpkt.ip6.IP6(packet.get_payload()) if is_icmp_neighbour_message(pkt): packet.accept() return aes_key_text = pkt.data[:256] aes_key_text = asymmetrickeya.decrypt(aes_key_text) nonce = struct.unpack(">I", pkt.data[256:260])[0] ecdhe = pkt.data[260:292] ci = struct.unpack(">I", pkt.data[292:296])[0] aes_key = AESGCM(aes_key_text) decrypted_block = bytes(aes_key.decrypt(bytes(nonce), pkt.data[296:], '')) ip_s = decrypted_block[:16] ecdhe_ac = X25519PrivateKey.generate() signature = sign(ecdhe_ac.public_key().public_bytes(), asymmetrickeya) pkt.data = decrypted_block[16:] + ecdhe_ac.public_key().public_bytes( ) + signature pkt.plen = len(pkt.data) pkt.dst = ip_s sockfd.sendto(bytes(pkt), (socket.inet_ntop(socket.AF_INET6, ip_s), 0)) packet.drop()
def _handshake(self): """Open a socket to address, port and initialize the encryption layer by exchanging a key using X25519. The key is used as an AES key throughout the communication. Returns ------- return itself """ private_key = X25519PrivateKey.generate() pubkey = private_key.public_key().public_bytes(encoding=Encoding.Raw, format=PublicFormat.Raw) # send client public key super().send(pubkey) # receive server public Key data = super().recv(32) # from public key get shared_key server_key = X25519PublicKey.from_public_bytes(data) shared_key = private_key.exchange(server_key) key = HKDF(algorithm=hashes.SHA256(), length=48, salt=None, info=b'handshake data', backend=default_backend()).derive(shared_key) self.cipher = Cipher(algorithms.AES(key[0:32]), modes.CBC(key[32:]), backend=default_backend()) return self
def __init__(self, identifier_other): self.identifier_other = identifier_other self.x3dh_status = get_x3dh_status(identifier_other) self.backup_path = path_bob_backup self.path_prev_pubkey = path_bob_prev_pubkey #print("status is:", self.x3dh_status) if self.x3dh_status == 0: # Not initialized # generate Bob's keys (self.IK, self.SPKb, self.OPKb) = load_bob_keys() self.Ns = 0 self.Nr = 1 self.PNs = 0 self.PNr = 1 # initialize Bob's DH ratchet self.DHratchet = X25519PrivateKey.generate() self.save_keys() with open(path_bob_x3dh_outstanding, 'ab') as f: f.write(bytes(identifier_other + os.linesep, 'utf-8')) elif self.x3dh_status == 1: # Initialized, waiting for response x3dh prekey bundle from alice self.load_keys() pass elif self.x3dh_status == 2: # x3dh completed load_status(self) pass
def __init__(self): self.s = socket.socket() host = socket.gethostname() port = 12345 self.s.connect((host, port)) self.messages = [] private_key_bob = X25519PrivateKey.generate() public_key_bob = private_key_bob.public_key() peer_public_alice_raw = (self.s.recv(2048)) #print(peer_public_alice_raw) self.s.send(public_key_bob.public_bytes(Encoding.Raw, PublicFormat.Raw)) peer_public_alice = X25519PublicKey.from_public_bytes( peer_public_alice_raw) shared_key = private_key_bob.exchange(peer_public_alice) derived_key = HKDF(algorithm=hashes.SHA256(), length=32, salt=None, info=b'handshake data', backend=default_backend()).derive(shared_key) self.f = Fernet(base64.urlsafe_b64encode(derived_key)) t = threading.Thread(target=self.recvMessages, args=(self.s, )) t.start()
def register(cls, password: bytes): """ Generate a new account. :param password The password for encrypting the keys. :return a Registration. """ reg = cls() # gen signature keypair sign_object = Ed25519PrivateKey.generate() reg.sign_pub = sign_object.public_key().public_bytes( serialization.Encoding.Raw, serialization.PublicFormat.Raw) sign = sign_object.private_bytes(serialization.Encoding.Raw, serialization.PrivateFormat.Raw, serialization.NoEncryption()) reg.sign_sig = sign_object.sign(sign) # the private signature key's hash become the account's ID reg.identity = blake2b(sign).digest() # gen encryption keypair xchg_object = X25519PrivateKey.generate() reg.xchg_pub = xchg_object.public_key().public_bytes( serialization.Encoding.Raw, serialization.PublicFormat.Raw) xchg = xchg_object.private_bytes(serialization.Encoding.Raw, serialization.PrivateFormat.Raw, serialization.NoEncryption()) reg.xchg_sig = sign_object.sign(xchg) # encrypt the private keys reg.set_passwd(sign, xchg, password) return reg
def create_keys(self): self.prv = X25519PrivateKey.generate() self.prv_bytes = self.prv.private_bytes( encoding=serialization.Encoding.Raw, format=serialization.PrivateFormat.Raw, encryption_algorithm=serialization.NoEncryption()) self.sig_prv = Ed25519PrivateKey.generate() self.sig_prv_bytes = self.sig_prv.private_bytes( encoding=serialization.Encoding.Raw, format=serialization.PrivateFormat.Raw, encryption_algorithm=serialization.NoEncryption()) self.pub = self.prv.public_key() self.pub_bytes = self.pub.public_bytes( encoding=serialization.Encoding.Raw, format=serialization.PublicFormat.Raw) self.sig_pub = self.sig_prv.public_key() self.sig_pub_bytes = self.sig_pub.public_bytes( encoding=serialization.Encoding.Raw, format=serialization.PublicFormat.Raw) self.update_hashes() RNS.log("Identity keys created for " + RNS.prettyhexrep(self.hash), RNS.LOG_VERBOSE)
def verify_start(config: Config, context: dict, ios_device_public_key: bytes) -> List[dict]: """pair_verify M1 and M2""" curve25519 = X25519PrivateKey.generate() accessory_curve25519_public_key: bytes = curve25519.public_key().public_bytes() shared_secret: bytes = curve25519.exchange(X25519PublicKey.from_public_bytes(ios_device_public_key)) accessory_info: bytes = accessory_curve25519_public_key + config.device_id.encode() + ios_device_public_key signing_key = ed25519.SigningKey(config.accessory_ltsk) accessory_signature = signing_key.sign(accessory_info) sub_tlv = tlv_parser.encode([{ TlvCode.identifier: config.device_id, TlvCode.signature: accessory_signature, }]) hkdf = HKDF(algorithm=SHA512(), length=32, salt=SALT_VERIFY, info=INFO_VERIFY, backend=default_backend()) session_key = hkdf.derive(shared_secret) chacha = ChaCha20Poly1305(session_key) encrypted_data = chacha.encrypt(NONCE_VERIFY_M2, sub_tlv, None) context['session_key'] = session_key context['shared_secret'] = shared_secret context['accessory_curve25519_public_key'] = accessory_curve25519_public_key context['ios_device_curve25519_public_key'] = ios_device_public_key return [{ TlvCode.state: TlvState.m2, TlvCode.public_key: accessory_curve25519_public_key, TlvCode.encrypted_data: encrypted_data, }]
def __init__(self, datablock, b_pub, nonce, predecessor_tag=None): self.datablock = datablock self.b_pub = b_pub self.nonce = nonce self.predecessor_tag = predecessor_tag self.a_priv = X25519PrivateKey.generate() self.a_pub = self.a_priv.public_key() self.k_sym = self.generate_k_sym()
def test_to_from_json(self): public_key = X25519PrivateKey.generate().public_key() pki = PublicKeyInfo(public_key) pki_json = pki.to_json() pki_deser = PublicKeyInfo.from_json(pki_json) assert pki.__dict__ == pki_deser.__dict__
def key_exchange(): key_pair = X25519PrivateKey.generate() public_key = key_pair.public_key() peer_public_key = X25519PublicKey.from_public_bytes(base64.b64decode(request.get_json().get('data').encode('utf-8'))) secret = key_pair.exchange(peer_public_key) id = base64.b64encode(urandom(16)).decode('utf-8') users[id] = secret return jsonify({'id': id, 'public_key': base64.b64encode( public_key.public_bytes(encoding=serialization.Encoding.Raw, format=serialization.PublicFormat.Raw)).decode('utf-8')})
def isCryptographyAdvanced(): """ Check if the cryptography library is present, and if it supports X25519, ChaCha20Poly1305 and such (v2.0 or later). """ try: import cryptography except ImportError: return False from distutils.version import LooseVersion lib_valid = LooseVersion(cryptography.__version__) >= LooseVersion("2.0") if not lib_valid: return False try: from cryptography.hazmat.primitives.asymmetric.x25519 import X25519PrivateKey X25519PrivateKey.generate() except: return False else: return True
def test_invalid_public_bytes(self, backend): key = X25519PrivateKey.generate().public_key() with pytest.raises(ValueError): key.public_bytes( serialization.Encoding.Raw, serialization.PublicFormat.SubjectPublicKeyInfo ) with pytest.raises(ValueError): key.public_bytes( serialization.Encoding.PEM, serialization.PublicFormat.PKCS1 ) with pytest.raises(ValueError): key.public_bytes( serialization.Encoding.PEM, serialization.PublicFormat.Raw )
def test_invalid_private_bytes(self, backend): key = X25519PrivateKey.generate() with pytest.raises(ValueError): key.private_bytes( serialization.Encoding.Raw, serialization.PrivateFormat.Raw, None ) with pytest.raises(ValueError): key.private_bytes( serialization.Encoding.Raw, serialization.PrivateFormat.PKCS8, None ) with pytest.raises(ValueError): key.private_bytes( serialization.Encoding.PEM, serialization.PrivateFormat.Raw, serialization.NoEncryption() )
def __generate_key(self): # Generate private and public key pair for client self.client_private_key = X25519PrivateKey.generate() self.client_public_key = self.client_private_key.public_key().public_bytes()
def test_deprecated_public_bytes(self, backend): key = X25519PrivateKey.generate().public_key() with pytest.warns(utils.DeprecatedIn25): key.public_bytes()
def test_public_bytes_bad_args(self, backend): key = X25519PrivateKey.generate().public_key() with pytest.raises(ValueError): key.public_bytes(None, serialization.PublicFormat.Raw) with pytest.raises(ValueError): key.public_bytes(serialization.Encoding.Raw)
def test_generate(self, backend): key = X25519PrivateKey.generate() assert key assert key.public_key()
def test_invalid_type_exchange(self, backend): key = X25519PrivateKey.generate() with pytest.raises(TypeError): key.exchange(object())
def test_round_trip_private_serialization(self, encoding, fmt, encryption, passwd, load_func, backend): key = X25519PrivateKey.generate() serialized = key.private_bytes(encoding, fmt, encryption) loaded_key = load_func(serialized, passwd, backend) assert isinstance(loaded_key, X25519PrivateKey)