OpenVPN
Data Structures | Macros | Functions
crypto.h File Reference
#include "crypto_backend.h"
#include "basic.h"
#include "buffer.h"
#include "packet_id.h"
#include "mtu.h"
Include dependency graph for crypto.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  sha256_digest
 Wrapper struct to pass around SHA256 digests. More...
 
struct  key_type
 
struct  key
 Container for unidirectional cipher and HMAC key material. More...
 
struct  key_ctx
 Container for one set of cipher and/or HMAC contexts. More...
 
struct  key2
 Container for bidirectional cipher and HMAC key material. More...
 
struct  key_direction_state
 Key ordering of the key2.keys array. More...
 
struct  key_ctx_bi
 Container for two sets of OpenSSL cipher and/or HMAC contexts for both sending and receiving directions. More...
 
struct  crypto_options
 Security parameter state for processing data channel packets. More...
 

Macros

#define KEY_DIRECTION_BIDIRECTIONAL   0 /* same keys for both directions */
 
#define KEY_DIRECTION_NORMAL   1 /* encrypt with keys[0], decrypt with keys[1] */
 
#define KEY_DIRECTION_INVERSE   2 /* encrypt with keys[1], decrypt with keys[0] */
 
#define CO_PACKET_ID_LONG_FORM   (1<<0)
 Bit-flag indicating whether to use OpenVPN's long packet ID format. More...
 
#define CO_IGNORE_PACKET_ID   (1<<1)
 Bit-flag indicating whether to ignore the packet ID of a received packet. More...
 
#define CO_MUTE_REPLAY_WARNINGS   (1<<2)
 Bit-flag indicating not to display replay warnings. More...
 
#define CO_USE_TLS_KEY_MATERIAL_EXPORT   (1<<3)
 Bit-flag indicating that data channel key derivation is done using TLS keying material export [RFC5705]. More...
 
#define CO_RESEND_WKC   (1<<4)
 Bit-flag indicating that the client is expected to resend the wrapped client key with the 2nd packet (packet-id 1) like with the HARD_RESET_CLIENT_V3 packet. More...
 
#define CO_FORCE_TLSCRYPTV2_COOKIE   (1<<5)
 Bit-flag indicating that we do not allow clients that do not support resending the wrapped client key (WKc) with the third packet of the three-way handshake. More...
 
#define CO_USE_CC_EXIT_NOTIFY   (1<<6)
 Bit-flag indicating that explicit exit notifies should be sent via the control channel instead of using an OCC message. More...
 
#define CO_USE_DYNAMIC_TLS_CRYPT   (1<<7)
 Bit-flag indicating that renegotiations are using tls-crypt with a TLS-EKM derived key. More...
 
#define CRYPT_ERROR(format)   do { msg(D_CRYPT_ERRORS, "%s: " format, error_prefix); goto error_exit; } while (false)
 
#define OPENVPN_AEAD_MIN_IV_LEN   (sizeof(packet_id_type) + 8)
 Minimal IV length for AEAD mode ciphers (in bytes): 4-byte packet id + 8 bytes implicit IV. More...
 
#define RKF_MUST_SUCCEED   (1<<0)
 
#define RKF_INLINE   (1<<1)
 

Functions

void read_key_file (struct key2 *key2, const char *file, const unsigned int flags)
 
int write_key_file (const int nkeys, const char *filename)
 Write nkeys 1024-bits keys to file. More...
 
bool check_key (struct key *key, const struct key_type *kt)
 
bool write_key (const struct key *key, const struct key_type *kt, struct buffer *buf)
 
int read_key (struct key *key, const struct key_type *kt, struct buffer *buf)
 
void init_key_type (struct key_type *kt, const char *ciphername, const char *authname, bool tls_mode, bool warn)
 Initialize a key_type structure with. More...
 
void init_key_ctx (struct key_ctx *ctx, const struct key *key, const struct key_type *kt, int enc, const char *prefix)
 
void free_key_ctx (struct key_ctx *ctx)
 
void init_key_ctx_bi (struct key_ctx_bi *ctx, const struct key2 *key2, int key_direction, const struct key_type *kt, const char *name)
 
void free_key_ctx_bi (struct key_ctx_bi *ctx)
 
bool crypto_check_replay (struct crypto_options *opt, const struct packet_id_net *pin, const char *error_prefix, struct gc_arena *gc)
 Check packet ID for replay, and perform replay administration. More...
 
unsigned int calculate_crypto_overhead (const struct key_type *kt, unsigned int pkt_id_size, bool occ)
 Calculate the maximum overhead that our encryption has on a packet. More...
 
