Commit b1b15770 authored by Martin Thomson's avatar Martin Thomson

Bug 1698419 - ECH -10 updates, r=bbeurdouche

The main changes here are:

* an update to HPKE -08
* a move to the single-byte configuration ID
* reordering of ECHConfig

The addition of the explicit configuration ID means that the API for
constructing ECHConfig(List) needs to change.  That means a name change,
unfortunately.  I took the opportunity to make further changes to the arguments.

Differential Revision: https://phabricator.services.mozilla.com/D108392

--HG--
extra : rebase_source : e66ae86be746afbadc6c444d0debcc5aaabd2eb5
parent a4413156
1 function with some indirect sub-type change:
[C]'function SECStatus SSL_HandshakeNegotiatedExtension(PRFileDesc*, SSLExtensionType, PRBool*)' at sslreveal.c:72:1 has some indirect sub-type changes:
parameter 2 of type 'typedef SSLExtensionType' has sub-type changes:
underlying type 'enum __anonymous_enum__' at sslt.h:519:1 changed:
type size hasn't changed
1 enumerator change:
'__anonymous_enum__::ssl_tls13_encrypted_client_hello_xtn' from value '65033' to '65034' at sslt.h:519:1
......@@ -1894,16 +1894,23 @@ configureEchWithPublicName(PRFileDesc *model_sock, const char *public_name)
SECKEYPrivateKey *privKey = NULL;
SECOidData *oidData;
char *echConfigBase64 = NULL;
PRUint8 configId = 0;
PRUint8 configBuf[1000];
unsigned int len = 0;
unsigned int echCipherSuite = ((unsigned int)HpkeKdfHkdfSha256 << 16) |
HpkeAeadChaCha20Poly1305;
HpkeSymmetricSuite echCipherSuite = { HpkeKdfHkdfSha256,
HpkeAeadChaCha20Poly1305 };
PK11SlotInfo *slot = PK11_GetInternalKeySlot();
if (!slot) {
errWarn("PK11_GetInternalKeySlot failed");
return SECFailure;
}
if (PK11_GenerateRandom(&configId, sizeof(configId)) != SECSuccess) {
errWarn("Failed to generate random configId");
goto loser;
}
oidData = SECOID_FindOIDByTag(SEC_OID_CURVE25519);
if (oidData && (2 + oidData->oid.len) < sizeof(paramBuf)) {
ecParams.data[0] = SEC_ASN1_OBJECT_ID;
......@@ -1916,16 +1923,17 @@ configureEchWithPublicName(PRFileDesc *model_sock, const char *public_name)
}
privKey = PK11_GenerateKeyPair(slot, CKM_EC_KEY_PAIR_GEN, &ecParams,
&pubKey, PR_FALSE, PR_FALSE, NULL);
if (!privKey || !pubKey) {
errWarn("Failed to generate ECH keypair");
goto loser;
}
rv = SSL_EncodeEchConfig(echParamsStr, &echCipherSuite, 1,
HpkeDhKemX25519Sha256, pubKey, 50,
configBuf, &len, sizeof(configBuf));
rv = SSL_EncodeEchConfigId(configId, echParamsStr, 100,
HpkeDhKemX25519Sha256, pubKey,
&echCipherSuite, 1,
configBuf, &len, sizeof(configBuf));
if (rv != SECSuccess) {
errWarn("SSL_EncodeEchConfig failed");
errWarn("SSL_EncodeEchConfigId failed");
goto loser;
}
......
......@@ -497,24 +497,3 @@ SECStatus SSLInt_SetRawEchConfigForRetry(PRFileDesc *fd, const uint8_t *buf,
PORT_Memcpy(cfg->raw.data, buf, len);
return SECSuccess;
}
// Zero the echConfig.config_id for all configured echConfigs.
// This mimics a collision on the 8B config ID so that we can
// test trial decryption.
SECStatus SSLInt_ZeroEchConfigIds(PRFileDesc *fd) {
if (!fd) {
return SECFailure;
}
sslSocket *ss = ssl_FindSocket(fd);
if (!ss) {
return SECFailure;
}
for (PRCList *cur_p = PR_LIST_HEAD(&ss->echConfigs); cur_p != &ss->echConfigs;
cur_p = PR_NEXT_LINK(cur_p)) {
PORT_Memset(((sslEchConfig *)cur_p)->configId, 0,
sizeof(((sslEchConfig *)cur_p)->configId));
}
return SECSuccess;
}
......@@ -51,5 +51,4 @@ SECStatus SSLInt_SetDCAdvertisedSigSchemes(PRFileDesc *fd,
SECStatus SSLInt_RemoveServerCertificates(PRFileDesc *fd);
SECStatus SSLInt_SetRawEchConfigForRetry(PRFileDesc *fd, const uint8_t *buf,
size_t len);
SECStatus SSLInt_ZeroEchConfigIds(PRFileDesc *fd);
#endif // ifndef libssl_internals_h_
......@@ -262,7 +262,7 @@ void TlsConnectTestBase::MakeEcKeyParams(SECItem* params, SSLNamedGroup group) {
}
void TlsConnectTestBase::GenerateEchConfig(
HpkeKemId kem_id, const std::vector<uint32_t>& cipher_suites,
HpkeKemId kem_id, const std::vector<HpkeSymmetricSuite>& cipher_suites,
const std::string& public_name, uint16_t max_name_len, DataBuffer& record,
ScopedSECKEYPublicKey& pubKey, ScopedSECKEYPrivateKey& privKey) {
bool gen_keys = !pubKey && !privKey;
......@@ -282,9 +282,9 @@ void TlsConnectTestBase::GenerateEchConfig(
SECITEM_FreeItem(&ecParams, PR_FALSE);
PRUint8 encoded[1024];
unsigned int encoded_len = 0;
SECStatus rv = SSL_EncodeEchConfig(
public_name.c_str(), cipher_suites.data(), cipher_suites.size(), kem_id,
pub, max_name_len, encoded, &encoded_len, sizeof(encoded));
SECStatus rv = SSL_EncodeEchConfigId(
77, public_name.c_str(), max_name_len, kem_id, pub, cipher_suites.data(),
cipher_suites.size(), encoded, &encoded_len, sizeof(encoded));
EXPECT_EQ(SECSuccess, rv);
EXPECT_GT(encoded_len, 0U);
......@@ -305,10 +305,9 @@ void TlsConnectTestBase::SetupEch(std::shared_ptr<TlsAgent>& client,
ScopedSECKEYPublicKey pub;
ScopedSECKEYPrivateKey priv;
DataBuffer record;
static const std::vector<uint32_t> kDefaultSuites = {
(static_cast<uint16_t>(HpkeKdfHkdfSha256) << 16) |
HpkeAeadChaCha20Poly1305,
(static_cast<uint16_t>(HpkeKdfHkdfSha256) << 16) | HpkeAeadAes128Gcm};
static const std::vector<HpkeSymmetricSuite> kDefaultSuites = {
{HpkeKdfHkdfSha256, HpkeAeadChaCha20Poly1305},
{HpkeKdfHkdfSha256, HpkeAeadAes128Gcm}};
GenerateEchConfig(kem_id, kDefaultSuites, "public.name", 100, record, pub,
priv);
......
......@@ -147,12 +147,10 @@ class TlsConnectTestBase : public ::testing::Test {
void RestoreAlgorithmPolicy();
static void MakeEcKeyParams(SECItem* params, SSLNamedGroup group);
static void GenerateEchConfig(HpkeKemId kem_id,
const std::vector<uint32_t>& cipher_suites,
const std::string& public_name,
uint16_t max_name_len, DataBuffer& record,
ScopedSECKEYPublicKey& pubKey,
ScopedSECKEYPrivateKey& privKey);
static void GenerateEchConfig(
HpkeKemId kem_id, const std::vector<HpkeSymmetricSuite>& cipher_suites,
const std::string& public_name, uint16_t max_name_len, DataBuffer& record,
ScopedSECKEYPublicKey& pubKey, ScopedSECKEYPrivateKey& privKey);
void SetupEch(std::shared_ptr<TlsAgent>& client,
std::shared_ptr<TlsAgent>& server,
HpkeKemId kem_id = HpkeDhKemX25519Sha256,
......
This diff is collapsed.
......@@ -10,6 +10,7 @@
#include "ssl.h"
#include "sslerr.h"
#include "pk11hpke.h"
SEC_BEGIN_PROTOS
......@@ -566,30 +567,33 @@ typedef SECStatus(PR_CALLBACK *SSLResumptionTokenCallback)(
/*
* Generate an encoded ECHConfig structure (presumably server side).
*
* configId -- an identifier for the configuration.
* publicName -- the public_name value to be placed in SNI.
* hpkeSuites -- the HPKE cipher suites that can be used
* hpkeSuitesCount -- the number of suites in hpkeSuites
* maxNameLen -- the maximum length of protected names
* kemId -- the HKPE KEM ID value
* group -- the named group this key corresponds to
* pubKey -- the public key for the key pair
* pad -- the maximum length to pad to
* hpkeSuites -- the HPKE cipher suites that can be used
* hpkeSuitesCount -- the number of suites in hpkeSuites
* out/outlen/maxlen -- where to output the data
*/
#define SSL_EncodeEchConfig(publicName, hpkeSuites, hpkeSuitesCount, \
kemId, pubKey, maxNameLen, out, outlen, \
maxlen) \
SSL_EXPERIMENTAL_API("SSL_EncodeEchConfig", \
(const char *_publicName, \
const PRUint32 *_hpkeSuites, \
unsigned int _hpkeSuitesCount, \
HpkeKemId _kemId, \
const SECKEYPublicKey *_pubKey, \
PRUint16 _maxNameLen, \
PRUint8 *_out, unsigned int *_outlen, \
unsigned int _maxlen), \
(publicName, hpkeSuites, hpkeSuitesCount, \
kemId, pubKey, maxNameLen, out, outlen, \
maxlen))
typedef struct HpkeSymmetricSuiteStr {
HpkeKdfId kdfId;
HpkeAeadId aeadId;
} HpkeSymmetricSuite;
#define SSL_EncodeEchConfigId(configId, publicName, maxNameLen, \
kemId, pubKey, hpkeSuites, hpkeSuiteCount, \
out, outlen, maxlen) \
SSL_EXPERIMENTAL_API("SSL_EncodeEchConfigId", \
(PRUint8 _configId, const char *_publicName, \
unsigned int _maxNameLen, HpkeKemId _kemId, \
const SECKEYPublicKey *_pubKey, \
const HpkeSymmetricSuite *_hpkeSuites, \
unsigned int _hpkeSuiteCount, \
PRUint8 *_out, unsigned int *_outlen, \
unsigned int _maxlen), \
(configId, publicName, maxNameLen, \
kemId, pubKey, hpkeSuites, hpkeSuiteCount, \
out, outlen, maxlen))
/* SSL_SetSecretCallback installs a callback that TLS calls when it installs new
* traffic secrets.
......@@ -1035,6 +1039,7 @@ typedef struct SSLMaskingContextStr {
#define SSL_EnableESNI(a, b, c, d) SSL_DEPRECATED_EXPERIMENTAL_API
#define SSL_EncodeESNIKeys(a, b, c, d, e, f, g, h, i, j) SSL_DEPRECATED_EXPERIMENTAL_API
#define SSL_SetESNIKeyPair(a, b, c, d) SSL_DEPRECATED_EXPERIMENTAL_API
#define SSL_EncodeEchConfig(a, b, c, d, e, f, g, h, i) SSL_DEPRECATED_EXPERIMENTAL_API
SEC_END_PROTOS
......
......@@ -4296,7 +4296,7 @@ struct {
EXP(DestroyResumptionTokenInfo),
EXP(EnableTls13BackendEch),
EXP(EnableTls13GreaseEch),
EXP(EncodeEchConfig),
EXP(EncodeEchConfigId),
EXP(GetCurrentEpoch),
EXP(GetEchRetryConfigs),
EXP(GetExtensionSupport),
......
......@@ -547,7 +547,7 @@ typedef enum {
ssl_tls13_short_header_xtn = 0xff03, /* Deprecated. */
ssl_tls13_ech_is_inner_xtn = 0xda09,
ssl_tls13_outer_extensions_xtn = 0xfd00,
ssl_tls13_encrypted_client_hello_xtn = 0xfe09,
ssl_tls13_encrypted_client_hello_xtn = 0xfe0a,
ssl_tls13_encrypted_sni_xtn = 0xffce, /* Deprecated. */
} SSLExtensionType;
......
This diff is collapsed.
......@@ -21,7 +21,7 @@
* - Some of the buffering (construction/compression/decompression) could likely
* be optimized, but the spec is still evolving so that work is deferred.
*/
#define TLS13_ECH_VERSION 0xfe09
#define TLS13_ECH_VERSION 0xfe0a
#define TLS13_ECH_SIGNAL_LEN 8
static const char kHpkeInfoEch[] = "tls ech";
......@@ -29,21 +29,21 @@ static const char hHkdfInfoEchConfigID[] = "tls ech config id";
static const char kHkdfInfoEchConfirm[] = "ech accept confirmation";
struct sslEchConfigContentsStr {
char *publicName;
SECItem publicKey; /* NULL on server. Use the keypair in sslEchConfig instead. */
PRUint8 configId;
HpkeKemId kemId;
SECItem publicKey; /* NULL on server. Use the keypair in sslEchConfig instead. */
HpkeKdfId kdfId;
HpkeAeadId aeadId;
SECItem suites; /* One or more HpkeCipherSuites. The selected s
* suite is placed in kdfId and aeadId. */
PRUint16 maxNameLen;
char *publicName;
/* No supported extensions. */
};
struct sslEchConfigStr {
PRCList link;
SECItem raw;
PRUint8 configId[8];
PRUint16 version;
sslEchConfigContents contents;
};
......@@ -51,7 +51,7 @@ struct sslEchConfigStr {
struct sslEchXtnStateStr {
SECItem innerCh; /* Server: ClientECH.payload */
SECItem senderPubKey; /* Server: ClientECH.enc */
SECItem configId; /* Server: ClientECH.config_id */
PRUint8 configId; /* Server: ClientECH.config_id */
HpkeKdfId kdfId; /* Server: ClientECH.cipher_suite.kdf */
HpkeAeadId aeadId; /* Server: ClientECH.cipher_suite.aead */
SECItem retryConfigs; /* Client: ServerECH.retry_configs*/
......@@ -60,10 +60,10 @@ struct sslEchXtnStateStr {
* verified to the ECHConfig public name). */
};
SECStatus SSLExp_EncodeEchConfig(const char *publicName, const PRUint32 *hpkeSuites,
unsigned int hpkeSuiteCount, HpkeKemId kemId,
const SECKEYPublicKey *pubKey, PRUint16 maxNameLen,
PRUint8 *out, unsigned int *outlen, unsigned int maxlen);
SECStatus SSLExp_EncodeEchConfigId(PRUint8 configId, const char *publicName, unsigned int maxNameLen,
HpkeKemId kemId, const SECKEYPublicKey *pubKey,
const HpkeSymmetricSuite *hpkeSuites, unsigned int hpkeSuiteCount,
PRUint8 *out, unsigned int *outlen, unsigned int maxlen);
SECStatus SSLExp_GetEchRetryConfigs(PRFileDesc *fd, SECItem *retryConfigs);
SECStatus SSLExp_SetClientEchConfigs(PRFileDesc *fd, const PRUint8 *echConfigs,
unsigned int echConfigsLen);
......
......@@ -1460,7 +1460,7 @@ tls13_ServerHandleEchXtn(const sslSocket *ss, TLSExtensionData *xtnData,
HpkeKdfId kdf;
HpkeAeadId aead;
PRUint32 tmp;
SECItem configId;
PRUint8 configId;
SECItem senderPubKey;
SECItem encryptedCh;
......@@ -1504,11 +1504,12 @@ tls13_ServerHandleEchXtn(const sslSocket *ss, TLSExtensionData *xtnData,
aead = (HpkeAeadId)tmp;
/* config_id */
rv = ssl3_ExtConsumeHandshakeVariable(ss, &configId, 1,
&data->data, &data->len);
rv = ssl3_ExtConsumeHandshakeNumber(ss, &tmp, 1,
&data->data, &data->len);
if (rv != SECSuccess) {
goto alert_loser;
}
configId = tmp;
/* enc */
rv = ssl3_ExtConsumeHandshakeVariable(ss, &senderPubKey, 2,
......@@ -1530,7 +1531,7 @@ tls13_ServerHandleEchXtn(const sslSocket *ss, TLSExtensionData *xtnData,
if (!ss->ssl3.hs.helloRetry) {
/* In the real ECH HRR case, config_id and enc should be empty. This
* is checked after acceptance, because it might be GREASE ECH. */
if (!configId.len || !senderPubKey.len) {
if (!senderPubKey.len) {
goto alert_loser;
}
......@@ -1538,17 +1539,13 @@ tls13_ServerHandleEchXtn(const sslSocket *ss, TLSExtensionData *xtnData,
if (rv == SECFailure) {
return SECFailure;
}
rv = SECITEM_CopyItem(NULL, &xtnData->ech->configId, &configId);
if (rv == SECFailure) {
return SECFailure;
}
}
rv = SECITEM_CopyItem(NULL, &xtnData->ech->innerCh, &encryptedCh);
if (rv == SECFailure) {
return SECFailure;
}
xtnData->ech->configId = configId;
xtnData->ech->kdfId = kdf;
xtnData->ech->aeadId = aead;
......
......@@ -24,9 +24,9 @@
* uint8 indicator = 0xff; // To disambiguate from tickets.
* uint16 cipherSuite; // Selected cipher suite.
* uint16 keyShare; // Requested key share group (0=none)
* PRUint8 echConfigId; // ECH config_id
* HpkeKdfId kdfId; // ECH KDF (uint16)
* HpkeAeadId aeadId; // ECH AEAD (uint16)
* opaque echConfigId<0..255>; // ECH config_id
* opaque echHpkeCtx<0..65535>; // ECH serialized HPKE context
* opaque applicationToken<0..65535>; // Application token
* opaque ch_hash[rest_of_buffer]; // H(ClientHello)
......@@ -63,20 +63,23 @@ tls13_MakeHrrCookie(sslSocket *ss, const sslNamedGroupDef *selectedGroup,
}
if (ss->xtnData.ech) {
rv = sslBuffer_AppendNumber(&cookieBuf, ss->xtnData.ech->kdfId, 2);
/* Record that we received ECH. */
rv = sslBuffer_AppendNumber(&cookieBuf, PR_TRUE, 1);
if (rv != SECSuccess) {
return SECFailure;
}
rv = sslBuffer_AppendNumber(&cookieBuf, ss->xtnData.ech->aeadId, 2);
rv = sslBuffer_AppendNumber(&cookieBuf, ss->xtnData.ech->configId,
1);
if (rv != SECSuccess) {
return SECFailure;
}
/* Received ECH config_id, regardless of acceptance or possession
* of a matching ECHConfig. */
PORT_Assert(ss->xtnData.ech->configId.len == 8);
rv = sslBuffer_AppendVariable(&cookieBuf, ss->xtnData.ech->configId.data,
ss->xtnData.ech->configId.len, 1);
rv = sslBuffer_AppendNumber(&cookieBuf, ss->xtnData.ech->kdfId, 2);
if (rv != SECSuccess) {
return SECFailure;
}
rv = sslBuffer_AppendNumber(&cookieBuf, ss->xtnData.ech->aeadId, 2);
if (rv != SECSuccess) {
return SECFailure;
}
......@@ -97,7 +100,7 @@ tls13_MakeHrrCookie(sslSocket *ss, const sslNamedGroupDef *selectedGroup,
return SECFailure;
}
} else {
rv = sslBuffer_AppendNumber(&cookieBuf, 0, 7);
rv = sslBuffer_AppendNumber(&cookieBuf, PR_FALSE, 1);
if (rv != SECSuccess) {
return SECFailure;
}
......@@ -132,7 +135,9 @@ tls13_MakeHrrCookie(sslSocket *ss, const sslNamedGroupDef *selectedGroup,
/* Given a cookie and cookieLen, decrypt and parse, returning
* any values that were requested via the "previous_" params. If
* recoverState is true, the transcript state and application
* token are restored. */
* token are restored. Note that previousEchKdfId, previousEchAeadId,
* previousEchConfigId, and previousEchHpkeCtx are not modified if ECH was not
* previously negotiated (i.e., previousEchOffered is PR_FALSE). */
SECStatus
tls13_HandleHrrCookie(sslSocket *ss,
unsigned char *cookie, unsigned int cookieLen,
......@@ -141,7 +146,7 @@ tls13_HandleHrrCookie(sslSocket *ss,
PRBool *previousEchOffered,
HpkeKdfId *previousEchKdfId,
HpkeAeadId *previousEchAeadId,
SECItem *previousEchConfigId,
PRUint8 *previousEchConfigId,
HpkeContext **previousEchHpkeCtx,
PRBool recoverState)
{
......@@ -150,12 +155,13 @@ tls13_HandleHrrCookie(sslSocket *ss,
unsigned int plaintextLen = 0;
sslBuffer messageBuf = SSL_BUFFER_EMPTY;
sslReadBuffer echHpkeBuf = { 0 };
sslReadBuffer echConfigIdBuf = { 0 };
PRBool receivedEch;
PRUint8 echConfigId = 0;
PRUint64 sentinel;
PRUint64 cipherSuite;
HpkeContext *hpkeContext = NULL;
HpkeKdfId echKdfId;
HpkeAeadId echAeadId;
HpkeKdfId echKdfId = 0;
HpkeAeadId echAeadId = 0;
PRUint64 group;
PRUint64 tmp64;
const sslNamedGroupDef *selectedGroup;
......@@ -190,31 +196,54 @@ tls13_HandleHrrCookie(sslSocket *ss,
}
selectedGroup = ssl_LookupNamedGroup(group);
/* ECH Ciphersuite */
rv = sslRead_ReadNumber(&reader, 2, &tmp64);
/* Was ECH received. */
rv = sslRead_ReadNumber(&reader, 1, &tmp64);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
echKdfId = (HpkeKdfId)tmp64;
receivedEch = tmp64 == PR_TRUE;
rv = sslRead_ReadNumber(&reader, 2, &tmp64);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
echAeadId = (HpkeAeadId)tmp64;
if (receivedEch) {
/* ECH config ID */
rv = sslRead_ReadNumber(&reader, 1, &tmp64);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
echConfigId = tmp64;
/* ECH Config ID and HPKE context may be empty. */
rv = sslRead_ReadVariable(&reader, 1, &echConfigIdBuf);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
rv = sslRead_ReadVariable(&reader, 2, &echHpkeBuf);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
/* ECH Ciphersuite */
rv = sslRead_ReadNumber(&reader, 2, &tmp64);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
echKdfId = (HpkeKdfId)tmp64;
rv = sslRead_ReadNumber(&reader, 2, &tmp64);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
echAeadId = (HpkeAeadId)tmp64;
/* ECH HPKE context may be empty. */
rv = sslRead_ReadVariable(&reader, 2, &echHpkeBuf);
if (rv != SECSuccess) {
FATAL_ERROR(ss, SSL_ERROR_RX_MALFORMED_CLIENT_HELLO, illegal_parameter);
return SECFailure;
}
if (previousEchHpkeCtx && echHpkeBuf.len) {
const SECItem hpkeItem = { siBuffer, CONST_CAST(unsigned char, echHpkeBuf.buf),
echHpkeBuf.len };
hpkeContext = PK11_HPKE_ImportContext(&hpkeItem, NULL);
if (!hpkeContext) {
FATAL_ERROR(ss, PORT_GetError(), illegal_parameter);
return SECFailure;
}
}
}
/* Application token. */
......@@ -276,36 +305,6 @@ tls13_HandleHrrCookie(sslSocket *ss,
}
}
if (previousEchHpkeCtx && echHpkeBuf.len) {
const SECItem hpkeItem = { siBuffer, CONST_CAST(unsigned char, echHpkeBuf.buf),
echHpkeBuf.len };
hpkeContext = PK11_HPKE_ImportContext(&hpkeItem, NULL);
if (!hpkeContext) {
FATAL_ERROR(ss, PORT_GetError(), illegal_parameter);
return SECFailure;
}
}
if (previousEchConfigId && echConfigIdBuf.len) {
SECItem tmp = { siBuffer, NULL, 0 };
rv = SECITEM_MakeItem(NULL, &tmp, echConfigIdBuf.buf, echConfigIdBuf.len);
if (rv != SECSuccess) {
PK11_HPKE_DestroyContext(hpkeContext, PR_TRUE);
FATAL_ERROR(ss, PORT_GetError(), internal_error);
return SECFailure;
}
*previousEchConfigId = tmp;
}
if (previousEchKdfId) {
*previousEchKdfId = echKdfId;
}
if (previousEchAeadId) {
*previousEchAeadId = echAeadId;
}
if (previousEchHpkeCtx) {
*previousEchHpkeCtx = hpkeContext;
}
if (previousCipherSuite) {
*previousCipherSuite = cipherSuite;
}
......@@ -313,7 +312,21 @@ tls13_HandleHrrCookie(sslSocket *ss,
*previousGroup = selectedGroup;
}
if (previousEchOffered) {
*previousEchOffered = echConfigIdBuf.len > 0;
*previousEchOffered = receivedEch;
}
if (receivedEch) {
if (previousEchConfigId) {
*previousEchConfigId = echConfigId;
}
if (previousEchKdfId) {
*previousEchKdfId = echKdfId;
}
if (previousEchAeadId) {
*previousEchAeadId = echAeadId;
}
if (previousEchHpkeCtx) {
*previousEchHpkeCtx = hpkeContext;
}
}
return SECSuccess;
}
......@@ -24,7 +24,7 @@ SECStatus tls13_HandleHrrCookie(sslSocket *ss,
PRBool *previousEchOffered,
HpkeKdfId *previousEchKdfId,
HpkeAeadId *previousEchAeadId,
SECItem *previousEchConfigId,
PRUint8 *previousEchConfigId,
HpkeContext **previousEchHpkeCtx,
PRBool recoverState);
#endif
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment