comparison src/event/ngx_event_quic.c @ 7643:76e29ff31cd3 quic

AEAD routines, introduced ngx_quic_tls_open()/ngx_quic_tls_seal().
author Sergey Kandaurov <pluknet@nginx.com>
date Fri, 28 Feb 2020 13:09:52 +0300
parents 4daf03d2bd0a
children a9ff4392ecde
comparison
equal deleted inserted replaced
7642:8964cc6ecc4a 7643:76e29ff31cd3
161 161
162 #endif 162 #endif
163 163
164 return NGX_OK; 164 return NGX_OK;
165 } 165 }
166
167
168 ngx_int_t
169 ngx_quic_tls_open(ngx_connection_t *c, const ngx_aead_cipher_t *cipher,
170 ngx_quic_secret_t *s, ngx_str_t *out, u_char *nonce, ngx_str_t *in,
171 ngx_str_t *ad)
172 {
173 out->len = in->len - EVP_GCM_TLS_TAG_LEN;
174 out->data = ngx_pnalloc(c->pool, out->len);
175 if (out->data == NULL) {
176 return NGX_ERROR;
177 }
178
179 #ifdef OPENSSL_IS_BORINGSSL
180 EVP_AEAD_CTX *ctx;
181
182 ctx = EVP_AEAD_CTX_new(cipher, s->key.data, s->key.len,
183 EVP_AEAD_DEFAULT_TAG_LENGTH);
184 if (ctx == NULL) {
185 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_AEAD_CTX_new() failed");
186 return NGX_ERROR;
187 }
188
189 if (EVP_AEAD_CTX_open(ctx, out->data, &out->len, out->len, nonce, s->iv.len,
190 in->data, in->len, ad->data, ad->len)
191 != 1)
192 {
193 EVP_AEAD_CTX_free(ctx);
194 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_AEAD_CTX_open() failed");
195 return NGX_ERROR;
196 }
197
198 EVP_AEAD_CTX_free(ctx);
199 #else
200 int len;
201 u_char *tag;
202 EVP_CIPHER_CTX *ctx;
203
204 ctx = EVP_CIPHER_CTX_new();
205 if (ctx == NULL) {
206 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_CIPHER_CTX_new() failed");
207 return NGX_ERROR;
208 }
209
210 if (EVP_DecryptInit_ex(ctx, cipher, NULL, NULL, NULL) != 1) {
211 EVP_CIPHER_CTX_free(ctx);
212 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_DecryptInit_ex() failed");
213 return NGX_ERROR;
214 }
215
216 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_IVLEN, s->iv.len, NULL)
217 == 0)
218 {
219 EVP_CIPHER_CTX_free(ctx);
220 ngx_ssl_error(NGX_LOG_INFO, c->log, 0,
221 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_IVLEN) failed");
222 return NGX_ERROR;
223 }
224
225 if (EVP_DecryptInit_ex(ctx, NULL, NULL, s->key.data, nonce) != 1) {
226 EVP_CIPHER_CTX_free(ctx);
227 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_DecryptInit_ex() failed");
228 return NGX_ERROR;
229 }
230
231 if (EVP_DecryptUpdate(ctx, NULL, &len, ad->data, ad->len) != 1) {
232 EVP_CIPHER_CTX_free(ctx);
233 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_DecryptUpdate() failed");
234 return NGX_ERROR;
235 }
236
237 if (EVP_DecryptUpdate(ctx, out->data, &len, in->data,
238 in->len - EVP_GCM_TLS_TAG_LEN)
239 != 1)
240 {
241 EVP_CIPHER_CTX_free(ctx);
242 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_DecryptUpdate() failed");
243 return NGX_ERROR;
244 }
245
246 out->len = len;
247 tag = in->data + in->len - EVP_GCM_TLS_TAG_LEN;
248
249 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_TAG, EVP_GCM_TLS_TAG_LEN, tag)
250 == 0)
251 {
252 EVP_CIPHER_CTX_free(ctx);
253 ngx_ssl_error(NGX_LOG_INFO, c->log, 0,
254 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_TAG) failed");
255 return NGX_ERROR;
256 }
257
258 if (EVP_DecryptFinal_ex(ctx, out->data + len, &len) <= 0) {
259 EVP_CIPHER_CTX_free(ctx);
260 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_DecryptFinal_ex failed");
261 return NGX_ERROR;
262 }
263
264 out->len += len;
265
266 EVP_CIPHER_CTX_free(ctx);
267 #endif
268
269 return NGX_OK;
270 }
271
272
273 ngx_int_t
274 ngx_quic_tls_seal(ngx_connection_t *c, const ngx_aead_cipher_t *cipher,
275 ngx_quic_secret_t *s, ngx_str_t *out, u_char *nonce, ngx_str_t *in,
276 ngx_str_t *ad)
277 {
278 out->len = in->len + EVP_GCM_TLS_TAG_LEN;
279 out->data = ngx_pnalloc(c->pool, out->len);
280 if (out->data == NULL) {
281 return NGX_ERROR;
282 }
283
284 #ifdef OPENSSL_IS_BORINGSSL
285 EVP_AEAD_CTX *ctx;
286
287 ctx = EVP_AEAD_CTX_new(cipher, s->key.data, s->key.len,
288 EVP_AEAD_DEFAULT_TAG_LENGTH);
289 if (ctx == NULL) {
290 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_AEAD_CTX_new() failed");
291 return NGX_ERROR;
292 }
293
294 if (EVP_AEAD_CTX_seal(ctx, out->data, &out->len, out->len, nonce, s->iv.len,
295 in->data, in->len, ad->data, ad->len)
296 != 1)
297 {
298 EVP_AEAD_CTX_free(ctx);
299 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_AEAD_CTX_seal() failed");
300 return NGX_ERROR;
301 }
302
303 EVP_AEAD_CTX_free(ctx);
304 #else
305 int len;
306 EVP_CIPHER_CTX *ctx;
307
308 ctx = EVP_CIPHER_CTX_new();
309 if (ctx == NULL) {
310 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_CIPHER_CTX_new() failed");
311 return NGX_ERROR;
312 }
313
314 if (EVP_EncryptInit_ex(ctx, cipher, NULL, NULL, NULL) != 1) {
315 EVP_CIPHER_CTX_free(ctx);
316 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_EncryptInit_ex() failed");
317 return NGX_ERROR;
318 }
319
320 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_SET_IVLEN, s->iv.len, NULL)
321 == 0)
322 {
323 EVP_CIPHER_CTX_free(ctx);
324 ngx_ssl_error(NGX_LOG_INFO, c->log, 0,
325 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_SET_IVLEN) failed");
326 return NGX_ERROR;
327 }
328
329 if (EVP_EncryptInit_ex(ctx, NULL, NULL, s->key.data, nonce) != 1) {
330 EVP_CIPHER_CTX_free(ctx);
331 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_EncryptInit_ex() failed");
332 return NGX_ERROR;
333 }
334
335 if (EVP_EncryptUpdate(ctx, NULL, &len, ad->data, ad->len) != 1) {
336 EVP_CIPHER_CTX_free(ctx);
337 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_EncryptUpdate() failed");
338 return NGX_ERROR;
339 }
340
341 if (EVP_EncryptUpdate(ctx, out->data, &len, in->data, in->len) != 1) {
342 EVP_CIPHER_CTX_free(ctx);
343 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_EncryptUpdate() failed");
344 return NGX_ERROR;
345 }
346
347 out->len = len;
348
349 if (EVP_EncryptFinal_ex(ctx, out->data + out->len, &len) <= 0) {
350 EVP_CIPHER_CTX_free(ctx);
351 ngx_ssl_error(NGX_LOG_INFO, c->log, 0, "EVP_EncryptFinal_ex failed");
352 return NGX_ERROR;
353 }
354
355 out->len += len;
356
357 if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GCM_GET_TAG, EVP_GCM_TLS_TAG_LEN,
358 out->data + in->len)
359 == 0)
360 {
361 EVP_CIPHER_CTX_free(ctx);
362 ngx_ssl_error(NGX_LOG_INFO, c->log, 0,
363 "EVP_CIPHER_CTX_ctrl(EVP_CTRL_GCM_GET_TAG) failed");
364 return NGX_ERROR;
365 }
366
367 EVP_CIPHER_CTX_free(ctx);
368
369 out->len += EVP_GCM_TLS_TAG_LEN;
370 #endif
371
372 return NGX_OK;
373 }