OpenVPN
ssl_pkt.c
Go to the documentation of this file.
1/*
2 * OpenVPN -- An application to securely tunnel IP networks
3 * over a single TCP/UDP port, with support for SSL/TLS-based
4 * session authentication and key exchange,
5 * packet encryption, packet authentication, and
6 * packet compression.
7 *
8 * Copyright (C) 2002-2026 OpenVPN Inc <sales@openvpn.net>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2
12 * as published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, see <https://www.gnu.org/licenses/>.
21 */
22#ifdef HAVE_CONFIG_H
23#include "config.h"
24#endif
25
26#include "syshead.h"
27
28#include "ssl_util.h"
29#include "ssl_pkt.h"
30#include "ssl_common.h"
31#include "crypto.h"
32#include "session_id.h"
33#include "reliable.h"
34#include "siphash.h"
35#include "tls_crypt.h"
36
37/*
38 * Dependent on hmac size, opcode size, and session_id size.
39 * Will assert if too small.
40 */
41#define SWAP_BUF_SIZE 256
42
60static bool
61swap_hmac(struct buffer *buf, const struct crypto_options *co, bool incoming)
62{
63 ASSERT(co);
64
65 const struct key_ctx *ctx = (incoming ? &co->key_ctx_bi.decrypt : &co->key_ctx_bi.encrypt);
66 ASSERT(ctx->hmac);
67
68 {
69 /* hmac + packet_id (8 bytes) */
70 const int hmac_size = hmac_ctx_size(ctx->hmac) + packet_id_size(true);
71
72 /* opcode (1 byte) + session_id (8 bytes) */
73 const int osid_size = 1 + SID_SIZE;
74
75 int e1, e2;
76 uint8_t *b = BPTR(buf);
77
78 if (incoming)
79 {
80 e1 = osid_size;
81 e2 = hmac_size;
82 }
83 else
84 {
85 e1 = hmac_size;
86 e2 = osid_size;
87 }
88
89 ASSERT(e1 <= SWAP_BUF_SIZE && e2 <= SWAP_BUF_SIZE);
90
91 if (buf->len >= e1 + e2)
92 {
93 uint8_t buf1[SWAP_BUF_SIZE];
94 uint8_t buf2[SWAP_BUF_SIZE];
95
96 memcpy(buf1, b, e1);
97 memcpy(buf2, b + e1, e2);
98 memcpy(b, buf2, e2);
99 memcpy(b + e2, buf1, e1);
100 return true;
101 }
102 else
103 {
104 return false;
105 }
106 }
107}
108
109#undef SWAP_BUF_SIZE
110
120static void
121tls_wrap_control(struct tls_wrap_ctx *ctx, uint8_t header, struct buffer *buf,
122 const struct session_id *session_id)
123{
124 if (ctx->mode == TLS_WRAP_AUTH || ctx->mode == TLS_WRAP_NONE)
125 {
127 ASSERT(buf_write_prepend(buf, &header, sizeof(header)));
128 }
129 if (ctx->mode == TLS_WRAP_AUTH)
130 {
131 struct buffer null = clear_buf();
132
133 /* no encryption, only write hmac */
134 openvpn_encrypt(buf, null, &ctx->opt);
135 ASSERT(swap_hmac(buf, &ctx->opt, false));
136 }
137 else if (ctx->mode == TLS_WRAP_CRYPT)
138 {
139 ASSERT(buf_init(&ctx->work, buf->offset));
140 ASSERT(buf_write(&ctx->work, &header, sizeof(header)));
142 if (!tls_crypt_wrap(buf, &ctx->work, &ctx->opt))
143 {
144 buf->len = 0;
145 return;
146 }
147
149 || (header >> P_OPCODE_SHIFT) == P_CONTROL_WKC_V1)
150 {
151 if (!ctx->tls_crypt_v2_wkc || !buf_copy(&ctx->work, ctx->tls_crypt_v2_wkc))
152 {
153 msg(D_TLS_ERRORS, "Could not append tls-crypt-v2 client key");
154 buf->len = 0;
155 return;
156 }
157 }
158
159 /* Don't change the original data in buf, it's used by the reliability
160 * layer to resend on failure. */
161 *buf = ctx->work;
162 }
163}
164
165void
166write_control_auth(struct tls_session *session, struct key_state *ks, struct buffer *buf,
167 struct link_socket_actual **to_link_addr, int opcode, int max_ack,
168 bool prepend_ack)
169{
170 ASSERT(ks->key_id >= 0 && ks->key_id <= P_KEY_ID_MASK);
171 ASSERT(opcode >= 0 && opcode <= P_LAST_OPCODE);
172 uint8_t header = (uint8_t)(ks->key_id | (opcode << P_OPCODE_SHIFT));
173
174 /* Workaround for Softether servers. Softether has a bug that it only
175 * allows 4 ACks in packets and drops packets if more ACKs are contained
176 * in a packet (see commit 37aa1ba5 in Softether) */
177 if (session->tls_wrap.mode == TLS_WRAP_NONE && !session->opt->server
178 && !(session->opt->crypto_flags & CO_USE_TLS_KEY_MATERIAL_EXPORT))
179 {
180 max_ack = min_int(max_ack, 4);
181 }
182
184 ASSERT(reliable_ack_write(ks->rec_ack, ks->lru_acks, buf, &ks->session_id_remote, max_ack,
185 prepend_ack));
186
187 msg(D_TLS_DEBUG, "%s(): %s", __func__, packet_opcode_name(opcode));
188
190 &session->session_id);
191
192 *to_link_addr = &ks->remote_addr;
193}
194
195bool
196read_control_auth(struct buffer *buf, struct tls_wrap_ctx *ctx,
197 const struct link_socket_actual *from, const struct tls_options *opt)
198{
199 struct gc_arena gc = gc_new();
200 bool ret = false;
201
202 const uint8_t opcode = *(BPTR(buf)) >> P_OPCODE_SHIFT;
203 if ((opcode == P_CONTROL_HARD_RESET_CLIENT_V3 || opcode == P_CONTROL_WKC_V1)
204 && !tls_crypt_v2_extract_client_key(buf, ctx, opt))
205 {
206 msg(D_TLS_ERRORS, "TLS Error: can not extract tls-crypt-v2 client key from %s",
208 goto cleanup;
209 }
210
211 if (ctx->mode == TLS_WRAP_AUTH)
212 {
213 struct buffer null = clear_buf();
214
215 /* move the hmac record to the front of the packet */
216 if (!swap_hmac(buf, &ctx->opt, true))
217 {
218 msg(D_TLS_ERRORS, "TLS Error: cannot locate HMAC in incoming packet from %s",
220 gc_free(&gc);
221 return false;
222 }
223
224 /* authenticate only (no decrypt) and remove the hmac record
225 * from the head of the buffer */
226 openvpn_decrypt(buf, null, &ctx->opt, NULL, BPTR(buf));
227 if (!buf->len)
228 {
229 msg(D_TLS_ERRORS, "TLS Error: incoming packet authentication failed from %s",
231 goto cleanup;
232 }
233 }
234 else if (ctx->mode == TLS_WRAP_CRYPT)
235 {
237 if (!tls_crypt_unwrap(buf, &tmp, &ctx->opt))
238 {
239 msg(D_TLS_ERRORS, "TLS Error: tls-crypt unwrapping failed from %s",
241 goto cleanup;
242 }
243 ASSERT(buf_init(buf, buf->offset));
244 ASSERT(buf_copy(buf, &tmp));
245 buf_clear(&tmp);
246 }
247 else if (ctx->tls_crypt_v2_server_key.cipher)
248 {
249 /* If tls-crypt-v2 is enabled, require *some* wrapping */
250 msg(D_TLS_ERRORS, "TLS Error: could not determine wrapping from %s",
252 /* TODO Do we want to support using tls-crypt-v2 and no control channel
253 * wrapping at all simultaneously? That would allow server admins to
254 * upgrade clients one-by-one without running a second instance, but we
255 * should not enable it by default because it breaks DoS-protection.
256 * So, add something like --tls-crypt-v2-allow-insecure-fallback ? */
257 goto cleanup;
258 }
259
260 if (ctx->mode == TLS_WRAP_NONE || ctx->mode == TLS_WRAP_AUTH)
261 {
262 /* advance buffer pointer past opcode & session_id since our caller
263 * already read it */
264 buf_advance(buf, SID_SIZE + 1);
265 }
266
267 ret = true;
268cleanup:
269 gc_free(&gc);
270 return ret;
271}
272
273void
283
284/*
285 * This function is similar to tls_pre_decrypt, except it is called
286 * when we are in server mode and receive an initial incoming
287 * packet. Note that we don't modify any state in our parameter
288 * objects except state. The purpose is solely to
289 * determine whether we should generate a client instance
290 * object, in which case true is returned.
291 *
292 * This function is essentially the first-line HMAC firewall
293 * on the UDP port listener in --mode server mode.
294 */
297 const struct link_socket_actual *from, const struct buffer *buf)
298{
299 struct gc_arena gc = gc_new();
300 /* A packet needs to have at least an opcode and session id */
301 if (BLENZ(buf) < 1 + SID_SIZE)
302 {
303 dmsg(D_TLS_STATE_ERRORS, "TLS State Error: Too short packet (length %d) received from %s",
304 buf->len, print_link_socket_actual(from, &gc));
305 goto error;
306 }
307
308 /* get opcode and key ID */
309 uint8_t pkt_firstbyte = *CBPTR(buf);
310 int op = pkt_firstbyte >> P_OPCODE_SHIFT;
311 int key_id = pkt_firstbyte & P_KEY_ID_MASK;
312
313 /* this packet is from an as-yet untrusted source, so
314 * scrutinize carefully */
315
316 /* Allow only the reset packet or the first packet of the actual handshake. */
318 && op != P_CONTROL_V1 && op != P_CONTROL_WKC_V1 && op != P_ACK_V1)
319 {
320 /*
321 * This can occur due to bogus data or DoS packets.
322 */
323 dmsg(D_TLS_STATE_ERRORS, "TLS State Error: No TLS state for client %s, opcode=%d",
324 print_link_socket_actual(from, &gc), op);
325 goto error;
326 }
327
328 if (key_id != 0)
329 {
331 "TLS State Error: Unknown key ID (%d) received from %s -- 0 was expected", key_id,
333 goto error;
334 }
335
336 /* read peer session id, we do this at this point since
337 * read_control_auth will skip over it */
338 struct buffer tmp = *buf;
339 buf_advance(&tmp, 1);
340 if (!session_id_read(&state->peer_session_id, &tmp)
342 {
343 msg(D_TLS_ERRORS, "TLS Error: session-id not found in packet from %s",
345 goto error;
346 }
347
348 state->newbuf = clone_buf(buf);
349 state->tls_wrap_tmp = tas->tls_wrap;
350
351 /* HMAC test and unwrapping the encrypted part of the control message
352 * into newbuf or just setting newbuf to point to the start of control
353 * message */
354 bool status = read_control_auth(&state->newbuf, &state->tls_wrap_tmp, from, NULL);
355
356 if (!status)
357 {
358 goto error;
359 }
360
361 /*
362 * At this point, if --tls-auth is being used, we know that
363 * the packet has passed the HMAC test, but we don't know if
364 * it is a replay yet. We will attempt to defeat replays
365 * by not advancing to the S_START state until we
366 * receive an ACK from our first reply to the client
367 * that includes an HMAC of our randomly generated 64 bit
368 * session ID.
369 *
370 * On the other hand if --tls-auth is not being used, we
371 * will proceed to begin the TLS authentication
372 * handshake with only cursory integrity checks having
373 * been performed, since we will be leaving the task
374 * of authentication solely up to TLS.
375 */
376 gc_free(&gc);
377 if (op == P_CONTROL_V1)
378 {
380 }
381 else if (op == P_ACK_V1)
382 {
384 }
385 else if (op == P_CONTROL_HARD_RESET_CLIENT_V3)
386 {
388 }
389 else if (op == P_CONTROL_WKC_V1)
390 {
392 }
393 else
394 {
396 }
397
398error:
400 gc_free(&gc);
401 return VERDICT_INVALID;
402}
403
404
405struct buffer
407 const struct session_id *own_sid, const struct session_id *remote_sid,
408 uint8_t header, bool request_resend_wkc)
409{
410 /* Copy buffer here to point at the same data but allow tls_wrap_control
411 * to potentially change buf to point to another buffer without
412 * modifying the buffer in tas */
413 struct buffer buf = tas->workbuf;
414 ASSERT(buf_init(&buf, tas->frame.buf.headroom));
415
416 /* Reliable ACK structure */
417 /* Length of the ACK structure - 1 ACK */
418 buf_write_u8(&buf, 1);
419
420 /* ACKed packet - first packet's id is always 0 */
421 buf_write_u32(&buf, 0);
422
423 /* Remote session id */
424 buf_write(&buf, remote_sid->id, SID_SIZE);
425
426 /* Packet ID of our own packet: Our reset packet is always using
427 * packet id 0 since it is the first packet */
428 packet_id_type net_pid = htonpid(0);
429
430 ASSERT(buf_write(&buf, &net_pid, sizeof(net_pid)));
431
432 /* Add indication for tls-crypt-v2 to resend the WKc with the reply */
433 if (request_resend_wkc)
434 {
435 buf_write_u16(&buf, TLV_TYPE_EARLY_NEG_FLAGS); /* TYPE: flags */
436 buf_write_u16(&buf, sizeof(uint16_t));
438 }
439
440 /* Add tls-auth/tls-crypt wrapping, this might replace buf with
441 * ctx->work */
442 tls_wrap_control(ctx, header, &buf, own_sid);
443
444 return buf;
445}
446
447struct session_id
448calculate_session_id_hmac(struct session_id client_sid, const struct openvpn_sockaddr *from,
449 const uint8_t *key, int handwindow, int offset)
450{
451 /* Get the valid time quantisation for our hmac,
452 * we divide time by handwindow/2 and allow the previous
453 * and future session time if specified by offset */
454 uint32_t session_id_time = ntohl((uint32_t)(now / ((handwindow + 1) / 2) + offset));
455
456 uint8_t input[64];
457
458 /* ensure input array is large enough */
459 static_assert(sizeof(input) >= sizeof(struct sockaddr_in6) + sizeof(session_id_time) + sizeof(client_sid.id), "input buffer not sized correctly");
460 static_assert(sizeof(input) >= sizeof(struct sockaddr_in) + sizeof(session_id_time) + sizeof(client_sid.id), "input buffer not sized correctly");
461
462 struct buffer in = { 0 };
463 buf_set_write(&in, input, sizeof(input));
464
465 /* We do not care about endian here since it does not need to be
466 * portable */
467 buf_write(&in, (const uint8_t *)&session_id_time, sizeof(session_id_time));
468
469 /* add client IP and port */
470 switch (from->addr.sa.sa_family)
471 {
472 case AF_INET:
473 buf_write(&in, (const uint8_t *)&from->addr.in4, sizeof(struct sockaddr_in));
474 break;
475
476 case AF_INET6:
477 buf_write(&in, (const uint8_t *)&from->addr.in6, sizeof(struct sockaddr_in6));
478 break;
479 }
480
481 /* add session id of client */
482 buf_write(&in, client_sid.id, SID_SIZE);
483
484 struct session_id sid;
485 siphash(buf_bptr(&in), buf_len(&in), key, sid.id, sizeof(sid.id));
486
487 return sid;
488}
489
490bool
492 const struct openvpn_sockaddr *from,
493 const uint8_t *key,
494 int handwindow,
495 bool pkt_is_ack)
496{
497 if (!from)
498 {
499 return false;
500 }
501
502 struct buffer buf = state->newbuf;
503 struct reliable_ack ack;
504
505 if (!reliable_ack_parse(&buf, &ack, &state->server_session_id))
506 {
507 return false;
508 }
509
510 /* Check if the packet ID of the packet or ACKED packet is <= 1 */
511 for (int i = 0; i < ack.len; i++)
512 {
513 /* This packet ACKs a packet that has a higher packet id than the
514 * ones expected in the three-way handshake, consider it as invalid
515 * for the session */
516 if (ack.packet_id[i] > 1)
517 {
518 return false;
519 }
520 }
521
522 if (!pkt_is_ack)
523 {
524 packet_id_type message_id;
525 /* Extract the packet ID from the packet */
526 if (!reliable_ack_read_packet_id(&buf, &message_id))
527 {
528 return false;
529 }
530
531 /* similar check. Anything larger than 1 is not considered part of the
532 * three-way handshake */
533 if (message_id > 1)
534 {
535 return false;
536 }
537 }
538
539
540 /* check adjacent timestamps too, the handwindow is split in 2 for the
541 * offset, so we check the current timeslot and the two before that */
542 for (int offset = -2; offset <= 0; offset++)
543 {
544 struct session_id expected_id =
545 calculate_session_id_hmac(state->peer_session_id, from, key, handwindow, offset);
546
547 if (memcmp_constant_time(&expected_id, &state->server_session_id, SID_SIZE) == 0)
548 {
549 return true;
550 }
551 }
552 return false;
553}
554
555struct buffer
557{
558 /* commands on the control channel are seperated by 0x00 bytes.
559 * cmdlen does not include the 0 byte of the string */
560 int cmdlen = (int)strnlen(BSTR(buf), BLENZ(buf));
561
562 if (cmdlen >= BLEN(buf))
563 {
564 buf_advance(buf, cmdlen);
565 /* Return empty buffer */
566 struct buffer empty = { 0 };
567 return empty;
568 }
569
570 /* include the NUL byte and ensure NUL termination */
571 cmdlen += 1;
572
573 /* Construct a buffer that only holds the current command and
574 * its closing NUL byte */
575 struct buffer cmdbuf = alloc_buf_gc(cmdlen, gc);
576 buf_write(&cmdbuf, BPTR(buf), cmdlen);
577
578 /* Remove \r and \n at the end of the buffer to avoid
579 * problems with scripts and other that add extra \r and \n */
580 buf_chomp(&cmdbuf);
581
582 /* check we have only printable characters or null byte in the
583 * command string and no newlines */
584 if (!string_check_buf(&cmdbuf, CC_PRINT | CC_NULL, CC_CRLF))
585 {
586 msg(D_PUSH_ERRORS, "WARNING: Received control with invalid characters: %s",
587 format_hex(BPTR(&cmdbuf), BLEN(&cmdbuf), 256, gc));
588 cmdbuf.len = 0;
589 }
590
591 buf_advance(buf, cmdlen);
592 return cmdbuf;
593}
void free_buf(struct buffer *buf)
Free the memory allocated for a buffer.
Definition buffer.c:169
void buf_clear(struct buffer *buf)
Zeroise and reset a buffer.
Definition buffer.c:148
struct buffer clone_buf(const struct buffer *buf)
Duplicate a buffer, including its content.
Definition buffer.c:99
struct buffer alloc_buf_gc(size_t size, struct gc_arena *gc)
Allocate a buffer of the given size under garbage collection.
Definition buffer.c:77
void buf_chomp(struct buffer *buf)
Remove trailing newline and carriage-return characters from a buffer.
Definition buffer.c:522
bool string_check_buf(const struct buffer *buf, const unsigned int inclusive, const unsigned int exclusive)
Check a buffer if it only consists of allowed characters.
Definition buffer.c:1028
static bool buf_write_u16(struct buffer *dest, uint16_t data)
Append a uint16_t to a buffer in network byte order.
Definition buffer.h:1320
static uint8_t * buf_bptr(struct buffer *buf)
Return a pointer to the start of the buffer content.
Definition buffer.h:449
#define BSTR(buf)
Return the buffer content pointer cast to char *.
Definition buffer.h:157
static struct buffer clear_buf(void)
Return an empty, undefined struct buffer (all fields zero).
Definition buffer.h:384
static bool buf_copy(struct buffer *dest, const struct buffer *src)
Copy the content of one buffer to the end of another.
Definition buffer.h:1365
#define BPTR(buf)
Return a pointer to the start of the buffer content.
Definition buffer.h:139
static bool buf_write_u32(struct buffer *dest, uint32_t data)
Append a uint32_t to a buffer in network byte order.
Definition buffer.h:1335
static bool buf_write_prepend(struct buffer *dest, const void *src, int size)
Prepend data to a buffer.
Definition buffer.h:1286
#define CC_CRLF
carriage return or newline
Definition buffer.h:1737
static void buf_set_write(struct buffer *buf, uint8_t *data, int size)
Initialise a buffer with an externally provided writable memory region.
Definition buffer.h:658
static int buf_len(const struct buffer *buf)
Return the length of the buffer content.
Definition buffer.h:462
#define CBPTR(buf)
Return a const pointer to the start of the buffer content.
Definition buffer.h:141
static void secure_memzero(void *data, size_t len)
Securely zeroise memory.
Definition buffer.h:769
static bool buf_advance(struct buffer *buf, ssize_t size)
Advance the content start of a buffer, consuming bytes from the front.
Definition buffer.h:1188
static bool buf_write(struct buffer *dest, const void *src, size_t size)
Append data to a buffer.
Definition buffer.h:1262
static bool buf_write_u8(struct buffer *dest, uint8_t data)
Append a uint8_t to a buffer.
Definition buffer.h:1306
#define BLEN(buf)
Return the length of the buffer content in bytes.
Definition buffer.h:151
static char * format_hex(const uint8_t *data, size_t size, size_t maxoutput, struct gc_arena *gc)
Format a binary buffer as a hex string with spaces every 4 bytes.
Definition buffer.h:983
#define BLENZ(buf)
Return the length of the buffer content as a size_t.
Definition buffer.h:153
#define CC_NULL
null character \0
Definition buffer.h:1701
static void gc_free(struct gc_arena *a)
Free all allocations in a garbage collection arena.
Definition buffer.h:1976
#define CC_PRINT
printable (>= 32, != 127)
Definition buffer.h:1708
#define buf_init(buf, offset)
Definition buffer.h:364
static struct gc_arena gc_new(void)
Allocate and return a new, empty garbage collection arena.
Definition buffer.h:1960
static int buf_forward_capacity_total(const struct buffer *buf)
Return the total number of bytes available from the current offset to the end of the allocated memory...
Definition buffer.h:1090
void free_key_ctx_bi(struct key_ctx_bi *ctx)
Definition crypto.c:1100
Data Channel Cryptography Module.
#define CO_USE_TLS_KEY_MATERIAL_EXPORT
Bit-flag indicating that data channel key derivation is done using TLS keying material export [RFC570...
Definition crypto.h:359
int memcmp_constant_time(const void *a, const void *b, size_t size)
As memcmp(), but constant-time.
int hmac_ctx_size(hmac_ctx_t *ctx)
#define D_TLS_STATE_ERRORS
Definition errlevel.h:133
#define D_PUSH_ERRORS
Definition errlevel.h:66
#define D_TLS_ERRORS
Definition errlevel.h:58
#define D_TLS_DEBUG
Definition errlevel.h:164
enum first_packet_verdict tls_pre_decrypt_lite(const struct tls_auth_standalone *tas, struct tls_pre_decrypt_state *state, const struct link_socket_actual *from, const struct buffer *buf)
Inspect an incoming packet for which no VPN tunnel is active, and determine whether a new VPN tunnel ...
Definition ssl_pkt.c:296
void openvpn_encrypt(struct buffer *buf, struct buffer work, struct crypto_options *opt)
Encrypt and HMAC sign a packet so that it can be sent as a data channel VPN tunnel packet to a remote...
Definition crypto.c:329
bool openvpn_decrypt(struct buffer *buf, struct buffer work, struct crypto_options *opt, const struct frame *frame, const uint8_t *ad_start)
HMAC verify and decrypt a data channel packet received from a remote OpenVPN peer.
Definition crypto.c:779
bool reliable_ack_read_packet_id(struct buffer *buf, packet_id_type *pid)
Read the packet ID of a received packet.
Definition reliable.c:76
bool reliable_ack_parse(struct buffer *buf, struct reliable_ack *ack, struct session_id *session_id_remote)
Parse an acknowledgment record from a received packet.
Definition reliable.c:133
bool reliable_ack_write(struct reliable_ack *ack, struct reliable_ack *ack_mru, struct buffer *buf, const struct session_id *sid, int max, bool prepend)
Write a packet ID acknowledgment record to a buffer.
Definition reliable.c:215
bool tls_crypt_v2_extract_client_key(struct buffer *buf, struct tls_wrap_ctx *ctx, const struct tls_options *opt)
Extract a tls-crypt-v2 client key from a P_CONTROL_HARD_RESET_CLIENT_V3 message, and load the key int...
Definition tls_crypt.c:610
bool tls_crypt_unwrap(const struct buffer *src, struct buffer *dst, struct crypto_options *opt)
Unwrap a control channel packet (decrypts, authenticates and performs replay checks).
Definition tls_crypt.c:211
bool tls_crypt_wrap(const struct buffer *src, struct buffer *dst, struct crypto_options *opt)
Wrap a control channel packet (both authenticates and encrypts the data).
Definition tls_crypt.c:138
static int min_int(int x, int y)
Definition integer.h:105
static SERVICE_STATUS status
Definition interactive.c:52
#define dmsg(flags,...)
Definition error.h:164
#define msg(flags,...)
Definition error.h:152
#define ASSERT(x)
Definition error.h:221
time_t now
Definition otime.c:33
#define htonpid(x)
Definition packet_id.h:61
uint32_t packet_id_type
Definition packet_id.h:45
static int packet_id_size(bool long_form)
Definition packet_id.h:322
Reliability Layer module header file.
static bool session_id_write_prepend(const struct session_id *sid, struct buffer *buf)
Definition session_id.h:65
static bool session_id_write(const struct session_id *sid, struct buffer *buf)
Definition session_id.h:71
static bool session_id_defined(const struct session_id *sid1)
Definition session_id.h:53
static bool session_id_read(struct session_id *sid, struct buffer *buf)
Definition session_id.h:59
#define SID_SIZE
Definition session_id.h:44
static void siphash(const void *in, size_t inlen, const void *k, uint8_t *out, size_t outlen)
Definition siphash.h:70
const char * print_link_socket_actual(const struct link_socket_actual *act, struct gc_arena *gc)
static bool link_socket_actual_defined(const struct link_socket_actual *act)
void tls_clear_error(void)
Clear the underlying SSL library's error state.
Control Channel Common Data Structures.
bool check_session_hmac_and_pkt_id(struct tls_pre_decrypt_state *state, const struct openvpn_sockaddr *from, const uint8_t *key, int handwindow, bool pkt_is_ack)
Checks if a control packet has a correct HMAC server session id.
Definition ssl_pkt.c:491
struct buffer tls_reset_standalone(struct tls_wrap_ctx *ctx, const struct tls_auth_standalone *tas, const struct session_id *own_sid, const struct session_id *remote_sid, uint8_t header, bool request_resend_wkc)
This function creates a reset packet using the information from the tls pre decrypt state.
Definition ssl_pkt.c:406
void free_tls_pre_decrypt_state(struct tls_pre_decrypt_state *state)
Definition ssl_pkt.c:274
void write_control_auth(struct tls_session *session, struct key_state *ks, struct buffer *buf, struct link_socket_actual **to_link_addr, int opcode, int max_ack, bool prepend_ack)
Definition ssl_pkt.c:166
static bool swap_hmac(struct buffer *buf, const struct crypto_options *co, bool incoming)
Move a packet authentication HMAC + related fields to or from the front of the buffer so it can be pr...
Definition ssl_pkt.c:61
struct buffer extract_command_buffer(struct buffer *buf, struct gc_arena *gc)
Extracts a control channel message from buf and adjusts the size of buf after the message has been ex...
Definition ssl_pkt.c:556
#define SWAP_BUF_SIZE
Definition ssl_pkt.c:41
static void tls_wrap_control(struct tls_wrap_ctx *ctx, uint8_t header, struct buffer *buf, const struct session_id *session_id)
Wraps a TLS control packet by adding tls-auth HMAC or tls-crypt(-v2) encryption and opcode header inc...
Definition ssl_pkt.c:121
bool read_control_auth(struct buffer *buf, struct tls_wrap_ctx *ctx, const struct link_socket_actual *from, const struct tls_options *opt)
Read a control channel authentication record.
Definition ssl_pkt.c:196
struct session_id calculate_session_id_hmac(struct session_id client_sid, const struct openvpn_sockaddr *from, const uint8_t *key, int handwindow, int offset)
Calculates the HMAC based server session id based on a client session id and socket addr.
Definition ssl_pkt.c:448
SSL control channel wrap/unwrap and decode functions.
#define EARLY_NEG_FLAG_RESEND_WKC
Definition ssl_pkt.h:314
#define P_OPCODE_SHIFT
Definition ssl_pkt.h:39
#define TLV_TYPE_EARLY_NEG_FLAGS
Definition ssl_pkt.h:313
#define P_ACK_V1
Definition ssl_pkt.h:46
#define P_CONTROL_WKC_V1
Definition ssl_pkt.h:59
#define P_KEY_ID_MASK
Definition ssl_pkt.h:38
static const char * packet_opcode_name(int op)
Definition ssl_pkt.h:232
#define P_CONTROL_V1
Definition ssl_pkt.h:45
first_packet_verdict
Definition ssl_pkt.h:85
@ VERDICT_VALID_ACK_V1
This packet is a valid ACK control packet from the peer, i.e.
Definition ssl_pkt.h:94
@ VERDICT_VALID_WKC_V1
The packet is a valid control packet with appended wrapped client key.
Definition ssl_pkt.h:96
@ VERDICT_VALID_RESET_V2
This packet is a valid reset packet from the peer (all but tls-crypt-v2).
Definition ssl_pkt.h:87
@ VERDICT_INVALID
the packet failed on of the various checks
Definition ssl_pkt.h:98
@ VERDICT_VALID_RESET_V3
This is a valid v3 reset (tls-crypt-v2).
Definition ssl_pkt.h:89
@ VERDICT_VALID_CONTROL_V1
This packet is a valid control packet from the peer.
Definition ssl_pkt.h:91
#define P_LAST_OPCODE
Definition ssl_pkt.h:65
#define P_CONTROL_HARD_RESET_CLIENT_V2
Definition ssl_pkt.h:51
static struct tls_wrap_ctx * tls_session_get_tls_wrap(struct tls_session *session, int key_id)
Determines if the current session should use the renegotiation tls wrap struct instead the normal one...
Definition ssl_pkt.h:283
#define P_CONTROL_HARD_RESET_CLIENT_V3
Definition ssl_pkt.h:55
SSL utility functions.
Wrapper structure for dynamically allocated memory.
Definition buffer.h:71
int len
Length in bytes of the actual content within the allocated memory.
Definition buffer.h:76
int offset
Offset in bytes of the actual content within the allocated memory.
Definition buffer.h:74
Security parameter state for processing data channel packets.
Definition crypto.h:293
struct key_ctx_bi key_ctx_bi
OpenSSL cipher and HMAC contexts for both sending and receiving directions.
Definition crypto.h:294
struct frame::@074234134026241341315172337061247271261307273127 buf
int headroom
the headroom in the buffer, this is choosen to allow all potential header to be added before the pack...
Definition mtu.h:124
Garbage collection arena used to keep track of dynamically allocated memory.
Definition buffer.h:127
struct key_ctx decrypt
cipher and/or HMAC contexts for receiving direction.
Definition crypto.h:283
struct key_ctx encrypt
Cipher and/or HMAC contexts for sending direction.
Definition crypto.h:281
Container for one set of cipher and/or HMAC contexts.
Definition crypto.h:202
cipher_ctx_t * cipher
Generic cipher context.
Definition crypto.h:203
hmac_ctx_t * hmac
Generic HMAC context.
Definition crypto.h:204
Security parameter state of one TLS and data channel key session.
Definition ssl_common.h:208
struct link_socket_actual remote_addr
Definition ssl_common.h:235
struct reliable_ack * rec_ack
Definition ssl_common.h:247
struct session_id session_id_remote
Definition ssl_common.h:234
int key_id
Key id for this key_state, inherited from struct tls_session.
Definition ssl_common.h:217
struct reliable_ack * lru_acks
Definition ssl_common.h:248
Container for unidirectional cipher and HMAC key material.
Definition crypto.h:152
The acknowledgment structure in which packet IDs are stored for later acknowledgment.
Definition reliable.h:75
packet_id_type packet_id[RELIABLE_ACK_SIZE]
Definition reliable.h:77
uint8_t id[8]
Definition session_id.h:39
struct frame frame
Definition ssl_pkt.h:81
struct buffer workbuf
Definition ssl_pkt.h:80
struct tls_wrap_ctx tls_wrap
Definition ssl_pkt.h:79
struct that stores the temporary data for the tls lite decrypt functions
Definition ssl_pkt.h:106
struct session_id peer_session_id
Definition ssl_pkt.h:109
struct session_id server_session_id
Definition ssl_pkt.h:110
struct buffer newbuf
Definition ssl_pkt.h:108
struct tls_wrap_ctx tls_wrap_tmp
Definition ssl_pkt.h:107
Security parameter state of a single session within a VPN tunnel.
Definition ssl_common.h:489
Control channel wrapping (–tls-auth/–tls-crypt) context.
Definition ssl_common.h:276
enum tls_wrap_ctx::@317033145106102005365073042374303036003032271350 mode
Control channel wrapping mode.
bool cleanup_key_ctx
opt.key_ctx_bi is owned by this context
Definition ssl_common.h:288
struct crypto_options opt
Crypto state.
Definition ssl_common.h:283
struct buffer work
Work buffer (only for –tls-crypt).
Definition ssl_common.h:284
struct key_ctx tls_crypt_v2_server_key
Decrypts client keys.
Definition ssl_common.h:285
const struct buffer * tls_crypt_v2_wkc
Wrapped client key, sent to server.
Definition ssl_common.h:286
struct key2 original_wrap_keydata
original key data to be xored in to the key for dynamic tls-crypt.
Definition ssl_common.h:298
static int cleanup(void **state)
struct gc_arena gc
Definition test_ssl.c:122