summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMarkus Friedl <markus@cvs.openbsd.org>2003-09-24 10:13:44 +0000
committerMarkus Friedl <markus@cvs.openbsd.org>2003-09-24 10:13:44 +0000
commit8fb6dc36aafc4e88a71f21465125a39f218c6486 (patch)
treed384f5ec5c9f65bbf5f7acd28c80339e27c381fc
parent67dad3bb6434822c3d946151d6e0a8d4e5e13b97 (diff)
back out EVP change; causes fd leaks; ok cedric@
-rw-r--r--sbin/isakmpd/crypto.c209
-rw-r--r--sbin/isakmpd/crypto.h75
-rw-r--r--sbin/isakmpd/regress/crypto/cryptotest.c4
3 files changed, 203 insertions, 85 deletions
diff --git a/sbin/isakmpd/crypto.c b/sbin/isakmpd/crypto.c
index 54ce6104919..df63774f80b 100644
--- a/sbin/isakmpd/crypto.c
+++ b/sbin/isakmpd/crypto.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: crypto.c,v 1.16 2003/08/28 14:43:35 markus Exp $ */
+/* $OpenBSD: crypto.c,v 1.17 2003/09/24 10:13:43 markus Exp $ */
/* $EOM: crypto.c,v 1.32 2000/03/07 20:08:51 niklas Exp $ */
/*
@@ -39,151 +39,216 @@
#include "crypto.h"
#include "log.h"
-enum cryptoerr evp_init (struct keystate *, u_int8_t *, u_int16_t,
- const EVP_CIPHER *);
enum cryptoerr des1_init (struct keystate *, u_int8_t *, u_int16_t);
enum cryptoerr des3_init (struct keystate *, u_int8_t *, u_int16_t);
enum cryptoerr blf_init (struct keystate *, u_int8_t *, u_int16_t);
enum cryptoerr cast_init (struct keystate *, u_int8_t *, u_int16_t);
-enum cryptoerr aes_init (struct keystate *, u_int8_t *, u_int16_t);
-void evp_encrypt (struct keystate *, u_int8_t *, u_int16_t);
-void evp_decrypt (struct keystate *, u_int8_t *, u_int16_t);
+void des1_encrypt (struct keystate *, u_int8_t *, u_int16_t);
+void des1_decrypt (struct keystate *, u_int8_t *, u_int16_t);
+void des3_encrypt (struct keystate *, u_int8_t *, u_int16_t);
+void des3_decrypt (struct keystate *, u_int8_t *, u_int16_t);
+void blf_encrypt (struct keystate *, u_int8_t *, u_int16_t);
+void blf_decrypt (struct keystate *, u_int8_t *, u_int16_t);
+void cast1_encrypt (struct keystate *, u_int8_t *, u_int16_t);
+void cast1_decrypt (struct keystate *, u_int8_t *, u_int16_t);
struct crypto_xf transforms[] = {
#ifdef USE_DES
{
DES_CBC, "Data Encryption Standard (CBC-Mode)", 8, 8, BLOCKSIZE, 0,
des1_init,
- evp_encrypt, evp_decrypt
+ des1_encrypt, des1_decrypt
},
#endif
#ifdef USE_TRIPLEDES
{
TRIPLEDES_CBC, "Triple-DES (CBC-Mode)", 24, 24, BLOCKSIZE, 0,
des3_init,
- evp_encrypt, evp_decrypt
+ des3_encrypt, des3_decrypt
},
#endif
#ifdef USE_BLOWFISH
{
BLOWFISH_CBC, "Blowfish (CBC-Mode)", 12, 56, BLOCKSIZE, 0,
blf_init,
- evp_encrypt, evp_decrypt
+ blf_encrypt, blf_decrypt
},
#endif
#ifdef USE_CAST
{
CAST_CBC, "CAST (CBC-Mode)", 12, 16, BLOCKSIZE, 0,
cast_init,
- evp_encrypt, evp_decrypt
- },
-#endif
-#ifdef USE_AES
- {
- AES_CBC, "AES (CBC-Mode)", 16, 32, 2*BLOCKSIZE, 0,
- aes_init,
- evp_encrypt, evp_decrypt
+ cast1_encrypt, cast1_decrypt
},
#endif
};
-#ifdef USE_DES
+/* Hmm, the function prototypes for des are really dumb */
+#ifdef __OpenBSD__
+#define DC (des_cblock *)
+#else
+#define DC (void *)
+#endif
+
enum cryptoerr
des1_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
{
- const EVP_CIPHER *evp;
+ /* des_set_key returns -1 for parity problems, and -2 for weak keys */
+ des_set_odd_parity (DC key);
+ switch (des_set_key (DC key, ks->ks_des[0]))
+ {
+ case -2:
+ return EWEAKKEY;
+ default:
+ return EOKAY;
+ }
+}
- evp = EVP_des_cbc();
- return evp_init (ks, key, len, evp);
+void
+des1_encrypt (struct keystate *ks, u_int8_t *d, u_int16_t len)
+{
+ des_cbc_encrypt (DC d, DC d, len, ks->ks_des[0], DC ks->riv, DES_ENCRYPT);
+}
+
+void
+des1_decrypt (struct keystate *ks, u_int8_t *d, u_int16_t len)
+{
+ des_cbc_encrypt (DC d, DC d, len, ks->ks_des[0], DC ks->riv, DES_DECRYPT);
}
-#endif
#ifdef USE_TRIPLEDES
enum cryptoerr
des3_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
{
- const EVP_CIPHER *evp;
+ des_set_odd_parity (DC key);
+ des_set_odd_parity (DC (key + 8));
+ des_set_odd_parity (DC (key + 16));
+
+ /* As of the draft Tripe-DES does not check for weak keys */
+ des_set_key (DC key, ks->ks_des[0]);
+ des_set_key (DC (key + 8), ks->ks_des[1]);
+ des_set_key (DC (key + 16), ks->ks_des[2]);
- evp = EVP_des_ede3_cbc();
- return evp_init (ks, key, len, evp);
+ return EOKAY;
}
-#endif
+
+void
+des3_encrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
+{
+ u_int8_t iv[MAXBLK];
+
+ memcpy (iv, ks->riv, ks->xf->blocksize);
+ des_ede3_cbc_encrypt (DC data, DC data, len, ks->ks_des[0], ks->ks_des[1],
+ ks->ks_des[2], DC iv, DES_ENCRYPT);
+}
+
+void
+des3_decrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
+{
+ u_int8_t iv[MAXBLK];
+
+ memcpy (iv, ks->riv, ks->xf->blocksize);
+ des_ede3_cbc_encrypt (DC data, DC data, len, ks->ks_des[0], ks->ks_des[1],
+ ks->ks_des[2], DC iv, DES_DECRYPT);
+}
+#undef DC
+#endif /* USE_TRIPLEDES */
#ifdef USE_BLOWFISH
enum cryptoerr
blf_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
{
- const EVP_CIPHER *evp;
+ blf_key (&ks->ks_blf, key, len);
- evp = EVP_bf_cbc();
- return evp_init (ks, key, len, evp);
+ return EOKAY;
}
-#endif
-#ifdef USE_CAST
-enum cryptoerr
-cast_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
+void
+blf_encrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
{
- const EVP_CIPHER *evp;
+ u_int16_t i, blocksize = ks->xf->blocksize;
+ u_int8_t *iv = ks->liv;
+ u_int32_t xl, xr;
- evp = EVP_cast5_cbc();
- return evp_init (ks, key, len, evp);
+ memcpy (iv, ks->riv, blocksize);
+
+ for (i = 0; i < len; data += blocksize, i += blocksize)
+ {
+ XOR64 (data, iv);
+ xl = GET_32BIT_BIG (data);
+ xr = GET_32BIT_BIG (data + 4);
+ Blowfish_encipher (&ks->ks_blf, &xl, &xr);
+ SET_32BIT_BIG (data, xl);
+ SET_32BIT_BIG (data + 4, xr);
+ SET64 (iv, data);
+ }
}
-#endif
-#ifdef USE_AES
-enum cryptoerr
-aes_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
+void
+blf_decrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
{
- const EVP_CIPHER *evp;
+ u_int16_t i, blocksize = ks->xf->blocksize;
+ u_int32_t xl, xr;
- switch (8 * len)
+ data += len - blocksize;
+ for (i = len - blocksize; i >= blocksize; data -= blocksize, i -= blocksize)
{
- case 128:
- evp = EVP_aes_128_cbc();
- break;
- case 192:
- evp = EVP_aes_192_cbc();
- break;
- case 256:
- evp = EVP_aes_256_cbc();
- break;
- default:
- return EKEYLEN;
+ xl = GET_32BIT_BIG (data);
+ xr = GET_32BIT_BIG (data + 4);
+ Blowfish_decipher (&ks->ks_blf, &xl, &xr);
+ SET_32BIT_BIG (data, xl);
+ SET_32BIT_BIG (data + 4, xr);
+ XOR64 (data, data - blocksize);
+
}
- return evp_init (ks, key, len, evp);
+ xl = GET_32BIT_BIG (data);
+ xr = GET_32BIT_BIG (data + 4);
+ Blowfish_decipher (&ks->ks_blf, &xl, &xr);
+ SET_32BIT_BIG (data, xl);
+ SET_32BIT_BIG (data + 4, xr);
+ XOR64 (data, ks->riv);
}
-#endif
+#endif /* USE_BLOWFISH */
+#ifdef USE_CAST
enum cryptoerr
-evp_init (struct keystate *ks, u_int8_t *key, u_int16_t len, const EVP_CIPHER *evp)
+cast_init (struct keystate *ks, u_int8_t *key, u_int16_t len)
{
- EVP_CIPHER_CTX_init(&ks->ks_evpenc);
- EVP_CIPHER_CTX_init(&ks->ks_evpdec);
-
- if (EVP_CIPHER_key_length(evp) != len
- && !(EVP_CIPHER_flags(evp) & EVP_CIPH_VARIABLE_LENGTH))
- return EKEYLEN;
- if (EVP_CipherInit(&ks->ks_evpenc, evp, key, NULL, 1) <= 0)
- return EKEYLEN;
- if (EVP_CipherInit(&ks->ks_evpdec, evp, key, NULL, 0) <= 0)
- return EKEYLEN;
+ cast_setkey (&ks->ks_cast, key, len);
return EOKAY;
}
void
-evp_encrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
+cast1_encrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
{
- (void) EVP_CipherInit(&ks->ks_evpenc, NULL, NULL, ks->riv, -1);
- EVP_Cipher(&ks->ks_evpenc, data, data, len);
+ u_int16_t i, blocksize = ks->xf->blocksize;
+ u_int8_t *iv = ks->liv;
+
+ memcpy (iv, ks->riv, blocksize);
+
+ for (i = 0; i < len; data += blocksize, i += blocksize)
+ {
+ XOR64 (data, iv);
+ cast_encrypt (&ks->ks_cast, data, data);
+ SET64 (iv, data);
+ }
}
void
-evp_decrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
+cast1_decrypt (struct keystate *ks, u_int8_t *data, u_int16_t len)
{
- (void) EVP_CipherInit(&ks->ks_evpdec, NULL, NULL, ks->riv, -1);
- EVP_Cipher(&ks->ks_evpdec, data, data, len);
+ u_int16_t i, blocksize = ks->xf->blocksize;
+
+ data += len - blocksize;
+ for (i = len - blocksize; i >= blocksize; data -= blocksize, i -= blocksize)
+ {
+ cast_decrypt (&ks->ks_cast, data, data);
+ XOR64 (data, data - blocksize);
+ }
+ cast_decrypt (&ks->ks_cast, data, data);
+ XOR64 (data, ks->riv);
}
+#endif /* USE_CAST */
struct crypto_xf *
crypto_get (enum transform id)
diff --git a/sbin/isakmpd/crypto.h b/sbin/isakmpd/crypto.h
index 6cce31f19e7..8de039b88a8 100644
--- a/sbin/isakmpd/crypto.h
+++ b/sbin/isakmpd/crypto.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: crypto.h,v 1.9 2003/08/28 14:43:35 markus Exp $ */
+/* $OpenBSD: crypto.h,v 1.10 2003/09/24 10:13:43 markus Exp $ */
/* $EOM: crypto.h,v 1.12 2000/10/15 21:56:41 niklas Exp $ */
/*
@@ -32,7 +32,56 @@
#ifndef _CRYPTO_H_
#define _CRYPTO_H_
-#include <openssl/evp.h>
+#if defined (__APPLE__)
+
+#include <openssl/des.h>
+#ifdef USE_BLOWFISH
+#include <openssl/blowfish.h>
+#endif
+#ifdef USE_CAST
+#include <openssl/cast.h>
+#endif
+
+#else
+
+#include <des.h>
+#ifdef USE_BLOWFISH
+#include <blf.h>
+#endif
+#ifdef USE_CAST
+#include <cast.h>
+#endif
+
+#endif /* __APPLE__ */
+
+#define USE_32BIT
+#if defined (USE_64BIT)
+
+#define XOR64(x,y) *(u_int64_t *)(x) ^= *(u_int64_t *)(y);
+#define SET64(x,y) *(u_int64_t *)(x) = *(u_int64_t *)(y);
+
+#elif defined (USE_32BIT)
+
+#define XOR64(x,y) *(u_int32_t *)(x) ^= *(u_int32_t *)(y); \
+ *(u_int32_t *)((u_int8_t *)(x) + 4) ^= *(u_int32_t *)((u_int8_t *)(y) + 4);
+#define SET64(x,y) *(u_int32_t *)(x) = *(u_int32_t *)(y); \
+ *(u_int32_t *)((u_int8_t *)(x) + 4) = *(u_int32_t *)((u_int8_t *)(y) + 4);
+
+#else
+
+#define XOR8(x,y,i) (x)[i] ^= (y)[i];
+#define XOR64(x,y) XOR8(x,y,0); XOR8(x,y,1); XOR8(x,y,2); XOR8(x,y,3); \
+ XOR8(x,y,4); XOR8(x,y,5); XOR8(x,y,6); XOR8(x,y,7);
+#define SET8(x,y,i) (x)[i] = (y)[i];
+#define SET64(x,y) SET8(x,y,0); SET8(x,y,1); SET8(x,y,2); SET8(x,y,3); \
+ SET8(x,y,4); SET8(x,y,5); SET8(x,y,6); SET8(x,y,7);
+
+#endif /* USE_64BIT */
+
+#define SET_32BIT_BIG(x,y) (x)[3]= (y); (x)[2]= (y) >> 8; \
+ (x)[1] = (y) >> 16; (x)[0]= (y) >> 24;
+#define GET_32BIT_BIG(x) (u_int32_t)(x)[3] | ((u_int32_t)(x)[2] << 8) | \
+ ((u_int32_t)(x)[1] << 16)| ((u_int32_t)(x)[0] << 24);
/*
* This is standard for all block ciphers we use at the moment.
@@ -41,7 +90,7 @@
*/
#define BLOCKSIZE 8
-#define MAXBLK (2*BLOCKSIZE)
+#define MAXBLK BLOCKSIZE
struct keystate {
struct crypto_xf *xf; /* Back pointer */
@@ -51,13 +100,20 @@ struct keystate {
u_int8_t iv[MAXBLK]; /* Next IV to use */
u_int8_t iv2[MAXBLK];
u_int8_t *riv, *liv;
- struct {
- EVP_CIPHER_CTX enc, dec;
- } evp;
+ union {
+ des_key_schedule desks[3];
+#ifdef USE_BLOWFISH
+ blf_ctx blfks;
+#endif
+#ifdef USE_CAST
+ cast_key castks;
+#endif
+ } keydata;
};
-#define ks_evpenc evp.enc
-#define ks_evpdec evp.dec
+#define ks_des keydata.desks
+#define ks_blf keydata.blfks
+#define ks_cast keydata.castks
/*
* Information about the cryptotransform.
@@ -74,8 +130,7 @@ enum transform {
BLOWFISH_CBC=3,
RC5_R16_B64_CBC=4, /* Licensed, DONT use */
TRIPLEDES_CBC=5, /* This is a SHOULD */
- CAST_CBC=6,
- AES_CBC=7
+ CAST_CBC=6
};
enum cryptoerr {
diff --git a/sbin/isakmpd/regress/crypto/cryptotest.c b/sbin/isakmpd/regress/crypto/cryptotest.c
index 6a9940f84f6..806f5610e8c 100644
--- a/sbin/isakmpd/regress/crypto/cryptotest.c
+++ b/sbin/isakmpd/regress/crypto/cryptotest.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: cryptotest.c,v 1.9 2003/08/28 14:43:35 markus Exp $ */
+/* $OpenBSD: cryptotest.c,v 1.10 2003/09/24 10:13:43 markus Exp $ */
/* $EOM: cryptotest.c,v 1.5 1998/10/07 16:40:49 niklas Exp $ */
/*
@@ -125,8 +125,6 @@ main (void)
test_crypto (CAST_CBC);
- test_crypto (AES_CBC);
-
special_test_blf ();
return 1;