unsigned int crypto_max_overhead (void)
 Return the worst-case OpenVPN crypto overhead (in bytes) More...
 
void write_pem_key_file (const char *filename, const char *key_name)
 Generate a server key with enough randomness to fill a key struct and write to file. More...
 
bool generate_ephemeral_key (struct buffer *key, const char *pem_name)
 Generate ephermal key material into the key structure. More...
 
bool read_pem_key_file (struct buffer *key, const char *pem_name, const char *key_file, bool key_inline)
 Read key material from a PEM encoded files into the key structure. More...
 
void prng_bytes (uint8_t *output, int len)
 
long int get_random (void)
 
void print_cipher (const char *cipher)
 Print a cipher list entry. More...
 
void test_crypto (struct crypto_options *co, struct frame *f)
 
void key_direction_state_init (struct key_direction_state *kds, int key_direction)
 
void verify_fix_key2 (struct key2 *key2, const struct key_type *kt, const char *shared_secret_file)
 
void must_have_n_keys (const char *filename, const char *option, const struct key2 *key2, int n)
 
int ascii2keydirection (int msglevel, const char *str)
 
const char * keydirection2ascii (int kd, bool remote, bool humanreadable)
 
void key2_print (const struct key2 *k, const struct key_type *kt, const char *prefix0, const char *prefix1)
 Prints the keys in a key2 structure. More...
 
void crypto_read_openvpn_key (const struct key_type *key_type, struct key_ctx_bi *ctx, const char *key_file, bool key_inline, const int key_direction, const char *key_name, const char *opt_name, struct key2 *keydata)
 
int memcmp_constant_time (const void *a, const void *b, size_t size)
 As memcmp(), but constant-time. More...
 
static bool key_ctx_bi_defined (const struct key_ctx_bi *key)
 
const char * print_key_filename (const char *str, bool is_inline)
 To be used when printing a string that may contain inline data. More...
 
static struct key_type create_kt (const char *cipher, const char *md, const char *optname)
 Creates and validates an instance of struct key_type with the provided algs. More...
 
bool check_tls_prf_working (void)
 Checks if the current TLS library supports the TLS 1.0 PRF with MD5+SHA1 that OpenVPN uses when TLS Keying Material Export is not available. More...
 
Functions for performing security operations on data channel packets
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 OpenVPN peer. More...
 
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. More...
 

Macro Definition Documentation

◆ CO_FORCE_TLSCRYPTV2_COOKIE

#define CO_FORCE_TLSCRYPTV2_COOKIE   (1<<5)

Bit-flag indicating that we do not allow clients that do not support resending the wrapped client key (WKc) with the third packet of the three-way handshake.

Definition at line 270 of file crypto.h.

◆ CO_IGNORE_PACKET_ID

#define CO_IGNORE_PACKET_ID   (1<<1)

Bit-flag indicating whether to ignore the packet ID of a received packet.

This flag is used during processing of the first packet received from a client.

Definition at line 253 of file crypto.h.

◆ CO_MUTE_REPLAY_WARNINGS

#define CO_MUTE_REPLAY_WARNINGS   (1<<2)

Bit-flag indicating not to display replay warnings.

Definition at line 259 of file crypto.h.

◆ CO_PACKET_ID_LONG_FORM

#define CO_PACKET_ID_LONG_FORM   (1<<0)

Bit-flag indicating whether to use OpenVPN's long packet ID format.

Definition at line 250 of file crypto.h.

◆ CO_RESEND_WKC

#define CO_RESEND_WKC   (1<<4)

Bit-flag indicating that the client is expected to resend the wrapped client key with the 2nd packet (packet-id 1) like with the HARD_RESET_CLIENT_V3 packet.

Definition at line 266 of file crypto.h.

◆ CO_USE_CC_EXIT_NOTIFY

#define CO_USE_CC_EXIT_NOTIFY   (1<<6)

Bit-flag indicating that explicit exit notifies should be sent via the control channel instead of using an OCC message.

Definition at line 274 of file crypto.h.

◆ CO_USE_DYNAMIC_TLS_CRYPT

#define CO_USE_DYNAMIC_TLS_CRYPT   (1<<7)

Bit-flag indicating that renegotiations are using tls-crypt with a TLS-EKM derived key.

Definition at line 278 of file crypto.h.

◆ CO_USE_TLS_KEY_MATERIAL_EXPORT

#define CO_USE_TLS_KEY_MATERIAL_EXPORT   (1<<3)

Bit-flag indicating that data channel key derivation is done using TLS keying material export [RFC5705].

Definition at line 262 of file crypto.h.

◆ CRYPT_ERROR

