mirror of
https://github.com/wolfSSL/wolfssl.git
synced 2025-07-31 19:24:42 +02:00
TLS 1.3 PSK: use the hash algorithm to choose cipher suite
See RFC 8446: 4.2.11 With TLS 1.3 PSK callback, If the returned cipher suite isn't available, use the hash from the cipher suite and choose from available list. Require exact match when: WOLFSSL_TLS13_PSK_NO_MATCH_HASH Alternative callback for client added that is passed a cipher suite string. Called for each cipher suite that is to be negotiated. If cipher suite to be used with PSK then return client identity. Returning an identity based on cipher suite hash will result in only one PSK extension being added per hash.
This commit is contained in:
@@ -2530,9 +2530,13 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args)
|
||||
const char *defaultCipherList = cipherList;
|
||||
|
||||
wolfSSL_CTX_set_psk_client_callback(ctx, my_psk_client_cb);
|
||||
#ifdef WOLFSSL_TLS13
|
||||
#ifdef WOLFSSL_TLS13
|
||||
#if !defined(WOLFSSL_PSK_TLS13_CB) && !defined(WOLFSSL_PSK_ONE_ID)
|
||||
wolfSSL_CTX_set_psk_client_cs_callback(ctx, my_psk_client_cs_cb);
|
||||
#else
|
||||
wolfSSL_CTX_set_psk_client_tls13_callback(ctx, my_psk_client_tls13_cb);
|
||||
#endif
|
||||
#endif
|
||||
if (defaultCipherList == NULL) {
|
||||
#if defined(HAVE_AESGCM) && !defined(NO_DH)
|
||||
#ifdef WOLFSSL_TLS13
|
||||
@@ -3268,7 +3272,7 @@ THREAD_RETURN WOLFSSL_THREAD client_test(void* args)
|
||||
* cipher name, or the requested cipher name is marked as an alias
|
||||
* that matches the established cipher.
|
||||
*/
|
||||
if (cipherList && (! XSTRSTR(cipherList, ":"))) {
|
||||
if (cipherList && !useDefCipherList && (! XSTRSTR(cipherList, ":"))) {
|
||||
WOLFSSL_CIPHER* established_cipher = wolfSSL_get_current_cipher(ssl);
|
||||
byte requested_cipherSuite0, requested_cipherSuite;
|
||||
int requested_cipherFlags;
|
||||
|
@@ -2879,7 +2879,7 @@ THREAD_RETURN WOLFSSL_THREAD server_test(void* args)
|
||||
* cipher name, or the requested cipher name is marked as an alias
|
||||
* that matches the established cipher.
|
||||
*/
|
||||
if (cipherList && (! XSTRSTR(cipherList, ":"))) {
|
||||
if (cipherList && !useDefCipherList && (! XSTRSTR(cipherList, ":"))) {
|
||||
WOLFSSL_CIPHER* established_cipher = wolfSSL_get_current_cipher(ssl);
|
||||
byte requested_cipherSuite0, requested_cipherSuite;
|
||||
int requested_cipherFlags;
|
||||
|
@@ -5479,6 +5479,7 @@ int SetSSL_CTX(WOLFSSL* ssl, WOLFSSL_CTX* ctx, int writeDup)
|
||||
ssl->options.server_psk_cb = ctx->server_psk_cb;
|
||||
ssl->options.psk_ctx = ctx->psk_ctx;
|
||||
#ifdef WOLFSSL_TLS13
|
||||
ssl->options.client_psk_cs_cb = ctx->client_psk_cs_cb;
|
||||
ssl->options.client_psk_tls13_cb = ctx->client_psk_tls13_cb;
|
||||
ssl->options.server_psk_tls13_cb = ctx->server_psk_tls13_cb;
|
||||
#endif
|
||||
@@ -27625,10 +27626,7 @@ static int DoSessionTicket(WOLFSSL* ssl, const byte* input, word32* inOutIdx,
|
||||
defined(OPENSSL_ALL)
|
||||
|
||||
/* search suites for specific one, idx on success, negative on error */
|
||||
#ifndef WOLFSSL_TLS13
|
||||
static
|
||||
#endif
|
||||
int FindSuite(Suites* suites, byte first, byte second)
|
||||
static int FindSuite(Suites* suites, byte first, byte second)
|
||||
{
|
||||
int i;
|
||||
|
||||
|
49
src/tls.c
49
src/tls.c
@@ -10397,7 +10397,49 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer)
|
||||
usingPSK = 1;
|
||||
}
|
||||
#endif
|
||||
#ifndef NO_PSK
|
||||
#ifndef NO_PSK
|
||||
#ifndef WOLFSSL_PSK_ONE_ID
|
||||
if (ssl->options.client_psk_cs_cb != NULL) {
|
||||
int i;
|
||||
ssl->arrays->client_identity[MAX_PSK_ID_LEN] = '\0';
|
||||
for (i = 0; i < ssl->suites->suiteSz; i += 2) {
|
||||
byte cipherSuite0 = ssl->suites->suites[i + 0];
|
||||
byte cipherSuite = ssl->suites->suites[i + 1];
|
||||
unsigned int keySz;
|
||||
|
||||
#ifdef HAVE_NULL_CIPHER
|
||||
if (cipherSuite0 == ECC_BYTE) {
|
||||
if (cipherSuite != TLS_SHA256_SHA256 &&
|
||||
cipherSuite != TLS_SHA384_SHA384) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
if (cipherSuite0 != TLS13_BYTE)
|
||||
continue;
|
||||
|
||||
keySz = ssl->options.client_psk_cs_cb(
|
||||
ssl, ssl->arrays->server_hint,
|
||||
ssl->arrays->client_identity, MAX_PSK_ID_LEN,
|
||||
ssl->arrays->psk_key, MAX_PSK_KEY_LEN,
|
||||
GetCipherNameInternal(cipherSuite0, cipherSuite));
|
||||
if (keySz > 0) {
|
||||
ssl->arrays->psk_keySz = keySz;
|
||||
ret = TLSX_PreSharedKey_Use(ssl,
|
||||
(byte*)ssl->arrays->client_identity,
|
||||
(word16)XSTRLEN(ssl->arrays->client_identity), 0,
|
||||
SuiteMac(ssl->suites->suites + i),
|
||||
cipherSuite0, cipherSuite, 0, NULL);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
usingPSK = 1;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
if (ssl->options.client_psk_cb != NULL ||
|
||||
ssl->options.client_psk_tls13_cb != NULL) {
|
||||
/* Default ciphersuite. */
|
||||
@@ -10412,7 +10454,7 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer)
|
||||
ssl->arrays->client_identity, MAX_PSK_ID_LEN,
|
||||
ssl->arrays->psk_key, MAX_PSK_KEY_LEN, &cipherName);
|
||||
if (GetCipherSuiteFromName(cipherName, &cipherSuite0,
|
||||
&cipherSuite, &cipherSuiteFlags) != 0) {
|
||||
&cipherSuite, &cipherSuiteFlags) != 0) {
|
||||
return PSK_KEY_ERROR;
|
||||
}
|
||||
}
|
||||
@@ -10426,6 +10468,7 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer)
|
||||
return PSK_KEY_ERROR;
|
||||
}
|
||||
ssl->arrays->client_identity[MAX_PSK_ID_LEN] = '\0';
|
||||
|
||||
ssl->options.cipherSuite0 = cipherSuite0;
|
||||
ssl->options.cipherSuite = cipherSuite;
|
||||
(void)cipherSuiteFlags;
|
||||
@@ -10444,7 +10487,7 @@ int TLSX_PopulateExtensions(WOLFSSL* ssl, byte isServer)
|
||||
|
||||
usingPSK = 1;
|
||||
}
|
||||
#endif
|
||||
#endif /* !NO_PSK */
|
||||
#if defined(HAVE_SESSION_TICKET) || !defined(NO_PSK)
|
||||
if (usingPSK) {
|
||||
byte modes;
|
||||
|
843
src/tls13.c
843
src/tls13.c
File diff suppressed because it is too large
Load Diff
@@ -1,15 +1,17 @@
|
||||
# server TLSv1.3 PSK
|
||||
# Use AES128-GCM and SHA256
|
||||
-v 4
|
||||
-s
|
||||
-l TLS13-AES128-GCM-SHA256
|
||||
-d
|
||||
|
||||
# client TLSv1.3 PSK
|
||||
# Use AES128-GCM and SHA256
|
||||
-v 4
|
||||
-s
|
||||
-l TLS13-AES128-GCM-SHA256
|
||||
|
||||
# server TLSv1.3 PSK
|
||||
# server TLSv1.3 PSK plus
|
||||
-v 4
|
||||
-j
|
||||
-l TLS13-AES128-GCM-SHA256
|
||||
@@ -29,3 +31,53 @@
|
||||
# client TLSv1.3 not-PSK
|
||||
-v 4
|
||||
-l TLS13-AES128-GCM-SHA256
|
||||
|
||||
# server TLSv1.3 PSK
|
||||
# AES256-GCM and SHA384
|
||||
-v 4
|
||||
-s
|
||||
-l TLS13-AES256-GCM-SHA384
|
||||
-d
|
||||
|
||||
# client TLSv1.3 PSK
|
||||
# AES256-GCM and SHA384
|
||||
-v 4
|
||||
-s
|
||||
-l TLS13-AES256-GCM-SHA384
|
||||
|
||||
# Disabling ChaCha20 results in failures.
|
||||
# server TLSv1.3 PSK
|
||||
# CHACHA20 only supported
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-CHACHA20-POLY1305-SHA256
|
||||
|
||||
# client TLSv1.3 PSK
|
||||
# AESGCM-SHA256 is first but CHACHA20 is negotiated as it is also SHA-256
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-AES128-GCM-SHA256:TLS13-CHACHA20-POLY1305-SHA256
|
||||
|
||||
# server TLSv1.3 PSK
|
||||
# AESGCM-SHA256 is first but CHACHA20 is negotiated as it is also SHA-256
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-AES128-GCM-SHA256:TLS13-CHACHA20-POLY1305-SHA256
|
||||
|
||||
# client TLSv1.3 PSK
|
||||
# CHACHA20 only supported
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-CHACHA20-POLY1305-SHA256
|
||||
|
||||
# server TLSv1.3 PSK
|
||||
# AESGCM-SHA256 is first but CHACHA20 is negotiated as it is also SHA-256
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-AES128-GCM-SHA256:TLS13-CHACHA20-POLY1305-SHA256
|
||||
|
||||
# client TLSv1.3 PSK
|
||||
# CHACHA20 only supported
|
||||
#-v 4
|
||||
#-s
|
||||
#-l TLS13-CHACHA20-POLY1305-SHA256:TLS13-AES128-GCM-SHA256
|
||||
|
@@ -1732,7 +1732,7 @@ WOLFSSL_LOCAL int DoApplicationData(WOLFSSL* ssl, byte* input, word32* inOutIdx)
|
||||
WOLFSSL_LOCAL int HandleTlsResumption(WOLFSSL* ssl, int bogusID,
|
||||
Suites* clSuites);
|
||||
#ifdef WOLFSSL_TLS13
|
||||
WOLFSSL_LOCAL int FindSuite(Suites* suites, byte first, byte second);
|
||||
WOLFSSL_LOCAL byte SuiteMac(byte* suite);
|
||||
#endif
|
||||
WOLFSSL_LOCAL int DoClientHello(WOLFSSL* ssl, const byte* input, word32*,
|
||||
word32);
|
||||
@@ -1899,11 +1899,15 @@ WOLFSSL_LOCAL int SetCipherList(WOLFSSL_CTX*, Suites*, const char* list);
|
||||
typedef unsigned int (*wc_psk_server_callback)(WOLFSSL*, const char*,
|
||||
unsigned char*, unsigned int);
|
||||
#ifdef WOLFSSL_TLS13
|
||||
typedef unsigned int (*wc_psk_client_cs_callback)(WOLFSSL*, const char*,
|
||||
char*, unsigned int, unsigned char*, unsigned int,
|
||||
const char* cipherName);
|
||||
typedef unsigned int (*wc_psk_client_tls13_callback)(WOLFSSL*, const char*,
|
||||
char*, unsigned int, unsigned char*, unsigned int,
|
||||
const char**);
|
||||
const char** cipherName);
|
||||
typedef unsigned int (*wc_psk_server_tls13_callback)(WOLFSSL*, const char*,
|
||||
unsigned char*, unsigned int, const char**);
|
||||
unsigned char*, unsigned int,
|
||||
const char** cipherName);
|
||||
#endif
|
||||
#endif /* PSK_TYPES_DEFINED */
|
||||
#if defined(WOLFSSL_DTLS) && defined(WOLFSSL_SESSION_EXPORT) && \
|
||||
@@ -2894,6 +2898,7 @@ struct WOLFSSL_CTX {
|
||||
wc_psk_client_callback client_psk_cb; /* client callback */
|
||||
wc_psk_server_callback server_psk_cb; /* server callback */
|
||||
#ifdef WOLFSSL_TLS13
|
||||
wc_psk_client_cs_callback client_psk_cs_cb; /* client callback */
|
||||
wc_psk_client_tls13_callback client_psk_tls13_cb; /* client callback */
|
||||
wc_psk_server_tls13_callback server_psk_tls13_cb; /* server callback */
|
||||
#endif
|
||||
@@ -3510,6 +3515,7 @@ typedef struct Options {
|
||||
wc_psk_use_session_cb_func session_psk_cb;
|
||||
#endif
|
||||
#ifdef WOLFSSL_TLS13
|
||||
wc_psk_client_cs_callback client_psk_cs_cb; /* client callback */
|
||||
wc_psk_client_tls13_callback client_psk_tls13_cb; /* client callback */
|
||||
wc_psk_server_tls13_callback server_psk_tls13_cb; /* server callback */
|
||||
#endif
|
||||
@@ -4735,6 +4741,8 @@ WOLFSSL_LOCAL int GrowInputBuffer(WOLFSSL* ssl, int size, int usedLength);
|
||||
|
||||
#if defined(WOLFSSL_TLS13) && (defined(HAVE_SESSION_TICKET) || !defined(NO_PSK))
|
||||
WOLFSSL_LOCAL word32 TimeNowInMilliseconds(void);
|
||||
|
||||
WOLFSSL_LOCAL int FindSuiteMac(WOLFSSL* ssl, byte* suite);
|
||||
#endif
|
||||
WOLFSSL_LOCAL word32 LowResTimer(void);
|
||||
|
||||
|
@@ -2178,9 +2178,9 @@ enum { /* ssl Constants */
|
||||
typedef unsigned int (*wc_psk_client_callback)(WOLFSSL*, const char*, char*,
|
||||
unsigned int, unsigned char*, unsigned int);
|
||||
WOLFSSL_API void wolfSSL_CTX_set_psk_client_callback(WOLFSSL_CTX*,
|
||||
wc_psk_client_callback);
|
||||
wc_psk_client_callback);
|
||||
WOLFSSL_API void wolfSSL_set_psk_client_callback(WOLFSSL*,
|
||||
wc_psk_client_callback);
|
||||
wc_psk_client_callback);
|
||||
#ifdef OPENSSL_EXTRA
|
||||
typedef int (*wc_psk_use_session_cb_func)(WOLFSSL* ssl,
|
||||
const WOLFSSL_EVP_MD* md, const unsigned char **id,
|
||||
@@ -2189,12 +2189,19 @@ enum { /* ssl Constants */
|
||||
wc_psk_use_session_cb_func cb);
|
||||
#endif
|
||||
#ifdef WOLFSSL_TLS13
|
||||
typedef unsigned int (*wc_psk_client_cs_callback)(WOLFSSL*, const char*,
|
||||
char*, unsigned int, unsigned char*, unsigned int, const char*);
|
||||
WOLFSSL_API void wolfSSL_CTX_set_psk_client_cs_callback(WOLFSSL_CTX*,
|
||||
wc_psk_client_cs_callback);
|
||||
WOLFSSL_API void wolfSSL_set_psk_client_cs_callback(WOLFSSL*,
|
||||
wc_psk_client_cs_callback);
|
||||
|
||||
typedef unsigned int (*wc_psk_client_tls13_callback)(WOLFSSL*, const char*,
|
||||
char*, unsigned int, unsigned char*, unsigned int, const char**);
|
||||
char*, unsigned int, unsigned char*, unsigned int, const char**);
|
||||
WOLFSSL_API void wolfSSL_CTX_set_psk_client_tls13_callback(WOLFSSL_CTX*,
|
||||
wc_psk_client_tls13_callback);
|
||||
wc_psk_client_tls13_callback);
|
||||
WOLFSSL_API void wolfSSL_set_psk_client_tls13_callback(WOLFSSL*,
|
||||
wc_psk_client_tls13_callback);
|
||||
wc_psk_client_tls13_callback);
|
||||
#endif
|
||||
|
||||
WOLFSSL_API const char* wolfSSL_get_psk_identity_hint(const WOLFSSL*);
|
||||
@@ -2206,16 +2213,16 @@ enum { /* ssl Constants */
|
||||
typedef unsigned int (*wc_psk_server_callback)(WOLFSSL*, const char*,
|
||||
unsigned char*, unsigned int);
|
||||
WOLFSSL_API void wolfSSL_CTX_set_psk_server_callback(WOLFSSL_CTX*,
|
||||
wc_psk_server_callback);
|
||||
wc_psk_server_callback);
|
||||
WOLFSSL_API void wolfSSL_set_psk_server_callback(WOLFSSL*,
|
||||
wc_psk_server_callback);
|
||||
wc_psk_server_callback);
|
||||
#ifdef WOLFSSL_TLS13
|
||||
typedef unsigned int (*wc_psk_server_tls13_callback)(WOLFSSL*, const char*,
|
||||
unsigned char*, unsigned int, const char**);
|
||||
unsigned char*, unsigned int, const char**);
|
||||
WOLFSSL_API void wolfSSL_CTX_set_psk_server_tls13_callback(WOLFSSL_CTX*,
|
||||
wc_psk_server_tls13_callback);
|
||||
wc_psk_server_tls13_callback);
|
||||
WOLFSSL_API void wolfSSL_set_psk_server_tls13_callback(WOLFSSL*,
|
||||
wc_psk_server_tls13_callback);
|
||||
wc_psk_server_tls13_callback);
|
||||
#endif
|
||||
WOLFSSL_API void* wolfSSL_get_psk_callback_ctx(WOLFSSL*);
|
||||
WOLFSSL_API int wolfSSL_set_psk_callback_ctx(WOLFSSL*, void*);
|
||||
@@ -2224,6 +2231,11 @@ enum { /* ssl Constants */
|
||||
WOLFSSL_API int wolfSSL_CTX_set_psk_callback_ctx(WOLFSSL_CTX*, void*);
|
||||
|
||||
#define PSK_TYPES_DEFINED
|
||||
|
||||
#ifdef WOLFSSL_TLS13
|
||||
WOLFSSL_API const char* wolfSSL_get_cipher_name_by_hash(WOLFSSL* ssl,
|
||||
const char* hash);
|
||||
#endif
|
||||
#endif /* NO_PSK */
|
||||
|
||||
|
||||
|
@@ -1499,14 +1499,18 @@ static WC_INLINE unsigned int my_psk_server_tls13_cb(WOLFSSL* ssl,
|
||||
{
|
||||
int i;
|
||||
int b = 0x01;
|
||||
int kIdLen = (int)XSTRLEN(kIdentityStr);
|
||||
const char* userCipher = (const char*)wolfSSL_get_psk_callback_ctx(ssl);
|
||||
|
||||
(void)ssl;
|
||||
(void)key_max_len;
|
||||
|
||||
/* see internal.h MAX_PSK_ID_LEN for PSK identity limit */
|
||||
if (XSTRNCMP(identity, kIdentityStr, XSTRLEN(kIdentityStr)) != 0)
|
||||
if (XSTRNCMP(identity, kIdentityStr, kIdLen) != 0)
|
||||
return 0;
|
||||
if (identity[kIdLen] != '\0') {
|
||||
userCipher = wolfSSL_get_cipher_name_by_hash(ssl, identity + kIdLen);
|
||||
}
|
||||
|
||||
for (i = 0; i < 32; i++, b += 0x22) {
|
||||
if (b >= 0x100)
|
||||
@@ -1590,6 +1594,31 @@ static WC_INLINE int my_psk_use_session_cb(WOLFSSL* ssl,
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
static WC_INLINE unsigned int my_psk_client_cs_cb(WOLFSSL* ssl,
|
||||
const char* hint, char* identity, unsigned int id_max_len,
|
||||
unsigned char* key, unsigned int key_max_len, const char* ciphersuite)
|
||||
{
|
||||
int i;
|
||||
int b = 0x01;
|
||||
|
||||
(void)ssl;
|
||||
(void)hint;
|
||||
(void)key_max_len;
|
||||
|
||||
/* see internal.h MAX_PSK_ID_LEN for PSK identity limit */
|
||||
XSTRNCPY(identity, kIdentityStr, id_max_len);
|
||||
XSTRNCAT(identity, ciphersuite + XSTRLEN(ciphersuite) - 6, id_max_len);
|
||||
|
||||
for (i = 0; i < 32; i++, b += 0x22) {
|
||||
if (b >= 0x100)
|
||||
b = 0x01;
|
||||
key[i] = b;
|
||||
}
|
||||
|
||||
return 32; /* length of key in octets or 0 for error */
|
||||
}
|
||||
|
||||
#endif /* !NO_PSK */
|
||||
|
||||
|
||||
|
Reference in New Issue
Block a user