libssh 0.12.0
The SSH library
Loading...
Searching...
No Matches
crypto.h
1/*
2 * This file is part of the SSH Library
3 *
4 * Copyright (c) 2003-2009 by Aris Adamantiadis
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21/*
22 * crypto.h is an include file for internal cryptographic structures of libssh
23 */
24
25#ifndef _CRYPTO_H_
26#define _CRYPTO_H_
27
28#include "config.h"
29
30#include <stdbool.h>
31
32#ifdef HAVE_LIBGCRYPT
33#include <gcrypt.h>
34#elif defined(HAVE_LIBMBEDCRYPTO)
35#include <mbedtls/gcm.h>
36#endif
37#ifdef HAVE_OPENSSL_ECDH_H
38#include <openssl/ecdh.h>
39#endif
40
41#include "libssh/wrapper.h"
42
43#ifdef cbc_encrypt
44#undef cbc_encrypt
45#endif
46#ifdef cbc_decrypt
47#undef cbc_decrypt
48#endif
49
50#include "libssh/curve25519.h"
51#include "libssh/dh.h"
52#include "libssh/ecdh.h"
53#include "libssh/kex.h"
54#include "libssh/sntrup761.h"
55
56#define DIGEST_MAX_LEN 64
57
58#define AES_GCM_TAGLEN 16
59#define AES_GCM_IVLEN 12
60
61enum ssh_key_exchange_e {
62 /* diffie-hellman-group1-sha1 */
63 SSH_KEX_DH_GROUP1_SHA1 = 1,
64 /* diffie-hellman-group14-sha1 */
65 SSH_KEX_DH_GROUP14_SHA1,
66#ifdef WITH_GEX
67 /* diffie-hellman-group-exchange-sha1 */
68 SSH_KEX_DH_GEX_SHA1,
69 /* diffie-hellman-group-exchange-sha256 */
70 SSH_KEX_DH_GEX_SHA256,
71#endif /* WITH_GEX */
72 /* ecdh-sha2-nistp256 */
73 SSH_KEX_ECDH_SHA2_NISTP256,
74 /* ecdh-sha2-nistp384 */
75 SSH_KEX_ECDH_SHA2_NISTP384,
76 /* ecdh-sha2-nistp521 */
77 SSH_KEX_ECDH_SHA2_NISTP521,
78 /* curve25519-sha256@libssh.org */
79 SSH_KEX_CURVE25519_SHA256_LIBSSH_ORG,
80 /* curve25519-sha256 */
81 SSH_KEX_CURVE25519_SHA256,
82 /* diffie-hellman-group16-sha512 */
83 SSH_KEX_DH_GROUP16_SHA512,
84 /* diffie-hellman-group18-sha512 */
85 SSH_KEX_DH_GROUP18_SHA512,
86 /* diffie-hellman-group14-sha256 */
87 SSH_KEX_DH_GROUP14_SHA256,
88 /* sntrup761x25519-sha512@openssh.com */
89 SSH_KEX_SNTRUP761X25519_SHA512_OPENSSH_COM,
90 /* sntrup761x25519-sha512 */
91 SSH_KEX_SNTRUP761X25519_SHA512,
92 /* mlkem768x25519-sha256 */
93 SSH_KEX_MLKEM768X25519_SHA256,
94 /* mlkem768nistp256-sha256 */
95 SSH_KEX_MLKEM768NISTP256_SHA256,
96#ifdef HAVE_MLKEM1024
97 /* mlkem1024nistp384-sha384 */
98 SSH_KEX_MLKEM1024NISTP384_SHA384,
99#endif /* HAVE_MLKEM1024 */
100 /* gss-group14-sha256-* */
101 SSH_GSS_KEX_DH_GROUP14_SHA256,
102 /* gss-group16-sha512-* */
103 SSH_GSS_KEX_DH_GROUP16_SHA512,
104 /* gss-nistp256-sha256-* */
105 SSH_GSS_KEX_ECDH_NISTP256_SHA256,
106 /* gss-curve25519-sha256-* */
107 SSH_GSS_KEX_CURVE25519_SHA256,
108};
109
110enum ssh_cipher_e {
111 SSH_NO_CIPHER=0,
112#ifdef HAVE_BLOWFISH
113 SSH_BLOWFISH_CBC,
114#endif /* HAVE_BLOWFISH */
115 SSH_3DES_CBC,
116 SSH_AES128_CBC,
117 SSH_AES192_CBC,
118 SSH_AES256_CBC,
119 SSH_AES128_CTR,
120 SSH_AES192_CTR,
121 SSH_AES256_CTR,
122 SSH_AEAD_AES128_GCM,
123 SSH_AEAD_AES256_GCM,
124 SSH_AEAD_CHACHA20_POLY1305
125};
126
127struct dh_ctx;
128
129struct ssh_crypto_struct {
130 bignum shared_secret;
131 ssh_string hybrid_client_init;
132 ssh_string hybrid_server_reply;
133 ssh_string hybrid_shared_secret;
134 struct dh_ctx *dh_ctx;
135#ifdef WITH_GEX
136 size_t dh_pmin; size_t dh_pn; size_t dh_pmax; /* preferred group parameters */
137#endif /* WITH_GEX */
138#ifdef HAVE_ECDH
139#ifdef HAVE_OPENSSL_ECC
140#if OPENSSL_VERSION_NUMBER < 0x30000000L
141 EC_KEY *ecdh_privkey;
142#else
143 EVP_PKEY *ecdh_privkey;
144#endif /* OPENSSL_VERSION_NUMBER */
145#elif defined HAVE_GCRYPT_ECC
146 gcry_sexp_t ecdh_privkey;
147#elif defined HAVE_LIBMBEDCRYPTO
148 mbedtls_ecp_keypair *ecdh_privkey;
149#endif
150 ssh_string ecdh_client_pubkey;
151 ssh_string ecdh_server_pubkey;
152#endif
153#ifdef HAVE_CURVE25519
154#ifdef HAVE_LIBCRYPTO
155 EVP_PKEY *curve25519_privkey;
156#elif defined(HAVE_GCRYPT_CURVE25519)
157 gcry_sexp_t curve25519_privkey;
158#else
159 ssh_curve25519_privkey curve25519_privkey;
160#endif
161 ssh_curve25519_pubkey curve25519_client_pubkey;
162 ssh_curve25519_pubkey curve25519_server_pubkey;
163#endif
164#ifdef HAVE_OPENSSL_MLKEM
165 EVP_PKEY *mlkem_privkey;
166#else
167 unsigned char *mlkem_privkey;
168 size_t mlkem_privkey_len;
169#endif
170 ssh_string mlkem_client_pubkey;
171 ssh_string mlkem_ciphertext;
172#ifdef HAVE_SNTRUP761
173 ssh_sntrup761_privkey sntrup761_privkey;
174 ssh_sntrup761_pubkey sntrup761_client_pubkey;
175 ssh_sntrup761_ciphertext sntrup761_ciphertext;
176#endif
177 ssh_string dh_server_signature; /* information used by dh_handshake. */
178 size_t session_id_len;
179 unsigned char *session_id;
180 size_t digest_len; /* len of the secret hash */
181 unsigned char *secret_hash; /* Secret hash is same as session id until re-kex */
182 unsigned char *encryptIV;
183 unsigned char *decryptIV;
184 unsigned char *decryptkey;
185 unsigned char *encryptkey;
186 unsigned char *encryptMAC;
187 unsigned char *decryptMAC;
188 unsigned char hmacbuf[DIGEST_MAX_LEN];
189 struct ssh_cipher_struct *in_cipher, *out_cipher; /* the cipher structures/objects */
190 enum ssh_hmac_e in_hmac, out_hmac; /* the MAC algorithms used */
191 bool in_hmac_etm, out_hmac_etm; /* Whether EtM mode is used or not */
192
193 ssh_key server_pubkey;
194 int do_compress_out; /* idem */
195 int do_compress_in; /* don't set them, set the option instead */
196 int delayed_compress_in; /* Use of zlib@openssh.org */
197 int delayed_compress_out;
198 void *compress_out_ctx; /* don't touch it */
199 void *compress_in_ctx; /* really, don't */
200 /* kex sent by server, client, and mutually elected methods */
201 struct ssh_kex_struct server_kex;
202 struct ssh_kex_struct client_kex;
203 char *kex_methods[SSH_KEX_METHODS];
204 enum ssh_key_exchange_e kex_type;
205 enum ssh_kdf_digest digest_type; /* Digest type for session keys derivation */
206 enum ssh_crypto_direction_e used; /* Is this crypto still used for either of directions? */
207};
208
209struct ssh_cipher_struct {
210 const char *name; /* ssh name of the algorithm */
211 unsigned int blocksize; /* blocksize of the algo */
212 enum ssh_cipher_e ciphertype;
213 uint32_t lenfield_blocksize; /* blocksize of the packet length field */
214 size_t keylen; /* length of the key structure */
215#ifdef HAVE_LIBGCRYPT
216 gcry_cipher_hd_t *key;
217 unsigned char last_iv[AES_GCM_IVLEN];
218#elif defined HAVE_LIBCRYPTO
219 struct ssh_3des_key_schedule *des3_key;
220 struct ssh_aes_key_schedule *aes_key;
221 const EVP_CIPHER *cipher;
222 EVP_CIPHER_CTX *ctx;
223#elif defined HAVE_LIBMBEDCRYPTO
224 mbedtls_cipher_context_t encrypt_ctx;
225 mbedtls_cipher_context_t decrypt_ctx;
226 mbedtls_cipher_type_t type;
227#ifdef MBEDTLS_GCM_C
228 mbedtls_gcm_context gcm_ctx;
229 unsigned char last_iv[AES_GCM_IVLEN];
230#endif /* MBEDTLS_GCM_C */
231#endif
232 struct chacha20_poly1305_keysched *chacha20_schedule;
233 unsigned int keysize; /* bytes of key used. != keylen */
234 size_t tag_size; /* overhead required for tag */
235 /* Counters for rekeying initialization */
236 uint32_t packets;
237 uint64_t blocks;
238 /* Rekeying limit for the cipher or manually enforced */
239 uint64_t max_blocks;
240 /* sets the new key for immediate use */
241 int (*set_encrypt_key)(struct ssh_cipher_struct *cipher, void *key, void *IV);
242 int (*set_decrypt_key)(struct ssh_cipher_struct *cipher, void *key, void *IV);
243 void (*encrypt)(struct ssh_cipher_struct *cipher,
244 void *in,
245 void *out,
246 size_t len);
247 void (*decrypt)(struct ssh_cipher_struct *cipher,
248 void *in,
249 void *out,
250 size_t len);
251 void (*aead_encrypt)(struct ssh_cipher_struct *cipher, void *in, void *out,
252 size_t len, uint8_t *mac, uint64_t seq);
253 int (*aead_decrypt_length)(struct ssh_cipher_struct *cipher, void *in,
254 uint8_t *out, size_t len, uint64_t seq);
255 int (*aead_decrypt)(struct ssh_cipher_struct *cipher, void *complete_packet, uint8_t *out,
256 size_t encrypted_size, uint64_t seq);
257 void (*cleanup)(struct ssh_cipher_struct *cipher);
258};
259
260#ifdef __cplusplus
261extern "C" {
262#endif
263
264const struct ssh_cipher_struct *ssh_get_chacha20poly1305_cipher(void);
265int sshkdf_derive_key(struct ssh_crypto_struct *crypto,
266 unsigned char *key, size_t key_len,
267 uint8_t key_type, unsigned char *output,
268 size_t requested_len);
269
270int secure_memcmp(const void *s1, const void *s2, size_t n);
271
272void compress_cleanup(struct ssh_crypto_struct *crypto);
273
274#ifdef __cplusplus
275}
276#endif
277
278#endif /* _CRYPTO_H_ */