#define CRYPT_ERROR (   format)    do { msg(D_CRYPT_ERRORS, "%s: " format, error_prefix); goto error_exit; } while (false)

Definition at line 287 of file crypto.h.

◆ KEY_DIRECTION_BIDIRECTIONAL

#define KEY_DIRECTION_BIDIRECTIONAL   0 /* same keys for both directions */

Definition at line 171 of file crypto.h.

◆ KEY_DIRECTION_INVERSE

#define KEY_DIRECTION_INVERSE   2 /* encrypt with keys[1], decrypt with keys[0] */

Definition at line 173 of file crypto.h.

◆ KEY_DIRECTION_NORMAL

#define KEY_DIRECTION_NORMAL   1 /* encrypt with keys[0], decrypt with keys[1] */

Definition at line 172 of file crypto.h.

◆ OPENVPN_AEAD_MIN_IV_LEN

#define OPENVPN_AEAD_MIN_IV_LEN   (sizeof(packet_id_type) + 8)

Minimal IV length for AEAD mode ciphers (in bytes): 4-byte packet id + 8 bytes implicit IV.

Definition at line 294 of file crypto.h.

◆ RKF_INLINE

#define RKF_INLINE   (1<<1)

Definition at line 297 of file crypto.h.

◆ RKF_MUST_SUCCEED

#define RKF_MUST_SUCCEED   (1<<0)

Definition at line 296 of file crypto.h.

Function Documentation

◆ ascii2keydirection()

int ascii2keydirection ( int  msglevel,
const char *  str 
)

Definition at line 1426 of file crypto.c.

References KEY_DIRECTION_BIDIRECTIONAL, KEY_DIRECTION_INVERSE, KEY_DIRECTION_NORMAL, and msg.

Referenced by add_option().

◆ calculate_crypto_overhead()

unsigned int calculate_crypto_overhead ( const struct key_type kt,
unsigned int  pkt_id_size,
bool  occ 
)

Calculate the maximum overhead that our encryption has on a packet.

This does not include needed additional buffer size

This does NOT include the padding and rounding of CBC size as the users (mssfix/fragment) of this function need to adjust for this and add it themselves.

Parameters
ktStruct with the crypto algorithm to use
packet_id_sizeSize of the packet id
occif true calculates the overhead for crypto in the same incorrect way as all previous OpenVPN versions did, to end up with identical numbers for OCC compatibility

Definition at line 670 of file crypto.c.

References key_type::cipher, cipher_defined(), cipher_kt_block_size(), cipher_kt_iv_size(), cipher_kt_mode_aead(), cipher_kt_mode_cbc(), cipher_kt_tag_size(), key_type::digest, md_defined(), and md_kt_size().

Referenced by frame_calculate_protocol_header_size().

◆ check_key()

bool check_key ( struct key key,
const struct key_type kt 
)

Definition at line 931 of file crypto.c.

References key_type::cipher, cipher_defined(), and key_is_zero().

Referenced by generate_key_expansion(), and verify_fix_key2().

◆ check_tls_prf_working()

bool check_tls_prf_working ( void  )

Checks if the current TLS library supports the TLS 1.0 PRF with MD5+SHA1 that OpenVPN uses when TLS Keying Material Export is not available.

Returns
true if supported, false otherwise.

Definition at line 1795 of file crypto.c.

References ssl_tls1_PRF().

Referenced by options_process_mutate_prf().

◆ create_kt()

static struct key_type create_kt ( const char *  cipher,
const char *  md,
const char *  optname 
)
inlinestatic

Creates and validates an instance of struct key_type with the provided algs.

Parameters
cipherthe cipher algorithm to use (must be a string literal)
mdthe digest algorithm to use (must be a string literal)
optnamethe name of the option requiring the key_type object
Returns
the initialized key_type instance

Definition at line 576 of file crypto.h.

References key_type::cipher, cipher_defined(), cipher_valid(), key_type::digest, M_WARN, md_defined(), md_valid(), and msg.

Referenced by auth_token_kt(), and tls_crypt_kt().

◆ crypto_check_replay()

bool crypto_check_replay ( struct crypto_options opt,
const struct packet_id_net pin,
const char *  error_prefix,
struct gc_arena gc 
)

Check packet ID for replay, and perform replay administration.

Parameters
optCrypto options for this packet, contains replay state.
pinPacket ID read from packet.
error_prefixPrefix to use when printing error messages.
gcGarbage collector to use.
Returns
true if packet ID is validated to be not a replay, false otherwise.

Definition at line 312 of file crypto.c.

