annotate src/event/quic/ngx_event_quic_protection.c @ 8734:c61fcdc1b8e3 quic

UDP: extended datagram context. Sometimes it is required to process datagram properties at higher level (i.e. QUIC is interested in source address which may change and IP options). The patch adds ngx_udp_dgram_t structure used to pass packet-related information in c->udp.
author Vladimir Homutov <vl@nginx.com>
date Fri, 02 Apr 2021 18:58:19 +0300
parents 0f8565e0fc76
children c0cd180308e4
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
2 /*
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
3 * Copyright (C) Nginx, Inc.
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
4 */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
5
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
6
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
7 #include <ngx_config.h>
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
8 #include <ngx_core.h>
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
9 #include <ngx_event.h>
8486
d0ac4449a07f QUIC: fixed bulding perl module by reducing header pollution.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8478
diff changeset
10 #include <ngx_event_quic_transport.h>
d0ac4449a07f QUIC: fixed bulding perl module by reducing header pollution.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8478
diff changeset
11 #include <ngx_event_quic_protection.h>
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
12
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
13
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
14 #define NGX_QUIC_IV_LEN 12
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
15
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
16 #define NGX_AES_128_GCM_SHA256 0x1301
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
17 #define NGX_AES_256_GCM_SHA384 0x1302
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
18 #define NGX_CHACHA20_POLY1305_SHA256 0x1303
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
19
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
20
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
21 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
22 #define ngx_quic_cipher_t EVP_AEAD
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
23 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
24 #define ngx_quic_cipher_t EVP_CIPHER
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
25 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
26
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
27
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
28 typedef struct {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
29 const ngx_quic_cipher_t *c;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
30 const EVP_CIPHER *hp;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
31 const EVP_MD *d;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
32 } ngx_quic_ciphers_t;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
33
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
34
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
35 typedef struct ngx_quic_secret_s {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
36 ngx_str_t secret;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
37 ngx_str_t key;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
38 ngx_str_t iv;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
39 ngx_str_t hp;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
40 } ngx_quic_secret_t;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
41
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
42
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
43 typedef struct {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
44 ngx_quic_secret_t client;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
45 ngx_quic_secret_t server;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
46 } ngx_quic_secrets_t;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
47
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
48
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
49 struct ngx_quic_keys_s {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
50 ngx_quic_secrets_t secrets[NGX_QUIC_ENCRYPTION_LAST];
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
51 ngx_quic_secrets_t next_key;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
52 ngx_uint_t cipher;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
53 };
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
54
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
55
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
56 static ngx_int_t ngx_hkdf_expand(u_char *out_key, size_t out_len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
57 const EVP_MD *digest, const u_char *prk, size_t prk_len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
58 const u_char *info, size_t info_len);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
59 static ngx_int_t ngx_hkdf_extract(u_char *out_key, size_t *out_len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
60 const EVP_MD *digest, const u_char *secret, size_t secret_len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
61 const u_char *salt, size_t salt_len);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
62
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
63 static uint64_t ngx_quic_parse_pn(u_char **pos, ngx_int_t len, u_char *mask,
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
64 uint64_t *largest_pn);
8310
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
65 static void ngx_quic_compute_nonce(u_char *nonce, size_t len, uint64_t pn);
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
66 static ngx_int_t ngx_quic_ciphers(ngx_uint_t id,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
67 ngx_quic_ciphers_t *ciphers, enum ssl_encryption_level_t level);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
68
8288
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
69 static ngx_int_t ngx_quic_tls_open(const ngx_quic_cipher_t *cipher,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
70 ngx_quic_secret_t *s, ngx_str_t *out, u_char *nonce, ngx_str_t *in,
8287
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
71 ngx_str_t *ad, ngx_log_t *log);
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
72 static ngx_int_t ngx_quic_tls_seal(const ngx_quic_cipher_t *cipher,
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
73 ngx_quic_secret_t *s, ngx_str_t *out, u_char *nonce, ngx_str_t *in,
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
74 ngx_str_t *ad, ngx_log_t *log);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
75 static ngx_int_t ngx_quic_tls_hp(ngx_log_t *log, const EVP_CIPHER *cipher,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
76 ngx_quic_secret_t *s, u_char *out, u_char *in);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
77 static ngx_int_t ngx_quic_hkdf_expand(ngx_pool_t *pool, const EVP_MD *digest,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
78 ngx_str_t *out, ngx_str_t *label, const uint8_t *prk, size_t prk_len);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
79
8644
e953bd2c5bb3 QUIC: merged create_long/short_packet() functions.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8643
diff changeset
80 static ngx_int_t ngx_quic_create_packet(ngx_quic_header_t *pkt,
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
81 ngx_str_t *res);
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
82 static ngx_int_t ngx_quic_create_retry_packet(ngx_quic_header_t *pkt,
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
83 ngx_str_t *res);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
84
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
85
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
86 static ngx_int_t
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
87 ngx_quic_ciphers(ngx_uint_t id, ngx_quic_ciphers_t *ciphers,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
88 enum ssl_encryption_level_t level)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
89 {
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
90 ngx_int_t len;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
91
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
92 if (level == ssl_encryption_initial) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
93 id = NGX_AES_128_GCM_SHA256;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
94 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
95
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
96 switch (id) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
97
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
98 case NGX_AES_128_GCM_SHA256:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
99 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
100 ciphers->c = EVP_aead_aes_128_gcm();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
101 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
102 ciphers->c = EVP_aes_128_gcm();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
103 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
104 ciphers->hp = EVP_aes_128_ctr();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
105 ciphers->d = EVP_sha256();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
106 len = 16;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
107 break;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
108
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
109 case NGX_AES_256_GCM_SHA384:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
110 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
111 ciphers->c = EVP_aead_aes_256_gcm();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
112 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
113 ciphers->c = EVP_aes_256_gcm();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
114 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
115 ciphers->hp = EVP_aes_256_ctr();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
116 ciphers->d = EVP_sha384();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
117 len = 32;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
118 break;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
119
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
120 case NGX_CHACHA20_POLY1305_SHA256:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
121 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
122 ciphers->c = EVP_aead_chacha20_poly1305();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
123 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
124 ciphers->c = EVP_chacha20_poly1305();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
125 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
126 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
127 ciphers->hp = (const EVP_CIPHER *) EVP_aead_chacha20_poly1305();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
128 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
129 ciphers->hp = EVP_chacha20();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
130 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
131 ciphers->d = EVP_sha256();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
132 len = 32;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
133 break;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
134
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
135 default:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
136 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
137 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
138
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
139 return len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
140 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
141
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
142
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
143 ngx_int_t
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
144 ngx_quic_keys_set_initial_secret(ngx_pool_t *pool, ngx_quic_keys_t *keys,
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
145 ngx_str_t *secret, uint32_t version)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
146 {
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
147 size_t is_len;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
148 uint8_t is[SHA256_DIGEST_LENGTH];
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
149 ngx_uint_t i;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
150 const EVP_MD *digest;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
151 const EVP_CIPHER *cipher;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
152 ngx_quic_secret_t *client, *server;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
153
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
154 static const uint8_t salt[20] =
8678
3443ee341cc1 QUIC: draft-33 salt and retry keys.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8673
diff changeset
155 "\x38\x76\x2c\xf7\xf5\x59\x34\xb3\x4d\x17"
3443ee341cc1 QUIC: draft-33 salt and retry keys.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8673
diff changeset
156 "\x9a\xe6\xa4\xc8\x0c\xad\xcc\xbb\x7f\x0a";
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
157 static const uint8_t salt29[20] =
8448
011668fc9efd Update Initial salt and Retry secret from quic-tls-29.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8446
diff changeset
158 "\xaf\xbf\xec\x28\x99\x93\xd2\x4c\x9e\x97"
011668fc9efd Update Initial salt and Retry secret from quic-tls-29.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8446
diff changeset
159 "\x86\xf1\x9c\x61\x11\xe0\x43\x90\xa8\x99";
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
160
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
161 client = &keys->secrets[ssl_encryption_initial].client;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
162 server = &keys->secrets[ssl_encryption_initial].server;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
163
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
164 /* AEAD_AES_128_GCM prior to handshake, quic-tls-23#section-5.3 */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
165
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
166 cipher = EVP_aes_128_gcm();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
167 digest = EVP_sha256();
8729
0f8565e0fc76 QUIC: HKDF API compatibility with OpenSSL master branch.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8716
diff changeset
168 is_len = SHA256_DIGEST_LENGTH;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
169
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
170 if (ngx_hkdf_extract(is, &is_len, digest, secret->data, secret->len,
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
171 (version & 0xff000000) ? salt29 : salt, sizeof(salt))
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
172 != NGX_OK)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
173 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
174 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
175 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
176
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
177 ngx_str_t iss = {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
178 .data = is,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
179 .len = is_len
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
180 };
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
181
8360
f175006124d0 Cleaned up hexdumps in debug output.
Vladimir Homutov <vl@nginx.com>
parents: 8359
diff changeset
182 ngx_log_debug0(NGX_LOG_DEBUG_EVENT, pool->log, 0,
8702
d4e02b3b734f QUIC: fixed indentation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8694
diff changeset
183 "quic ngx_quic_set_initial_secret");
8578
52ad697f9d1c QUIC: enabled more key-related debug by default.
Vladimir Homutov <vl@nginx.com>
parents: 8565
diff changeset
184 #ifdef NGX_QUIC_DEBUG_CRYPTO
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
185 ngx_log_debug3(NGX_LOG_DEBUG_EVENT, pool->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
186 "quic salt len:%uz %*xs", sizeof(salt), sizeof(salt), salt);
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
187 ngx_log_debug3(NGX_LOG_DEBUG_EVENT, pool->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
188 "quic initial secret len:%uz %*xs", is_len, is_len, is);
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
189 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
190
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
191 /* draft-ietf-quic-tls-23#section-5.2 */
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
192 client->secret.len = SHA256_DIGEST_LENGTH;
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
193 server->secret.len = SHA256_DIGEST_LENGTH;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
194
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
195 client->key.len = EVP_CIPHER_key_length(cipher);
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
196 server->key.len = EVP_CIPHER_key_length(cipher);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
197
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
198 client->hp.len = EVP_CIPHER_key_length(cipher);
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
199 server->hp.len = EVP_CIPHER_key_length(cipher);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
200
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
201 client->iv.len = EVP_CIPHER_iv_length(cipher);
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
202 server->iv.len = EVP_CIPHER_iv_length(cipher);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
203
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
204 struct {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
205 ngx_str_t label;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
206 ngx_str_t *key;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
207 ngx_str_t *prk;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
208 } seq[] = {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
209
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
210 /* draft-ietf-quic-tls-23#section-5.2 */
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
211 { ngx_string("tls13 client in"), &client->secret, &iss },
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
212 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
213 ngx_string("tls13 quic key"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
214 &client->key,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
215 &client->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
216 },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
217 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
218 ngx_string("tls13 quic iv"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
219 &client->iv,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
220 &client->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
221 },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
222 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
223 /* AEAD_AES_128_GCM prior to handshake, quic-tls-23#section-5.4.1 */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
224 ngx_string("tls13 quic hp"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
225 &client->hp,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
226 &client->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
227 },
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
228 { ngx_string("tls13 server in"), &server->secret, &iss },
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
229 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
230 /* AEAD_AES_128_GCM prior to handshake, quic-tls-23#section-5.3 */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
231 ngx_string("tls13 quic key"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
232 &server->key,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
233 &server->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
234 },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
235 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
236 ngx_string("tls13 quic iv"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
237 &server->iv,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
238 &server->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
239 },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
240 {
8702
d4e02b3b734f QUIC: fixed indentation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8694
diff changeset
241 /* AEAD_AES_128_GCM prior to handshake, quic-tls-23#section-5.4.1 */
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
242 ngx_string("tls13 quic hp"),
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
243 &server->hp,
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
244 &server->secret,
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
245 },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
246
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
247 };
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
248
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
249 for (i = 0; i < (sizeof(seq) / sizeof(seq[0])); i++) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
250
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
251 if (ngx_quic_hkdf_expand(pool, digest, seq[i].key, &seq[i].label,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
252 seq[i].prk->data, seq[i].prk->len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
253 != NGX_OK)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
254 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
255 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
256 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
257 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
258
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
259 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
260 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
261
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
262
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
263 static ngx_int_t
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
264 ngx_quic_hkdf_expand(ngx_pool_t *pool, const EVP_MD *digest, ngx_str_t *out,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
265 ngx_str_t *label, const uint8_t *prk, size_t prk_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
266 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
267 size_t info_len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
268 uint8_t *p;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
269 uint8_t info[20];
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
270
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
271 if (out->data == NULL) {
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
272 out->data = ngx_pnalloc(pool, out->len);
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
273 if (out->data == NULL) {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
274 return NGX_ERROR;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
275 }
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
276 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
277
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
278 info_len = 2 + 1 + label->len + 1;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
279
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
280 info[0] = 0;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
281 info[1] = out->len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
282 info[2] = label->len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
283 p = ngx_cpymem(&info[3], label->data, label->len);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
284 *p = '\0';
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
285
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
286 if (ngx_hkdf_expand(out->data, out->len, digest,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
287 prk, prk_len, info, info_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
288 != NGX_OK)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
289 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
290 ngx_ssl_error(NGX_LOG_INFO, pool->log, 0,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
291 "ngx_hkdf_expand(%V) failed", label);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
292 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
293 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
294
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
295 #ifdef NGX_QUIC_DEBUG_CRYPTO
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
296 ngx_log_debug3(NGX_LOG_DEBUG_EVENT, pool->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
297 "quic expand %V key len:%uz %xV", label, out->len, out);
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
298 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
299
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
300 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
301 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
302
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
303
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
304 static ngx_int_t
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
305 ngx_hkdf_expand(u_char *out_key, size_t out_len, const EVP_MD *digest,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
306 const uint8_t *prk, size_t prk_len, const u_char *info, size_t info_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
307 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
308 #ifdef OPENSSL_IS_BORINGSSL
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
309
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
310 if (HKDF_expand(out_key, out_len, digest, prk, prk_len, info, info_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
311 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
312 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
313 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
314 }
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
315
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
316 return NGX_OK;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
317
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
318 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
319
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
320 EVP_PKEY_CTX *pctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
321
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
322 pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_HKDF, NULL);
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
323 if (pctx == NULL) {
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
324 return NGX_ERROR;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
325 }
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
326
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
327 if (EVP_PKEY_derive_init(pctx) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
328 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
329 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
330
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
331 if (EVP_PKEY_CTX_hkdf_mode(pctx, EVP_PKEY_HKDEF_MODE_EXPAND_ONLY) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
332 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
333 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
334
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
335 if (EVP_PKEY_CTX_set_hkdf_md(pctx, digest) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
336 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
337 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
338
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
339 if (EVP_PKEY_CTX_set1_hkdf_key(pctx, prk, prk_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
340 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
341 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
342
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
343 if (EVP_PKEY_CTX_add1_hkdf_info(pctx, info, info_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
344 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
345 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
346
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
347 if (EVP_PKEY_derive(pctx, out_key, &out_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
348 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
349 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
350
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
351 return NGX_OK;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
352
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
353 failed:
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
354
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
355 EVP_PKEY_CTX_free(pctx);
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
356
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
357 return NGX_ERROR;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
358
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
359 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
360 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
361
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
362
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
363 static ngx_int_t
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
364 ngx_hkdf_extract(u_char *out_key, size_t *out_len, const EVP_MD *digest,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
365 const u_char *secret, size_t secret_len, const u_char *salt,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
366 size_t salt_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
367 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
368 #ifdef OPENSSL_IS_BORINGSSL
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
369
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
370 if (HKDF_extract(out_key, out_len, digest, secret, secret_len, salt,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
371 salt_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
372 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
373 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
374 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
375 }
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
376
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
377 return NGX_OK;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
378
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
379 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
380
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
381 EVP_PKEY_CTX *pctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
382
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
383 pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_HKDF, NULL);
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
384 if (pctx == NULL) {
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
385 return NGX_ERROR;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
386 }
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
387
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
388 if (EVP_PKEY_derive_init(pctx) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
389 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
390 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
391
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
392 if (EVP_PKEY_CTX_hkdf_mode(pctx, EVP_PKEY_HKDEF_MODE_EXTRACT_ONLY) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
393 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
394 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
395
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
396 if (EVP_PKEY_CTX_set_hkdf_md(pctx, digest) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
397 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
398 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
399
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
400 if (EVP_PKEY_CTX_set1_hkdf_key(pctx, secret, secret_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
401 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
402 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
403
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
404 if (EVP_PKEY_CTX_set1_hkdf_salt(pctx, salt, salt_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
405 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
406 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
407
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
408 if (EVP_PKEY_derive(pctx, out_key, out_len) <= 0) {
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
409 goto failed;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
410 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
411
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
412 return NGX_OK;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
413
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
414 failed:
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
415
8716
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
416 EVP_PKEY_CTX_free(pctx);
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
417
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
418 return NGX_ERROR;
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
419
1c48629cfa74 QUIC: added error handling to ngx_hkdf_extract()/ngx_hkdf_expand().
Vladimir Homutov <vl@nginx.com>
parents: 8710
diff changeset
420 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
421 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
422
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
423
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
424 static ngx_int_t
8288
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
425 ngx_quic_tls_open(const ngx_quic_cipher_t *cipher, ngx_quic_secret_t *s,
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
426 ngx_str_t *out, u_char *nonce, ngx_str_t *in, ngx_str_t *ad,
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
427 ngx_log_t *log)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
428 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
429
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
430 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
431 EVP_AEAD_CTX *ctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
432
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
433 ctx = EVP_AEAD_CTX_new(cipher, s->key.data, s->key.len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
434 EVP_AEAD_DEFAULT_TAG_LENGTH);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
435 if (ctx == NULL) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
436 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_AEAD_CTX_new() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
437 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
438 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
439
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
440 if (EVP_AEAD_CTX_open(ctx, out->data, &out->len, out->len, nonce, s->iv.len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
441 in->data, in->len, ad->data, ad->len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
442 != 1)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
443 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
444 EVP_AEAD_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
445 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_AEAD_CTX_open() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
446 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
447 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
448
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
449 EVP_AEAD_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
450 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
451 int len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
452 u_char *tag;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
453 EVP_CIPHER_CTX *ctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
454
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
455 ctx = EVP_CIPHER_CTX_new();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
456 if (ctx == NULL) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
457 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_CIPHER_CTX_new() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
458 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
459 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
460
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
461 if (EVP_DecryptInit_ex(ctx, cipher, NULL, NULL, NULL) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
462 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
463 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_DecryptInit_ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
464 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
465 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
466
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
467 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_IVLEN, s->iv.len, NULL)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
468 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
469 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
470 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
471 ngx_ssl_error(NGX_LOG_INFO, log, 0,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
472 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_IVLEN) failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
473 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
474 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
475
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
476 if (EVP_DecryptInit_ex(ctx, NULL, NULL, s->key.data, nonce) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
477 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
478 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_DecryptInit_ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
479 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
480 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
481
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
482 if (EVP_DecryptUpdate(ctx, NULL, &len, ad->data, ad->len) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
483 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
484 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_DecryptUpdate() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
485 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
486 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
487
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
488 if (EVP_DecryptUpdate(ctx, out->data, &len, in->data,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
489 in->len - EVP_GCM_TLS_TAG_LEN)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
490 != 1)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
491 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
492 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
493 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_DecryptUpdate() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
494 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
495 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
496
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
497 out->len = len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
498 tag = in->data + in->len - EVP_GCM_TLS_TAG_LEN;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
499
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
500 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_TAG, EVP_GCM_TLS_TAG_LEN, tag)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
501 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
502 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
503 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
504 ngx_ssl_error(NGX_LOG_INFO, log, 0,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
505 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_TAG) failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
506 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
507 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
508
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
509 if (EVP_DecryptFinal_ex(ctx, out->data + len, &len) <= 0) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
510 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
511 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_DecryptFinal_ex failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
512 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
513 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
514
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
515 out->len += len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
516
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
517 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
518 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
519
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
520 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
521 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
522
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
523
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
524 static ngx_int_t
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
525 ngx_quic_tls_seal(const ngx_quic_cipher_t *cipher, ngx_quic_secret_t *s,
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
526 ngx_str_t *out, u_char *nonce, ngx_str_t *in, ngx_str_t *ad, ngx_log_t *log)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
527 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
528
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
529 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
530 EVP_AEAD_CTX *ctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
531
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
532 ctx = EVP_AEAD_CTX_new(cipher, s->key.data, s->key.len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
533 EVP_AEAD_DEFAULT_TAG_LENGTH);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
534 if (ctx == NULL) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
535 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_AEAD_CTX_new() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
536 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
537 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
538
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
539 if (EVP_AEAD_CTX_seal(ctx, out->data, &out->len, out->len, nonce, s->iv.len,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
540 in->data, in->len, ad->data, ad->len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
541 != 1)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
542 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
543 EVP_AEAD_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
544 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_AEAD_CTX_seal() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
545 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
546 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
547
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
548 EVP_AEAD_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
549 #else
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
550 int len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
551 EVP_CIPHER_CTX *ctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
552
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
553 ctx = EVP_CIPHER_CTX_new();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
554 if (ctx == NULL) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
555 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_CIPHER_CTX_new() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
556 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
557 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
558
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
559 if (EVP_EncryptInit_ex(ctx, cipher, NULL, NULL, NULL) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
560 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
561 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptInit_ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
562 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
563 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
564
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
565 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_IVLEN, s->iv.len, NULL)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
566 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
567 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
568 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
569 ngx_ssl_error(NGX_LOG_INFO, log, 0,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
570 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_IVLEN) failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
571 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
572 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
573
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
574 if (EVP_EncryptInit_ex(ctx, NULL, NULL, s->key.data, nonce) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
575 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
576 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptInit_ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
577 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
578 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
579
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
580 if (EVP_EncryptUpdate(ctx, NULL, &len, ad->data, ad->len) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
581 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
582 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptUpdate() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
583 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
584 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
585
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
586 if (EVP_EncryptUpdate(ctx, out->data, &len, in->data, in->len) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
587 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
588 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptUpdate() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
589 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
590 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
591
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
592 out->len = len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
593
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
594 if (EVP_EncryptFinal_ex(ctx, out->data + out->len, &len) <= 0) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
595 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
596 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptFinal_ex failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
597 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
598 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
599
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
600 out->len += len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
601
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
602 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_GET_TAG, EVP_GCM_TLS_TAG_LEN,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
603 out->data + in->len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
604 == 0)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
605 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
606 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
607 ngx_ssl_error(NGX_LOG_INFO, log, 0,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
608 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_GET_TAG) failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
609 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
610 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
611
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
612 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
613
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
614 out->len += EVP_GCM_TLS_TAG_LEN;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
615 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
616 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
617 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
618
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
619
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
620 static ngx_int_t
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
621 ngx_quic_tls_hp(ngx_log_t *log, const EVP_CIPHER *cipher,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
622 ngx_quic_secret_t *s, u_char *out, u_char *in)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
623 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
624 int outlen;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
625 EVP_CIPHER_CTX *ctx;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
626 u_char zero[5] = {0};
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
627
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
628 #ifdef OPENSSL_IS_BORINGSSL
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
629 uint32_t counter;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
630
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
631 ngx_memcpy(&counter, in, sizeof(uint32_t));
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
632
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
633 if (cipher == (const EVP_CIPHER *) EVP_aead_chacha20_poly1305()) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
634 CRYPTO_chacha_20(out, zero, 5, s->hp.data, &in[4], counter);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
635 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
636 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
637 #endif
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
638
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
639 ctx = EVP_CIPHER_CTX_new();
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
640 if (ctx == NULL) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
641 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
642 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
643
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
644 if (EVP_EncryptInit_ex(ctx, cipher, NULL, s->hp.data, in) != 1) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
645 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptInit_ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
646 goto failed;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
647 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
648
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
649 if (!EVP_EncryptUpdate(ctx, out, &outlen, zero, 5)) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
650 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptUpdate() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
651 goto failed;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
652 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
653
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
654 if (!EVP_EncryptFinal_ex(ctx, out + 5, &outlen)) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
655 ngx_ssl_error(NGX_LOG_INFO, log, 0, "EVP_EncryptFinal_Ex() failed");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
656 goto failed;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
657 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
658
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
659 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
660
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
661 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
662
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
663 failed:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
664
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
665 EVP_CIPHER_CTX_free(ctx);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
666
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
667 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
668 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
669
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
670
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
671 int ngx_quic_keys_set_encryption_secret(ngx_pool_t *pool, ngx_uint_t is_write,
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
672 ngx_quic_keys_t *keys, enum ssl_encryption_level_t level,
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
673 const SSL_CIPHER *cipher, const uint8_t *secret, size_t secret_len)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
674 {
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
675 ngx_int_t key_len;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
676 ngx_uint_t i;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
677 ngx_quic_secret_t *peer_secret;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
678 ngx_quic_ciphers_t ciphers;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
679
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
680 peer_secret = is_write ? &keys->secrets[level].server
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
681 : &keys->secrets[level].client;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
682
8667
a4c05aff8ec0 QUIC: converted to SSL_CIPHER_get_protocol_id().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8651
diff changeset
683 keys->cipher = SSL_CIPHER_get_protocol_id(cipher);
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
684
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
685 key_len = ngx_quic_ciphers(keys->cipher, &ciphers, level);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
686
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
687 if (key_len == NGX_ERROR) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
688 ngx_ssl_error(NGX_LOG_INFO, pool->log, 0, "unexpected cipher");
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
689 return 0;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
690 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
691
8306
058a5af7ddfc Refactored QUIC secrets storage.
Vladimir Homutov <vl@nginx.com>
parents: 8303
diff changeset
692 if (level == ssl_encryption_initial) {
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
693 return 0;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
694 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
695
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
696 peer_secret->secret.data = ngx_pnalloc(pool, secret_len);
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
697 if (peer_secret->secret.data == NULL) {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
698 return NGX_ERROR;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
699 }
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
700
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
701 peer_secret->secret.len = secret_len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
702 ngx_memcpy(peer_secret->secret.data, secret, secret_len);
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
703
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
704 peer_secret->key.len = key_len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
705 peer_secret->iv.len = NGX_QUIC_IV_LEN;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
706 peer_secret->hp.len = key_len;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
707
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
708 struct {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
709 ngx_str_t label;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
710 ngx_str_t *key;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
711 const uint8_t *secret;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
712 } seq[] = {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
713 { ngx_string("tls13 quic key"), &peer_secret->key, secret },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
714 { ngx_string("tls13 quic iv"), &peer_secret->iv, secret },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
715 { ngx_string("tls13 quic hp"), &peer_secret->hp, secret },
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
716 };
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
717
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
718 for (i = 0; i < (sizeof(seq) / sizeof(seq[0])); i++) {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
719
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
720 if (ngx_quic_hkdf_expand(pool, ciphers.d, seq[i].key, &seq[i].label,
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
721 seq[i].secret, secret_len)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
722 != NGX_OK)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
723 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
724 return 0;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
725 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
726 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
727
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
728 return 1;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
729 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
730
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
731
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
732 ngx_quic_keys_t *
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
733 ngx_quic_keys_new(ngx_pool_t *pool)
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
734 {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
735 return ngx_pcalloc(pool, sizeof(ngx_quic_keys_t));
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
736 }
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
737
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
738
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
739 ngx_uint_t
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
740 ngx_quic_keys_available(ngx_quic_keys_t *keys,
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
741 enum ssl_encryption_level_t level)
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
742 {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
743 return keys->secrets[level].client.key.len != 0;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
744 }
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
745
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
746
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
747 void
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
748 ngx_quic_keys_discard(ngx_quic_keys_t *keys,
8702
d4e02b3b734f QUIC: fixed indentation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8694
diff changeset
749 enum ssl_encryption_level_t level)
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
750 {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
751 keys->secrets[level].client.key.len = 0;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
752 }
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
753
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
754
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
755 void
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
756 ngx_quic_keys_switch(ngx_connection_t *c, ngx_quic_keys_t *keys)
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
757 {
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
758 ngx_quic_secrets_t *current, *next, tmp;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
759
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
760 current = &keys->secrets[ssl_encryption_application];
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
761 next = &keys->next_key;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
762
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
763 tmp = *current;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
764 *current = *next;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
765 *next = tmp;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
766 }
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
767
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
768
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
769 ngx_int_t
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
770 ngx_quic_keys_update(ngx_connection_t *c, ngx_quic_keys_t *keys)
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
771 {
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
772 ngx_uint_t i;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
773 ngx_quic_ciphers_t ciphers;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
774 ngx_quic_secrets_t *current, *next;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
775
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
776 current = &keys->secrets[ssl_encryption_application];
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
777 next = &keys->next_key;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
778
8360
f175006124d0 Cleaned up hexdumps in debug output.
Vladimir Homutov <vl@nginx.com>
parents: 8359
diff changeset
779 ngx_log_debug0(NGX_LOG_DEBUG_EVENT, c->log, 0, "quic key update");
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
780
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
781 if (ngx_quic_ciphers(keys->cipher, &ciphers, ssl_encryption_application)
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
782 == NGX_ERROR)
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
783 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
784 return NGX_ERROR;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
785 }
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
786
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
787 next->client.secret.len = current->client.secret.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
788 next->client.key.len = current->client.key.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
789 next->client.iv.len = current->client.iv.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
790 next->client.hp = current->client.hp;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
791
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
792 next->server.secret.len = current->server.secret.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
793 next->server.key.len = current->server.key.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
794 next->server.iv.len = current->server.iv.len;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
795 next->server.hp = current->server.hp;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
796
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
797 struct {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
798 ngx_str_t label;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
799 ngx_str_t *key;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
800 ngx_str_t *secret;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
801 } seq[] = {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
802 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
803 ngx_string("tls13 quic ku"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
804 &next->client.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
805 &current->client.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
806 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
807 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
808 ngx_string("tls13 quic key"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
809 &next->client.key,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
810 &next->client.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
811 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
812 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
813 ngx_string("tls13 quic iv"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
814 &next->client.iv,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
815 &next->client.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
816 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
817 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
818 ngx_string("tls13 quic ku"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
819 &next->server.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
820 &current->server.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
821 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
822 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
823 ngx_string("tls13 quic key"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
824 &next->server.key,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
825 &next->server.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
826 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
827 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
828 ngx_string("tls13 quic iv"),
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
829 &next->server.iv,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
830 &next->server.secret,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
831 },
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
832 };
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
833
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
834 for (i = 0; i < (sizeof(seq) / sizeof(seq[0])); i++) {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
835
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
836 if (ngx_quic_hkdf_expand(c->pool, ciphers.d, seq[i].key, &seq[i].label,
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
837 seq[i].secret->data, seq[i].secret->len)
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
838 != NGX_OK)
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
839 {
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
840 return NGX_ERROR;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
841 }
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
842 }
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
843
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
844 return NGX_OK;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
845 }
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
846
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
847
8376
2d0f4aa78ed6 Restored ngx_quic_encrypt return type.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8375
diff changeset
848 static ngx_int_t
8644
e953bd2c5bb3 QUIC: merged create_long/short_packet() functions.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8643
diff changeset
849 ngx_quic_create_packet(ngx_quic_header_t *pkt, ngx_str_t *res)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
850 {
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
851 u_char *pnp, *sample;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
852 ngx_str_t ad, out;
8315
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
853 ngx_uint_t i;
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
854 ngx_quic_secret_t *secret;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
855 ngx_quic_ciphers_t ciphers;
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
856 u_char nonce[12], mask[16];
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
857
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
858 out.len = pkt->payload.len + EVP_GCM_TLS_TAG_LEN;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
859
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
860 ad.data = res->data;
8642
05b1ee464350 QUIC: hide header creation internals in ngx_event_quic_transport.c.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8621
diff changeset
861 ad.len = ngx_quic_create_header(pkt, ad.data, out.len, &pnp);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
862
8318
1bb5e8538d0c Removed excessive debugging in QUIC packet creation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8317
diff changeset
863 out.data = res->data + ad.len;
1bb5e8538d0c Removed excessive debugging in QUIC packet creation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8317
diff changeset
864
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
865 #ifdef NGX_QUIC_DEBUG_CRYPTO
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
866 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
867 "quic ad len:%uz %xV", ad.len, &ad);
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
868 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
869
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
870 if (ngx_quic_ciphers(pkt->keys->cipher, &ciphers, pkt->level) == NGX_ERROR)
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
871 {
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
872 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
873 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
874
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
875 secret = &pkt->keys->secrets[pkt->level].server;
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
876
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
877 ngx_memcpy(nonce, secret->iv.data, secret->iv.len);
8310
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
878 ngx_quic_compute_nonce(nonce, sizeof(nonce), pkt->number);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
879
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
880 if (ngx_quic_tls_seal(ciphers.c, secret, &out,
8318
1bb5e8538d0c Removed excessive debugging in QUIC packet creation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8317
diff changeset
881 nonce, &pkt->payload, &ad, pkt->log)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
882 != NGX_OK)
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
883 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
884 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
885 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
886
8315
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
887 sample = &out.data[4 - pkt->num_len];
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
888 if (ngx_quic_tls_hp(pkt->log, ciphers.hp, secret, mask, sample)
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
889 != NGX_OK)
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
890 {
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
891 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
892 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
893
8315
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
894 /* quic-tls: 5.4.1. Header Protection Application */
8643
5fdd0ef42232 QUIC: macros for manipulating header protection and reserved bits.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8642
diff changeset
895 ad.data[0] ^= mask[0] & ngx_quic_pkt_hp_mask(pkt->flags);
8315
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
896
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
897 for (i = 0; i < pkt->num_len; i++) {
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
898 pnp[i] ^= mask[i + 1];
fdda518d10ba Proper handling of packet number in header.
Vladimir Homutov <vl@nginx.com>
parents: 8313
diff changeset
899 }
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
900
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
901 res->len = ad.len + out.len;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
902
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
903 return NGX_OK;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
904 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
905
8285
f85749b60e58 Removed memory allocations from encryption code.
Vladimir Homutov <vl@nginx.com>
parents: 8265
diff changeset
906
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
907 static ngx_int_t
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
908 ngx_quic_create_retry_packet(ngx_quic_header_t *pkt, ngx_str_t *res)
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
909 {
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
910 u_char *start;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
911 ngx_str_t ad, itag;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
912 ngx_quic_secret_t secret;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
913 ngx_quic_ciphers_t ciphers;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
914
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
915 /* 5.8. Retry Packet Integrity */
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
916 static u_char key[16] =
8678
3443ee341cc1 QUIC: draft-33 salt and retry keys.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8673
diff changeset
917 "\xbe\x0c\x69\x0b\x9f\x66\x57\x5a\x1d\x76\x6b\x54\xe3\x68\xc8\x4e";
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
918 static u_char key29[16] =
8448
011668fc9efd Update Initial salt and Retry secret from quic-tls-29.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8446
diff changeset
919 "\xcc\xce\x18\x7e\xd0\x9a\x09\xd0\x57\x28\x15\x5a\x6c\xb9\x6b\xe1";
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
920 static u_char nonce[12] =
8678
3443ee341cc1 QUIC: draft-33 salt and retry keys.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8673
diff changeset
921 "\x46\x15\x99\xd3\x5d\x63\x2b\xf2\x23\x98\x25\xbb";
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
922 static u_char nonce29[12] =
8448
011668fc9efd Update Initial salt and Retry secret from quic-tls-29.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8446
diff changeset
923 "\xe5\x49\x30\xf9\x7f\x21\x36\xf0\x53\x0a\x8c\x1c";
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
924 static ngx_str_t in = ngx_string("");
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
925
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
926 ad.data = res->data;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
927 ad.len = ngx_quic_create_retry_itag(pkt, ad.data, &start);
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
928
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
929 itag.data = ad.data + ad.len;
8394
df18ae7161b8 Assorted fixes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8386
diff changeset
930 itag.len = EVP_GCM_TLS_TAG_LEN;
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
931
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
932 #ifdef NGX_QUIC_DEBUG_CRYPTO
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
933 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
934 "quic retry itag len:%uz %xV", ad.len, &ad);
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
935 #endif
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
936
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
937 if (ngx_quic_ciphers(0, &ciphers, pkt->level) == NGX_ERROR) {
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
938 return NGX_ERROR;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
939 }
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
940
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
941 secret.key.len = sizeof(key);
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
942 secret.key.data = (pkt->version & 0xff000000) ? key29 : key;
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
943 secret.iv.len = sizeof(nonce);
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
944
8710
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
945 if (ngx_quic_tls_seal(ciphers.c, &secret, &itag,
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
946 (pkt->version & 0xff000000) ? nonce29 : nonce,
44b4c6180106 QUIC: multiple versions support.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8709
diff changeset
947 &in, &ad, pkt->log)
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
948 != NGX_OK)
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
949 {
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
950 return NGX_ERROR;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
951 }
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
952
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
953 res->len = itag.data + itag.len - start;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
954 res->data = start;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
955
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
956 return NGX_OK;
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
957 }
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
958
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
959
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
960 ngx_int_t
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
961 ngx_quic_derive_key(ngx_log_t *log, const char *label, ngx_str_t *secret,
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
962 ngx_str_t *salt, u_char *out, size_t len)
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
963 {
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
964 size_t is_len, info_len;
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
965 uint8_t *p;
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
966 const EVP_MD *digest;
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
967
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
968 uint8_t is[SHA256_DIGEST_LENGTH];
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
969 uint8_t info[20];
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
970
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
971 digest = EVP_sha256();
8729
0f8565e0fc76 QUIC: HKDF API compatibility with OpenSSL master branch.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8716
diff changeset
972 is_len = SHA256_DIGEST_LENGTH;
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
973
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
974 if (ngx_hkdf_extract(is, &is_len, digest, secret->data, secret->len,
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
975 salt->data, salt->len)
8702
d4e02b3b734f QUIC: fixed indentation.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8694
diff changeset
976 != NGX_OK)
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
977 {
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
978 ngx_ssl_error(NGX_LOG_INFO, log, 0,
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
979 "ngx_hkdf_extract(%s) failed", label);
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
980 return NGX_ERROR;
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
981 }
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
982
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
983 info[0] = 0;
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
984 info[1] = len;
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
985 info[2] = ngx_strlen(label);
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
986
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
987 info_len = 2 + 1 + info[2] + 1;
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
988
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
989 if (info_len >= 20) {
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
990 ngx_log_error(NGX_LOG_INFO, log, 0,
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
991 "ngx_quic_create_key label \"%s\" too long", label);
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
992 return NGX_ERROR;
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
993 }
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
994
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
995 p = ngx_cpymem(&info[3], label, info[2]);
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
996 *p = '\0';
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
997
8694
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
998 if (ngx_hkdf_expand(out, len, digest, is, is_len, info, info_len) != NGX_OK)
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
999 {
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
1000 ngx_ssl_error(NGX_LOG_INFO, log, 0,
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
1001 "ngx_hkdf_expand(%s) failed", label);
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
1002 return NGX_ERROR;
cef042935003 QUIC: the "quic_host_key" directive.
Vladimir Homutov <vl@nginx.com>
parents: 8678
diff changeset
1003 }
8562
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
1004
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
1005 return NGX_OK;
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
1006 }
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
1007
b31c02454539 QUIC: added stateless reset support.
Vladimir Homutov <vl@nginx.com>
parents: 8558
diff changeset
1008
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1009 static uint64_t
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1010 ngx_quic_parse_pn(u_char **pos, ngx_int_t len, u_char *mask,
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1011 uint64_t *largest_pn)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1012 {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1013 u_char *p;
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1014 uint64_t truncated_pn, expected_pn, candidate_pn;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1015 uint64_t pn_nbits, pn_win, pn_hwin, pn_mask;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1016
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1017 pn_nbits = ngx_min(len * 8, 62);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1018
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1019 p = *pos;
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1020 truncated_pn = *p++ ^ *mask++;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1021
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1022 while (--len) {
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1023 truncated_pn = (truncated_pn << 8) + (*p++ ^ *mask++);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1024 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1025
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1026 *pos = p;
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1027
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1028 expected_pn = *largest_pn + 1;
8394
df18ae7161b8 Assorted fixes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8386
diff changeset
1029 pn_win = 1ULL << pn_nbits;
8339
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1030 pn_hwin = pn_win / 2;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1031 pn_mask = pn_win - 1;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1032
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1033 candidate_pn = (expected_pn & ~pn_mask) | truncated_pn;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1034
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1035 if ((int64_t) candidate_pn <= (int64_t) (expected_pn - pn_hwin)
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1036 && candidate_pn < (1ULL << 62) - pn_win)
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1037 {
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1038 candidate_pn += pn_win;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1039
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1040 } else if (candidate_pn > expected_pn + pn_hwin
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1041 && candidate_pn >= pn_win)
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1042 {
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1043 candidate_pn -= pn_win;
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1044 }
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1045
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1046 *largest_pn = ngx_max((int64_t) *largest_pn, (int64_t) candidate_pn);
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1047
aba84d9ab256 Parsing of truncated packet numbers.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8324
diff changeset
1048 return candidate_pn;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1049 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1050
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1051
8310
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1052 static void
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1053 ngx_quic_compute_nonce(u_char *nonce, size_t len, uint64_t pn)
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1054 {
8313
c625bde6cb77 Fixed computing nonce again, by properly shifting packet number.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8310
diff changeset
1055 nonce[len - 4] ^= (pn & 0xff000000) >> 24;
c625bde6cb77 Fixed computing nonce again, by properly shifting packet number.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8310
diff changeset
1056 nonce[len - 3] ^= (pn & 0x00ff0000) >> 16;
c625bde6cb77 Fixed computing nonce again, by properly shifting packet number.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8310
diff changeset
1057 nonce[len - 2] ^= (pn & 0x0000ff00) >> 8;
c625bde6cb77 Fixed computing nonce again, by properly shifting packet number.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8310
diff changeset
1058 nonce[len - 1] ^= (pn & 0x000000ff);
8310
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1059 }
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1060
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1061
8376
2d0f4aa78ed6 Restored ngx_quic_encrypt return type.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8375
diff changeset
1062 ngx_int_t
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1063 ngx_quic_encrypt(ngx_quic_header_t *pkt, ngx_str_t *res)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1064 {
8383
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
1065 if (ngx_quic_pkt_retry(pkt->flags)) {
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
1066 return ngx_quic_create_retry_packet(pkt, res);
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
1067 }
7ea34e13937f Address validation using Retry packets.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8376
diff changeset
1068
8644
e953bd2c5bb3 QUIC: merged create_long/short_packet() functions.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8643
diff changeset
1069 return ngx_quic_create_packet(pkt, res);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1070 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1071
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1072
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1073 ngx_int_t
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1074 ngx_quic_decrypt(ngx_quic_header_t *pkt, uint64_t *largest_pn)
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1075 {
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1076 u_char *p, *sample;
8558
0f37b4ef3cd9 QUIC: keep the entire packet size in pkt->len.
Roman Arutyunyan <arut@nginx.com>
parents: 8544
diff changeset
1077 size_t len;
8532
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1078 uint64_t pn, lpn;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1079 ngx_int_t pnl, rc, key_phase;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1080 ngx_str_t in, ad;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1081 ngx_quic_secret_t *secret;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1082 ngx_quic_ciphers_t ciphers;
8288
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
1083 uint8_t mask[16], nonce[12];
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1084
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1085 if (ngx_quic_ciphers(pkt->keys->cipher, &ciphers, pkt->level) == NGX_ERROR)
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1086 {
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1087 return NGX_ERROR;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1088 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1089
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1090 secret = &pkt->keys->secrets[pkt->level].client;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1091
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1092 p = pkt->raw->pos;
8558
0f37b4ef3cd9 QUIC: keep the entire packet size in pkt->len.
Roman Arutyunyan <arut@nginx.com>
parents: 8544
diff changeset
1093 len = pkt->data + pkt->len - p;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1094
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1095 /* draft-ietf-quic-tls-23#section-5.4.2:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1096 * the Packet Number field is assumed to be 4 bytes long
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1097 * draft-ietf-quic-tls-23#section-5.4.[34]:
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1098 * AES-Based and ChaCha20-Based header protections sample 16 bytes
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1099 */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1100
8558
0f37b4ef3cd9 QUIC: keep the entire packet size in pkt->len.
Roman Arutyunyan <arut@nginx.com>
parents: 8544
diff changeset
1101 if (len < EVP_GCM_TLS_TAG_LEN + 4) {
8543
9aedab0f0dff QUIC: check that the packet length is of at least sample size.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8542
diff changeset
1102 return NGX_DECLINED;
9aedab0f0dff QUIC: check that the packet length is of at least sample size.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8542
diff changeset
1103 }
9aedab0f0dff QUIC: check that the packet length is of at least sample size.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8542
diff changeset
1104
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1105 sample = p + 4;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1106
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1107 /* header protection */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1108
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1109 if (ngx_quic_tls_hp(pkt->log, ciphers.hp, secret, mask, sample)
8287
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
1110 != NGX_OK)
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
1111 {
8446
df29219988bc Discard short packets which could not be decrypted.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8445
diff changeset
1112 return NGX_DECLINED;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1113 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1114
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1115 pkt->flags ^= mask[0] & ngx_quic_pkt_hp_mask(pkt->flags);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1116
8643
5fdd0ef42232 QUIC: macros for manipulating header protection and reserved bits.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8642
diff changeset
1117 if (ngx_quic_short_pkt(pkt->flags)) {
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1118 key_phase = (pkt->flags & NGX_QUIC_PKT_KPHASE) != 0;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1119
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1120 if (key_phase != pkt->key_phase) {
8621
9c3be23ddbe7 QUIC: refactored key handling.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8609
diff changeset
1121 secret = &pkt->keys->next_key.client;
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1122 pkt->key_update = 1;
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1123 }
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1124 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1125
8532
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1126 lpn = *largest_pn;
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1127
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1128 pnl = (pkt->flags & 0x03) + 1;
8532
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1129 pn = ngx_quic_parse_pn(&p, pnl, &mask[1], &lpn);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1130
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1131 pkt->pn = pn;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1132
8287
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
1133 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1134 "quic packet rx clearflags:%xd", pkt->flags);
8287
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
1135 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
8609
f32740ddd484 QUIC: got rid of "pkt" abbreviation in logs.
Vladimir Homutov <vl@nginx.com>
parents: 8608
diff changeset
1136 "quic packet rx number:%uL len:%xi", pn, pnl);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1137
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1138 /* packet protection */
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1139
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1140 in.data = p;
8558
0f37b4ef3cd9 QUIC: keep the entire packet size in pkt->len.
Roman Arutyunyan <arut@nginx.com>
parents: 8544
diff changeset
1141 in.len = len - pnl;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1142
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1143 ad.len = p - pkt->data;
8288
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
1144 ad.data = pkt->plaintext;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1145
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1146 ngx_memcpy(ad.data, pkt->data, ad.len);
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1147 ad.data[0] = pkt->flags;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1148
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1149 do {
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1150 ad.data[ad.len - pnl] = pn >> (8 * (pnl - 1)) % 256;
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1151 } while (--pnl);
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1152
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1153 ngx_memcpy(nonce, secret->iv.data, secret->iv.len);
8310
7ac890c18f5e Fixed computing nonce by xoring all packet number bytes.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8307
diff changeset
1154 ngx_quic_compute_nonce(nonce, sizeof(nonce), pn);
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1155
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
1156 #ifdef NGX_QUIC_DEBUG_CRYPTO
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
1157 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
1158 "quic ad len:%uz %xV", ad.len, &ad);
8359
2f900ae486bc Debug cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8339
diff changeset
1159 #endif
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1160
8288
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
1161 pkt->payload.len = in.len - EVP_GCM_TLS_TAG_LEN;
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
1162 pkt->payload.data = pkt->plaintext + ad.len;
ebd5c71b9f02 Got rid of memory allocation in decryption.
Vladimir Homutov <vl@nginx.com>
parents: 8287
diff changeset
1163
8319
29354c6fc5f2 TLS Key Update in QUIC.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8318
diff changeset
1164 rc = ngx_quic_tls_open(ciphers.c, secret, &pkt->payload,
8287
ccb9cc95ad5e Logging cleanup.
Vladimir Homutov <vl@nginx.com>
parents: 8285
diff changeset
1165 nonce, &in, &ad, pkt->log);
8386
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1166 if (rc != NGX_OK) {
8446
df29219988bc Discard short packets which could not be decrypted.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8445
diff changeset
1167 return NGX_DECLINED;
8386
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1168 }
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1169
8646
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1170 if (pkt->payload.len == 0) {
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1171 /*
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1172 * An endpoint MUST treat receipt of a packet containing no
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1173 * frames as a connection error of type PROTOCOL_VIOLATION.
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1174 */
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1175 ngx_log_error(NGX_LOG_INFO, pkt->log, 0, "quic zero-length packet");
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1176 pkt->error = NGX_QUIC_ERR_PROTOCOL_VIOLATION;
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1177 return NGX_ERROR;
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1178 }
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1179
8645
ae4bffb75df8 QUIC: simplified and streamlined ngx_quic_decrypt().
Sergey Kandaurov <pluknet@nginx.com>
parents: 8644
diff changeset
1180 if (pkt->flags & ngx_quic_pkt_rb_mask(pkt->flags)) {
8386
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1181 /*
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1182 * An endpoint MUST treat receipt of a packet that has
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1183 * a non-zero value for these bits, after removing both
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1184 * packet and header protection, as a connection error
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1185 * of type PROTOCOL_VIOLATION.
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1186 */
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1187 ngx_log_error(NGX_LOG_INFO, pkt->log, 0,
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1188 "quic reserved bit set in packet");
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1189 pkt->error = NGX_QUIC_ERR_PROTOCOL_VIOLATION;
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1190 return NGX_ERROR;
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1191 }
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1192
8646
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1193 #if defined(NGX_QUIC_DEBUG_CRYPTO) && defined(NGX_QUIC_DEBUG_PACKETS)
8651
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
1194 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, pkt->log, 0,
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
1195 "quic packet payload len:%uz %xV",
dbad2d6d1898 QUIC: removed ngx_quic_hexdump() macro.
Vladimir Homutov <vl@nginx.com>
parents: 8646
diff changeset
1196 pkt->payload.len, &pkt->payload);
8646
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1197 #endif
4bf332873a83 QUIC: rejecting zero-length packets with PROTOCOL_VIOLATION.
Sergey Kandaurov <pluknet@nginx.com>
parents: 8645
diff changeset
1198
8532
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1199 *largest_pn = lpn;
b13141d6d250 QUIC: do not update largest packet number from a bad packet.
Roman Arutyunyan <arut@nginx.com>
parents: 8525
diff changeset
1200
8386
81f85c479d7e Discard packets without fixed bit or reserved bits set.
Vladimir Homutov <vl@nginx.com>
parents: 8383
diff changeset
1201 return NGX_OK;
8221
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1202 }
69345a26ba69 Split transport and crypto parts into separate files.
Vladimir Homutov <vl@nginx.com>
parents:
diff changeset
1203