|
Packit Service |
4684c1 |
/*
|
|
Packit Service |
4684c1 |
* Copyright (C) 2000-2012 Free Software Foundation, Inc.
|
|
Packit Service |
4684c1 |
* Copyright (C) 2017 Red Hat, Inc.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* Author: Nikos Mavrogiannopoulos
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* This file is part of GnuTLS.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* The GnuTLS is free software; you can redistribute it and/or
|
|
Packit Service |
4684c1 |
* modify it under the terms of the GNU Lesser General Public License
|
|
Packit Service |
4684c1 |
* as published by the Free Software Foundation; either version 2.1 of
|
|
Packit Service |
4684c1 |
* the License, or (at your option) any later version.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* This library is distributed in the hope that it will be useful, but
|
|
Packit Service |
4684c1 |
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
Packit Service |
4684c1 |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
Packit Service |
4684c1 |
* Lesser General Public License for more details.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* You should have received a copy of the GNU Lesser General Public License
|
|
Packit Service |
4684c1 |
* along with this program. If not, see <https://www.gnu.org/licenses/>
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Contains functions that are supposed to pack and unpack session data,
|
|
Packit Service |
4684c1 |
* before and after they are sent to the database backend.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
#include "gnutls_int.h"
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_SRP
|
|
Packit Service |
4684c1 |
#include <auth/srp_kx.h>
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_PSK
|
|
Packit Service |
4684c1 |
#include <auth/psk.h>
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#include <auth/anon.h>
|
|
Packit Service |
4684c1 |
#include <auth/cert.h>
|
|
Packit Service |
4684c1 |
#include "errors.h"
|
|
Packit Service |
4684c1 |
#include <auth.h>
|
|
Packit Service |
4684c1 |
#include <session_pack.h>
|
|
Packit Service |
4684c1 |
#include <datum.h>
|
|
Packit Service |
4684c1 |
#include <num.h>
|
|
Packit Service |
4684c1 |
#include <hello_ext.h>
|
|
Packit Service |
4684c1 |
#include <constate.h>
|
|
Packit Service |
4684c1 |
#include <algorithms.h>
|
|
Packit Service |
4684c1 |
#include <state.h>
|
|
Packit Service |
4684c1 |
#include <db.h>
|
|
Packit Service |
4684c1 |
#include "tls13/session_ticket.h"
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int pack_certificate_auth_info(gnutls_session_t,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int unpack_certificate_auth_info(gnutls_session_t,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int unpack_srp_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int pack_srp_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int unpack_psk_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int pack_psk_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int unpack_anon_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int pack_anon_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int unpack_security_parameters(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int pack_security_parameters(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int tls13_unpack_security_parameters(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
static int tls13_pack_security_parameters(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * packed_session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Since auth_info structures contain malloced data, this function
|
|
Packit Service |
4684c1 |
* is required in order to pack these structures in a vector in
|
|
Packit Service |
4684c1 |
* order to store them to the DB.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* packed_session will contain the session data.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* The data will be in a platform independent format.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
int
|
|
Packit Service |
4684c1 |
_gnutls_session_pack(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_datum_t * packed_session)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
gnutls_buffer_st sb;
|
|
Packit Service |
4684c1 |
uint8_t id;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (packed_session == NULL) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
_gnutls_buffer_init(&sb);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
id = gnutls_auth_get_type(session);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(&sb, PACKED_SESSION_MAGIC);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(&sb, session->security_parameters.timestamp);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(&sb, session->internals.expire_time);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND(&sb, &id, 1);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
switch (id) {
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_SRP
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_SRP:
|
|
Packit Service |
4684c1 |
ret = pack_srp_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_PSK
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_PSK:
|
|
Packit Service |
4684c1 |
ret = pack_psk_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_ANON
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_ANON:
|
|
Packit Service |
4684c1 |
ret = pack_anon_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_CERTIFICATE:
|
|
Packit Service |
4684c1 |
ret = pack_certificate_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
default:
|
|
Packit Service |
4684c1 |
ret = gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Auth_info structures copied. Now copy security_parameters_st.
|
|
Packit Service |
4684c1 |
* packed_session must have allocated space for the security parameters.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
ret = pack_security_parameters(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
ret = tls13_pack_security_parameters(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Extensions are re-negotiated in a resumed session under TLS 1.3 */
|
|
Packit Service |
4684c1 |
if (!session->security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
ret = _gnutls_hello_ext_pack(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto fail;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return _gnutls_buffer_to_datum(&sb, packed_session, 0);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
fail:
|
|
Packit Service |
4684c1 |
_gnutls_buffer_clear(&sb);
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Load session data from a buffer.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
int
|
|
Packit Service |
4684c1 |
_gnutls_session_unpack(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
const gnutls_datum_t * packed_session)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
gnutls_buffer_st sb;
|
|
Packit Service |
4684c1 |
uint32_t magic;
|
|
Packit Service |
4684c1 |
uint32_t expire_time;
|
|
Packit Service |
4684c1 |
uint8_t id;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
_gnutls_buffer_init(&sb);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (packed_session == NULL || packed_session->size == 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_buffer_append_data(&sb, packed_session->data,
|
|
Packit Service |
4684c1 |
packed_session->size);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->key.auth_info != NULL) {
|
|
Packit Service |
4684c1 |
_gnutls_free_auth_info(session);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(&sb, magic);
|
|
Packit Service |
4684c1 |
if (magic != PACKED_SESSION_MAGIC) {
|
|
Packit Service |
4684c1 |
ret = gnutls_assert_val(GNUTLS_E_DB_ERROR);
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(&sb,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
timestamp);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(&sb, expire_time);
|
|
Packit Service |
4684c1 |
(void) expire_time;
|
|
Packit Service |
4684c1 |
BUFFER_POP(&sb, &id, 1);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
switch (id) {
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_SRP
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_SRP:
|
|
Packit Service |
4684c1 |
ret = unpack_srp_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_PSK
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_PSK:
|
|
Packit Service |
4684c1 |
ret = unpack_psk_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_ANON
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_ANON:
|
|
Packit Service |
4684c1 |
ret = unpack_anon_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
case GNUTLS_CRD_CERTIFICATE:
|
|
Packit Service |
4684c1 |
ret = unpack_certificate_auth_info(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
break;
|
|
Packit Service |
4684c1 |
default:
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Auth_info structures copied. Now copy security_parameters_st.
|
|
Packit Service |
4684c1 |
* packed_session must have allocated space for the security parameters.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
ret = unpack_security_parameters(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
/* 'prf' will not be NULL at this point, else unpack_security_parameters() would have failed */
|
|
Packit Service |
4684c1 |
ret = tls13_unpack_security_parameters(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (!session->internals.resumed_security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
ret = _gnutls_hello_ext_unpack(session, &sb);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
_gnutls_buffer_clear(&sb);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/*
|
|
Packit Service |
4684c1 |
* If we're using TLS 1.3 semantics, we might have TLS 1.3-specific data.
|
|
Packit Service |
4684c1 |
* Format:
|
|
Packit Service |
4684c1 |
* 4 bytes the total length
|
|
Packit Service |
4684c1 |
* 4 bytes the ticket lifetime
|
|
Packit Service |
4684c1 |
* 4 bytes the ticket age add value
|
|
Packit Service |
4684c1 |
* 1 byte the ticket nonce length
|
|
Packit Service |
4684c1 |
* x bytes the ticket nonce
|
|
Packit Service |
4684c1 |
* 4 bytes the ticket length
|
|
Packit Service |
4684c1 |
* x bytes the ticket
|
|
Packit Service |
4684c1 |
* 1 bytes the resumption master secret length
|
|
Packit Service |
4684c1 |
* x bytes the resumption master secret
|
|
Packit Service |
4684c1 |
* 12 bytes the ticket arrival time
|
|
Packit Service |
4684c1 |
* 4 bytes the max early data size
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* We only store that info if we received a TLS 1.3 NewSessionTicket at some point.
|
|
Packit Service |
4684c1 |
* If we didn't receive any NST then we cannot resume a TLS 1.3 session and hence
|
|
Packit Service |
4684c1 |
* its nonsense to store all that info.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
tls13_pack_security_parameters(gnutls_session_t session, gnutls_buffer_st *ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret = 0;
|
|
Packit Service |
4684c1 |
uint32_t length = 0;
|
|
Packit Service |
4684c1 |
size_t length_pos;
|
|
Packit Service |
4684c1 |
tls13_ticket_st *ticket = &session->internals.tls13_ticket;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
length_pos = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (ticket->ticket.data != NULL) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, ticket->lifetime);
|
|
Packit Service |
4684c1 |
length += 4;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, ticket->age_add);
|
|
Packit Service |
4684c1 |
length += 4;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX1(ps,
|
|
Packit Service |
4684c1 |
ticket->nonce,
|
|
Packit Service |
4684c1 |
ticket->nonce_size);
|
|
Packit Service |
4684c1 |
length += (1 + ticket->nonce_size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps,
|
|
Packit Service |
4684c1 |
ticket->ticket.data,
|
|
Packit Service |
4684c1 |
ticket->ticket.size);
|
|
Packit Service |
4684c1 |
length += (4 + ticket->ticket.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX1(ps,
|
|
Packit Service |
4684c1 |
ticket->resumption_master_secret,
|
|
Packit Service |
4684c1 |
ticket->prf->output_size);
|
|
Packit Service |
4684c1 |
length += (1 + ticket->prf->output_size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_TS(ps, ticket->arrival_time);
|
|
Packit Service |
4684c1 |
length += 12;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_early_data_size);
|
|
Packit Service |
4684c1 |
length += 4;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Overwrite the length field */
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(length, ps->data + length_pos);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
tls13_unpack_security_parameters(gnutls_session_t session, gnutls_buffer_st *ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
uint32_t ttl_len;
|
|
Packit Service |
4684c1 |
tls13_ticket_st *ticket = &session->internals.tls13_ticket;
|
|
Packit Service |
4684c1 |
gnutls_datum_t t;
|
|
Packit Service |
4684c1 |
int ret = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, ttl_len);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (ttl_len > 0) {
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, ticket->lifetime);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, ticket->age_add);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = _gnutls_buffer_pop_datum_prefix8(ps, &t);
|
|
Packit Service |
4684c1 |
if (ret < 0 || t.size > sizeof(ticket->nonce)) {
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_PARSING_ERROR;
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
ticket->nonce_size = t.size;
|
|
Packit Service |
4684c1 |
memcpy(ticket->nonce, t.data, t.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &ticket->ticket);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = _gnutls_buffer_pop_datum_prefix8(ps, &t);
|
|
Packit Service |
4684c1 |
if (ret < 0 || t.size > sizeof(ticket->resumption_master_secret)) {
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_PARSING_ERROR;
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
memcpy(ticket->resumption_master_secret, t.data, t.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (unlikely(session->internals.resumed_security_parameters.prf == NULL ||
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.prf->output_size != t.size))
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ticket->prf = session->internals.resumed_security_parameters.prf;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_TS(ps, ticket->arrival_time);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_early_data_size);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Format:
|
|
Packit Service |
4684c1 |
* 1 byte the credentials type
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the whole structure
|
|
Packit Service |
4684c1 |
* DH stuff
|
|
Packit Service |
4684c1 |
* 2 bytes the size of secret key in bits
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the prime
|
|
Packit Service |
4684c1 |
* x bytes the prime
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the generator
|
|
Packit Service |
4684c1 |
* x bytes the generator
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the public key
|
|
Packit Service |
4684c1 |
* x bytes the public key
|
|
Packit Service |
4684c1 |
* RSA stuff
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the modulus
|
|
Packit Service |
4684c1 |
* x bytes the modulus
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the exponent
|
|
Packit Service |
4684c1 |
* x bytes the exponent
|
|
Packit Service |
4684c1 |
* CERTIFICATES
|
|
Packit Service |
4684c1 |
* 4 bytes the length of the certificate list
|
|
Packit Service |
4684c1 |
* 4 bytes the size of first certificate
|
|
Packit Service |
4684c1 |
* x bytes the certificate
|
|
Packit Service |
4684c1 |
* and so on...
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
pack_certificate_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
unsigned int i;
|
|
Packit Service |
4684c1 |
int cur_size, ret;
|
|
Packit Service |
4684c1 |
cert_auth_info_t info = _gnutls_get_auth_info(session, GNUTLS_CRD_CERTIFICATE);
|
|
Packit Service |
4684c1 |
int size_offset;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
size_offset = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
cur_size = ps->length;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (info) {
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.prime.data,
|
|
Packit Service |
4684c1 |
info->dh.prime.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.generator.data,
|
|
Packit Service |
4684c1 |
info->dh.generator.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.public_key.data,
|
|
Packit Service |
4684c1 |
info->dh.public_key.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, info->ncerts);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (i = 0; i < info->ncerts; i++) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps,
|
|
Packit Service |
4684c1 |
info->raw_certificate_list[i].
|
|
Packit Service |
4684c1 |
data,
|
|
Packit Service |
4684c1 |
info->raw_certificate_list[i].
|
|
Packit Service |
4684c1 |
size);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, info->nocsp);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (i = 0; i < info->nocsp; i++) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps,
|
|
Packit Service |
4684c1 |
info->raw_ocsp_list[i].
|
|
Packit Service |
4684c1 |
data,
|
|
Packit Service |
4684c1 |
info->raw_ocsp_list[i].
|
|
Packit Service |
4684c1 |
size);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* write the real size */
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(ps->length - cur_size,
|
|
Packit Service |
4684c1 |
ps->data + size_offset);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Upack certificate info.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
unpack_certificate_auth_info(gnutls_session_t session,
|
|
Packit Service |
4684c1 |
gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
unsigned int i = 0, j = 0;
|
|
Packit Service |
4684c1 |
size_t pack_size;
|
|
Packit Service |
4684c1 |
cert_auth_info_t info = NULL;
|
|
Packit Service |
4684c1 |
unsigned cur_ncerts = 0;
|
|
Packit Service |
4684c1 |
unsigned cur_nocsp = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, pack_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (pack_size == 0)
|
|
Packit Service |
4684c1 |
return 0; /* nothing to be done */
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* client and server have the same auth_info here
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_auth_info_init(session, GNUTLS_CRD_CERTIFICATE,
|
|
Packit Service |
4684c1 |
sizeof(cert_auth_info_st), 1);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
info = _gnutls_get_auth_info(session, GNUTLS_CRD_CERTIFICATE);
|
|
Packit Service |
4684c1 |
if (info == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.prime);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.generator);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.public_key);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, info->ncerts);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (info->ncerts > 0) {
|
|
Packit Service |
4684c1 |
info->raw_certificate_list =
|
|
Packit Service |
4684c1 |
gnutls_calloc(info->ncerts, sizeof(gnutls_datum_t));
|
|
Packit Service |
4684c1 |
if (info->raw_certificate_list == NULL) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_MEMORY_ERROR;
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (i = 0; i < info->ncerts; i++) {
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->raw_certificate_list[i]);
|
|
Packit Service |
4684c1 |
cur_ncerts++;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* read OCSP responses */
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, info->nocsp);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (info->nocsp > 0) {
|
|
Packit Service |
4684c1 |
info->raw_ocsp_list =
|
|
Packit Service |
4684c1 |
gnutls_calloc(info->nocsp, sizeof(gnutls_datum_t));
|
|
Packit Service |
4684c1 |
if (info->raw_ocsp_list == NULL) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_MEMORY_ERROR;
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (i = 0; i < info->nocsp; i++) {
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->raw_ocsp_list[i]);
|
|
Packit Service |
4684c1 |
cur_nocsp++;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
if (info) {
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.prime);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.generator);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.public_key);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (j = 0; j < cur_ncerts; j++)
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->raw_certificate_list[j]);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
for (j = 0; j < cur_nocsp; j++)
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->raw_ocsp_list[j]);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
gnutls_free(info->raw_certificate_list);
|
|
Packit Service |
4684c1 |
gnutls_free(info->raw_ocsp_list);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_SRP
|
|
Packit Service |
4684c1 |
/* Packs the SRP session authentication data.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Format:
|
|
Packit Service |
4684c1 |
* 1 byte the credentials type
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the SRP username (x)
|
|
Packit Service |
4684c1 |
* x bytes the SRP username
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
pack_srp_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
srp_server_auth_info_t info = _gnutls_get_auth_info(session, GNUTLS_CRD_SRP);
|
|
Packit Service |
4684c1 |
int len, ret;
|
|
Packit Service |
4684c1 |
int size_offset;
|
|
Packit Service |
4684c1 |
size_t cur_size;
|
|
Packit Service |
4684c1 |
const char *username = NULL;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (info) {
|
|
Packit Service |
4684c1 |
username = info->username;
|
|
Packit Service |
4684c1 |
len = strlen(info->username) + 1; /* include the terminating null */
|
|
Packit Service |
4684c1 |
} else
|
|
Packit Service |
4684c1 |
len = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
size_offset = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
cur_size = ps->length;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, username, len);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* write the real size */
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(ps->length - cur_size,
|
|
Packit Service |
4684c1 |
ps->data + size_offset);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
unpack_srp_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
size_t username_size;
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
srp_server_auth_info_t info;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, username_size);
|
|
Packit Service |
4684c1 |
if (username_size > sizeof(info->username)) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_auth_info_init(session, GNUTLS_CRD_SRP,
|
|
Packit Service |
4684c1 |
sizeof(srp_server_auth_info_st), 1);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
info = _gnutls_get_auth_info(session, GNUTLS_CRD_SRP);
|
|
Packit Service |
4684c1 |
if (info == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps, info->username, username_size);
|
|
Packit Service |
4684c1 |
if (username_size == 0)
|
|
Packit Service |
4684c1 |
info->username[0] = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_ANON
|
|
Packit Service |
4684c1 |
/* Packs the ANON session authentication data.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Format:
|
|
Packit Service |
4684c1 |
* 1 byte the credentials type
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the whole structure
|
|
Packit Service |
4684c1 |
* 2 bytes the size of secret key in bits
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the prime
|
|
Packit Service |
4684c1 |
* x bytes the prime
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the generator
|
|
Packit Service |
4684c1 |
* x bytes the generator
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the public key
|
|
Packit Service |
4684c1 |
* x bytes the public key
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
pack_anon_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int cur_size, ret;
|
|
Packit Service |
4684c1 |
anon_auth_info_t info = _gnutls_get_auth_info(session, GNUTLS_CRD_ANON);
|
|
Packit Service |
4684c1 |
int size_offset;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
size_offset = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
cur_size = ps->length;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (info) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.prime.data,
|
|
Packit Service |
4684c1 |
info->dh.prime.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.generator.data,
|
|
Packit Service |
4684c1 |
info->dh.generator.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.public_key.data,
|
|
Packit Service |
4684c1 |
info->dh.public_key.size);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* write the real size */
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(ps->length - cur_size,
|
|
Packit Service |
4684c1 |
ps->data + size_offset);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
unpack_anon_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
size_t pack_size;
|
|
Packit Service |
4684c1 |
anon_auth_info_t info = NULL;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, pack_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (pack_size == 0)
|
|
Packit Service |
4684c1 |
return 0; /* nothing to be done */
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* client and server have the same auth_info here
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_auth_info_init(session, GNUTLS_CRD_ANON,
|
|
Packit Service |
4684c1 |
sizeof(anon_auth_info_st), 1);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
info = _gnutls_get_auth_info(session, GNUTLS_CRD_ANON);
|
|
Packit Service |
4684c1 |
if (info == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.prime);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.generator);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.public_key);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
if (info) {
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.prime);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.generator);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.public_key);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
#endif /* ANON */
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
#ifdef ENABLE_PSK
|
|
Packit Service |
4684c1 |
/* Packs the PSK session authentication data.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Format:
|
|
Packit Service |
4684c1 |
* 1 byte the credentials type
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the whole structure
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the PSK username (x)
|
|
Packit Service |
4684c1 |
* x bytes the PSK username
|
|
Packit Service |
4684c1 |
* 2 bytes the size of secret key in bits
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the prime
|
|
Packit Service |
4684c1 |
* x bytes the prime
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the generator
|
|
Packit Service |
4684c1 |
* x bytes the generator
|
|
Packit Service |
4684c1 |
* 4 bytes the size of the public key
|
|
Packit Service |
4684c1 |
* x bytes the public key
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
pack_psk_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
psk_auth_info_t info;
|
|
Packit Service |
4684c1 |
int username_len;
|
|
Packit Service |
4684c1 |
int hint_len, ret;
|
|
Packit Service |
4684c1 |
int size_offset;
|
|
Packit Service |
4684c1 |
size_t cur_size;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
info = _gnutls_get_auth_info(session, GNUTLS_CRD_PSK);
|
|
Packit Service |
4684c1 |
if (info == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
username_len = info->username_len;
|
|
Packit Service |
4684c1 |
hint_len = strlen(info->hint) + 1; /* include the terminating null */
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
size_offset = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
cur_size = ps->length;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->username, username_len);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->hint, hint_len);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.prime.data, info->dh.prime.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.generator.data,
|
|
Packit Service |
4684c1 |
info->dh.generator.size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX4(ps, info->dh.public_key.data,
|
|
Packit Service |
4684c1 |
info->dh.public_key.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* write the real size */
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(ps->length - cur_size,
|
|
Packit Service |
4684c1 |
ps->data + size_offset);
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
unpack_psk_auth_info(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
size_t username_size, hint_size;
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
psk_auth_info_t info;
|
|
Packit Service |
4684c1 |
unsigned pack_size;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_auth_info_init(session, GNUTLS_CRD_PSK,
|
|
Packit Service |
4684c1 |
sizeof(psk_auth_info_st), 1);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
info = _gnutls_get_auth_info(session, GNUTLS_CRD_PSK);
|
|
Packit Service |
4684c1 |
if (info == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, pack_size);
|
|
Packit Service |
4684c1 |
if (pack_size == 0)
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INVALID_REQUEST;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, username_size);
|
|
Packit Service |
4684c1 |
if (username_size > (sizeof(info->username) - 1)) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps, info->username, username_size);
|
|
Packit Service |
4684c1 |
if (username_size == 0)
|
|
Packit Service |
4684c1 |
info->username[0] = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* append a null terminator and set length */
|
|
Packit Service |
4684c1 |
info->username[username_size] = 0;
|
|
Packit Service |
4684c1 |
info->username_len = username_size;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, hint_size);
|
|
Packit Service |
4684c1 |
if (hint_size > sizeof(info->hint)) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INTERNAL_ERROR;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps, info->hint, hint_size);
|
|
Packit Service |
4684c1 |
if (hint_size == 0)
|
|
Packit Service |
4684c1 |
info->hint[0] = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, info->dh.secret_bits);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.prime);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.generator);
|
|
Packit Service |
4684c1 |
BUFFER_POP_DATUM(ps, &info->dh.public_key);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.prime);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.generator);
|
|
Packit Service |
4684c1 |
_gnutls_free_datum(&info->dh.public_key);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
#endif
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* Packs the security parameters.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
pack_security_parameters(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
int size_offset;
|
|
Packit Service |
4684c1 |
size_t cur_size;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->security_parameters.epoch_read
|
|
Packit Service |
4684c1 |
!= session->security_parameters.epoch_write &&
|
|
Packit Service |
4684c1 |
!(session->internals.hsk_flags & HSK_EARLY_START_USED)) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return GNUTLS_E_UNAVAILABLE_DURING_HANDSHAKE;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = _gnutls_epoch_get(session, EPOCH_READ_CURRENT, NULL);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* move after the auth info stuff.
|
|
Packit Service |
4684c1 |
*/
|
|
Packit Service |
4684c1 |
size_offset = ps->length;
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
cur_size = ps->length;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.entity);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.prf->id);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.client_auth_type);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.server_auth_type);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND(ps, &session->security_parameters.session_id_size,
|
|
Packit Service |
4684c1 |
1);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND(ps, session->security_parameters.session_id,
|
|
Packit Service |
4684c1 |
session->security_parameters.session_id_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.pversion->id);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.client_ctype);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.server_ctype);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* if we are under TLS 1.3 do not pack keys or params negotiated using an extension
|
|
Packit Service |
4684c1 |
* they are not necessary */
|
|
Packit Service |
4684c1 |
if (!session->security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND(ps, session->security_parameters.cs->id, 2);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX1(ps, session->security_parameters.master_secret,
|
|
Packit Service |
4684c1 |
GNUTLS_MASTER_SIZE);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX1(ps, session->security_parameters.client_random,
|
|
Packit Service |
4684c1 |
GNUTLS_RANDOM_SIZE);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_PFX1(ps, session->security_parameters.server_random,
|
|
Packit Service |
4684c1 |
GNUTLS_RANDOM_SIZE);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* reset max_record_recv_size if it was negotiated
|
|
Packit Service |
4684c1 |
* using the record_size_limit extension */
|
|
Packit Service |
4684c1 |
if (session->internals.hsk_flags & HSK_RECORD_SIZE_LIMIT_NEGOTIATED) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_user_record_send_size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_user_record_recv_size);
|
|
Packit Service |
4684c1 |
} else {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_record_recv_size);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.
|
|
Packit Service |
4684c1 |
max_record_send_size);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->security_parameters.grp) {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, session->security_parameters.grp->id);
|
|
Packit Service |
4684c1 |
} else {
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps, 0);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.server_sign_algo);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.client_sign_algo);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.ext_master_secret);
|
|
Packit Service |
4684c1 |
BUFFER_APPEND_NUM(ps,
|
|
Packit Service |
4684c1 |
session->security_parameters.etm);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
_gnutls_write_uint32(ps->length - cur_size,
|
|
Packit Service |
4684c1 |
ps->data + size_offset);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
static int
|
|
Packit Service |
4684c1 |
unpack_security_parameters(gnutls_session_t session, gnutls_buffer_st * ps)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
size_t pack_size;
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
unsigned version;
|
|
Packit Service |
4684c1 |
gnutls_datum_t t;
|
|
Packit Service |
4684c1 |
time_t timestamp;
|
|
Packit Service |
4684c1 |
uint8_t cs[2];
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, pack_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (pack_size == 0)
|
|
Packit Service |
4684c1 |
return GNUTLS_E_INVALID_REQUEST;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
timestamp =
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.timestamp;
|
|
Packit Service |
4684c1 |
memset(&session->internals.resumed_security_parameters, 0,
|
|
Packit Service |
4684c1 |
sizeof(session->internals.resumed_security_parameters));
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.timestamp =
|
|
Packit Service |
4684c1 |
timestamp;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
entity);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, version);
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.prf = mac_to_entry(version);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.prf == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
client_auth_type);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
server_auth_type);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps,
|
|
Packit Service |
4684c1 |
&session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
session_id_size, 1);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
session_id,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
session_id_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, version);
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.pversion =
|
|
Packit Service |
4684c1 |
version_to_entry(version);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.pversion ==
|
|
Packit Service |
4684c1 |
NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
client_ctype);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
server_ctype);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (!session->internals.resumed_security_parameters.pversion->tls13_sem) {
|
|
Packit Service |
4684c1 |
BUFFER_POP(ps, cs, 2);
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.cs = ciphersuite_to_entry(cs);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.cs == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* master secret */
|
|
Packit Service |
4684c1 |
ret = _gnutls_buffer_pop_datum_prefix8(ps, &t);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_PARSING_ERROR;
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
if (t.size == GNUTLS_MASTER_SIZE)
|
|
Packit Service |
4684c1 |
memcpy(session->internals.resumed_security_parameters.master_secret, t.data, t.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* client random */
|
|
Packit Service |
4684c1 |
ret = _gnutls_buffer_pop_datum_prefix8(ps, &t);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_PARSING_ERROR;
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
if (t.size == GNUTLS_RANDOM_SIZE)
|
|
Packit Service |
4684c1 |
memcpy(session->internals.resumed_security_parameters.client_random, t.data, t.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/* server random */
|
|
Packit Service |
4684c1 |
ret = _gnutls_buffer_pop_datum_prefix8(ps, &t);
|
|
Packit Service |
4684c1 |
if (ret < 0) {
|
|
Packit Service |
4684c1 |
ret = GNUTLS_E_PARSING_ERROR;
|
|
Packit Service |
4684c1 |
gnutls_assert();
|
|
Packit Service |
4684c1 |
goto error;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
if (t.size == GNUTLS_RANDOM_SIZE)
|
|
Packit Service |
4684c1 |
memcpy(session->internals.resumed_security_parameters.server_random, t.data, t.size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_send_size);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_recv_size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps, ret);
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.grp = _gnutls_id_to_group(ret);
|
|
Packit Service |
4684c1 |
/* it can be null */
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
server_sign_algo);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
client_sign_algo);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
ext_master_secret);
|
|
Packit Service |
4684c1 |
BUFFER_POP_NUM(ps,
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
etm);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_recv_size == 0
|
|
Packit Service |
4684c1 |
|| session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_send_size == 0) {
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INTERNAL_ERROR);
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
error:
|
|
Packit Service |
4684c1 |
return ret;
|
|
Packit Service |
4684c1 |
}
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
/**
|
|
Packit Service |
4684c1 |
* gnutls_session_set_premaster:
|
|
Packit Service |
4684c1 |
* @session: is a #gnutls_session_t type.
|
|
Packit Service |
4684c1 |
* @entity: GNUTLS_SERVER or GNUTLS_CLIENT
|
|
Packit Service |
4684c1 |
* @version: the TLS protocol version
|
|
Packit Service |
4684c1 |
* @kx: the key exchange method
|
|
Packit Service |
4684c1 |
* @cipher: the cipher
|
|
Packit Service |
4684c1 |
* @mac: the MAC algorithm
|
|
Packit Service |
4684c1 |
* @comp: the compression method (ignored)
|
|
Packit Service |
4684c1 |
* @master: the master key to use
|
|
Packit Service |
4684c1 |
* @session_id: the session identifier
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* This function sets the premaster secret in a session. This is
|
|
Packit Service |
4684c1 |
* a function intended for exceptional uses. Do not use this
|
|
Packit Service |
4684c1 |
* function unless you are implementing a legacy protocol.
|
|
Packit Service |
4684c1 |
* Use gnutls_session_set_data() instead.
|
|
Packit Service |
4684c1 |
*
|
|
Packit Service |
4684c1 |
* Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise
|
|
Packit Service |
4684c1 |
* an error code is returned.
|
|
Packit Service |
4684c1 |
**/
|
|
Packit Service |
4684c1 |
int
|
|
Packit Service |
4684c1 |
gnutls_session_set_premaster(gnutls_session_t session, unsigned int entity,
|
|
Packit Service |
4684c1 |
gnutls_protocol_t version,
|
|
Packit Service |
4684c1 |
gnutls_kx_algorithm_t kx,
|
|
Packit Service |
4684c1 |
gnutls_cipher_algorithm_t cipher,
|
|
Packit Service |
4684c1 |
gnutls_mac_algorithm_t mac,
|
|
Packit Service |
4684c1 |
gnutls_compression_method_t comp,
|
|
Packit Service |
4684c1 |
const gnutls_datum_t * master,
|
|
Packit Service |
4684c1 |
const gnutls_datum_t * session_id)
|
|
Packit Service |
4684c1 |
{
|
|
Packit Service |
4684c1 |
int ret;
|
|
Packit Service |
4684c1 |
uint8_t cs[2];
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
memset(&session->internals.resumed_security_parameters, 0,
|
|
Packit Service |
4684c1 |
sizeof(session->internals.resumed_security_parameters));
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.entity = entity;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
ret =
|
|
Packit Service |
4684c1 |
_gnutls_cipher_suite_get_id(kx, cipher, mac, cs);
|
|
Packit Service |
4684c1 |
if (ret < 0)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(ret);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.cs = ciphersuite_to_entry(cs);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.cs == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.client_ctype =
|
|
Packit Service |
4684c1 |
DEFAULT_CERT_TYPE;
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.server_ctype =
|
|
Packit Service |
4684c1 |
DEFAULT_CERT_TYPE;
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.pversion =
|
|
Packit Service |
4684c1 |
version_to_entry(version);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.pversion ==
|
|
Packit Service |
4684c1 |
NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.pversion->selectable_prf)
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.prf = mac_to_entry(session->internals.resumed_security_parameters.cs->prf);
|
|
Packit Service |
4684c1 |
else
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.prf = mac_to_entry(GNUTLS_MAC_MD5_SHA1);
|
|
Packit Service |
4684c1 |
if (session->internals.resumed_security_parameters.prf == NULL)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (master->size != GNUTLS_MASTER_SIZE)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
memcpy(session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
master_secret, master->data, master->size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
if (session_id->size > GNUTLS_MAX_SESSION_ID)
|
|
Packit Service |
4684c1 |
return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.session_id_size =
|
|
Packit Service |
4684c1 |
session_id->size;
|
|
Packit Service |
4684c1 |
memcpy(session->internals.resumed_security_parameters.session_id,
|
|
Packit Service |
4684c1 |
session_id->data, session_id->size);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_send_size =
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.
|
|
Packit Service |
4684c1 |
max_record_recv_size = DEFAULT_MAX_RECORD_SIZE;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.timestamp =
|
|
Packit Service |
4684c1 |
gnutls_time(0);
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.grp = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.resumed_security_parameters.post_handshake_auth = 0;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
session->internals.premaster_set = 1;
|
|
Packit Service |
4684c1 |
|
|
Packit Service |
4684c1 |
return 0;
|
|
Packit Service |
4684c1 |
}
|