References CO_MUTE_REPLAY_WARNINGS, CO_PACKET_ID_LONG_FORM, D_REPLAY_ERRORS, crypto_options::flags, msg, crypto_options::packet_id, packet_id_add(), packet_id_net_print(), packet_id_persist_save_obj(), packet_id_reap_test(), packet_id_test(), crypto_options::pid_persist, and packet_id::rec.

Referenced by openvpn_decrypt_aead(), openvpn_decrypt_v1(), and tls_crypt_unwrap().

◆ crypto_max_overhead()

unsigned int crypto_max_overhead ( void  )

Return the worst-case OpenVPN crypto overhead (in bytes)

Definition at line 719 of file crypto.c.

References max_int(), OPENVPN_AEAD_TAG_LENGTH, OPENVPN_MAX_CIPHER_BLOCK_SIZE, OPENVPN_MAX_HMAC_SIZE, OPENVPN_MAX_IV_LENGTH, and packet_id_size().

Referenced by frame_finalize_options().

◆ crypto_read_openvpn_key()

void crypto_read_openvpn_key ( const struct key_type key_type,
struct key_ctx_bi ctx,
const char *  key_file,
bool  key_inline,
const int  key_direction,
const char *  key_name,
const char *  opt_name,
struct key2 keydata 
)

◆ free_key_ctx()

void free_key_ctx ( struct key_ctx ctx)

◆ free_key_ctx_bi()

void free_key_ctx_bi ( struct key_ctx_bi ctx)

◆ generate_ephemeral_key()

bool generate_ephemeral_key ( struct buffer key,
const char *  pem_name 
)

Generate ephermal key material into the key structure.

Parameters
keythe key structure that will hold the key material
pem_namethe name used for logging
Returns
true if key generation was successful

Definition at line 1738 of file crypto.c.

References BCAP, BEND, buf_inc_len(), buffer::len, M_INFO, M_WARN, msg, and rand_bytes().

Referenced by auth_token_init_secret().

◆ get_random()

long int get_random ( void  )

◆ init_key_ctx()

void init_key_ctx ( struct key_ctx ctx,
const struct key key,
const struct key_type kt,
int  enc,
const char *  prefix 
)

◆ init_key_ctx_bi()

void init_key_ctx_bi ( struct key_ctx_bi ctx,
const struct key2 key2,
int  key_direction,
const struct key_type kt,
const char *  name 
)

◆ init_key_type()

void init_key_type ( struct key_type kt,
const char *  ciphername,
const char *  authname,
bool  tls_mode,
bool  warn 
)

Initialize a key_type structure with.

Parameters
ktThe struct key_type to initialize
ciphernameThe name of the cipher to use
authnameThe name of the HMAC digest to use
tls_modeSpecifies whether we are running in TLS mode, which allows more ciphers than static key mode.
warnPrint warnings when null cipher / auth is used.

Definition at line 744 of file crypto.c.

References ASSERT, key_type::cipher, cipher_kt_block_size(), cipher_kt_mode_aead(), cipher_kt_mode_cbc(), cipher_kt_mode_ofb_cfb(), cipher_valid(), CLEAR, key_type::digest, ENABLE_OFB_CFB_MODE, M_FATAL, M_WARN, md_kt_size(), msg, OPENVPN_MAX_CIPHER_BLOCK_SIZE, OPENVPN_MAX_HMAC_SIZE, and warn_insecure_key_type().

Referenced by calc_options_string_link_mtu(), do_init_crypto_none(), do_init_crypto_static(), do_init_crypto_tls_c1(), init_tas_auth(), options_string(), test_mssfix_mtu_calculation(), and tls_session_update_crypto_params_do_work().

◆ key2_print()

void key2_print ( const struct key2 k,
const struct key_type kt,
const char *  prefix0,
const char *  prefix1 
)

Prints the keys in a key2 structure.

Definition at line 988 of file crypto.c.

References ASSERT, key_print(), key2::keys, and key2::n.

Referenced by generate_key_expansion().

◆ key_ctx_bi_defined()

static bool key_ctx_bi_defined ( const struct key_ctx_bi key)
inlinestatic

Definition at line 548 of file crypto.h.

References key::cipher, and key::hmac.

Referenced by do_init_crypto_static().

◆ key_direction_state_init()

void key_direction_state_init ( struct key_direction_state kds,
int  key_direction 
)

◆ keydirection2ascii()

const char* keydirection2ascii ( int  kd,
bool  remote,
bool  humanreadable 
)

◆ memcmp_constant_time()

int memcmp_constant_time ( const void *  a,
const void *  b,
size_t  size 
)

As memcmp(), but constant-time.

Returns 0 when data is equal, non-zero otherwise.

Definition at line 1328 of file crypto_openssl.c.

