Skip to content
This repository has been archived by the owner on Jan 8, 2025. It is now read-only.

Commit

Permalink
Updated hybrid key format. (#291)
Browse files Browse the repository at this point in the history
  • Loading branch information
xvzcf authored Mar 11, 2021
1 parent 656edc5 commit f593774
Show file tree
Hide file tree
Showing 3 changed files with 65 additions and 39 deletions.
90 changes: 53 additions & 37 deletions ssl/statem/ext_oqs_extra.h
Original file line number Diff line number Diff line change
@@ -1,62 +1,78 @@
/* Extras for OQS extension */

#define ENCODE_UINT16(pbuf, i) (pbuf)[index] = (unsigned char)((i>>8) & 0xff); \
(pbuf)[index+1] = (unsigned char)((i ) & 0xff)
#define DECODE_UINT16(i, pbuf) i = ((uint16_t) (pbuf)[index]) << 8; \
i |= ((uint16_t) (pbuf)[index+1])

/* Encodes two messages (classical and PQC) into one hybrid message:
msg1_len || msg1 || msg2_len || msg2
classical_msg || pq_msg
hybrid_msg is allocated in this function.
Follows format specified in https://tools.ietf.org/html/draft-stebila-tls-hybrid-design-03
Follows format specified in https://tools.ietf.org/html/draft-ietf-tls-hybrid-design-01#section-3.2
*/
static int OQS_encode_hybrid_message(const unsigned char* msg1, uint16_t msg1_len,
const unsigned char* msg2, uint16_t msg2_len,
unsigned char** hybrid_msg, uint16_t* hybrid_msg_len) {
int index = 0;
*hybrid_msg_len = msg1_len + msg2_len + (2 * sizeof(uint16_t));
static int OQS_encode_hybrid_message(const unsigned char* classical_msg,
const uint16_t classical_msg_len,
const unsigned char* pq_msg,
const uint16_t pq_msg_len,
unsigned char** hybrid_msg,
uint16_t* hybrid_msg_len) {
*hybrid_msg_len = classical_msg_len + pq_msg_len;
*hybrid_msg = OPENSSL_malloc(*hybrid_msg_len);
if (*hybrid_msg == NULL) {
return 0;
}

ENCODE_UINT16(*hybrid_msg, msg1_len);
index += sizeof(uint16_t);
memcpy(*hybrid_msg + index, msg1, msg1_len);
index += msg1_len;
memcpy(*hybrid_msg, classical_msg, classical_msg_len);
memcpy(*hybrid_msg + classical_msg_len, pq_msg, pq_msg_len);

ENCODE_UINT16(*hybrid_msg, msg2_len);
index += sizeof(uint16_t);
memcpy(*hybrid_msg + index, msg2, msg2_len);

return 1;
}

/* Decodes hybrid message returning the classical and PQC messages:
msg1_len || msg1 || msg2_len || msg2
msg1 and msg2 are allocated in this function.
Follows format specified in https://tools.ietf.org/html/draft-stebila-tls-hybrid-design-03
classical_msg || pq_msg
classical_msg and pq_msg are allocated in this function.
Follows format specified in https://tools.ietf.org/html/draft-ietf-tls-hybrid-design-01#section-3.2
*/
static int OQS_decode_hybrid_message(const unsigned char* hybrid_msg,
unsigned char** msg1, uint16_t* msg1_len,
unsigned char** msg2, uint16_t* msg2_len) {
int index = 0;
DECODE_UINT16(*msg1_len, hybrid_msg);
index += sizeof(uint16_t);
*msg1 = OPENSSL_malloc(*msg1_len);
if (*msg1 == NULL) {
const unsigned int group_id,
const int is_server,
unsigned char** classical_msg,
uint16_t* classical_msg_len,
unsigned char** pq_msg,
uint16_t* pq_msg_len) {

int ec_curve_id = OQS_KEM_CLASSICAL_CURVEID(group_id);
unsigned int pq_kem_id = OQS_KEM_NID(group_id);

switch (ec_curve_id) {
case 23: /* P-256 */
*classical_msg_len = 65;
break;
case 24: /* P-384 */
*classical_msg_len = 97;
break;
case 25: /* P-521 */
*classical_msg_len = 133;
break;
default:
return 0;
}
*classical_msg = OPENSSL_malloc(*classical_msg_len);
if (*classical_msg == NULL) {
return 0;
}
memcpy(*msg1, hybrid_msg + index, *msg1_len);
index += *msg1_len;
memcpy(*classical_msg, hybrid_msg, *classical_msg_len);

OQS_KEM* oqs_kem = OQS_KEM_new(OQS_ALG_NAME(pq_kem_id));
if (oqs_kem == NULL) {
return 0;
}
if (is_server) {
*pq_msg_len = oqs_kem->length_public_key;
} else {
*pq_msg_len = oqs_kem->length_ciphertext;
}

DECODE_UINT16(*msg2_len, hybrid_msg);
index += sizeof(uint16_t);
*msg2 = OPENSSL_malloc(*msg2_len);
if (*msg2 == NULL) {
*pq_msg = OPENSSL_malloc(*pq_msg_len);
if (*pq_msg == NULL) {
return 0;
}
memcpy(*msg2, hybrid_msg + index, *msg2_len);
memcpy(*pq_msg, hybrid_msg + *classical_msg_len, *pq_msg_len);

return 1;
}
6 changes: 5 additions & 1 deletion ssl/statem/extensions_clnt.c
Original file line number Diff line number Diff line change
Expand Up @@ -1935,7 +1935,11 @@ int tls_parse_stoc_key_share(SSL *s, PACKET *pkt, unsigned int context, X509 *x,

/* parse the encoded_pt, which is either a classical, PQC, or hybrid (both) message. */
if (do_hybrid) {
if (!OQS_decode_hybrid_message(PACKET_data(&encoded_pt), &classical_encoded_pt, &classical_encodedlen, &oqs_encoded_pt, &oqs_encodedlen)) {
if (!OQS_decode_hybrid_message(PACKET_data(&encoded_pt), group_id, false,
&classical_encoded_pt,
&classical_encodedlen,
&oqs_encoded_pt,
&oqs_encodedlen)) {
has_error = 1;
goto oqs_cleanup;
}
Expand Down
8 changes: 7 additions & 1 deletion ssl/statem/extensions_srvr.c
Original file line number Diff line number Diff line change
Expand Up @@ -725,7 +725,13 @@ int tls_parse_ctos_key_share(SSL *s, PACKET *pkt, unsigned int context, X509 *x,

/* parse the encoded_pt, which is either a classical, PQC, or hybrid (both) message. */
if (do_hybrid) {
if (!OQS_decode_hybrid_message(PACKET_data(&encoded_pt), &classical_encoded_pt, &classical_encodedlen, &oqs_encoded_pt, &oqs_encodedlen)) {
if (!OQS_decode_hybrid_message(PACKET_data(&encoded_pt),
group_id,
true,
&classical_encoded_pt,
&classical_encodedlen,
&oqs_encoded_pt,
&oqs_encodedlen)) {
has_error = 1;
goto oqs_cleanup;
}
Expand Down

0 comments on commit f593774

Please sign in to comment.