Blame lib/cipher.c

Packit aea12f
/*
Packit aea12f
 * Copyright (C) 2000-2013 Free Software Foundation, Inc.
Packit aea12f
 * Copyright (C) 2013 Nikos Mavrogiannopoulos
Packit aea12f
 * Copyright (C) 2017-2018 Red Hat, Inc.
Packit aea12f
 *
Packit aea12f
 * Author: Nikos Mavrogiannopoulos
Packit aea12f
 *
Packit aea12f
 * This file is part of GnuTLS.
Packit aea12f
 *
Packit aea12f
 * The GnuTLS is free software; you can redistribute it and/or
Packit aea12f
 * modify it under the terms of the GNU Lesser General Public License
Packit aea12f
 * as published by the Free Software Foundation; either version 2.1 of
Packit aea12f
 * the License, or (at your option) any later version.
Packit aea12f
 *
Packit aea12f
 * This library is distributed in the hope that it will be useful, but
Packit aea12f
 * WITHOUT ANY WARRANTY; without even the implied warranty of
Packit aea12f
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
Packit aea12f
 * Lesser General Public License for more details.
Packit aea12f
 *
Packit aea12f
 * You should have received a copy of the GNU Lesser General Public License
Packit aea12f
 * along with this program.  If not, see <https://www.gnu.org/licenses/>
Packit aea12f
 *
Packit aea12f
 */
Packit aea12f
Packit aea12f
/* Some high level functions to be used in the record encryption are
Packit aea12f
 * included here.
Packit aea12f
 */
Packit aea12f
Packit aea12f
#include "gnutls_int.h"
Packit aea12f
#include "errors.h"
Packit aea12f
#include "cipher.h"
Packit aea12f
#include "algorithms.h"
Packit aea12f
#include "hash_int.h"
Packit aea12f
#include "cipher_int.h"
Packit aea12f
#include "debug.h"
Packit aea12f
#include "num.h"
Packit aea12f
#include "datum.h"
Packit aea12f
#include "kx.h"
Packit aea12f
#include "record.h"
Packit aea12f
#include "constate.h"
Packit aea12f
#include "mbuffers.h"
Packit aea12f
#include <state.h>
Packit aea12f
#include <random.h>
Packit aea12f
Packit aea12f
static int encrypt_packet(gnutls_session_t session,
Packit aea12f
			    uint8_t * cipher_data, int cipher_size,
Packit aea12f
			    gnutls_datum_t * plain,
Packit aea12f
			    size_t min_pad,
Packit aea12f
			    content_type_t _type,
Packit aea12f
			    record_parameters_st * params);
Packit aea12f
Packit aea12f
static int decrypt_packet(gnutls_session_t session,
Packit aea12f
			    gnutls_datum_t * ciphertext,
Packit aea12f
			    gnutls_datum_t * plain,
Packit aea12f
			    content_type_t type,
Packit aea12f
			    record_parameters_st * params,
Packit Service 991b93
			    uint64_t sequence);
Packit aea12f
Packit aea12f
static int
Packit aea12f
decrypt_packet_tls13(gnutls_session_t session,
Packit aea12f
		     gnutls_datum_t * ciphertext,
Packit aea12f
		     gnutls_datum_t * plain,
Packit aea12f
		     content_type_t *type, record_parameters_st * params,
Packit Service 991b93
		     uint64_t sequence);
Packit aea12f
Packit aea12f
static int
Packit aea12f
encrypt_packet_tls13(gnutls_session_t session,
Packit aea12f
		     uint8_t *cipher_data, size_t cipher_size,
Packit aea12f
		     gnutls_datum_t *plain,
Packit aea12f
		     size_t pad_size,
Packit aea12f
		     uint8_t type,
Packit aea12f
		     record_parameters_st *params);
Packit aea12f
Packit aea12f
/* returns ciphertext which contains the headers too. This also
Packit aea12f
 * calculates the size in the header field.
Packit Service 991b93
 *
Packit aea12f
 */
Packit aea12f
int
Packit aea12f
_gnutls_encrypt(gnutls_session_t session,
Packit aea12f
		const uint8_t *data, size_t data_size,
Packit aea12f
		size_t min_pad,
Packit aea12f
		mbuffer_st *bufel,
Packit aea12f
		content_type_t type, record_parameters_st *params)
