OpenVPN
ssl_ncp.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 * Copyright (C) 2010-2026 Sentyron B.V. <openvpn@sentyron.com>
10 * Copyright (C) 2008-2026 David Sommerseth <dazo@eurephia.org>
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License version 2
14 * as published by the Free Software Foundation.
15 *
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
20 *
21 * You should have received a copy of the GNU General Public License along
22 * with this program; if not, see <https://www.gnu.org/licenses/>.
23 */
24
31/*
32 * The routines in this file deal with dynamically negotiating
33 * the data channel HMAC and cipher keys through a TLS session.
34 *
35 * Both the TLS session and the data channel are multiplexed
36 * over the same TCP/UDP port.
37 */
38#ifdef HAVE_CONFIG_H
39#include "config.h"
40#endif
41
42#include <string.h>
43
44#include "syshead.h"
45#include "win32.h"
46
47#include "error.h"
48#include "common.h"
49
50#include "ssl_ncp.h"
51#include "ssl_util.h"
52#include "openvpn.h"
53
58static unsigned int
59tls_peer_info_ncp_ver(const char *peer_info)
60{
61 return peer_info_extract_uint(peer_info, "IV_NCP=");
62}
63
68bool
69tls_peer_supports_ncp(const char *peer_info)
70{
71 if (!peer_info)
72 {
73 return false;
74 }
75 else if (tls_peer_info_ncp_ver(peer_info) >= 2 || strstr(peer_info, "IV_CIPHERS="))
76 {
77 return true;
78 }
79 else
80 {
81 return false;
82 }
83}
84
85char *
86mutate_ncp_cipher_list(const char *list, struct gc_arena *gc)
87{
88 bool error_found = false;
89
91
92 char *const tmp_ciphers = string_alloc(list, NULL);
93 char *lasts = NULL;
94 const char *token = strtok_r(tmp_ciphers, ":", &lasts);
95 while (token)
96 {
97 /*
98 * Going cipher_kt_name (and translate_cipher_name_from_openvpn/
99 * translate_cipher_name_to_openvpn) also normalises the cipher name,
100 * e.g. replacing AeS-128-gCm with AES-128-GCM
101 *
102 * ciphers that have ? in front of them are considered optional and
103 * OpenVPN will only warn if they are not found (and remove them from
104 * the list)
105 */
106 bool optional = false;
107 if (token[0] == '?')
108 {
109 token++;
110 optional = true;
111 }
112
113 const bool nonecipher = (strcmp(token, "none") == 0);
114 const char *optstr = optional ? "optional " : "";
115
116 if (nonecipher)
117 {
118 msg(M_WARN, "WARNING: cipher 'none' specified for --data-ciphers. "
119 "This allows negotiation of NO encryption and "
120 "tunnelled data WILL then be transmitted in clear text "
121 "over the network! "
122 "PLEASE DO RECONSIDER THIS SETTING!");
123 }
124 if (!nonecipher && !cipher_valid(token))
125 {
126 msg(M_WARN, "Unsupported %scipher in --data-ciphers: %s", optstr, token);
128 }
131 {
132 msg(M_WARN,
133 "Unsupported %scipher algorithm '%s'. It does not use "
134 "CFB, OFB, CBC, or a supported AEAD mode",
135 optstr, token);
137 }
138 else
139 {
141 if (nonecipher)
142 {
143 /* NULL resolves to [null-cipher] but we need none for
144 * data-ciphers */
145 ovpn_cipher_name = "none";
146 }
147
148 if (buf_len(&new_list) > 0)
149 {
150 /* The next if condition ensure there is always space for
151 * a :
152 */
153 buf_puts(&new_list, ":");
154 }
155
156 /* Ensure buffer has capacity for cipher name + : + \0 */
158 {
159 msg(M_WARN, "Length of --data-ciphers is over the "
160 "limit of 127 chars");
161 error_found = true;
162 }
163 else
164 {
166 }
167 }
168 token = strtok_r(NULL, ":", &lasts);
169 }
170
171
172 char *ret = NULL;
173 if (!error_found && buf_len(&new_list) > 0)
174 {
177 }
178 free(tmp_ciphers);
180
181 return ret;
182}
183
184
185void
186append_cipher_to_ncp_list(struct options *o, const char *ciphername)
187{
188 /* Append the --cipher to ncp_ciphers to allow it in NCP */
189 size_t newlen = strlen(o->ncp_ciphers) + 1 + strlen(ciphername) + 1;
190 char *ncp_ciphers = gc_malloc(newlen, false, &o->gc);
191
192 ASSERT(checked_snprintf(ncp_ciphers, newlen, "%s:%s", o->ncp_ciphers, ciphername));
193 o->ncp_ciphers = ncp_ciphers;
194}
195
196bool
197tls_item_in_cipher_list(const char *item, const char *list)
198{
199 char *tmp_ciphers = string_alloc(list, NULL);
201 char *lasts = NULL;
202
203 const char *token = strtok_r(tmp_ciphers, ":", &lasts);
204 while (token)
205 {
206 if (0 == strcmp(token, item))
207 {
208 break;
209 }
210 token = strtok_r(NULL, ":", &lasts);
211 }
212 free(tmp_ciphers_orig);
213
214 return token != NULL;
215}
216const char *
217tls_peer_ncp_list(const char *peer_info, struct gc_arena *gc)
218{
219 /* Check if the peer sends the IV_CIPHERS list */
220 const char *iv_ciphers = extract_var_peer_info(peer_info, "IV_CIPHERS=", gc);
221 if (iv_ciphers)
222 {
223 return iv_ciphers;
224 }
225 else if (tls_peer_info_ncp_ver(peer_info) >= 2)
226 {
227 /* If the peer announces IV_NCP=2 then it supports the AES GCM
228 * ciphers */
229 return "AES-256-GCM:AES-128-GCM";
230 }
231 else
232 {
233 return "";
234 }
235}
236
237char *
238ncp_get_best_cipher(const char *server_list, const char *peer_info, const char *remote_cipher,
239 struct gc_arena *gc)
240{
241 /*
242 * The gc of the parameter is tied to the VPN session, create a
243 * short lived gc arena that is only valid for the duration of
244 * this function
245 */
246
247 struct gc_arena gc_tmp = gc_new();
248
249 const char *peer_ncp_list = tls_peer_ncp_list(peer_info, &gc_tmp);
250
251 /* non-NCP clients without OCC? "assume nothing" */
252 /* For client doing the newer version of NCP (that send IV_CIPHERS)
253 * we cannot assume that they will accept remote_cipher */
254 if (remote_cipher == NULL || (peer_info && strstr(peer_info, "IV_CIPHERS=")))
255 {
256 remote_cipher = "";
257 }
258
259 char *tmp_ciphers = string_alloc(server_list, &gc_tmp);
260
261 const char *token;
262 while ((token = strsep(&tmp_ciphers, ":")))
263 {
264 if (tls_item_in_cipher_list(token, peer_ncp_list) || streq(token, remote_cipher))
265 {
266 break;
267 }
268 }
269
270 char *ret = NULL;
271 if (token != NULL)
272 {
273 ret = string_alloc(token, gc);
274 }
275
276 gc_free(&gc_tmp);
277 return ret;
278}
279
289static bool
290tls_poor_mans_ncp(struct options *o, const char *remote_ciphername)
291{
292 if (remote_ciphername && tls_item_in_cipher_list(remote_ciphername, o->ncp_ciphers))
293 {
294 o->ciphername = string_alloc(remote_ciphername, &o->gc);
295 msg(D_TLS_DEBUG_LOW, "Using peer cipher '%s'", o->ciphername);
296 return true;
297 }
298 return false;
299}
300
301bool
302check_pull_client_ncp(struct context *c, const uint64_t found)
303{
304 if (found & OPT_P_NCP)
305 {
306 msg(D_PUSH_DEBUG, "OPTIONS IMPORT: data channel crypto options modified");
307 return true;
308 }
309
310 /* If the server did not push a --cipher, we will switch to the
311 * remote cipher if it is in our ncp-ciphers list */
313 {
314 return true;
315 }
316
317 /* We could not figure out the peer's cipher but we have fallback
318 * enabled */
320 {
321 return true;
322 }
323
324 /* We failed negotiation, give appropriate error message */
326 {
328 "OPTIONS ERROR: failed to negotiate "
329 "cipher with server. Add the server's "
330 "cipher ('%s') to --data-ciphers (currently '%s'), e.g."
331 "--data-ciphers %s:%s if you want to connect to this server.",
334 return false;
335 }
336 else
337 {
338 msg(D_TLS_ERRORS, "OPTIONS ERROR: failed to negotiate "
339 "cipher with server. Configure "
340 "--data-ciphers-fallback if you want to connect "
341 "to this server.");
342 return false;
343 }
344}
345
346const char *
347get_p2p_ncp_cipher(struct tls_session *session, const char *peer_info, struct gc_arena *gc)
348{
349 /* we use a local gc arena to keep the temporary strings needed by strsep */
350 struct gc_arena gc_local = gc_new();
351 const char *peer_ciphers = extract_var_peer_info(peer_info, "IV_CIPHERS=", &gc_local);
352
353 if (!peer_ciphers)
354 {
355 gc_free(&gc_local);
356 return NULL;
357 }
358
359 const char *server_ciphers;
360 const char *client_ciphers;
361
362 if (session->opt->server)
363 {
364 server_ciphers = session->opt->config_ncp_ciphers;
365 client_ciphers = peer_ciphers;
366 }
367 else
368 {
369 client_ciphers = session->opt->config_ncp_ciphers;
370 server_ciphers = peer_ciphers;
371 }
372
373 /* Find the first common cipher from TLS server and TLS client. We
374 * use the preference of the server here to make it deterministic */
375 char *tmp_ciphers = string_alloc(server_ciphers, &gc_local);
376
377 const char *token;
378 while ((token = strsep(&tmp_ciphers, ":")))
379 {
380 if (tls_item_in_cipher_list(token, client_ciphers))
381 {
382 break;
383 }
384 }
385
386 const char *ret = NULL;
387 if (token != NULL)
388 {
389 ret = string_alloc(token, gc);
390 }
391 gc_free(&gc_local);
392
393 return ret;
394}
395
396static void
397p2p_ncp_set_options(struct tls_multi *multi, struct tls_session *session, const char *common_cipher)
398{
399 /* will return 0 if peer_info is null */
400 const unsigned int iv_proto_peer = extract_iv_proto(multi->peer_info);
401 const unsigned int tx_peer_id = extract_asymmetric_peer_id(multi->peer_info);
402
403 /* The other peer does not support P2P NCP */
404 if (!(iv_proto_peer & IV_PROTO_NCP_P2P))
405 {
406 return;
407 }
408
409 if (iv_proto_peer & IV_PROTO_DATA_V2)
410 {
411 multi->use_peer_id = true;
412 }
413
414 if (iv_proto_peer & IV_PROTO_CC_EXIT_NOTIFY)
415 {
416 session->opt->crypto_flags |= CO_USE_CC_EXIT_NOTIFY;
417 }
418
419 if (session->opt->data_epoch_supported && (iv_proto_peer & IV_PROTO_DATA_EPOCH) && common_cipher
420 && cipher_kt_mode_aead(common_cipher))
421 {
422 session->opt->crypto_flags |= CO_EPOCH_DATA_KEY_FORMAT;
423 }
424 else
425 {
426 /* The peer might have changed its ciphers options during reconnect,
427 * ensure we clear the flag if we previously had it enabled */
428 session->opt->crypto_flags &= ~CO_EPOCH_DATA_KEY_FORMAT;
429 }
430
431 if (iv_proto_peer & IV_PROTO_TLS_KEY_EXPORT)
432 {
433 session->opt->crypto_flags |= CO_USE_TLS_KEY_MATERIAL_EXPORT;
434 }
435
436 if (multi->use_peer_id)
437 {
438 /* The asymmetric peer-id trumps on the EKM generated ones */
439 if ((iv_proto_peer & IV_PROTO_TLS_KEY_EXPORT)
440 && (tx_peer_id != MAX_PEER_ID) && !multi->opt.dco_enabled)
441 {
442 multi->tx_peer_id = tx_peer_id;
443 multi->use_asymmetric_peer_id = true;
444 }
445 else
446 {
447 uint8_t peerid[3];
448 /* Using a non hardcoded peer-id makes a tiny bit harder to
449 * fingerprint packets and also gives each connection a unique
450 * peer-id that can be useful for NAT tracking etc. */
451 if ((iv_proto_peer & IV_PROTO_TLS_KEY_EXPORT)
453 strlen(EXPORT_P2P_PEERID_LABEL), &peerid, 3))
454 {
455 multi->rx_peer_id = (peerid[0] << 16) + (peerid[1] << 8) + peerid[2];
456 }
457 else
458 {
459 if (iv_proto_peer & IV_PROTO_TLS_KEY_EXPORT)
460 {
461 /* Non DCO setup might still work but also this should never
462 * happen or very likely the TLS encryption key exporter will
463 * also fail */
464 msg(M_NONFATAL, "TLS key export for P2P peer id failed. "
465 "Continuing anyway, expect problems");
466 }
467 multi->rx_peer_id = 0x76706e; /* 'v' 'p' 'n' */
468 }
469 multi->tx_peer_id = multi->rx_peer_id;
470 }
471 }
472 if (iv_proto_peer & IV_PROTO_DYN_TLS_CRYPT)
473 {
474 session->opt->crypto_flags |= CO_USE_DYNAMIC_TLS_CRYPT;
475 }
476}
477
478void
480{
481 struct gc_arena gc = gc_new();
482
483 /* Query the common cipher here to log it as part of our message.
484 * We postpone switching the cipher to do_up */
485 const char *common_cipher = get_p2p_ncp_cipher(session, multi->peer_info, &gc);
486
487 /* Set the common options */
488 p2p_ncp_set_options(multi, session, common_cipher);
489
490 if (!common_cipher)
491 {
492 struct buffer out = alloc_buf_gc(128, &gc);
493 /* at this point we do not really know if our fallback is
494 * not enabled or if we use 'none' cipher as fallback, so
495 * keep this ambiguity here and print fallback-cipher: none
496 */
497
498 const char *fallback_name = "none";
499 const char *ciphername = session->opt->key_type.cipher;
500
501 if (cipher_defined(ciphername))
502 {
503 fallback_name = cipher_kt_name(ciphername);
504 }
505
506 buf_printf(&out, "(not negotiated, fallback-cipher: %s)", fallback_name);
507 common_cipher = BSTR(&out);
508 }
509
510 msg(D_TLS_DEBUG_LOW, "P2P mode NCP negotiation result: "
511 "TLS_export=%d, DATA_v2=%d, rx-peer-id %d, tx-peer-id %d, epoch=%d, cipher=%s",
512 (bool)(session->opt->crypto_flags & CO_USE_TLS_KEY_MATERIAL_EXPORT),
513 multi->use_peer_id,
514 multi->rx_peer_id,
515 multi->tx_peer_id,
516 (bool)(session->opt->crypto_flags & CO_EPOCH_DATA_KEY_FORMAT),
518
519 gc_free(&gc);
520}
521
522
523bool
525{
527 options->enable_ncp_fallback && streq(options->ciphername, session->opt->config_ciphername);
528
529 if (!session->opt->server && !cipher_allowed_as_fallback
531 {
532 struct gc_arena gc = gc_new();
533 msg(D_TLS_ERRORS, "Error: negotiated cipher not allowed - %s not in %s%s",
535 /* undo cipher push, abort connection setup */
536 options->ciphername = session->opt->config_ciphername;
537 gc_free(&gc);
538 return false;
539 }
540 else
541 {
542 return true;
543 }
544}
545
552static void
553replace_default_in_ncp_ciphers_option(struct options *o, const char *replace)
554{
555 const char *search = "DEFAULT";
556 const size_t ncp_ciphers_len = strlen(o->ncp_ciphers) + strlen(replace) - strlen(search) + 1;
557
558 uint8_t *ncp_ciphers = gc_malloc(ncp_ciphers_len, true, &o->gc);
559
560 struct buffer ncp_ciphers_buf;
562 buf_set_write(&ncp_ciphers_buf, ncp_ciphers, (int)ncp_ciphers_len);
563
564 const char *def = strstr(o->ncp_ciphers, search);
565
566 /* Copy everything before the DEFAULT string */
567 buf_write(&ncp_ciphers_buf, o->ncp_ciphers, def - o->ncp_ciphers);
568
569 /* copy the default string. */
571
572 /* copy the rest of the ncp cipher string */
573 const char *after_default = def + strlen(search);
575
576 o->ncp_ciphers = (char *)ncp_ciphers;
577}
578
584void
586{
588 o->ncp_ciphers && tls_item_in_cipher_list("DEFAULT", o->ncp_ciphers);
589
590 /* preserve the values that the user put into the configuration */
591 o->ncp_ciphers_conf = o->ncp_ciphers;
592
593 /* check if crypto library supports chacha */
594 bool can_do_chacha = cipher_valid("CHACHA20-POLY1305");
595
597 {
598 /* also make sure that dco supports chacha */
600 }
601
602 const char *default_ciphers = "AES-256-GCM:AES-128-GCM:CHACHA20-POLY1305";
603
604 if (!can_do_chacha)
605 {
606 default_ciphers = "AES-256-GCM:AES-128-GCM";
607 }
608
609 /* want to rather print DEFAULT instead of a manually set default list */
610 if (!o->ncp_ciphers_conf || !strcmp(default_ciphers, o->ncp_ciphers_conf))
611 {
612 o->ncp_ciphers = default_ciphers;
613 o->ncp_ciphers_conf = "DEFAULT";
614 }
615 else if (!default_in_cipher_list)
616 {
617 /* custom cipher list without DEFAULT string in it,
618 * nothing to replace/mutate */
619 return;
620 }
621 else
622 {
624 }
625}
626
627const char *
629{
630 if (!strcmp(o->ncp_ciphers, o->ncp_ciphers_conf))
631 {
632 /* expanded ciphers and user set ciphers are identical, no need to
633 * add an expanded version */
634 return "";
635 }
636
637 /* two extra brackets, one space, NUL byte */
638 struct buffer expanded_ciphers_buf = alloc_buf_gc(strlen(o->ncp_ciphers) + 4, gc);
639
640 buf_printf(&expanded_ciphers_buf, " (%s)", o->ncp_ciphers);
641 return BSTR(&expanded_ciphers_buf);
642}
void free_buf(struct buffer *buf)
Free the memory allocated for a buffer.
Definition buffer.c:169
bool buf_printf(struct buffer *buf, const char *format,...)
printf-style append to a buffer with overflow check.
Definition buffer.c:226
bool buf_puts(struct buffer *buf, const char *str)
Append a string to a buffer with overflow check.
Definition buffer.c:253
void buf_null_terminate(struct buffer *buf)
Force a null terminator at the end of the buffer content.
Definition buffer.c:501
void * gc_malloc(size_t size, bool clear, struct gc_arena *a)
Allocate memory and, optionally, zero it.
Definition buffer.c:318
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
struct buffer alloc_buf(size_t size)
Allocate a buffer of the given size.
Definition buffer.c:60
bool checked_snprintf(char *str, size_t size, const char *format,...)
Like snprintf() but returns an boolean.
Definition buffer.c:1121
char * string_alloc(const char *str, struct gc_arena *gc)
Duplicate a string, allocating memory under garbage collection.
Definition buffer.c:616
#define BSTR(buf)
Return the buffer content pointer cast to char *.
Definition buffer.h:151
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:594
static int buf_len(const struct buffer *buf)
Return the length of the buffer content.
Definition buffer.h:438
static int buf_forward_capacity(const struct buffer *buf)
Return the number of bytes that can still be appended to the buffer.
Definition buffer.h:997
static bool buf_write(struct buffer *dest, const void *src, size_t size)
Append data to a buffer.
Definition buffer.h:1198
static void gc_free(struct gc_arena *a)
Free all allocations in a garbage collection arena.
Definition buffer.h:1912
static char * buf_str(const struct buffer *buf)
Return the buffer content pointer cast to char *.
Definition buffer.h:521
static struct gc_arena gc_new(void)
Allocate and return a new, empty garbage collection arena.
Definition buffer.h:1896
char * strsep(char **stringp, const char *delim)
char * strtok_r(char *s, const char *delim, char **last)
#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
#define CO_USE_DYNAMIC_TLS_CRYPT
Bit-flag indicating that renegotiations are using tls-crypt with a TLS-EKM derived key.
Definition crypto.h:375
#define CO_EPOCH_DATA_KEY_FORMAT
Bit-flag indicating the epoch the data format.
Definition crypto.h:379
#define CO_USE_CC_EXIT_NOTIFY
Bit-flag indicating that explicit exit notifies should be sent via the control channel instead of usi...
Definition crypto.h:371
bool cipher_kt_mode_cbc(const char *ciphername)
Check if the supplied cipher is a supported CBC mode cipher.
static bool cipher_defined(const char *ciphername)
Checks if the cipher is defined and is not the null (none) cipher.
bool cipher_kt_mode_aead(const char *ciphername)
Check if the supplied cipher is a supported AEAD mode cipher.
bool cipher_kt_mode_ofb_cfb(const char *ciphername)
Check if the supplied cipher is a supported OFB or CFB mode cipher.
static bool cipher_valid(const char *ciphername)
Returns if the cipher is valid, based on the given cipher name.
const char * cipher_kt_name(const char *ciphername)
Retrieve a normalised string describing the cipher (e.g.
static const char * dco_get_supported_ciphers(void)
Definition dco.h:381
#define D_TLS_DEBUG_LOW
Definition errlevel.h:76
#define D_PUSH_DEBUG
Definition errlevel.h:149
#define D_TLS_ERRORS
Definition errlevel.h:58
#define M_NONFATAL
Definition error.h:91
#define msg(flags,...)
Definition error.h:152
#define ASSERT(x)
Definition error.h:219
#define M_WARN
Definition error.h:92
#define MAX_PEER_ID
Definition openvpn.h:550
#define OPT_P_NCP
Negotiable crypto parameters.
Definition options.h:743
#define streq(x, y)
Definition options.h:726
static bool dco_enabled(const struct options *o)
Returns whether the current configuration has dco enabled.
Definition options.h:961
#define IV_PROTO_CC_EXIT_NOTIFY
Support for explicit exit notify via control channel This also includes support for the protocol-flag...
Definition ssl.h:102
#define IV_PROTO_DATA_EPOCH
Support the extended packet id and epoch format for data channel packets.
Definition ssl.h:111
#define IV_PROTO_DATA_V2
Support P_DATA_V2.
Definition ssl.h:80
#define IV_PROTO_TLS_KEY_EXPORT
Supports key derivation via TLS key material exporter [RFC5705].
Definition ssl.h:87
#define IV_PROTO_DYN_TLS_CRYPT
Support to dynamic tls-crypt (renegotiation with TLS-EKM derived tls-crypt key)
Definition ssl.h:108
#define IV_PROTO_NCP_P2P
Support doing NCP in P2P mode.
Definition ssl.h:95
#define EXPORT_P2P_PEERID_LABEL
bool key_state_export_keying_material(struct tls_session *session, const char *label, size_t label_size, void *ekm, size_t ekm_size)
Keying Material Exporters [RFC 5705] allows additional keying material to be derived from existing TL...
bool check_pull_client_ncp(struct context *c, const uint64_t found)
Checks whether the cipher negotiation is in an acceptable state and we continue to connect or should ...
Definition ssl_ncp.c:302
char * ncp_get_best_cipher(const char *server_list, const char *peer_info, const char *remote_cipher, struct gc_arena *gc)
Iterates through the ciphers in server_list and return the first cipher that is also supported by the...
Definition ssl_ncp.c:238
const char * tls_peer_ncp_list(const char *peer_info, struct gc_arena *gc)
Returns the support cipher list from the peer according to the IV_NCP and IV_CIPHER values in peer_in...
Definition ssl_ncp.c:217
void options_postprocess_setdefault_ncpciphers(struct options *o)
Checks for availibility of Chacha20-Poly1305 and sets the ncp_cipher to either AES-256-GCM:AES-128-GC...
Definition ssl_ncp.c:585
const char * ncp_expanded_ciphers(struct options *o, struct gc_arena *gc)
returns the o->ncp_ciphers in brackets, e.g.
Definition ssl_ncp.c:628
bool check_session_cipher(struct tls_session *session, struct options *options)
Checks if the cipher is allowed, otherwise returns false and reset the cipher to the config cipher.
Definition ssl_ncp.c:524
void p2p_mode_ncp(struct tls_multi *multi, struct tls_session *session)
Determines if there is common cipher of both peer by looking at the IV_CIPHER peer info.
Definition ssl_ncp.c:479
bool tls_item_in_cipher_list(const char *item, const char *list)
Return true iff item is present in the colon-separated zero-terminated cipher list.
Definition ssl_ncp.c:197
void append_cipher_to_ncp_list(struct options *o, const char *ciphername)
Appends the cipher specified by the ciphernamer parameter to to the o->ncp_ciphers list.
Definition ssl_ncp.c:186
static void p2p_ncp_set_options(struct tls_multi *multi, struct tls_session *session, const char *common_cipher)
Definition ssl_ncp.c:397
bool tls_peer_supports_ncp(const char *peer_info)
Returns whether the client supports NCP either by announcing IV_NCP>=2 or the IV_CIPHERS list.
Definition ssl_ncp.c:69
static bool tls_poor_mans_ncp(struct options *o, const char *remote_ciphername)
"Poor man's NCP": Use peer cipher if it is an allowed (NCP) cipher.
Definition ssl_ncp.c:290
char * mutate_ncp_cipher_list(const char *list, struct gc_arena *gc)
Check whether the ciphers in the supplied list are supported.
Definition ssl_ncp.c:86
const char * get_p2p_ncp_cipher(struct tls_session *session, const char *peer_info, struct gc_arena *gc)
Determines the best common cipher from both peers IV_CIPHER lists.
Definition ssl_ncp.c:347
static unsigned int tls_peer_info_ncp_ver(const char *peer_info)
Return the Negotiable Crypto Parameters version advertised in the peer info string,...
Definition ssl_ncp.c:59
static void replace_default_in_ncp_ciphers_option(struct options *o, const char *replace)
Replaces the string DEFAULT with the string replace.
Definition ssl_ncp.c:553
Control Channel SSL/Data dynamic negotiation Module This file is split from ssl.h to be able to unit ...
#define MAX_NCP_CIPHERS_LENGTH
The maximum length of a ncp-cipher string that is accepted.
Definition ssl_ncp.h:123
char * extract_var_peer_info(const char *peer_info, const char *var, struct gc_arena *gc)
Extracts a variable from peer info, the returned string will be allocated using the supplied gc_arena...
Definition ssl_util.c:63
uint32_t extract_asymmetric_peer_id(const char *peer_info)
Extracts the ID variable and returns its value or MAX_PEER_ID if it cannot be extracted.
Definition ssl_util.c:115
unsigned int peer_info_extract_uint(const char *peer_info, const char *field)
Extracts the named integer variable and returns its value or 0 if it cannot be extracted.
Definition ssl_util.c:109
SSL utility functions.
static unsigned int extract_iv_proto(const char *peer_info)
Extracts the IV_PROTO variable and returns its value or 0 if it cannot be extracted.
Definition ssl_util.h:77
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
struct tls_multi * tls_multi
TLS state structure for this VPN tunnel.
Definition openvpn.h:324
Contains all state information for one tunnel.
Definition openvpn.h:471
struct context_2 c2
Level 2 context.
Definition openvpn.h:514
struct options options
Options loaded from command line or configuration file.
Definition openvpn.h:472
Garbage collection arena used to keep track of dynamically allocated memory.
Definition buffer.h:127
const char * ncp_ciphers_conf
The original ncp_ciphers specified by the user in the configuration.
Definition options.h:579
const char * ncp_ciphers
Definition options.h:580
const char * ciphername
Definition options.h:575
bool enable_ncp_fallback
If defined fall back to ciphername if NCP fails.
Definition options.h:576
struct gc_arena gc
Definition options.h:258
Security parameter state for a single VPN tunnel.
Definition ssl_common.h:611
char * peer_info
A multi-line string of general-purpose info received from peer over control channel.
Definition ssl_common.h:672
char * remote_ciphername
cipher specified in peer's config file
Definition ssl_common.h:704
struct tls_options opt
Definition ssl_common.h:616
bool use_peer_id
Definition ssl_common.h:701
bool use_asymmetric_peer_id
Definition ssl_common.h:702
uint32_t tx_peer_id
Definition ssl_common.h:700
uint32_t rx_peer_id
Definition ssl_common.h:699
bool dco_enabled
Whether keys have to be installed in DCO or not.
Definition ssl_common.h:454
Security parameter state of a single session within a VPN tunnel.
Definition ssl_common.h:489
struct gc_arena gc
Definition test_ssl.c:122