FD.io VPP  v21.06-3-gbb25fbf28
Vector Packet Processing
wireguard_noise.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2020 Doc.ai and/or its affiliates.
3  * Copyright (c) 2015-2020 Jason A. Donenfeld <Jason@zx2c4.com>.
4  * Copyright (c) 2019-2020 Matt Dunwoodie <ncon@noconroy.net>.
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at:
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 
18 #ifndef __included_wg_noise_h__
19 #define __included_wg_noise_h__
20 
21 #include <vlib/vlib.h>
22 #include <vnet/crypto/crypto.h>
25 
26 #define NOISE_PUBLIC_KEY_LEN CURVE25519_KEY_SIZE
27 #define NOISE_SYMMETRIC_KEY_LEN 32 // CHACHA20POLY1305_KEY_SIZE
28 #define NOISE_TIMESTAMP_LEN (sizeof(uint64_t) + sizeof(uint32_t))
29 #define NOISE_AUTHTAG_LEN 16 //CHACHA20POLY1305_AUTHTAG_SIZE
30 #define NOISE_HASH_LEN BLAKE2S_HASH_SIZE
31 
32 /* Protocol string constants */
33 #define NOISE_HANDSHAKE_NAME "Noise_IKpsk2_25519_ChaChaPoly_BLAKE2s"
34 #define NOISE_IDENTIFIER_NAME "WireGuard v1 zx2c4 Jason@zx2c4.com"
35 
36 /* Constants for the counter */
37 #define COUNTER_BITS_TOTAL 8192
38 #define COUNTER_BITS (sizeof(unsigned long) * 8)
39 #define COUNTER_NUM (COUNTER_BITS_TOTAL / COUNTER_BITS)
40 #define COUNTER_WINDOW_SIZE (COUNTER_BITS_TOTAL - COUNTER_BITS)
41 
42 /* Constants for the keypair */
43 #define REKEY_AFTER_MESSAGES (1ull << 60)
44 #define REJECT_AFTER_MESSAGES (UINT64_MAX - COUNTER_WINDOW_SIZE - 1)
45 #define REKEY_AFTER_TIME 120
46 #define REKEY_AFTER_TIME_RECV 165
47 #define REJECT_AFTER_TIME 180
48 #define REJECT_INTERVAL (0.02) /* fifty times per sec */
49 /* 24 = floor(log2(REJECT_INTERVAL)) */
50 #define REJECT_INTERVAL_MASK (~((1ull<<24)-1))
51 
53 {
54  SC_OK = 0,
58 };
59 
61 {
62  HS_ZEROED = 0,
67 };
68 
69 typedef struct noise_handshake
70 {
72  uint32_t hs_local_index;
73  uint32_t hs_remote_index;
78 
79 typedef struct noise_counter
80 {
81  uint64_t c_send;
82  uint64_t c_recv;
83  unsigned long c_backtrack[COUNTER_NUM];
85 
86 typedef struct noise_keypair
87 {
88  int kp_valid;
90  uint32_t kp_local_index;
91  uint32_t kp_remote_index;
97 
98 typedef struct noise_local noise_local_t;
99 typedef struct noise_remote
100 {
101  uint32_t r_peer_idx;
103  uint32_t r_local_idx;
105 
110 
114 
115 typedef struct noise_local
116 {
119 
121  {
122  void *u_arg;
123  noise_remote_t *(*u_remote_get) (const uint8_t[NOISE_PUBLIC_KEY_LEN]);
124  uint32_t (*u_index_set) (noise_remote_t *);
125  void (*u_index_drop) (uint32_t);
126  } l_upcall;
127 } noise_local_t;
128 
129 /* pool of noise_local */
131 
132 /* Set/Get noise parameters */
134 noise_local_get (uint32_t locali)
135 {
136  return (pool_elt_at_index (noise_local_pool, locali));
137 }
138 
139 void noise_local_init (noise_local_t *, struct noise_upcall *);
141  const uint8_t[NOISE_PUBLIC_KEY_LEN]);
142 
143 void noise_remote_init (noise_remote_t *, uint32_t,
144  const uint8_t[NOISE_PUBLIC_KEY_LEN], uint32_t);
145 
146 /* Should be called anytime noise_local_set_private is called */
148 
149 /* Cryptographic functions */
151  uint32_t * s_idx,
152  uint8_t ue[NOISE_PUBLIC_KEY_LEN],
153  uint8_t es[NOISE_PUBLIC_KEY_LEN +
155  uint8_t ets[NOISE_TIMESTAMP_LEN +
157 
159  noise_remote_t **,
160  uint32_t s_idx,
161  uint8_t ue[NOISE_PUBLIC_KEY_LEN],
162  uint8_t es[NOISE_PUBLIC_KEY_LEN +
164  uint8_t ets[NOISE_TIMESTAMP_LEN +
166 
168  uint32_t * s_idx,
169  uint32_t * r_idx,
170  uint8_t ue[NOISE_PUBLIC_KEY_LEN],
171  uint8_t en[0 + NOISE_AUTHTAG_LEN]);
172 
174  uint32_t s_idx,
175  uint32_t r_idx,
176  uint8_t ue[NOISE_PUBLIC_KEY_LEN],
177  uint8_t en[0 + NOISE_AUTHTAG_LEN]);
178 
182 
184 
187  uint32_t * r_idx,
188  uint64_t * nonce,
189  uint8_t * src, size_t srclen, uint8_t * dst);
192  uint32_t r_idx,
193  uint64_t nonce,
194  uint8_t * src, size_t srclen, uint8_t * dst);
195 
196 
197 #endif /* __included_wg_noise_h__ */
198 
199 /*
200  * fd.io coding-style-patch-verification: ON
201  *
202  * Local Variables:
203  * eval: (c-set-style "gnu")
204  * End:
205  */
noise_keypair::kp_is_initiator
int kp_is_initiator
Definition: wireguard_noise.h:89
vlib.h
noise_local::noise_upcall::u_index_drop
void(* u_index_drop)(uint32_t)
Definition: wireguard_noise.h:125
noise_remote::r_previous
noise_keypair_t * r_previous
Definition: wireguard_noise.h:112
noise_remote::r_public
uint8_t r_public[NOISE_PUBLIC_KEY_LEN]
Definition: wireguard_noise.h:102
noise_create_initiation
bool noise_create_initiation(vlib_main_t *vm, noise_remote_t *, uint32_t *s_idx, uint8_t ue[NOISE_PUBLIC_KEY_LEN], uint8_t es[NOISE_PUBLIC_KEY_LEN+NOISE_AUTHTAG_LEN], uint8_t ets[NOISE_TIMESTAMP_LEN+NOISE_AUTHTAG_LEN])
Definition: wireguard_noise.c:118
wireguard_key.h
noise_keypair
Definition: wireguard_noise.h:86
NOISE_HASH_LEN
#define NOISE_HASH_LEN
Definition: wireguard_noise.h:30
noise_remote::r_local_idx
uint32_t r_local_idx
Definition: wireguard_noise.h:103
crypto.h
noise_remote_expire_current
void noise_remote_expire_current(noise_remote_t *r)
Definition: wireguard_noise.c:466
NOISE_SYMMETRIC_KEY_LEN
#define NOISE_SYMMETRIC_KEY_LEN
Definition: wireguard_noise.h:27
pool_elt_at_index
#define pool_elt_at_index(p, i)
Returns pointer to element at given index.
Definition: pool.h:553
NOISE_AUTHTAG_LEN
#define NOISE_AUTHTAG_LEN
Definition: wireguard_noise.h:29
noise_handshake::hs_hash
uint8_t hs_hash[NOISE_HASH_LEN]
Definition: wireguard_noise.h:75
SC_KEEP_KEY_FRESH
@ SC_KEEP_KEY_FRESH
Definition: wireguard_noise.h:56
noise_keypair::kp_birthdate
f64 kp_birthdate
Definition: wireguard_noise.h:94
noise_remote::r_keypair_lock
clib_rwlock_t r_keypair_lock
Definition: wireguard_noise.h:111
noise_keypair_t
struct noise_keypair noise_keypair_t
noise_local::l_upcall
struct noise_local::noise_upcall l_upcall
blake2s.h
noise_counter::c_backtrack
unsigned long c_backtrack[COUNTER_NUM]
Definition: wireguard_noise.h:83
HS_ZEROED
@ HS_ZEROED
Definition: wireguard_noise.h:62
noise_handshake::hs_local_index
uint32_t hs_local_index
Definition: wireguard_noise.h:72
noise_local_pool
noise_local_t * noise_local_pool
Definition: wireguard_noise.c:29
vnet_crypto_key_index_t
u32 vnet_crypto_key_index_t
Definition: crypto.h:378
noise_consume_response
bool noise_consume_response(vlib_main_t *vm, noise_remote_t *, uint32_t s_idx, uint32_t r_idx, uint8_t ue[NOISE_PUBLIC_KEY_LEN], uint8_t en[0+NOISE_AUTHTAG_LEN])
Definition: wireguard_noise.c:307
vm
vlib_main_t * vm
X-connect all packets from the HOST to the PHY.
Definition: nat44_ei.c:3047
CONSUMED_RESPONSE
@ CONSUMED_RESPONSE
Definition: wireguard_noise.h:66
SC_FAILED
@ SC_FAILED
Definition: wireguard_noise.h:57
COUNTER_NUM
#define COUNTER_NUM
Definition: wireguard_noise.h:39
noise_remote::r_timestamp
uint8_t r_timestamp[NOISE_TIMESTAMP_LEN]
Definition: wireguard_noise.h:108
noise_counter::c_recv
uint64_t c_recv
Definition: wireguard_noise.h:82
noise_remote_decrypt
enum noise_state_crypt noise_remote_decrypt(vlib_main_t *vm, noise_remote_t *, uint32_t r_idx, uint64_t nonce, uint8_t *src, size_t srclen, uint8_t *dst)
Definition: wireguard_noise.c:596
r
vnet_hw_if_output_node_runtime_t * r
Definition: interface_output.c:1071
noise_local::l_private
uint8_t l_private[NOISE_PUBLIC_KEY_LEN]
Definition: wireguard_noise.h:118
noise_keypair::kp_ctr
noise_counter_t kp_ctr
Definition: wireguard_noise.h:95
noise_local_t
struct noise_local noise_local_t
Definition: wireguard_noise.h:98
noise_handshake::hs_ck
uint8_t hs_ck[NOISE_HASH_LEN]
Definition: wireguard_noise.h:76
noise_remote_t
struct noise_remote noise_remote_t
CREATED_INITIATION
@ CREATED_INITIATION
Definition: wireguard_noise.h:63
noise_remote::r_current
noise_keypair_t * r_current
Definition: wireguard_noise.h:112
noise_remote::r_handshake
noise_handshake_t r_handshake
Definition: wireguard_noise.h:106
noise_remote_ready
bool noise_remote_ready(noise_remote_t *)
Definition: wireguard_noise.c:477
static_always_inline
#define static_always_inline
Definition: clib.h:112
clib_rw_lock_
Definition: lock.h:139
noise_remote::r_psk
uint8_t r_psk[NOISE_SYMMETRIC_KEY_LEN]
Definition: wireguard_noise.h:107
noise_remote_precompute
void noise_remote_precompute(noise_remote_t *)
Definition: wireguard_noise.c:105
noise_remote
Definition: wireguard_noise.h:99
noise_counter::c_send
uint64_t c_send
Definition: wireguard_noise.h:81
noise_remote_encrypt
enum noise_state_crypt noise_remote_encrypt(vlib_main_t *vm, noise_remote_t *, uint32_t *r_idx, uint64_t *nonce, uint8_t *src, size_t srclen, uint8_t *dst)
Definition: wireguard_noise.c:544
f64
double f64
Definition: types.h:142
noise_state_crypt
noise_state_crypt
Definition: wireguard_noise.h:52
noise_counter_t
struct noise_counter noise_counter_t
SC_CONN_RESET
@ SC_CONN_RESET
Definition: wireguard_noise.h:55
src
vl_api_address_t src
Definition: gre.api:54
noise_keypair::kp_valid
int kp_valid
Definition: wireguard_noise.h:88
CREATED_RESPONSE
@ CREATED_RESPONSE
Definition: wireguard_noise.h:65
noise_handshake::hs_state
enum noise_state_hs hs_state
Definition: wireguard_noise.h:71
noise_create_response
bool noise_create_response(vlib_main_t *vm, noise_remote_t *, uint32_t *s_idx, uint32_t *r_idx, uint8_t ue[NOISE_PUBLIC_KEY_LEN], uint8_t en[0+NOISE_AUTHTAG_LEN])
Definition: wireguard_noise.c:254
noise_local_get
static_always_inline noise_local_t * noise_local_get(uint32_t locali)
Definition: wireguard_noise.h:134
noise_local
Definition: wireguard_noise.h:115
NOISE_PUBLIC_KEY_LEN
#define NOISE_PUBLIC_KEY_LEN
Definition: wireguard_noise.h:26
noise_local_init
void noise_local_init(noise_local_t *, struct noise_upcall *)
Definition: wireguard_noise.c:74
dst
vl_api_ip4_address_t dst
Definition: pnat.api:41
noise_remote::r_peer_idx
uint32_t r_peer_idx
Definition: wireguard_noise.h:101
noise_local::noise_upcall
Definition: wireguard_noise.h:120
noise_remote_init
void noise_remote_init(noise_remote_t *, uint32_t, const uint8_t[NOISE_PUBLIC_KEY_LEN], uint32_t)
noise_remote::r_ss
uint8_t r_ss[NOISE_PUBLIC_KEY_LEN]
Definition: wireguard_noise.h:104
SC_OK
@ SC_OK
Definition: wireguard_noise.h:54
noise_remote_clear
void noise_remote_clear(vlib_main_t *vm, noise_remote_t *r)
Definition: wireguard_noise.c:450
noise_handshake::hs_remote_index
uint32_t hs_remote_index
Definition: wireguard_noise.h:73
vlib_main_t
Definition: main.h:102
noise_remote_begin_session
bool noise_remote_begin_session(vlib_main_t *vm, noise_remote_t *r)
Definition: wireguard_noise.c:368
noise_consume_initiation
bool noise_consume_initiation(vlib_main_t *vm, noise_local_t *, noise_remote_t **, uint32_t s_idx, uint8_t ue[NOISE_PUBLIC_KEY_LEN], uint8_t es[NOISE_PUBLIC_KEY_LEN+NOISE_AUTHTAG_LEN], uint8_t ets[NOISE_TIMESTAMP_LEN+NOISE_AUTHTAG_LEN])
Definition: wireguard_noise.c:170
noise_local::l_public
uint8_t l_public[NOISE_PUBLIC_KEY_LEN]
Definition: wireguard_noise.h:117
noise_handshake::hs_e
uint8_t hs_e[NOISE_PUBLIC_KEY_LEN]
Definition: wireguard_noise.h:74
noise_counter
Definition: wireguard_noise.h:79
CONSUMED_INITIATION
@ CONSUMED_INITIATION
Definition: wireguard_noise.h:64
noise_state_hs
noise_state_hs
Definition: wireguard_noise.h:60
noise_remote::r_last_init
f64 r_last_init
Definition: wireguard_noise.h:109
noise_remote::r_next
noise_keypair_t * r_next
Definition: wireguard_noise.h:112
noise_keypair::kp_recv_index
vnet_crypto_key_index_t kp_recv_index
Definition: wireguard_noise.h:93
NOISE_TIMESTAMP_LEN
#define NOISE_TIMESTAMP_LEN
Definition: wireguard_noise.h:28
noise_handshake
Definition: wireguard_noise.h:69
noise_local::noise_upcall::u_arg
void * u_arg
Definition: wireguard_noise.h:122
noise_handshake_t
struct noise_handshake noise_handshake_t
noise_keypair::kp_local_index
uint32_t kp_local_index
Definition: wireguard_noise.h:90
noise_local::noise_upcall::u_index_set
uint32_t(* u_index_set)(noise_remote_t *)
Definition: wireguard_noise.h:124
noise_keypair::kp_remote_index
uint32_t kp_remote_index
Definition: wireguard_noise.h:91
noise_local_set_private
bool noise_local_set_private(noise_local_t *, const uint8_t[NOISE_PUBLIC_KEY_LEN])
Definition: wireguard_noise.c:81
noise_keypair::kp_send_index
vnet_crypto_key_index_t kp_send_index
Definition: wireguard_noise.h:92