Referenced by check_hmac_token(), check_session_id_hmac(), is_auth_token(), man_check_password(), openvpn_decrypt_v1(), tls_crypt_unwrap(), tls_crypt_v2_unwrap_client_key(), verify_auth_token(), and verify_cert().

◆ must_have_n_keys()

void must_have_n_keys ( const char *  filename,
const char *  option,
const struct key2 key2,
int  n 
)

Definition at line 1413 of file crypto.c.

References M_FATAL, msg, key2::n, and PACKAGE.

Referenced by crypto_read_openvpn_key().

◆ print_cipher()

void print_cipher ( const char *  cipher)

Print a cipher list entry.

Definition at line 1623 of file crypto.c.

References cipher_kt_block_size(), cipher_kt_key_size(), cipher_kt_mode_cbc(), cipher_kt_name(), and cipher_valid_reason().

Referenced by show_available_ciphers().

◆ print_key_filename()

const char* print_key_filename ( const char *  str,
bool  is_inline 
)

To be used when printing a string that may contain inline data.

If "is_inline" is true, return the inline tag. If "is_inline" is false and "str" is not NULL, return "str". Return the constant string "[NULL]" otherwise.

Parameters
strthe original string to return when is_inline is false
is_inlinetrue when str contains an inline data of some sort

Definition at line 1083 of file crypto.c.

References np().

Referenced by backend_tls_ctx_reload_crl(), crypto_read_openvpn_key(), read_key_file(), tls_ctx_load_ca(), tls_ctx_load_dh_params(), tls_ctx_load_extra_certs(), and tls_ctx_load_priv_file().

◆ prng_bytes()

void prng_bytes ( uint8_t *  output,
int  len 
)

Definition at line 1604 of file crypto.c.

References ASSERT, and rand_bytes().

Referenced by get_random(), hostname_randomize(), openvpn_encrypt_v1(), and session_id_random().

◆ read_key()

int read_key ( struct key key,
const struct key_type kt,
struct buffer buf 
)

◆ read_key_file()

void read_key_file ( struct key2 key2,
const char *  file,
const unsigned int  flags 
)

◆ read_pem_key_file()

bool read_pem_key_file ( struct buffer key,
const char *  pem_name,
const char *  key_file,
bool  key_inline 
)

Read key material from a PEM encoded files into the key structure.

Parameters
keythe key structure that will hold the key material
pem_namethe name used in the pem encoding start/end lines
key_filename of the file to read or the key itself if key_inline is true
key_inlineTrue if key_file contains an inline key, False otherwise.
Returns
true if reading into key was successful

Definition at line 1756 of file crypto.c.

References buf_clear(), buf_set_read(), buf_valid(), buffer_read_from_file(), cleanup(), crypto_pem_decode(), gc_free(), gc_new(), M_WARN, and msg.

Referenced by auth_token_init_secret(), tls_crypt_v2_init_client_key(), and tls_crypt_v2_init_server_key().

◆ test_crypto()

void test_crypto ( struct crypto_options co,
struct frame f 
)

◆ verify_fix_key2()

void verify_fix_key2 ( struct key2 key2,
const struct key_type kt,
const char *  shared_secret_file 
)

Definition at line 1507 of file crypto.c.

References check_key(), key2::keys, M_FATAL, msg, and key2::n.

Referenced by crypto_read_openvpn_key().

◆ write_key()

bool write_key ( const struct key key,
const struct key_type kt,
struct buffer buf 
)

◆ write_key_file()

int write_key_file ( const int  nkeys,
const char *  filename 
)

Write nkeys 1024-bits keys to file.

Returns
number of random bits written, or -1 on failure.

Definition at line 1350 of file crypto.c.

References alloc_buf_gc(), BLEN, BPTR, buf_clear(), buf_printf(), buffer_write_file(), format_hex_ex(), gc_free(), gc_new(), generate_key_random(), secure_memzero(), static_key_foot, and static_key_head.

Referenced by do_genkey().

◆ write_pem_key_file()

void write_pem_key_file ( const char *  filename,
const char *  key_name 
)

Generate a server key with enough randomness to fill a key struct and write to file.

Parameters
filenameFilename of the server key file to create.
pem_nameThe name to use in the PEM header/footer.

Definition at line 1700 of file crypto.c.

References BLEN, BPTR, buf_clear(), buf_set_read(), buffer_write_file(), cleanup(), clear_buf(), crypto_pem_encode(), gc_free(), gc_new(), M_ERR, M_NONFATAL, M_WARN, msg, rand_bytes(), and secure_memzero().

Referenced by auth_token_write_server_key_file(), and tls_crypt_v2_write_server_key_file().