def _send_key_exchange(self): K_eph = os.urandom(28) Q_eph = EllipticCurve.multiply_by_number(EllipticCurve.get_forming(), K_eph) PS = os.urandom(32) H = hash256(self._r_c + self._r_s) keg_res = KEG(K_eph, self._server_pub, H) k_exp_mac = keg_res[:len(keg_res) // 2] k_exp_enc = keg_res[len(keg_res) // 2:] IV = H[25:(24 + len(H) // 2)] PMSEXP = KExp15(PS, k_exp_enc, k_exp_mac, IV) algorithm = "best_algorithm" parameters = "best_params" subjectPublicKey = Q_eph encoder = asn1.Encoder() encoder.start() encoder.enter() encoder.write(PMSEXP) encoder.enter() encoder.enter() encoder.write(algorithm) encoder.write(parameters) encoder.leave() encoder.write(subjectPublicKey) encoder.leave() encoder.leave() encoded_bytes = encoder.output() self._send(encoded_bytes)
def _receive_finished(self): bytes_str = self._receive() finished_message = FINISHED_MESSAGE.parse_bytes(bytes_str) client_verify_data = finished_message['verify_data'] expected_client_verify_data = prf256(self._ms, bytes("server_finished", 'utf-8'), hash256(self._hm), 1) assert client_verify_data == expected_client_verify_data self._hm += get_history_record(bytes_str)
def _generate_keys(self): self._ms = prf256(self._pms, bytes("extended master secret", 'utf-8'), hash256(self._hm), 2)[:48] keys = prf256(self._ms, bytes("key expansion", 'utf-8'), self._r_s + self._r_c, int(ceil((4 * KEY_LENGTH + BLOCK_LENGTH) / 32))) self._k_read_mac_s = keys[:KEY_LENGTH] self._k_write_mac_s = keys[KEY_LENGTH:2 * KEY_LENGTH] self._k_read_enc_s = keys[2 * KEY_LENGTH:3 * KEY_LENGTH] self._k_write_enc_s = keys[3 * KEY_LENGTH:4 * KEY_LENGTH] self._iv_read_s = keys[4 * KEY_LENGTH:4 * KEY_LENGTH + BLOCK_LENGTH // 2] self._iv_write_s = keys[4 * KEY_LENGTH + BLOCK_LENGTH // 2:4 * KEY_LENGTH + BLOCK_LENGTH]
def _receive_key_exchange(self): bytes_str = self._receive() key_exchange_message = CLIENT_KEY_EXCHANGE_MESSAGE.parse_bytes( bytes_str) exchange_keys = key_exchange_message['exchange_keys'] decoder = asn1.Decoder() decoder.start(exchange_keys) ''' decoder.enter() ( tag, PMSEXP = decoder.read() decoder.enter() ( decoder.enter() ( tag, algorithm = decoder.read() tag, parameters = decoder.read() ) decoder.leave() tag, subjectPublicKey = decoder.read() ) decoder.leave() ) decoder.leave() ''' decoder.enter() tag, PMSEXP = decoder.read() decoder.enter() decoder.enter() tag, algorithm = decoder.read() tag, parameters = decoder.read() decoder.leave() tag, subjectPublicKey = decoder.read() decoder.leave() decoder.leave() Q_eph = subjectPublicKey H = hash256(self._r_c + self._r_s) k_s = get_private_key_bytes() keg_res = KEG(k_s, Q_eph, H) k_exp_mac = keg_res[:len(keg_res) // 2] k_exp_enc = keg_res[len(keg_res) // 2:] IV = H[25:(24 + BLOCK_LENGTH // 2)] self._PMS = KExp15(PMSEXP, k_exp_mac, k_exp_enc, IV) self._hm += get_history_record(bytes_str)
def _send_finished(self): server_verify_data = prf256(self._ms, bytes("client_finished", 'utf-8'), hash256(self._hm), 1) self._send({'verify_data': server_verify_data}, FINISHED_MESSAGE)