summaryrefslogtreecommitdiff
path: root/cipher.c
diff options
context:
space:
mode:
authorColin Watson <cjwatson@debian.org>2009-12-29 21:32:03 +0000
committerColin Watson <cjwatson@debian.org>2009-12-29 21:32:03 +0000
commit04942aa41fa94ec6f2c3ce1d348f600f31bb7c78 (patch)
treeaf8e928bd79d3f2d0219bb5b2c78b573ec31d94c /cipher.c
parent9ad7b718d42e43f3a285fcbc8f91193931fce324 (diff)
parent16704d57999d987fb8d9ba53379841a79f016d67 (diff)
import openssh-4.2p1-gsskex-20050926-2.patch
Diffstat (limited to 'cipher.c')
-rw-r--r--cipher.c102
1 files changed, 41 insertions, 61 deletions
diff --git a/cipher.c b/cipher.c
index beba4618d..0dddf270a 100644
--- a/cipher.c
+++ b/cipher.c
@@ -35,7 +35,7 @@
35 */ 35 */
36 36
37#include "includes.h" 37#include "includes.h"
38RCSID("$OpenBSD: cipher.c,v 1.73 2005/01/23 10:18:12 djm Exp $"); 38RCSID("$OpenBSD: cipher.c,v 1.77 2005/07/16 01:35:24 djm Exp $");
39 39
40#include "xmalloc.h" 40#include "xmalloc.h"
41#include "log.h" 41#include "log.h"
@@ -43,25 +43,8 @@ RCSID("$OpenBSD: cipher.c,v 1.73 2005/01/23 10:18:12 djm Exp $");
43 43
44#include <openssl/md5.h> 44#include <openssl/md5.h>
45 45
46#if OPENSSL_VERSION_NUMBER < 0x00906000L 46/* compatibility with old or broken OpenSSL versions */
47#define SSH_OLD_EVP 47#include "openbsd-compat/openssl-compat.h"
48#define EVP_CIPHER_CTX_get_app_data(e) ((e)->app_data)
49#endif
50
51#if OPENSSL_VERSION_NUMBER < 0x00907000L
52extern const EVP_CIPHER *evp_rijndael(void);
53extern void ssh_rijndael_iv(EVP_CIPHER_CTX *, int, u_char *, u_int);
54#endif
55
56#if !defined(EVP_CTRL_SET_ACSS_MODE)
57# if (OPENSSL_VERSION_NUMBER >= 0x00907000L)
58extern const EVP_CIPHER *evp_acss(void);
59# define EVP_acss evp_acss
60# define EVP_CTRL_SET_ACSS_MODE xxx /* used below */
61# else
62# define EVP_acss NULL /* Don't try to support ACSS on older OpenSSL */
63# endif /* (OPENSSL_VERSION_NUMBER >= 0x00906000L) */
64#endif /* !defined(EVP_CTRL_SET_ACSS_MODE) */
65 48
66extern const EVP_CIPHER *evp_ssh1_bf(void); 49extern const EVP_CIPHER *evp_ssh1_bf(void);
67extern const EVP_CIPHER *evp_ssh1_3des(void); 50extern const EVP_CIPHER *evp_ssh1_3des(void);
@@ -74,39 +57,32 @@ struct Cipher {
74 int number; /* for ssh1 only */ 57 int number; /* for ssh1 only */
75 u_int block_size; 58 u_int block_size;
76 u_int key_len; 59 u_int key_len;
60 u_int discard_len;
77 const EVP_CIPHER *(*evptype)(void); 61 const EVP_CIPHER *(*evptype)(void);
78} ciphers[] = { 62} ciphers[] = {
79 { "none", SSH_CIPHER_NONE, 8, 0, EVP_enc_null }, 63 { "none", SSH_CIPHER_NONE, 8, 0, 0, EVP_enc_null },
80 { "des", SSH_CIPHER_DES, 8, 8, EVP_des_cbc }, 64 { "des", SSH_CIPHER_DES, 8, 8, 0, EVP_des_cbc },
81 { "3des", SSH_CIPHER_3DES, 8, 16, evp_ssh1_3des }, 65 { "3des", SSH_CIPHER_3DES, 8, 16, 0, evp_ssh1_3des },
82 { "blowfish", SSH_CIPHER_BLOWFISH, 8, 32, evp_ssh1_bf }, 66 { "blowfish", SSH_CIPHER_BLOWFISH, 8, 32, 0, evp_ssh1_bf },
83 67
84 { "3des-cbc", SSH_CIPHER_SSH2, 8, 24, EVP_des_ede3_cbc }, 68 { "3des-cbc", SSH_CIPHER_SSH2, 8, 24, 0, EVP_des_ede3_cbc },
85 { "blowfish-cbc", SSH_CIPHER_SSH2, 8, 16, EVP_bf_cbc }, 69 { "blowfish-cbc", SSH_CIPHER_SSH2, 8, 16, 0, EVP_bf_cbc },
86 { "cast128-cbc", SSH_CIPHER_SSH2, 8, 16, EVP_cast5_cbc }, 70 { "cast128-cbc", SSH_CIPHER_SSH2, 8, 16, 0, EVP_cast5_cbc },
87 { "arcfour", SSH_CIPHER_SSH2, 8, 16, EVP_rc4 }, 71 { "arcfour", SSH_CIPHER_SSH2, 8, 16, 0, EVP_rc4 },
88#if OPENSSL_VERSION_NUMBER < 0x00907000L 72 { "arcfour128", SSH_CIPHER_SSH2, 8, 16, 1536, EVP_rc4 },
89 { "aes128-cbc", SSH_CIPHER_SSH2, 16, 16, evp_rijndael }, 73 { "arcfour256", SSH_CIPHER_SSH2, 8, 32, 1536, EVP_rc4 },
90 { "aes192-cbc", SSH_CIPHER_SSH2, 16, 24, evp_rijndael }, 74 { "aes128-cbc", SSH_CIPHER_SSH2, 16, 16, 0, EVP_aes_128_cbc },
91 { "aes256-cbc", SSH_CIPHER_SSH2, 16, 32, evp_rijndael }, 75 { "aes192-cbc", SSH_CIPHER_SSH2, 16, 24, 0, EVP_aes_192_cbc },
76 { "aes256-cbc", SSH_CIPHER_SSH2, 16, 32, 0, EVP_aes_256_cbc },
92 { "rijndael-cbc@lysator.liu.se", 77 { "rijndael-cbc@lysator.liu.se",
93 SSH_CIPHER_SSH2, 16, 32, evp_rijndael }, 78 SSH_CIPHER_SSH2, 16, 32, 0, EVP_aes_256_cbc },
94#else 79 { "aes128-ctr", SSH_CIPHER_SSH2, 16, 16, 0, evp_aes_128_ctr },
95 { "aes128-cbc", SSH_CIPHER_SSH2, 16, 16, EVP_aes_128_cbc }, 80 { "aes192-ctr", SSH_CIPHER_SSH2, 16, 24, 0, evp_aes_128_ctr },
96 { "aes192-cbc", SSH_CIPHER_SSH2, 16, 24, EVP_aes_192_cbc }, 81 { "aes256-ctr", SSH_CIPHER_SSH2, 16, 32, 0, evp_aes_128_ctr },
97 { "aes256-cbc", SSH_CIPHER_SSH2, 16, 32, EVP_aes_256_cbc }, 82#ifdef USE_CIPHER_ACSS
98 { "rijndael-cbc@lysator.liu.se", 83 { "acss@openssh.org", SSH_CIPHER_SSH2, 16, 5, 0, EVP_acss },
99 SSH_CIPHER_SSH2, 16, 32, EVP_aes_256_cbc },
100#endif
101#if OPENSSL_VERSION_NUMBER >= 0x00905000L
102 { "aes128-ctr", SSH_CIPHER_SSH2, 16, 16, evp_aes_128_ctr },
103 { "aes192-ctr", SSH_CIPHER_SSH2, 16, 24, evp_aes_128_ctr },
104 { "aes256-ctr", SSH_CIPHER_SSH2, 16, 32, evp_aes_128_ctr },
105#endif 84#endif
106#if defined(EVP_CTRL_SET_ACSS_MODE) 85 { NULL, SSH_CIPHER_INVALID, 0, 0, 0, NULL }
107 { "acss@openssh.org", SSH_CIPHER_SSH2, 16, 5, EVP_acss },
108#endif
109 { NULL, SSH_CIPHER_INVALID, 0, 0, NULL }
110}; 86};
111 87
112/*--*/ 88/*--*/
@@ -222,8 +198,9 @@ cipher_init(CipherContext *cc, Cipher *cipher,
222 EVP_CIPHER *type; 198 EVP_CIPHER *type;
223#else 199#else
224 const EVP_CIPHER *type; 200 const EVP_CIPHER *type;
225#endif
226 int klen; 201 int klen;
202#endif
203 u_char *junk, *discard;
227 204
228 if (cipher->number == SSH_CIPHER_DES) { 205 if (cipher->number == SSH_CIPHER_DES) {
229 if (dowarn) { 206 if (dowarn) {
@@ -261,7 +238,7 @@ cipher_init(CipherContext *cc, Cipher *cipher,
261 fatal("cipher_init: EVP_CipherInit failed for %s", 238 fatal("cipher_init: EVP_CipherInit failed for %s",
262 cipher->name); 239 cipher->name);
263 klen = EVP_CIPHER_CTX_key_length(&cc->evp); 240 klen = EVP_CIPHER_CTX_key_length(&cc->evp);
264 if (klen > 0 && keylen != klen) { 241 if (klen > 0 && keylen != (u_int)klen) {
265 debug2("cipher_init: set keylen (%d -> %d)", klen, keylen); 242 debug2("cipher_init: set keylen (%d -> %d)", klen, keylen);
266 if (EVP_CIPHER_CTX_set_key_length(&cc->evp, keylen) == 0) 243 if (EVP_CIPHER_CTX_set_key_length(&cc->evp, keylen) == 0)
267 fatal("cipher_init: set keylen failed (%d -> %d)", 244 fatal("cipher_init: set keylen failed (%d -> %d)",
@@ -271,6 +248,17 @@ cipher_init(CipherContext *cc, Cipher *cipher,
271 fatal("cipher_init: EVP_CipherInit: set key failed for %s", 248 fatal("cipher_init: EVP_CipherInit: set key failed for %s",
272 cipher->name); 249 cipher->name);
273#endif 250#endif
251
252 if (cipher->discard_len > 0) {
253 junk = xmalloc(cipher->discard_len);
254 discard = xmalloc(cipher->discard_len);
255 if (EVP_Cipher(&cc->evp, discard, junk,
256 cipher->discard_len) == 0)
257 fatal("evp_crypt: EVP_Cipher failed during discard");
258 memset(discard, 0, cipher->discard_len);
259 xfree(junk);
260 xfree(discard);
261 }
274} 262}
275 263
276void 264void
@@ -278,23 +266,15 @@ cipher_crypt(CipherContext *cc, u_char *dest, const u_char *src, u_int len)
278{ 266{
279 if (len % cc->cipher->block_size) 267 if (len % cc->cipher->block_size)
280 fatal("cipher_encrypt: bad plaintext length %d", len); 268 fatal("cipher_encrypt: bad plaintext length %d", len);
281#ifdef SSH_OLD_EVP
282 EVP_Cipher(&cc->evp, dest, (u_char *)src, len);
283#else
284 if (EVP_Cipher(&cc->evp, dest, (u_char *)src, len) == 0) 269 if (EVP_Cipher(&cc->evp, dest, (u_char *)src, len) == 0)
285 fatal("evp_crypt: EVP_Cipher failed"); 270 fatal("evp_crypt: EVP_Cipher failed");
286#endif
287} 271}
288 272
289void 273void
290cipher_cleanup(CipherContext *cc) 274cipher_cleanup(CipherContext *cc)
291{ 275{
292#ifdef SSH_OLD_EVP
293 EVP_CIPHER_CTX_cleanup(&cc->evp);
294#else
295 if (EVP_CIPHER_CTX_cleanup(&cc->evp) == 0) 276 if (EVP_CIPHER_CTX_cleanup(&cc->evp) == 0)
296 error("cipher_cleanup: EVP_CIPHER_CTX_cleanup failed"); 277 error("cipher_cleanup: EVP_CIPHER_CTX_cleanup failed");
297#endif
298} 278}
299 279
300/* 280/*
@@ -349,9 +329,9 @@ cipher_get_keyiv(CipherContext *cc, u_char *iv, u_int len)
349 case SSH_CIPHER_DES: 329 case SSH_CIPHER_DES:
350 case SSH_CIPHER_BLOWFISH: 330 case SSH_CIPHER_BLOWFISH:
351 evplen = EVP_CIPHER_CTX_iv_length(&cc->evp); 331 evplen = EVP_CIPHER_CTX_iv_length(&cc->evp);
352 if (evplen == 0) 332 if (evplen <= 0)
353 return; 333 return;
354 if (evplen != len) 334 if ((u_int)evplen != len)
355 fatal("%s: wrong iv length %d != %d", __func__, 335 fatal("%s: wrong iv length %d != %d", __func__,
356 evplen, len); 336 evplen, len);
357#if OPENSSL_VERSION_NUMBER < 0x00907000L 337#if OPENSSL_VERSION_NUMBER < 0x00907000L