From 51c568b30980e5993b4d493fe438d5196d5d0bd1 Mon Sep 17 00:00:00 2001 From: Ben Laurie Date: Sat, 30 Aug 2003 15:50:26 +0000 Subject: [PATCH] Add 3-DES CFB-r mode (no test vectors yet). --- crypto/des/cfb64ede.c | 111 +++++++++++++++++++++++++++++++++++++ crypto/des/des.h | 4 ++ crypto/evp/e_des3.c | 46 +++++++++++++++ crypto/objects/obj_dat.h | 12 +++- crypto/objects/obj_mac.h | 8 +++ crypto/objects/obj_mac.num | 2 + crypto/objects/objects.txt | 2 + 7 files changed, 182 insertions(+), 3 deletions(-) diff --git a/crypto/des/cfb64ede.c b/crypto/des/cfb64ede.c index 60c1aa08db..7ec54c6b6f 100644 --- a/crypto/des/cfb64ede.c +++ b/crypto/des/cfb64ede.c @@ -140,3 +140,114 @@ void DES_ede2_cfb64_encrypt(unsigned char *in, unsigned char *out, long length, DES_ede3_cfb64_encrypt(in,out,length,ks1,ks2,ks1,ivec,num,enc); } #endif + +/* This is compatible with the single key CFB-r for DES, even thought that's + * not what EVP needs. + */ + +void DES_ede3_cfb_encrypt(const unsigned char *in,unsigned char *out, + int numbits,long length,DES_key_schedule *ks1, + DES_key_schedule *ks2,DES_key_schedule *ks3, + DES_cblock *ivec,int enc) + { + register DES_LONG d0,d1,v0,v1,n=(numbits+7)/8; + register unsigned long l=length; + register int num=numbits; + DES_LONG ti[2]; + unsigned char *iv; + unsigned char ovec[16]; + + if (num > 64) return; + iv = &(*ivec)[0]; + c2l(iv,v0); + c2l(iv,v1); + if (enc) + { + while (l >= n) + { + l-=n; + ti[0]=v0; + ti[1]=v1; + DES_encrypt3(ti,ks1,ks2,ks3); + c2ln(in,d0,d1,n); + in+=n; + d0^=ti[0]; + d1^=ti[1]; + l2cn(d0,d1,out,n); + out+=n; + /* 30-08-94 - eay - changed because l>>32 and + * l<<32 are bad under gcc :-( */ + if (num == 32) + { v0=v1; v1=d0; } + else if (num == 64) + { v0=d0; v1=d1; } + else + { + iv=&ovec[0]; + l2c(v0,iv); + l2c(v1,iv); + l2c(d0,iv); + l2c(d1,iv); + /* shift ovec left most of the bits... */ + memmove(ovec,ovec+num/8,8+(num%8 ? 1 : 0)); + /* now the remaining bits */ + if(num%8 != 0) + for(n=0 ; n < 8 ; ++n) + { + ovec[n]<<=num%8; + ovec[n]|=ovec[n+1]>>(8-num%8); + } + iv=&ovec[0]; + c2l(iv,v0); + c2l(iv,v1); + } + } + } + else + { + while (l >= n) + { + l-=n; + ti[0]=v0; + ti[1]=v1; + DES_encrypt3(ti,ks1,ks2,ks3); + c2ln(in,d0,d1,n); + in+=n; + /* 30-08-94 - eay - changed because l>>32 and + * l<<32 are bad under gcc :-( */ + if (num == 32) + { v0=v1; v1=d0; } + else if (num == 64) + { v0=d0; v1=d1; } + else + { + iv=&ovec[0]; + l2c(v0,iv); + l2c(v1,iv); + l2c(d0,iv); + l2c(d1,iv); + /* shift ovec left most of the bits... */ + memmove(ovec,ovec+num/8,8+(num%8 ? 1 : 0)); + /* now the remaining bits */ + if(num%8 != 0) + for(n=0 ; n < 8 ; ++n) + { + ovec[n]<<=num%8; + ovec[n]|=ovec[n+1]>>(8-num%8); + } + iv=&ovec[0]; + c2l(iv,v0); + c2l(iv,v1); + } + d0^=ti[0]; + d1^=ti[1]; + l2cn(d0,d1,out,n); + out+=n; + } + } + iv = &(*ivec)[0]; + l2c(v0,iv); + l2c(v1,iv); + v0=v1=d0=d1=ti[0]=ti[1]=0; + } + diff --git a/crypto/des/des.h b/crypto/des/des.h index bb3a0e299d..c5df1c9c7b 100644 --- a/crypto/des/des.h +++ b/crypto/des/des.h @@ -187,6 +187,10 @@ void DES_ede3_cfb64_encrypt(const unsigned char *in,unsigned char *out, long length,DES_key_schedule *ks1, DES_key_schedule *ks2,DES_key_schedule *ks3, DES_cblock *ivec,int *num,int enc); +void DES_ede3_cfb_encrypt(const unsigned char *in,unsigned char *out, + int numbits,long length,DES_key_schedule *ks1, + DES_key_schedule *ks2,DES_key_schedule *ks3, + DES_cblock *ivec,int enc); void DES_ede3_ofb64_encrypt(const unsigned char *in,unsigned char *out, long length,DES_key_schedule *ks1, DES_key_schedule *ks2,DES_key_schedule *ks3, diff --git a/crypto/evp/e_des3.c b/crypto/evp/e_des3.c index 6e3d8d57c0..3e1132289d 100644 --- a/crypto/evp/e_des3.c +++ b/crypto/evp/e_des3.c @@ -130,6 +130,42 @@ static int des_ede_cfb64_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, return 1; } +/* Although we have a CFB-r implementation for 3-DES, it doesn't pack the right + way, so wrap it here */ +static int des_ede3_cfb1_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, + const unsigned char *in, unsigned int inl) + { + unsigned int n; + unsigned char c[8],d[8]; /* DES_cfb_encrypt rudely overwrites the whole buffer*/ + + memset(out,0,(inl+7)/8); + for(n=0 ; n < inl ; ++n) + { + c[0]=(in[n/8]&(1 << (7-n%8))) ? 0x80 : 0; + DES_ede3_cfb_encrypt(c,d,1,1, + &data(ctx)->ks1,&data(ctx)->ks2,&data(ctx)->ks3, + (DES_cblock *)ctx->iv,ctx->encrypt); + out[n/8]=(out[n/8]&~(0x80 >> (n%8)))|((d[0]&0x80) >> (n%8)); + } + + return 1; + } + +static int des_ede3_cfb8_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, + const unsigned char *in, unsigned int inl) + { + unsigned char *tmp; /* DES_cfb_encrypt rudely overwrites the whole buffer*/ + + tmp=alloca(inl+7); + memcpy(tmp,in,inl); + DES_ede3_cfb_encrypt(tmp,tmp,8,inl, + &data(ctx)->ks1,&data(ctx)->ks2,&data(ctx)->ks3, + (DES_cblock *)ctx->iv,ctx->encrypt); + memcpy(out,tmp,inl); + + return 1; + } + BLOCK_CIPHER_defs(des_ede, DES_EDE_KEY, NID_des_ede, 8, 16, 8, 64, 0, des_ede_init_key, NULL, EVP_CIPHER_set_asn1_iv, @@ -147,6 +183,16 @@ BLOCK_CIPHER_defs(des_ede3, DES_EDE_KEY, NID_des_ede3, 8, 24, 8, 64, EVP_CIPHER_get_asn1_iv, NULL) +BLOCK_CIPHER_def_cfb(des_ede3,DES_EDE_KEY,NID_des_ede3,24,8,1,0, + des_ede3_init_key,NULL, + EVP_CIPHER_set_asn1_iv, + EVP_CIPHER_get_asn1_iv,NULL) + +BLOCK_CIPHER_def_cfb(des_ede3,DES_EDE_KEY,NID_des_ede3,24,8,8,0, + des_ede3_init_key,NULL, + EVP_CIPHER_set_asn1_iv, + EVP_CIPHER_get_asn1_iv,NULL) + static int des_ede_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key, const unsigned char *iv, int enc) { diff --git a/crypto/objects/obj_dat.h b/crypto/objects/obj_dat.h index 08a9928e96..9de7b1217e 100644 --- a/crypto/objects/obj_dat.h +++ b/crypto/objects/obj_dat.h @@ -62,9 +62,9 @@ * [including the GNU Public Licence.] */ -#define NUM_NID 658 -#define NUM_SN 651 -#define NUM_LN 651 +#define NUM_NID 660 +#define NUM_SN 653 +#define NUM_LN 653 #define NUM_OBJ 617 static unsigned char lvalues[4455]={ @@ -1736,6 +1736,8 @@ static ASN1_OBJECT nid_objs[NUM_NID]={ {"AES-256-CFB8","aes-256-cfb8",NID_aes_256_cfb8,0,NULL}, {"DES-CFB1","des-cfb1",NID_des_cfb1,0,NULL}, {"DES-CFB8","des-cfb8",NID_des_cfb8,0,NULL}, +{"DES-EDE3-CFB1","des-ede3-cfb1",NID_des_ede3_cfb1,0,NULL}, +{"DES-EDE3-CFB8","des-ede3-cfb8",NID_des_ede3_cfb8,0,NULL}, }; static ASN1_OBJECT *sn_objs[NUM_SN]={ @@ -1786,6 +1788,8 @@ static ASN1_OBJECT *sn_objs[NUM_SN]={ &(nid_objs[33]),/* "DES-EDE3" */ &(nid_objs[44]),/* "DES-EDE3-CBC" */ &(nid_objs[61]),/* "DES-EDE3-CFB" */ +&(nid_objs[658]),/* "DES-EDE3-CFB1" */ +&(nid_objs[659]),/* "DES-EDE3-CFB8" */ &(nid_objs[63]),/* "DES-EDE3-OFB" */ &(nid_objs[45]),/* "DES-OFB" */ &(nid_objs[80]),/* "DESX-CBC" */ @@ -2563,6 +2567,8 @@ static ASN1_OBJECT *ln_objs[NUM_LN]={ &(nid_objs[33]),/* "des-ede3" */ &(nid_objs[44]),/* "des-ede3-cbc" */ &(nid_objs[61]),/* "des-ede3-cfb" */ +&(nid_objs[658]),/* "des-ede3-cfb1" */ +&(nid_objs[659]),/* "des-ede3-cfb8" */ &(nid_objs[63]),/* "des-ede3-ofb" */ &(nid_objs[45]),/* "des-ofb" */ &(nid_objs[107]),/* "description" */ diff --git a/crypto/objects/obj_mac.h b/crypto/objects/obj_mac.h index 04ee272ffe..ceeaaa391d 100644 --- a/crypto/objects/obj_mac.h +++ b/crypto/objects/obj_mac.h @@ -2041,6 +2041,14 @@ #define LN_des_cfb8 "des-cfb8" #define NID_des_cfb8 657 +#define SN_des_ede3_cfb1 "DES-EDE3-CFB1" +#define LN_des_ede3_cfb1 "des-ede3-cfb1" +#define NID_des_ede3_cfb1 658 + +#define SN_des_ede3_cfb8 "DES-EDE3-CFB8" +#define LN_des_ede3_cfb8 "des-ede3-cfb8" +#define NID_des_ede3_cfb8 659 + #define SN_hold_instruction_code "holdInstructionCode" #define LN_hold_instruction_code "Hold Instruction Code" #define NID_hold_instruction_code 430 diff --git a/crypto/objects/obj_mac.num b/crypto/objects/obj_mac.num index 091a9a4eb7..4dffeaed22 100644 --- a/crypto/objects/obj_mac.num +++ b/crypto/objects/obj_mac.num @@ -655,3 +655,5 @@ aes_192_cfb8 654 aes_256_cfb8 655 des_cfb1 656 des_cfb8 657 +des_ede3_cfb1 658 +des_ede3_cfb8 659 diff --git a/crypto/objects/objects.txt b/crypto/objects/objects.txt index 5299d7b3aa..cd315d0cc0 100644 --- a/crypto/objects/objects.txt +++ b/crypto/objects/objects.txt @@ -691,6 +691,8 @@ aes 44 : AES-256-CFB : aes-256-cfb : AES-256-CFB8 : aes-256-cfb8 : DES-CFB1 : des-cfb1 : DES-CFB8 : des-cfb8 + : DES-EDE3-CFB1 : des-ede3-cfb1 + : DES-EDE3-CFB8 : des-ede3-cfb8 # Hold instruction CRL entry extension !Cname hold-instruction-code -- 2.25.1