Packit aea12f
{
Packit aea12f
	gnutls_datum_t plaintext;
Packit aea12f
	const version_entry_st *vers = get_version(session);
Packit aea12f
	int ret;
Packit aea12f
Packit aea12f
	plaintext.data = (uint8_t *) data;
Packit aea12f
	plaintext.size = data_size;
Packit aea12f
Packit aea12f
	if (vers && vers->tls13_sem) {
Packit aea12f
		/* it fills the header, as it is included in the authenticated
Packit aea12f
		 * data of the AEAD cipher. */
Packit aea12f
		ret =
Packit aea12f
		    encrypt_packet_tls13(session,
Packit aea12f
					 _mbuffer_get_udata_ptr(bufel),
Packit aea12f
					 _mbuffer_get_udata_size(bufel),
Packit aea12f
					 &plaintext, min_pad, type,
Packit aea12f
					 params);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
	} else {
Packit aea12f
		ret =
Packit aea12f
		    encrypt_packet(session,
Packit aea12f
				   _mbuffer_get_udata_ptr(bufel),
Packit aea12f
				   _mbuffer_get_udata_size
Packit aea12f
				   (bufel), &plaintext, min_pad, type,
Packit aea12f
				   params);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (IS_DTLS(session))
Packit aea12f
		_gnutls_write_uint16(ret,
Packit aea12f
				     ((uint8_t *)
Packit aea12f
				      _mbuffer_get_uhead_ptr(bufel)) + 11);
Packit aea12f
	else
Packit aea12f
		_gnutls_write_uint16(ret,
Packit aea12f
				     ((uint8_t *)
Packit aea12f
				      _mbuffer_get_uhead_ptr(bufel)) + 3);
Packit aea12f
Packit aea12f
	_mbuffer_set_udata_size(bufel, ret);
Packit aea12f
	_mbuffer_set_uhead_size(bufel, 0);
Packit aea12f
Packit aea12f
	return _mbuffer_get_udata_size(bufel);
Packit aea12f
}
Packit aea12f
Packit aea12f
/* Decrypts the given data.
Packit aea12f
 * Returns the decrypted data length.
Packit aea12f
 *
Packit aea12f
 * The output is preallocated with the maximum allowed data size.
Packit aea12f
 */
Packit aea12f
int
Packit aea12f
_gnutls_decrypt(gnutls_session_t session,
Packit aea12f
		gnutls_datum_t *ciphertext,
Packit aea12f
		gnutls_datum_t *output,
Packit aea12f
		content_type_t *type,
Packit aea12f
		record_parameters_st *params,
Packit Service 991b93
		uint64_t sequence)
Packit aea12f
{
Packit aea12f
	int ret;
Packit aea12f
	const version_entry_st *vers = get_version(session);
Packit aea12f
Packit aea12f
	if (ciphertext->size == 0)
Packit aea12f
		return 0;
Packit aea12f
Packit aea12f
	if (vers && vers->tls13_sem)
Packit aea12f
		ret =
Packit aea12f
		    decrypt_packet_tls13(session, ciphertext,
Packit aea12f
					 output, type, params,
Packit aea12f
					 sequence);
Packit aea12f
	else
Packit aea12f
		ret =
Packit aea12f
		    decrypt_packet(session, ciphertext,
Packit aea12f
				   output, *type, params,
Packit aea12f
				   sequence);
Packit aea12f
	if (ret < 0)
Packit aea12f
		return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
	return ret;
Packit aea12f
}
Packit aea12f
Packit aea12f
Packit aea12f
inline static int
Packit aea12f
calc_enc_length_block(gnutls_session_t session,
Packit aea12f
		      const version_entry_st * ver,
Packit aea12f
		      int data_size,
Packit aea12f
		      int hash_size, uint8_t * pad,
Packit aea12f
		      unsigned auth_cipher,
Packit aea12f
		      uint16_t blocksize,
Packit aea12f
		      unsigned etm)
Packit aea12f
{
Packit aea12f
	/* pad is the LH pad the user wants us to add. Besides
Packit aea12f
	 * this LH pad, we only add minimal padding
Packit aea12f
	 */
Packit aea12f
	unsigned int pre_length = data_size + *pad;
Packit aea12f
	unsigned int length, new_pad;
Packit aea12f
Packit aea12f
	if (etm == 0)
Packit aea12f
		pre_length += hash_size;
Packit aea12f
Packit aea12f
	new_pad = (uint8_t) (blocksize - (pre_length % blocksize)) + *pad;
Packit aea12f
Packit aea12f
	if (new_pad > 255)
Packit aea12f
		new_pad -= blocksize;
Packit aea12f
	*pad = new_pad;
Packit aea12f
Packit aea12f
	length = data_size + hash_size + *pad;
Packit aea12f
Packit aea12f
	if (_gnutls_version_has_explicit_iv(ver))
Packit aea12f
		length += blocksize;	/* for the IV */
Packit aea12f
Packit aea12f
	return length;
Packit aea12f
}
Packit aea12f
Packit aea12f
inline static int
Packit aea12f
calc_enc_length_stream(gnutls_session_t session, int data_size,
Packit aea12f
		       int hash_size, unsigned auth_cipher,
Packit aea12f
		       unsigned exp_iv_size)
Packit aea12f
{
Packit aea12f
	unsigned int length;
Packit aea12f
Packit aea12f
	length = data_size + hash_size;
Packit aea12f
	if (auth_cipher)
Packit aea12f
		length += exp_iv_size;
Packit aea12f
Packit aea12f
	return length;
Packit aea12f
}
Packit aea12f
Packit aea12f
/* generates the authentication data (data to be hashed only
Packit aea12f
 * and are not to be sent). Returns their size.
Packit aea12f
 */
Packit aea12f
int
Packit Service 991b93
_gnutls_make_preamble(uint64_t uint64_data, uint8_t type, unsigned int length,
Packit aea12f
		      const version_entry_st * ver, uint8_t preamble[MAX_PREAMBLE_SIZE])
Packit aea12f
{
Packit aea12f
	uint8_t *p = preamble;
Packit aea12f
	uint16_t c_length;
Packit aea12f
Packit aea12f
	c_length = _gnutls_conv_uint16(length);
Packit aea12f
Packit Service 991b93
	_gnutls_write_uint64(uint64_data, p);
Packit aea12f
	p += 8;
Packit aea12f
	*p = type;
Packit aea12f
	p++;
Packit aea12f
#ifdef ENABLE_SSL3
Packit aea12f
	if (ver->id != GNUTLS_SSL3)
Packit aea12f
#endif
Packit aea12f
	{	/* TLS protocols */
Packit aea12f
		*p = ver->major;
Packit aea12f
		p++;
Packit aea12f
		*p = ver->minor;
Packit aea12f
		p++;
Packit aea12f
	}
Packit aea12f
	memcpy(p, &c_length, 2);
Packit aea12f
	p += 2;
Packit aea12f
	return p - preamble;
Packit aea12f
}
Packit aea12f
Packit Service 991b93
/* This is the actual encryption
Packit aea12f
 * Encrypts the given plaintext datum, and puts the result to cipher_data,
Packit aea12f
 * which has cipher_size size.
Packit aea12f
 * return the actual encrypted data length.
Packit aea12f
 */
Packit aea12f
static int
Packit aea12f
encrypt_packet(gnutls_session_t session,
Packit aea12f
			 uint8_t * cipher_data, int cipher_size,
Packit aea12f
			 gnutls_datum_t * plain,
Packit aea12f
			 size_t min_pad,
Packit aea12f
			 content_type_t type,
Packit aea12f
			 record_parameters_st * params)
Packit aea12f
{
Packit aea12f
	uint8_t pad;
Packit aea12f
	int length, ret;
Packit aea12f
	uint8_t preamble[MAX_PREAMBLE_SIZE];
Packit aea12f
	int preamble_size;
Packit aea12f
	int tag_size =
Packit aea12f
	    _gnutls_auth_cipher_tag_len(&params->write.ctx.tls12);
Packit aea12f
	int blocksize = _gnutls_cipher_get_block_size(params->cipher);
Packit aea12f
	unsigned algo_type = _gnutls_cipher_type(params->cipher);
Packit aea12f
	uint8_t *data_ptr, *full_cipher_ptr;
Packit aea12f
	const version_entry_st *ver = get_version(session);
Packit aea12f
	int explicit_iv = _gnutls_version_has_explicit_iv(ver);
Packit aea12f
	int auth_cipher =
Packit aea12f
	    _gnutls_auth_cipher_is_aead(&params->write.ctx.tls12);
Packit aea12f
	uint8_t nonce[MAX_CIPHER_IV_SIZE];
Packit aea12f
	unsigned imp_iv_size = 0, exp_iv_size = 0;
Packit aea12f
	bool etm = 0;
Packit aea12f
Packit aea12f
	if (unlikely(ver == NULL))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
	if (algo_type == CIPHER_BLOCK && params->etm != 0)
Packit aea12f
		etm = 1;
Packit aea12f
Packit aea12f
	_gnutls_hard_log("ENC[%p]: cipher: %s, MAC: %s, Epoch: %u\n",
Packit aea12f
			 session, _gnutls_cipher_get_name(params->cipher),
Packit aea12f
			 _gnutls_mac_get_name(params->mac),
Packit aea12f
			 (unsigned int) params->epoch);
Packit aea12f
Packit aea12f
	/* Calculate the encrypted length (padding etc.)
Packit aea12f
	 */
Packit aea12f
	if (algo_type == CIPHER_BLOCK) {
Packit aea12f
		/* Call gnutls_rnd() once. Get data used for the IV
Packit aea12f
		 */
Packit aea12f
		ret = gnutls_rnd(GNUTLS_RND_NONCE, nonce, blocksize);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		pad = min_pad;
Packit aea12f
Packit aea12f
		length =
Packit aea12f
		    calc_enc_length_block(session, ver, plain->size,
Packit aea12f
					  tag_size, &pad, auth_cipher,
Packit aea12f
					  blocksize, etm);
Packit aea12f
	} else { /* AEAD + STREAM */
Packit aea12f
		imp_iv_size = _gnutls_cipher_get_implicit_iv_size(params->cipher);
Packit aea12f
		exp_iv_size = _gnutls_cipher_get_explicit_iv_size(params->cipher);
Packit aea12f
Packit aea12f
		pad = 0;
Packit aea12f
		length =
Packit aea12f
		    calc_enc_length_stream(session, plain->size,
Packit aea12f
					   tag_size, auth_cipher,
Packit aea12f
					   exp_iv_size);
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (length < 0)
Packit aea12f
		return gnutls_assert_val(length);
Packit aea12f
Packit aea12f
	/* copy the encrypted data to cipher_data.
Packit aea12f
	 */
Packit aea12f
	if (cipher_size < length)
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
	data_ptr = cipher_data;
Packit aea12f
	full_cipher_ptr = data_ptr;
Packit aea12f
Packit aea12f
	if (algo_type == CIPHER_BLOCK || algo_type == CIPHER_STREAM) {
Packit aea12f
		if (algo_type == CIPHER_BLOCK && explicit_iv != 0) {
Packit aea12f
			/* copy the random IV.
Packit aea12f
			 */
Packit aea12f
			memcpy(data_ptr, nonce, blocksize);
Packit Service 991b93
			ret = _gnutls_auth_cipher_setiv(&params->write.
Packit aea12f
						  ctx.tls12, data_ptr,
Packit aea12f
						  blocksize);
Packit Service 991b93
			if (ret < 0)
Packit Service 991b93
				return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
			/*data_ptr += blocksize;*/
Packit aea12f
			cipher_data += blocksize;
Packit aea12f
		}
Packit aea12f
	} else { /* AEAD */
Packit Service 991b93
		if ((params->cipher->flags & GNUTLS_CIPHER_FLAG_XOR_NONCE) == 0) {
Packit aea12f
			/* Values in AEAD are pretty fixed in TLS 1.2 for 128-bit block
Packit aea12f
			 */
Packit aea12f
			 if (params->write.iv_size != imp_iv_size)
Packit aea12f
				return
Packit aea12f
				    gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
			/* Instead of generating a new nonce on every packet, we use the
Packit aea12f
			 * write.sequence_number (It is a MAY on RFC 5288), and safer
Packit aea12f
			 * as it will never reuse a value.
Packit aea12f
			 */
Packit aea12f
			memcpy(nonce, params->write.iv,
Packit aea12f
			       params->write.iv_size);
Packit Service 991b93
			_gnutls_write_uint64(params->write.sequence_number, &nonce[imp_iv_size]);
Packit aea12f
Packit aea12f
			memcpy(data_ptr, &nonce[imp_iv_size],
Packit aea12f
			       exp_iv_size);
Packit aea12f
Packit aea12f
			/*data_ptr += exp_iv_size;*/
Packit aea12f
			cipher_data += exp_iv_size;
Packit aea12f
		} else { /* XOR nonce with IV */
Packit aea12f
			if (unlikely(params->write.iv_size != 12 || imp_iv_size != 12 || exp_iv_size != 0))
Packit aea12f
				return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
			memset(nonce, 0, 4);
Packit Service 991b93
			_gnutls_write_uint64(params->write.sequence_number, &nonce[4]);
Packit aea12f
Packit aea12f
			memxor(nonce, params->write.iv, 12);
Packit aea12f
		}
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (etm)
Packit aea12f
		ret = length-tag_size;
Packit aea12f
	else
Packit aea12f
		ret = plain->size;
Packit aea12f
Packit aea12f
	preamble_size =
Packit Service 991b93
	    _gnutls_make_preamble(params->write.sequence_number,
Packit aea12f
				  type, ret, ver, preamble);
Packit aea12f
Packit aea12f
	if (algo_type == CIPHER_BLOCK || algo_type == CIPHER_STREAM) {
Packit aea12f
		/* add the authenticated data */
Packit aea12f
		ret =
Packit aea12f
		    _gnutls_auth_cipher_add_auth(&params->write.ctx.tls12,
Packit aea12f
					 preamble, preamble_size);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		if (etm && explicit_iv) {
Packit aea12f
			/* In EtM we need to hash the IV as well */
Packit aea12f
			ret =
Packit aea12f
			    _gnutls_auth_cipher_add_auth(&params->write.ctx.tls12,
Packit aea12f
						 full_cipher_ptr, blocksize);
Packit aea12f
			if (ret < 0)
Packit aea12f
				return gnutls_assert_val(ret);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		/* Actual encryption.
Packit aea12f
		 */
Packit aea12f
		ret =
Packit aea12f
		    _gnutls_auth_cipher_encrypt2_tag(&params->write.ctx.tls12,
Packit aea12f
						     plain->data,
Packit aea12f
						     plain->size, cipher_data,
Packit aea12f
						     cipher_size, pad);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
	} else { /* AEAD */
Packit aea12f
		ret = _gnutls_aead_cipher_encrypt(&params->write.ctx.tls12.cipher,
Packit aea12f
						  nonce, imp_iv_size + exp_iv_size,
Packit aea12f
						  preamble, preamble_size,
Packit aea12f
						  tag_size,
Packit aea12f
						  plain->data, plain->size,
Packit aea12f
						  cipher_data, cipher_size);
Packit aea12f
		if (ret < 0)
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
	}
Packit aea12f
Packit aea12f
	return length;
Packit aea12f
}
Packit aea12f
Packit aea12f
static int
Packit aea12f
encrypt_packet_tls13(gnutls_session_t session,
Packit aea12f
		     uint8_t *cipher_data, size_t cipher_size,
Packit aea12f
		     gnutls_datum_t *plain,
Packit aea12f
		     size_t pad_size,
Packit aea12f
		     uint8_t type,
Packit aea12f
		     record_parameters_st *params)
Packit aea12f
{
Packit aea12f
	int ret;
Packit aea12f
	unsigned int tag_size = params->write.aead_tag_size;
Packit aea12f
	const version_entry_st *ver = get_version(session);
Packit aea12f
	uint8_t nonce[MAX_CIPHER_IV_SIZE];
Packit aea12f
	unsigned iv_size = 0;
Packit aea12f
	ssize_t max, total;
Packit aea12f
	uint8_t aad[5];
Packit aea12f
	giovec_t auth_iov[1];
Packit aea12f
	giovec_t iov[2];
Packit aea12f
Packit aea12f
	if (unlikely(ver == NULL))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
	_gnutls_hard_log("ENC[%p]: cipher: %s, MAC: %s, Epoch: %u\n",
Packit aea12f
			 session, _gnutls_cipher_get_name(params->cipher),
Packit aea12f
			 _gnutls_mac_get_name(params->mac),
Packit aea12f
			 (unsigned int) params->epoch);
Packit aea12f
Packit aea12f
	iv_size = params->write.iv_size;
Packit aea12f
Packit aea12f
	if (params->cipher->id == GNUTLS_CIPHER_NULL) {
Packit aea12f
		if (cipher_size < plain->size+1)
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
		memcpy(cipher_data, plain->data, plain->size);
Packit aea12f
		return plain->size;
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (unlikely(iv_size < 8))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit Service 991b93
	memset(nonce, 0, iv_size - 8);
Packit Service 991b93
	_gnutls_write_uint64(params->write.sequence_number, &nonce[iv_size-8]);
Packit Service 991b93
	memxor(nonce, params->write.iv, iv_size);
Packit aea12f
Packit aea12f
	max = MAX_RECORD_SEND_SIZE(session);
Packit aea12f
Packit aea12f
	/* make TLS 1.3 form of data */
Packit aea12f
	total = plain->size + 1 + pad_size;
Packit aea12f
Packit aea12f
	/* check whether padding would exceed max */
Packit aea12f
	if (total > max) {
Packit aea12f
		if (unlikely(max < (ssize_t)plain->size+1))
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
		pad_size = max - plain->size - 1;
Packit aea12f
		total = max;
Packit aea12f
	}
Packit aea12f
Packit aea12f
	/* create authenticated data header */
Packit aea12f
	aad[0] = GNUTLS_APPLICATION_DATA;
Packit aea12f
	aad[1] = 0x03;
Packit aea12f
	aad[2] = 0x03;
Packit aea12f
	_gnutls_write_uint16(total+tag_size, &aad[3]);
Packit aea12f
Packit aea12f
	auth_iov[0].iov_base = aad;
Packit aea12f
	auth_iov[0].iov_len = sizeof(aad);
Packit aea12f
Packit aea12f
	iov[0].iov_base = plain->data;
Packit aea12f
	iov[0].iov_len = plain->size;
Packit aea12f
Packit aea12f
	if (pad_size || (session->internals.flags & GNUTLS_SAFE_PADDING_CHECK)) {
Packit aea12f
		uint8_t *pad = gnutls_calloc(1, 1+pad_size);
Packit aea12f
		if (pad == NULL)
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_MEMORY_ERROR);
Packit aea12f
Packit aea12f
		pad[0] = type;
Packit aea12f
Packit aea12f
		iov[1].iov_base = pad;
Packit aea12f
		iov[1].iov_len = 1+pad_size;
Packit aea12f
Packit aea12f
		ret = gnutls_aead_cipher_encryptv(&params->write.ctx.aead,
Packit aea12f
						  nonce, iv_size,
Packit aea12f
						  auth_iov, 1,
Packit aea12f
						  tag_size,
Packit aea12f
						  iov, 2,
Packit aea12f
						  cipher_data, &cipher_size);
Packit aea12f
		gnutls_free(pad);
Packit aea12f
	} else {
Packit aea12f
		iov[1].iov_base = &type;
Packit aea12f
		iov[1].iov_len = 1;
Packit aea12f
Packit aea12f
		ret = gnutls_aead_cipher_encryptv(&params->write.ctx.aead,
Packit aea12f
						  nonce, iv_size,
Packit aea12f
						  auth_iov, 1,
Packit aea12f
						  tag_size,
Packit aea12f
						  iov, 2,
Packit aea12f
						  cipher_data, &cipher_size);
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (ret < 0)
Packit aea12f
		return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
	return cipher_size;
Packit aea12f
}
Packit aea12f
Packit aea12f
Packit aea12f
/* Deciphers the ciphertext packet, and puts the result to plain.
Packit aea12f
 * Returns the actual plaintext packet size.
Packit aea12f
 */
Packit aea12f
static int
Packit aea12f
decrypt_packet(gnutls_session_t session,
Packit aea12f
		gnutls_datum_t * ciphertext,
Packit aea12f
		gnutls_datum_t * plain,
Packit aea12f
		content_type_t type, record_parameters_st * params,
Packit Service 991b93
		uint64_t sequence)
Packit aea12f
{
Packit aea12f
	uint8_t tag[MAX_HASH_SIZE];
Packit aea12f
	uint8_t nonce[MAX_CIPHER_IV_SIZE];
Packit aea12f
	const uint8_t *tag_ptr = NULL;
Packit aea12f
	unsigned int pad = 0;
Packit aea12f
	int length, length_to_decrypt;
Packit aea12f
	uint16_t blocksize;
Packit aea12f
	int ret;
Packit aea12f
	uint8_t preamble[MAX_PREAMBLE_SIZE];
Packit aea12f
	unsigned int preamble_size = 0;
Packit aea12f
	const version_entry_st *ver = get_version(session);
Packit aea12f
	unsigned int tag_size =
Packit aea12f
	    _gnutls_auth_cipher_tag_len(&params->read.ctx.tls12);
Packit aea12f
	unsigned int explicit_iv = _gnutls_version_has_explicit_iv(ver);
Packit aea12f
	unsigned imp_iv_size, exp_iv_size;
Packit aea12f
	unsigned cipher_type = _gnutls_cipher_type(params->cipher);
Packit aea12f
	bool etm = 0;
Packit aea12f
Packit aea12f
	if (unlikely(ver == NULL))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
	imp_iv_size = _gnutls_cipher_get_implicit_iv_size(params->cipher);
Packit aea12f
	exp_iv_size = _gnutls_cipher_get_explicit_iv_size(params->cipher);
Packit aea12f
	blocksize = _gnutls_cipher_get_block_size(params->cipher);
Packit aea12f
Packit aea12f
	if (params->etm !=0 && cipher_type == CIPHER_BLOCK)
Packit aea12f
		etm = 1;
Packit aea12f
Packit aea12f
	/* if EtM mode and not AEAD */
Packit aea12f
	if (etm) {
Packit aea12f
		if (unlikely(ciphertext->size < tag_size))
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
Packit aea12f
Packit Service 991b93
		preamble_size = _gnutls_make_preamble(sequence,
Packit aea12f
						      type, ciphertext->size-tag_size,
Packit aea12f
						      ver, preamble);
Packit aea12f
Packit aea12f
		ret = _gnutls_auth_cipher_add_auth(&params->read.
Packit aea12f
						   ctx.tls12, preamble,
Packit aea12f
						   preamble_size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		ret = _gnutls_auth_cipher_add_auth(&params->read.
Packit aea12f
						   ctx.tls12,
Packit aea12f
						   ciphertext->data,
Packit aea12f
						   ciphertext->size-tag_size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		ret = _gnutls_auth_cipher_tag(&params->read.ctx.tls12, tag, tag_size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit Service 991b93
Packit aea12f
		if (unlikely(gnutls_memcmp(tag, &ciphertext->data[ciphertext->size-tag_size], tag_size) != 0)) {
Packit aea12f
			/* HMAC was not the same. */
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
		}
Packit aea12f
	}
Packit aea12f
Packit aea12f
	/* actual decryption (inplace)
Packit aea12f
	 */
Packit aea12f
	switch (cipher_type) {
Packit aea12f
	case CIPHER_AEAD:
Packit aea12f
		/* The way AEAD ciphers are defined in RFC5246, it allows
Packit aea12f
		 * only stream ciphers.
Packit aea12f
		 */
Packit aea12f
		if (unlikely(_gnutls_auth_cipher_is_aead(&params->read.
Packit aea12f
						   ctx.tls12) == 0))
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
Packit aea12f
		if (unlikely(ciphertext->size < (tag_size + exp_iv_size)))
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit Service 991b93
		if ((params->cipher->flags & GNUTLS_CIPHER_FLAG_XOR_NONCE) == 0) {
Packit aea12f
			/* Values in AEAD are pretty fixed in TLS 1.2 for 128-bit block
Packit aea12f
			 */
Packit aea12f
			 if (unlikely(params->read.iv_size != 4))
Packit aea12f
				return
Packit aea12f
				    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
			memcpy(nonce, params->read.iv,
Packit aea12f
			       imp_iv_size);
Packit aea12f
Packit aea12f
			memcpy(&nonce[imp_iv_size],
Packit aea12f
			       ciphertext->data, exp_iv_size);
Packit aea12f
Packit aea12f
			ciphertext->data += exp_iv_size;
Packit aea12f
			ciphertext->size -= exp_iv_size;
Packit aea12f
		} else { /* XOR nonce with IV */
Packit aea12f
			if (unlikely(params->read.iv_size != 12 || imp_iv_size != 12 || exp_iv_size != 0))
Packit aea12f
				return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
			memset(nonce, 0, 4);
Packit Service 991b93
			_gnutls_write_uint64(sequence, &nonce[4]);
Packit aea12f
Packit aea12f
			memxor(nonce, params->read.iv, 12);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		length =
Packit aea12f
		    ciphertext->size - tag_size;
Packit aea12f
Packit aea12f
		length_to_decrypt = ciphertext->size;
Packit aea12f
Packit aea12f
		/* Pass the type, version, length and plain through
Packit aea12f
		 * MAC.
Packit aea12f
		 */
Packit aea12f
		preamble_size =
Packit Service 991b93
		    _gnutls_make_preamble(sequence, type,
Packit aea12f
					  length, ver, preamble);
Packit aea12f
Packit aea12f
Packit aea12f
		if (unlikely
Packit aea12f
		    ((unsigned) length_to_decrypt > plain->size)) {
Packit aea12f
			_gnutls_audit_log(session,
Packit aea12f
					  "Received %u bytes, while expecting less than %u\n",
Packit aea12f
					  (unsigned int) length_to_decrypt,
Packit aea12f
					  (unsigned int) plain->size);
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		ret = _gnutls_aead_cipher_decrypt(&params->read.ctx.tls12.cipher,
Packit aea12f
						  nonce, exp_iv_size + imp_iv_size,
Packit aea12f
						  preamble, preamble_size,
Packit aea12f
						  tag_size,
Packit aea12f
						  ciphertext->data, length_to_decrypt,
Packit aea12f
						  plain->data, plain->size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		return length;
Packit aea12f
Packit aea12f
		break;
Packit aea12f
	case CIPHER_STREAM:
Packit aea12f
		if (unlikely(ciphertext->size < tag_size))
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val
Packit aea12f
			    (GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
Packit aea12f
Packit aea12f
		length_to_decrypt = ciphertext->size;
Packit aea12f
		length = ciphertext->size - tag_size;
Packit aea12f
		tag_ptr = plain->data + length;
Packit aea12f
Packit aea12f
		/* Pass the type, version, length and plain through
Packit aea12f
		 * MAC.
Packit aea12f
		 */
Packit aea12f
		preamble_size =
Packit Service 991b93
		    _gnutls_make_preamble(sequence, type,
Packit aea12f
					  length, ver, preamble);
Packit aea12f
Packit aea12f
		ret =
Packit aea12f
		    _gnutls_auth_cipher_add_auth(&params->read.
Packit aea12f
						 ctx.tls12, preamble,
Packit aea12f
						 preamble_size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		if (unlikely
Packit aea12f
		    ((unsigned) length_to_decrypt > plain->size)) {
Packit aea12f
			_gnutls_audit_log(session,
Packit aea12f
					  "Received %u bytes, while expecting less than %u\n",
Packit aea12f
					  (unsigned int) length_to_decrypt,
Packit aea12f
					  (unsigned int) plain->size);
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		ret =
Packit aea12f
		    _gnutls_auth_cipher_decrypt2(&params->read.
Packit aea12f
						 ctx.tls12,
Packit aea12f
						 ciphertext->data,
Packit aea12f
						 length_to_decrypt,
Packit aea12f
						 plain->data,
Packit aea12f
						 plain->size);
Packit aea12f
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		ret =
Packit aea12f
		    _gnutls_auth_cipher_tag(&params->read.ctx.tls12, tag,
Packit aea12f
					    tag_size);
Packit aea12f
		if (unlikely(ret < 0))
Packit aea12f
			return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
		if (unlikely
Packit aea12f
		    (gnutls_memcmp(tag, tag_ptr, tag_size) != 0)) {
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		break;
Packit aea12f
	case CIPHER_BLOCK:
Packit aea12f
		if (unlikely(ciphertext->size < blocksize))
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val
Packit aea12f
			    (GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
Packit aea12f
Packit aea12f
		if (etm == 0) {
Packit aea12f
			if (unlikely(ciphertext->size % blocksize != 0))
Packit aea12f
				return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
Packit aea12f
		} else {
Packit aea12f
			if (unlikely((ciphertext->size - tag_size) % blocksize != 0))
Packit aea12f
				return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
Packit aea12f
		}
Packit aea12f
Packit aea12f
		/* ignore the IV in TLS 1.1+
Packit aea12f
		 */
Packit aea12f
		if (explicit_iv) {
Packit Service 991b93
			ret = _gnutls_auth_cipher_setiv(&params->read.
Packit aea12f
						  ctx.tls12,
Packit aea12f
						  ciphertext->data,
Packit aea12f
						  blocksize);
Packit Service 991b93
			if (ret < 0)
Packit Service 991b93
				return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
			memcpy(nonce, ciphertext->data, blocksize);
Packit aea12f
			ciphertext->size -= blocksize;
Packit aea12f
			ciphertext->data += blocksize;
Packit aea12f
		}
Packit aea12f
Packit aea12f
		if (unlikely(ciphertext->size < tag_size + 1))
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
		/* we don't use the auth_cipher interface here, since
Packit aea12f
		 * TLS with block ciphers is impossible to be used under such
Packit aea12f
		 * an API. (the length of plaintext is required to calculate
Packit aea12f
		 * auth_data, but it is not available before decryption).
Packit aea12f
		 */
Packit aea12f
		if (unlikely(ciphertext->size > plain->size))
Packit aea12f
			return
Packit aea12f
			    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
		if (etm == 0) {
Packit aea12f
			ret =
Packit aea12f
			    _gnutls_cipher_decrypt2(&params->read.ctx.tls12.
Packit aea12f
						    cipher, ciphertext->data,
Packit aea12f
						    ciphertext->size,
Packit aea12f
						    plain->data,
Packit aea12f
						    plain->size);
Packit aea12f
			if (unlikely(ret < 0))
Packit aea12f
				return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
			ret = cbc_mac_verify(session, params, preamble, type,
Packit aea12f
					     sequence, plain->data, ciphertext->size,
Packit aea12f
					     tag_size);
Packit aea12f
			if (unlikely(ret < 0))
Packit aea12f
				return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
			length = ret;
Packit aea12f
		} else { /* EtM */
Packit aea12f
			ret =
Packit aea12f
			    _gnutls_cipher_decrypt2(&params->read.ctx.tls12.
Packit aea12f
						    cipher, ciphertext->data,
Packit aea12f
						    ciphertext->size - tag_size,
Packit aea12f
						    plain->data,
Packit aea12f
						    plain->size);
Packit aea12f
			if (unlikely(ret < 0))
Packit aea12f
				return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
			pad = plain->data[ciphertext->size - tag_size - 1]; /* pad */
Packit aea12f
			length = ciphertext->size - tag_size - pad - 1;
Packit Service 991b93
Packit aea12f
			if (unlikely(length < 0))
Packit aea12f
				return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
		}
Packit aea12f
		break;
Packit aea12f
	default:
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
	}
Packit aea12f
Packit aea12f
Packit aea12f
	return length;
Packit aea12f
}
Packit aea12f
Packit aea12f
static int
Packit aea12f
decrypt_packet_tls13(gnutls_session_t session,
Packit aea12f
		     gnutls_datum_t *ciphertext,
Packit aea12f
		     gnutls_datum_t *plain,
Packit aea12f
		     content_type_t *type, record_parameters_st *params,
Packit Service 991b93
		     uint64_t sequence)
Packit aea12f
{
Packit aea12f
	uint8_t nonce[MAX_CIPHER_IV_SIZE];
Packit aea12f
	size_t length, length_to_decrypt;
Packit aea12f
	int ret;
Packit aea12f
	const version_entry_st *ver = get_version(session);
Packit aea12f
	unsigned int tag_size = params->read.aead_tag_size;
Packit aea12f
	unsigned iv_size;
Packit aea12f
	unsigned j;
Packit aea12f
	volatile unsigned length_set;
Packit aea12f
	uint8_t aad[5];
Packit aea12f
Packit aea12f
	if (unlikely(ver == NULL))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
	if (params->cipher->id == GNUTLS_CIPHER_NULL) {
Packit aea12f
		if (plain->size < ciphertext->size)
Packit aea12f
			return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
Packit aea12f
Packit aea12f
		length = ciphertext->size;
Packit aea12f
		memcpy(plain->data, ciphertext->data, length);
Packit aea12f
Packit aea12f
		return length;
Packit aea12f
	}
Packit aea12f
Packit aea12f
	iv_size = _gnutls_cipher_get_iv_size(params->cipher);
Packit aea12f
Packit aea12f
	/* The way AEAD ciphers are defined in RFC5246, it allows
Packit aea12f
	 * only stream ciphers.
Packit aea12f
	 */
Packit aea12f
	if (unlikely(ciphertext->size < tag_size))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
	if (unlikely(params->read.iv_size != iv_size || iv_size < 8))
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit Service 991b93
	memset(nonce, 0, iv_size - 8);
Packit Service 991b93
	_gnutls_write_uint64(sequence, &nonce[iv_size-8]);
Packit Service 991b93
	memxor(nonce, params->read.iv, params->read.iv_size);
Packit aea12f
Packit aea12f
	length =
Packit aea12f
	    ciphertext->size - tag_size;
Packit aea12f
Packit aea12f
	length_to_decrypt = ciphertext->size;
Packit aea12f
Packit aea12f
	if (unlikely
Packit aea12f
	    ((unsigned) length_to_decrypt > plain->size)) {
Packit aea12f
			_gnutls_audit_log(session,
Packit aea12f
				  "Received %u bytes, while expecting less than %u\n",
Packit aea12f
				  (unsigned int) length_to_decrypt,
Packit aea12f
				  (unsigned int) plain->size);
Packit aea12f
		return
Packit aea12f
		    gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
	}
Packit aea12f
Packit aea12f
	aad[0] = GNUTLS_APPLICATION_DATA;
Packit aea12f
	aad[1] = 0x03;
Packit aea12f
	aad[2] = 0x03;
Packit aea12f
	_gnutls_write_uint16(ciphertext->size, &aad[3]);
Packit aea12f
Packit aea12f
	ret = gnutls_aead_cipher_decrypt(&params->read.ctx.aead,
Packit aea12f
					 nonce, iv_size,
Packit aea12f
					 aad, sizeof(aad),
Packit aea12f
					 tag_size,
Packit aea12f
					 ciphertext->data, length_to_decrypt,
Packit aea12f
					 plain->data, &length);
Packit aea12f
	if (unlikely(ret < 0))
Packit aea12f
		return gnutls_assert_val(ret);
Packit aea12f
Packit aea12f
	/* 1 octet for content type */
Packit aea12f
	if (length > max_decrypted_size(session) + 1) {
Packit aea12f
		_gnutls_audit_log
Packit aea12f
		    (session, "Received packet with illegal length: %u\n",
Packit aea12f
		     (unsigned int) length);
Packit aea12f
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_RECORD_OVERFLOW);
Packit aea12f
	}
Packit aea12f
Packit aea12f
	length_set = 0;
Packit aea12f
Packit aea12f
	/* now figure the actual data size. We intentionally iterate through all data,
Packit aea12f
	 * to avoid leaking the padding length due to timing differences in processing.
Packit aea12f
	 */
Packit aea12f
	for (j=length;j>0;j--) {
Packit aea12f
		if (plain->data[j-1]!=0 && length_set == 0) {
Packit aea12f
			*type = plain->data[j-1];
Packit aea12f
			length = j-1;
Packit aea12f
			length_set = 1;
Packit aea12f
			if (!(session->internals.flags & GNUTLS_SAFE_PADDING_CHECK))
Packit aea12f
				break;
Packit aea12f
		}
Packit aea12f
	}
Packit aea12f
Packit aea12f
	if (!length_set)
Packit aea12f
		return gnutls_assert_val(GNUTLS_E_DECRYPTION_FAILED);
Packit aea12f
Packit aea12f
	return length;
Packit aea12f
}