mirror of
git://git.gnupg.org/gnupg.git
synced 2024-12-22 10:19:57 +01:00
cast5 does now work
This commit is contained in:
parent
aa713cb0f5
commit
53a578711f
8
NEWS
8
NEWS
@ -1,3 +1,11 @@
|
|||||||
|
Noteworthy changes in version 0.2.15
|
||||||
|
------------------------------------
|
||||||
|
|
||||||
|
* CAST5 works (using the PGP's special CFB mode).
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Noteworthy changes in version 0.2.14
|
Noteworthy changes in version 0.2.14
|
||||||
------------------------------------
|
------------------------------------
|
||||||
|
|
||||||
|
@ -1,6 +1,10 @@
|
|||||||
|
Sat Apr 4 19:52:08 1998 Werner Koch (wk@isil.d.shuttle.de)
|
||||||
|
|
||||||
|
* cast5.c: Implemented and tested.
|
||||||
|
|
||||||
Wed Apr 1 16:38:27 1998 Werner Koch (wk@isil.d.shuttle.de)
|
Wed Apr 1 16:38:27 1998 Werner Koch (wk@isil.d.shuttle.de)
|
||||||
|
|
||||||
* elgamla.c (elg_generate): Faster generation of x in some cases.
|
* elgamal.c (elg_generate): Faster generation of x in some cases.
|
||||||
|
|
||||||
Thu Mar 19 13:54:48 1998 Werner Koch (wk@isil.d.shuttle.de)
|
Thu Mar 19 13:54:48 1998 Werner Koch (wk@isil.d.shuttle.de)
|
||||||
|
|
||||||
|
@ -8,6 +8,8 @@ noinst_LIBRARIES = libcipher.a
|
|||||||
|
|
||||||
libcipher_a_SOURCES = blowfish.c \
|
libcipher_a_SOURCES = blowfish.c \
|
||||||
blowfish.h \
|
blowfish.h \
|
||||||
|
cast5.c \
|
||||||
|
cast5.h \
|
||||||
elgamal.c \
|
elgamal.c \
|
||||||
elgamal.h \
|
elgamal.h \
|
||||||
md5.c \
|
md5.c \
|
||||||
|
@ -99,6 +99,8 @@ noinst_LIBRARIES = libcipher.a
|
|||||||
|
|
||||||
libcipher_a_SOURCES = blowfish.c \
|
libcipher_a_SOURCES = blowfish.c \
|
||||||
blowfish.h \
|
blowfish.h \
|
||||||
|
cast5.c \
|
||||||
|
cast5.h \
|
||||||
elgamal.c \
|
elgamal.c \
|
||||||
elgamal.h \
|
elgamal.h \
|
||||||
md5.c \
|
md5.c \
|
||||||
@ -129,8 +131,8 @@ DEFS = @DEFS@ -I. -I$(srcdir) -I..
|
|||||||
CPPFLAGS = @CPPFLAGS@
|
CPPFLAGS = @CPPFLAGS@
|
||||||
LDFLAGS = @LDFLAGS@
|
LDFLAGS = @LDFLAGS@
|
||||||
LIBS = @LIBS@
|
LIBS = @LIBS@
|
||||||
libcipher_a_OBJECTS = blowfish.o elgamal.o md5.o primegen.o random.o \
|
libcipher_a_OBJECTS = blowfish.o cast5.o elgamal.o md5.o primegen.o \
|
||||||
rmd160.o sha1.o dsa.o md.o misc.o smallprime.o
|
random.o rmd160.o sha1.o dsa.o md.o misc.o smallprime.o
|
||||||
AR = ar
|
AR = ar
|
||||||
CFLAGS = @CFLAGS@
|
CFLAGS = @CFLAGS@
|
||||||
COMPILE = $(CC) $(DEFS) $(INCLUDES) $(CPPFLAGS) $(CFLAGS)
|
COMPILE = $(CC) $(DEFS) $(INCLUDES) $(CPPFLAGS) $(CFLAGS)
|
||||||
@ -142,9 +144,9 @@ DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST)
|
|||||||
|
|
||||||
TAR = tar
|
TAR = tar
|
||||||
GZIP = --best
|
GZIP = --best
|
||||||
DEP_FILES = .deps/blowfish.P .deps/dsa.P .deps/elgamal.P .deps/md.P \
|
DEP_FILES = .deps/blowfish.P .deps/cast5.P .deps/dsa.P .deps/elgamal.P \
|
||||||
.deps/md5.P .deps/misc.P .deps/primegen.P .deps/random.P .deps/rmd160.P \
|
.deps/md.P .deps/md5.P .deps/misc.P .deps/primegen.P .deps/random.P \
|
||||||
.deps/sha1.P .deps/smallprime.P
|
.deps/rmd160.P .deps/sha1.P .deps/smallprime.P
|
||||||
SOURCES = $(libcipher_a_SOURCES)
|
SOURCES = $(libcipher_a_SOURCES)
|
||||||
OBJECTS = $(libcipher_a_OBJECTS)
|
OBJECTS = $(libcipher_a_OBJECTS)
|
||||||
|
|
||||||
|
427
cipher/cast5.c
427
cipher/cast5.c
@ -18,6 +18,23 @@
|
|||||||
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/* Test vectors:
|
||||||
|
*
|
||||||
|
* 128-bit key = 01 23 45 67 12 34 56 78 23 45 67 89 34 56 78 9A
|
||||||
|
* plaintext = 01 23 45 67 89 AB CD EF
|
||||||
|
* ciphertext = 23 8B 4F E5 84 7E 44 B2
|
||||||
|
*
|
||||||
|
* 80-bit key = 01 23 45 67 12 34 56 78 23 45
|
||||||
|
* = 01 23 45 67 12 34 56 78 23 45 00 00 00 00 00 00
|
||||||
|
* plaintext = 01 23 45 67 89 AB CD EF
|
||||||
|
* ciphertext = EB 6A 71 1A 2C 02 27 1B
|
||||||
|
*
|
||||||
|
* 40-bit key = 01 23 45 67 12
|
||||||
|
* = 01 23 45 67 12 00 00 00 00 00 00 00 00 00 00 00
|
||||||
|
* plaintext = 01 23 45 67 89 AB CD EF
|
||||||
|
* ciphertext = 7A C8 16 D1 6E 9B 30 2E
|
||||||
|
*/
|
||||||
|
|
||||||
#include <config.h>
|
#include <config.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
@ -26,6 +43,7 @@
|
|||||||
#include "util.h"
|
#include "util.h"
|
||||||
#include "types.h"
|
#include "types.h"
|
||||||
#include "cast5.h"
|
#include "cast5.h"
|
||||||
|
#include "random.h"
|
||||||
|
|
||||||
static const u32 s1[256] = {
|
static const u32 s1[256] = {
|
||||||
0x30fb40d4, 0x9fa0ff0b, 0x6beccd2f, 0x3f258c7a, 0x1e213f2f, 0x9c004dd3, 0x6003e540, 0xcf9fc949,
|
0x30fb40d4, 0x9fa0ff0b, 0x6beccd2f, 0x3f258c7a, 0x1e213f2f, 0x9c004dd3, 0x6003e540, 0xcf9fc949,
|
||||||
@ -301,171 +319,251 @@ static const u32 s8[256] = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
#if defined(__GNUC__) && defined(__i386__)
|
||||||
|
static inline u32
|
||||||
|
rol(int n, u32 x)
|
||||||
static u32
|
|
||||||
function_F( CAST5_context *bc, u32 x )
|
|
||||||
{
|
{
|
||||||
u16 a, b, c, d, y;
|
__asm__("roll %%cl,%0"
|
||||||
|
:"=r" (x)
|
||||||
d = x & 0x00ff;
|
:"0" (x),"c" (n));
|
||||||
x >>= 8;
|
return x;
|
||||||
c = x & 0x00ff;
|
|
||||||
x >>= 8;
|
|
||||||
b = x & 0x00ff;
|
|
||||||
x >>= 8;
|
|
||||||
a = x & 0x00ff;
|
|
||||||
y = bc->s0[a] + bc->s1[b];
|
|
||||||
y ^= bc->s2[c];
|
|
||||||
y += bc->s3[d];
|
|
||||||
|
|
||||||
return y;
|
|
||||||
}
|
}
|
||||||
|
#else
|
||||||
|
#define rol(n,x) ( ((x) << (n)) | ((x) >> (32-(n))) )
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define F1(D,m,r) ( (I = ((m) + (D))), (I=rol((r),I)), \
|
||||||
|
(((s1[I >> 24] ^ s2[(I>>16)&0xff]) - s3[(I>>8)&0xff]) + s4[I&0xff]) )
|
||||||
|
#define F2(D,m,r) ( (I = ((m) ^ (D))), (I=rol((r),I)), \
|
||||||
|
(((s1[I >> 24] - s2[(I>>16)&0xff]) + s3[(I>>8)&0xff]) ^ s4[I&0xff]) )
|
||||||
|
#define F3(D,m,r) ( (I = ((m) - (D))), (I=rol((r),I)), \
|
||||||
|
(((s1[I >> 24] + s2[(I>>16)&0xff]) ^ s3[(I>>8)&0xff]) - s4[I&0xff]) )
|
||||||
|
|
||||||
static void
|
static void
|
||||||
encrypt( CAST5_context *bc, u32 *ret_xl, u32 *ret_xr )
|
encrypt_block( CAST5_context *c, byte *outbuf, byte *inbuf )
|
||||||
{
|
{
|
||||||
u32 xl, xr, temp;
|
u32 l, r, t;
|
||||||
int i;
|
u32 I; /* used by the Fx macros */
|
||||||
|
u32 *Km;
|
||||||
|
byte *Kr;
|
||||||
|
|
||||||
|
Km = c->Km;
|
||||||
|
Kr = c->Kr;
|
||||||
|
|
||||||
/* (L0,R0) <-- (m1...m64). (Split the plaintext into left and
|
/* (L0,R0) <-- (m1...m64). (Split the plaintext into left and
|
||||||
* right 32-bit halves L0 = m1...m32 and R0 = m33...m64.)
|
* right 32-bit halves L0 = m1...m32 and R0 = m33...m64.)
|
||||||
*/
|
*/
|
||||||
xl = *ret_xl;
|
l = inbuf[0] << 24 | inbuf[1] << 16 | inbuf[2] << 8 | inbuf[3];
|
||||||
xr = *ret_xr;
|
r = inbuf[4] << 24 | inbuf[5] << 16 | inbuf[6] << 8 | inbuf[7];
|
||||||
|
|
||||||
for(i=0; i < 16; i++ ) {
|
/* (16 rounds) for i from 1 to 16, compute Li and Ri as follows:
|
||||||
/* (16 rounds) for i from 1 to 16, compute Li and Ri as follows:
|
* Li = Ri-1;
|
||||||
* Li = Ri-1;
|
* Ri = Li-1 ^ f(Ri-1,Kmi,Kri), where f is defined in Section 2.2
|
||||||
* Ri = Li-1 ^ f(Ri-1,Kmi,Kri), where f is defined in Section 2.2
|
* Rounds 1, 4, 7, 10, 13, and 16 use f function Type 1.
|
||||||
* (f is of Type 1, Type 2, or Type 3, depending on i).
|
* Rounds 2, 5, 8, 11, and 14 use f function Type 2.
|
||||||
*/
|
* Rounds 3, 6, 9, 12, and 15 use f function Type 3.
|
||||||
xl ^= bc->p[i];
|
*/
|
||||||
xr ^= function_F(bc, xl);
|
|
||||||
temp = xl;
|
t = l; l = r; r = t ^ F1(r, Km[ 0], Kr[ 0]);
|
||||||
xl = xr;
|
t = l; l = r; r = t ^ F2(r, Km[ 1], Kr[ 1]);
|
||||||
xr = temp;
|
t = l; l = r; r = t ^ F3(r, Km[ 2], Kr[ 2]);
|
||||||
}
|
t = l; l = r; r = t ^ F1(r, Km[ 3], Kr[ 3]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[ 4], Kr[ 4]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[ 5], Kr[ 5]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 6], Kr[ 6]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[ 7], Kr[ 7]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[ 8], Kr[ 8]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 9], Kr[ 9]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[10], Kr[10]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[11], Kr[11]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[12], Kr[12]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[13], Kr[13]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[14], Kr[14]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[15], Kr[15]);
|
||||||
|
|
||||||
/* c1...c64 <-- (R16,L16). (Exchange final blocks L16, R16 and
|
/* c1...c64 <-- (R16,L16). (Exchange final blocks L16, R16 and
|
||||||
* concatenate to form the ciphertext.) */
|
* concatenate to form the ciphertext.) */
|
||||||
temp = xl;
|
outbuf[0] = (r >> 24) & 0xff;
|
||||||
xl = xr;
|
outbuf[1] = (r >> 16) & 0xff;
|
||||||
xr = temp;
|
outbuf[2] = (r >> 8) & 0xff;
|
||||||
|
outbuf[3] = r & 0xff;
|
||||||
xr ^= bc->p[CAST5_ROUNDS];
|
outbuf[4] = (l >> 24) & 0xff;
|
||||||
xl ^= bc->p[CAST5_ROUNDS+1];
|
outbuf[5] = (l >> 16) & 0xff;
|
||||||
|
outbuf[6] = (l >> 8) & 0xff;
|
||||||
*ret_xl = xl;
|
outbuf[7] = l & 0xff;
|
||||||
*ret_xr = xr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
decrypted( CAST5_context *bc, u32 *ret_xl, u32 *ret_xr )
|
decrypt_block( CAST5_context *c, byte *outbuf, byte *inbuf )
|
||||||
{
|
{
|
||||||
u32 xl, xr, temp;
|
u32 l, r, t;
|
||||||
int i;
|
u32 I;
|
||||||
|
u32 *Km;
|
||||||
|
byte *Kr;
|
||||||
|
|
||||||
xl = *ret_xl;
|
Km = c->Km;
|
||||||
xr = *ret_xr;
|
Kr = c->Kr;
|
||||||
|
|
||||||
|
l = inbuf[0] << 24 | inbuf[1] << 16 | inbuf[2] << 8 | inbuf[3];
|
||||||
|
r = inbuf[4] << 24 | inbuf[5] << 16 | inbuf[6] << 8 | inbuf[7];
|
||||||
|
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[15], Kr[15]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[14], Kr[14]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[13], Kr[13]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[12], Kr[12]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[11], Kr[11]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[10], Kr[10]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 9], Kr[ 9]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[ 8], Kr[ 8]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[ 7], Kr[ 7]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 6], Kr[ 6]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[ 5], Kr[ 5]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[ 4], Kr[ 4]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 3], Kr[ 3]);
|
||||||
|
t = l; l = r; r = t ^ F3(r, Km[ 2], Kr[ 2]);
|
||||||
|
t = l; l = r; r = t ^ F2(r, Km[ 1], Kr[ 1]);
|
||||||
|
t = l; l = r; r = t ^ F1(r, Km[ 0], Kr[ 0]);
|
||||||
|
|
||||||
|
outbuf[0] = (r >> 24) & 0xff;
|
||||||
|
outbuf[1] = (r >> 16) & 0xff;
|
||||||
|
outbuf[2] = (r >> 8) & 0xff;
|
||||||
|
outbuf[3] = r & 0xff;
|
||||||
|
outbuf[4] = (l >> 24) & 0xff;
|
||||||
|
outbuf[5] = (l >> 16) & 0xff;
|
||||||
|
outbuf[6] = (l >> 8) & 0xff;
|
||||||
|
outbuf[7] = l & 0xff;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
selftest()
|
||||||
|
{
|
||||||
|
CAST5_context c;
|
||||||
|
byte key[16] = { 0x01, 0x23, 0x45, 0x67, 0x12, 0x34, 0x56, 0x78,
|
||||||
|
0x23, 0x45, 0x67, 0x89, 0x34, 0x56, 0x78, 0x9A };
|
||||||
|
byte plain[8] = { 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF };
|
||||||
|
byte cipher[8]= { 0x23, 0x8B, 0x4F, 0xE5, 0x84, 0x7E, 0x44, 0xB2 };
|
||||||
|
byte buffer[8];
|
||||||
|
|
||||||
|
cast5_setkey( &c, key, 16 );
|
||||||
|
encrypt_block( &c, buffer, plain );
|
||||||
|
if( memcmp( buffer, cipher, 8 ) )
|
||||||
|
log_error("wrong cast5-128 encryption\n");
|
||||||
|
decrypt_block( &c, buffer, buffer );
|
||||||
|
if( memcmp( buffer, plain, 8 ) )
|
||||||
|
log_bug("cast5-128 failed\n");
|
||||||
|
|
||||||
|
#if 0 /* full maintenance test */
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
byte a0[16] = { 0x01,0x23,0x45,0x67,0x12,0x34,0x56,0x78,
|
||||||
|
0x23,0x45,0x67,0x89,0x34,0x56,0x78,0x9A };
|
||||||
|
byte b0[16] = { 0x01,0x23,0x45,0x67,0x12,0x34,0x56,0x78,
|
||||||
|
0x23,0x45,0x67,0x89,0x34,0x56,0x78,0x9A };
|
||||||
|
byte a1[16] = { 0xEE,0xA9,0xD0,0xA2,0x49,0xFD,0x3B,0xA6,
|
||||||
|
0xB3,0x43,0x6F,0xB8,0x9D,0x6D,0xCA,0x92 };
|
||||||
|
byte b1[16] = { 0xB2,0xC9,0x5E,0xB0,0x0C,0x31,0xAD,0x71,
|
||||||
|
0x80,0xAC,0x05,0xB8,0xE8,0x3D,0x69,0x6E };
|
||||||
|
|
||||||
|
for(i=0; i < 1000000; i++ ) {
|
||||||
|
cast5_setkey( &c, b0, 16 );
|
||||||
|
encrypt_block( &c, a0, a0 );
|
||||||
|
encrypt_block( &c, a0+8, a0+8 );
|
||||||
|
cast5_setkey( &c, a0, 16 );
|
||||||
|
encrypt_block( &c, b0, b0 );
|
||||||
|
encrypt_block( &c, b0+8, b0+8 );
|
||||||
|
}
|
||||||
|
if( memcmp( a0, a1, 16 ) || memcmp( b0, b1, 16 ) )
|
||||||
|
log_bug("cast5-128 maintenance test failed\n");
|
||||||
|
|
||||||
for(i=CAST5_ROUNDS+1; i > 1; i-- ) {
|
|
||||||
xl ^= bc->p[i];
|
|
||||||
xr ^= function_F(bc, xl);
|
|
||||||
temp = xl;
|
|
||||||
xl = xr;
|
|
||||||
xr = temp;
|
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
temp = xl;
|
|
||||||
xl = xr;
|
|
||||||
xr = temp;
|
|
||||||
|
|
||||||
xr ^= bc->p[1];
|
|
||||||
xl ^= bc->p[0];
|
|
||||||
|
|
||||||
*ret_xl = xl;
|
|
||||||
*ret_xr = xr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
|
||||||
encrypted_block( CAST5_context *bc, byte *outbuf, byte *inbuf )
|
|
||||||
{
|
|
||||||
u32 d1, d2;
|
|
||||||
|
|
||||||
d1 = ((u32*)inbuf)[0];
|
|
||||||
d2 = ((u32*)inbuf)[1];
|
|
||||||
encrypted( bc, &d1, &d2 );
|
|
||||||
((u32*)outbuf)[0] = d1;
|
|
||||||
((u32*)outbuf)[1] = d2;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
decrypted_block( CAST5_context *bc, byte *outbuf, byte *inbuf )
|
key_schedule( u32 *x, u32 *z, u32 *k )
|
||||||
{
|
{
|
||||||
u32 d1, d2;
|
|
||||||
|
|
||||||
d1 = ((u32*)inbuf)[0];
|
#define xi(i) ((x[(i)/4] >> (8*(3-((i)%4)))) & 0xff)
|
||||||
d2 = ((u32*)inbuf)[1];
|
#define zi(i) ((z[(i)/4] >> (8*(3-((i)%4)))) & 0xff)
|
||||||
decrypted( bc, &d1, &d2 );
|
|
||||||
((u32*)outbuf)[0] = d1;
|
z[0] = x[0] ^ s5[xi(13)]^s6[xi(15)]^s7[xi(12)]^s8[xi(14)]^s7[xi( 8)];
|
||||||
((u32*)outbuf)[1] = d2;
|
z[1] = x[2] ^ s5[zi( 0)]^s6[zi( 2)]^s7[zi( 1)]^s8[zi( 3)]^s8[xi(10)];
|
||||||
|
z[2] = x[3] ^ s5[zi( 7)]^s6[zi( 6)]^s7[zi( 5)]^s8[zi( 4)]^s5[xi( 9)];
|
||||||
|
z[3] = x[1] ^ s5[zi(10)]^s6[zi( 9)]^s7[zi(11)]^s8[zi( 8)]^s6[xi(11)];
|
||||||
|
k[0] = s5[zi( 8)]^s6[zi( 9)]^s7[zi( 7)]^s8[zi( 6)]^s5[zi( 2)];
|
||||||
|
k[1] = s5[zi(10)]^s6[zi(11)]^s7[zi( 5)]^s8[zi( 4)]^s6[zi( 6)];
|
||||||
|
k[2] = s5[zi(12)]^s6[zi(13)]^s7[zi( 3)]^s8[zi( 2)]^s7[zi( 9)];
|
||||||
|
k[3] = s5[zi(14)]^s6[zi(15)]^s7[zi( 1)]^s8[zi( 0)]^s8[zi(12)];
|
||||||
|
|
||||||
|
x[0] = z[2] ^ s5[zi( 5)]^s6[zi( 7)]^s7[zi( 4)]^s8[zi( 6)]^s7[zi( 0)];
|
||||||
|
x[1] = z[0] ^ s5[xi( 0)]^s6[xi( 2)]^s7[xi( 1)]^s8[xi( 3)]^s8[zi( 2)];
|
||||||
|
x[2] = z[1] ^ s5[xi( 7)]^s6[xi( 6)]^s7[xi( 5)]^s8[xi( 4)]^s5[zi( 1)];
|
||||||
|
x[3] = z[3] ^ s5[xi(10)]^s6[xi( 9)]^s7[xi(11)]^s8[xi( 8)]^s6[zi( 3)];
|
||||||
|
k[4] = s5[xi( 3)]^s6[xi( 2)]^s7[xi(12)]^s8[xi(13)]^s5[xi( 8)];
|
||||||
|
k[5] = s5[xi( 1)]^s6[xi( 0)]^s7[xi(14)]^s8[xi(15)]^s6[xi(13)];
|
||||||
|
k[6] = s5[xi( 7)]^s6[xi( 6)]^s7[xi( 8)]^s8[xi( 9)]^s7[xi( 3)];
|
||||||
|
k[7] = s5[xi( 5)]^s6[xi( 4)]^s7[xi(10)]^s8[xi(11)]^s8[xi( 7)];
|
||||||
|
|
||||||
|
z[0] = x[0] ^ s5[xi(13)]^s6[xi(15)]^s7[xi(12)]^s8[xi(14)]^s7[xi( 8)];
|
||||||
|
z[1] = x[2] ^ s5[zi( 0)]^s6[zi( 2)]^s7[zi( 1)]^s8[zi( 3)]^s8[xi(10)];
|
||||||
|
z[2] = x[3] ^ s5[zi( 7)]^s6[zi( 6)]^s7[zi( 5)]^s8[zi( 4)]^s5[xi( 9)];
|
||||||
|
z[3] = x[1] ^ s5[zi(10)]^s6[zi( 9)]^s7[zi(11)]^s8[zi( 8)]^s6[xi(11)];
|
||||||
|
k[8] = s5[zi( 3)]^s6[zi( 2)]^s7[zi(12)]^s8[zi(13)]^s5[zi( 9)];
|
||||||
|
k[9] = s5[zi( 1)]^s6[zi( 0)]^s7[zi(14)]^s8[zi(15)]^s6[zi(12)];
|
||||||
|
k[10]= s5[zi( 7)]^s6[zi( 6)]^s7[zi( 8)]^s8[zi( 9)]^s7[zi( 2)];
|
||||||
|
k[11]= s5[zi( 5)]^s6[zi( 4)]^s7[zi(10)]^s8[zi(11)]^s8[zi( 6)];
|
||||||
|
|
||||||
|
x[0] = z[2] ^ s5[zi( 5)]^s6[zi( 7)]^s7[zi( 4)]^s8[zi( 6)]^s7[zi( 0)];
|
||||||
|
x[1] = z[0] ^ s5[xi( 0)]^s6[xi( 2)]^s7[xi( 1)]^s8[xi( 3)]^s8[zi( 2)];
|
||||||
|
x[2] = z[1] ^ s5[xi( 7)]^s6[xi( 6)]^s7[xi( 5)]^s8[xi( 4)]^s5[zi( 1)];
|
||||||
|
x[3] = z[3] ^ s5[xi(10)]^s6[xi( 9)]^s7[xi(11)]^s8[xi( 8)]^s6[zi( 3)];
|
||||||
|
k[12]= s5[xi( 8)]^s6[xi( 9)]^s7[xi( 7)]^s8[xi( 6)]^s5[xi( 3)];
|
||||||
|
k[13]= s5[xi(10)]^s6[xi(11)]^s7[xi( 5)]^s8[xi( 4)]^s6[xi( 7)];
|
||||||
|
k[14]= s5[xi(12)]^s6[xi(13)]^s7[xi( 3)]^s8[xi( 2)]^s7[xi( 8)];
|
||||||
|
k[15]= s5[xi(14)]^s6[xi(15)]^s7[xi( 1)]^s8[xi( 0)]^s8[xi(13)];
|
||||||
|
|
||||||
|
#undef xi
|
||||||
|
#undef zi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
cast5_setkey( CAST5_context *c, byte *key, unsigned keylen )
|
cast5_setkey( CAST5_context *c, byte *key, unsigned keylen )
|
||||||
{
|
{
|
||||||
int i, j, k;
|
static int initialized;
|
||||||
u32 data, datal, datar;
|
int i;
|
||||||
|
u32 x[4];
|
||||||
|
u32 z[4];
|
||||||
|
u32 k[16];
|
||||||
|
|
||||||
for(i=0; i < CAST5_ROUNDS+2; i++ )
|
if( !initialized ) {
|
||||||
c->p[i] = ps[i];
|
initialized = 1;
|
||||||
for(i=0; i < 256; i++ ) {
|
selftest();
|
||||||
c->s0[i] = ks0[i];
|
|
||||||
c->s1[i] = ks1[i];
|
|
||||||
c->s2[i] = ks2[i];
|
|
||||||
c->s3[i] = ks3[i];
|
|
||||||
}
|
}
|
||||||
|
fast_random_poll();
|
||||||
|
|
||||||
for(i=j=0; i < BLOWFISH_ROUNDS+2; i++ ) {
|
assert(keylen==16);
|
||||||
data = 0;
|
x[0] = key[0] << 24 | key[1] << 16 | key[2] << 8 | key[3];
|
||||||
for(k=0; k < 4; k++) {
|
x[1] = key[4] << 24 | key[5] << 16 | key[6] << 8 | key[7];
|
||||||
data = (data << 8) | key[j];
|
x[2] = key[8] << 24 | key[9] << 16 | key[10] << 8 | key[11];
|
||||||
if( ++j >= keylen )
|
x[3] = key[12] << 24 | key[13] << 16 | key[14] << 8 | key[15];
|
||||||
j = 0;
|
|
||||||
}
|
|
||||||
c->p[i] ^= data;
|
|
||||||
}
|
|
||||||
|
|
||||||
datal = datar = 0;
|
key_schedule( x, z, k );
|
||||||
for(i=0; i < CAST5_ROUNDS+2; i += 2 ) {
|
for(i=0; i < 16; i++ )
|
||||||
encrypted( c, &datal, &datar );
|
c->Km[i] = k[i];
|
||||||
c->p[i] = datal;
|
key_schedule( x, z, k );
|
||||||
c->p[i+1] = datar;
|
for(i=0; i < 16; i++ )
|
||||||
}
|
c->Kr[i] = k[i] & 0x1f;
|
||||||
for(i=0; i < 256; i += 2 ) {
|
|
||||||
encrypted( c, &datal, &datar );
|
memset(&x,0, sizeof x);
|
||||||
c->s0[i] = datal;
|
memset(&z,0, sizeof z);
|
||||||
c->s0[i+1] = datar;
|
memset(&k,0, sizeof k);
|
||||||
}
|
|
||||||
for(i=0; i < 256; i += 2 ) {
|
#undef xi
|
||||||
encrypted( c, &datal, &datar );
|
#undef zi
|
||||||
c->s1[i] = datal;
|
|
||||||
c->s1[i+1] = datar;
|
|
||||||
}
|
|
||||||
for(i=0; i < 256; i += 2 ) {
|
|
||||||
encrypted( c, &datal, &datar );
|
|
||||||
c->s2[i] = datal;
|
|
||||||
c->s2[i+1] = datar;
|
|
||||||
}
|
|
||||||
for(i=0; i < 256; i += 2 ) {
|
|
||||||
encrypted( c, &datal, &datar );
|
|
||||||
c->s3[i] = datal;
|
|
||||||
c->s3[i+1] = datar;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -477,7 +575,7 @@ cast5_setiv( CAST5_context *c, byte *iv )
|
|||||||
else
|
else
|
||||||
memset( c->iv, 0, CAST5_BLOCKSIZE );
|
memset( c->iv, 0, CAST5_BLOCKSIZE );
|
||||||
c->count = 0;
|
c->count = 0;
|
||||||
encrypted_block( c, c->eniv, c->iv );
|
encrypt_block( c, c->eniv, c->iv );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -488,7 +586,7 @@ cast5_encode( CAST5_context *c, byte *outbuf, byte *inbuf,
|
|||||||
unsigned n;
|
unsigned n;
|
||||||
|
|
||||||
for(n=0; n < nblocks; n++ ) {
|
for(n=0; n < nblocks; n++ ) {
|
||||||
encrypted_block( c, outbuf, inbuf );
|
encrypt_block( c, outbuf, inbuf );
|
||||||
inbuf += CAST5_BLOCKSIZE;;
|
inbuf += CAST5_BLOCKSIZE;;
|
||||||
outbuf += CAST5_BLOCKSIZE;
|
outbuf += CAST5_BLOCKSIZE;
|
||||||
}
|
}
|
||||||
@ -501,7 +599,7 @@ cast5_decode( CAST5_context *c, byte *outbuf, byte *inbuf,
|
|||||||
unsigned n;
|
unsigned n;
|
||||||
|
|
||||||
for(n=0; n < nblocks; n++ ) {
|
for(n=0; n < nblocks; n++ ) {
|
||||||
decrypted_block( c, outbuf, inbuf );
|
decrypt_block( c, outbuf, inbuf );
|
||||||
inbuf += CAST5_BLOCKSIZE;;
|
inbuf += CAST5_BLOCKSIZE;;
|
||||||
outbuf += CAST5_BLOCKSIZE;
|
outbuf += CAST5_BLOCKSIZE;
|
||||||
}
|
}
|
||||||
@ -527,9 +625,10 @@ xorblock( byte *out, byte *a, byte *b, unsigned count )
|
|||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
cast5_encode_cfb( CAST5_context *c, byte *outbuf,
|
cast5_encode_cfb( CAST5_context *c, byte *outbuf,
|
||||||
byte *inbuf, unsigned nbytes)
|
byte *inbuf, unsigned nbytes)
|
||||||
{
|
{
|
||||||
unsigned n;
|
unsigned n;
|
||||||
|
int is_aligned;
|
||||||
|
|
||||||
if( c->count ) { /* must make a full block first */
|
if( c->count ) { /* must make a full block first */
|
||||||
assert( c->count < CAST5_BLOCKSIZE );
|
assert( c->count < CAST5_BLOCKSIZE );
|
||||||
@ -544,17 +643,35 @@ cast5_encode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
outbuf += n;
|
outbuf += n;
|
||||||
assert( c->count <= CAST5_BLOCKSIZE);
|
assert( c->count <= CAST5_BLOCKSIZE);
|
||||||
if( c->count == CAST5_BLOCKSIZE ) {
|
if( c->count == CAST5_BLOCKSIZE ) {
|
||||||
encrypted_block( c, c->eniv, c->iv );
|
encrypt_block( c, c->eniv, c->iv );
|
||||||
c->count = 0;
|
c->count = 0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
assert(!c->count);
|
assert(!c->count);
|
||||||
|
is_aligned = !((ulong)inbuf % SIZEOF_UNSIGNED_LONG);
|
||||||
while( nbytes >= CAST5_BLOCKSIZE ) {
|
while( nbytes >= CAST5_BLOCKSIZE ) {
|
||||||
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
if( is_aligned ) {
|
||||||
|
#if SIZEOF_UNSIGNED_LONG == CAST5_BLOCKSIZE
|
||||||
|
*(ulong*)outbuf = *(ulong*)c->eniv ^ *(ulong*)inbuf;
|
||||||
|
#elif (2*SIZEOF_UNSIGNED_LONG) == CAST5_BLOCKSIZE
|
||||||
|
((ulong*)outbuf)[0] = ((ulong*)c->eniv)[0] ^ ((ulong*)inbuf)[0];
|
||||||
|
((ulong*)outbuf)[1] = ((ulong*)c->eniv)[1] ^ ((ulong*)inbuf)[1];
|
||||||
|
#elif (4*SIZEOF_UNSIGNED_LONG) == CAST5_BLOCKSIZE
|
||||||
|
((ulong*)outbuf)[0] = ((ulong*)c->eniv)[0] ^ ((ulong*)inbuf)[0];
|
||||||
|
((ulong*)outbuf)[1] = ((ulong*)c->eniv)[1] ^ ((ulong*)inbuf)[1];
|
||||||
|
((ulong*)outbuf)[2] = ((ulong*)c->eniv)[2] ^ ((ulong*)inbuf)[2];
|
||||||
|
((ulong*)outbuf)[3] = ((ulong*)c->eniv)[3] ^ ((ulong*)inbuf)[3];
|
||||||
|
#else
|
||||||
|
#error Please remove this info line.
|
||||||
|
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else /* not aligned */
|
||||||
|
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
||||||
memcpy( c->iv, outbuf, CAST5_BLOCKSIZE);
|
memcpy( c->iv, outbuf, CAST5_BLOCKSIZE);
|
||||||
encrypted_block( c, c->eniv, c->iv );
|
encrypt_block( c, c->eniv, c->iv );
|
||||||
nbytes -= CAST5_BLOCKSIZE;
|
nbytes -= CAST5_BLOCKSIZE;
|
||||||
inbuf += CAST5_BLOCKSIZE;
|
inbuf += CAST5_BLOCKSIZE;
|
||||||
outbuf += CAST5_BLOCKSIZE;
|
outbuf += CAST5_BLOCKSIZE;
|
||||||
@ -571,9 +688,10 @@ cast5_encode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
|
|
||||||
void
|
void
|
||||||
cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
||||||
byte *inbuf, unsigned nbytes)
|
byte *inbuf, unsigned nbytes)
|
||||||
{
|
{
|
||||||
unsigned n;
|
unsigned n;
|
||||||
|
int is_aligned;
|
||||||
|
|
||||||
if( c->count ) { /* must make a full block first */
|
if( c->count ) { /* must make a full block first */
|
||||||
assert( c->count < CAST5_BLOCKSIZE );
|
assert( c->count < CAST5_BLOCKSIZE );
|
||||||
@ -588,7 +706,7 @@ cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
outbuf += n;
|
outbuf += n;
|
||||||
assert( c->count <= CAST5_BLOCKSIZE);
|
assert( c->count <= CAST5_BLOCKSIZE);
|
||||||
if( c->count == CAST5_BLOCKSIZE ) {
|
if( c->count == CAST5_BLOCKSIZE ) {
|
||||||
encrypted_block( c, c->eniv, c->iv );
|
encrypt_block( c, c->eniv, c->iv );
|
||||||
c->count = 0;
|
c->count = 0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -596,10 +714,28 @@ cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
}
|
}
|
||||||
|
|
||||||
assert(!c->count);
|
assert(!c->count);
|
||||||
|
is_aligned = !((ulong)inbuf % SIZEOF_UNSIGNED_LONG);
|
||||||
while( nbytes >= CAST5_BLOCKSIZE ) {
|
while( nbytes >= CAST5_BLOCKSIZE ) {
|
||||||
memcpy( c->iv, inbuf, CAST5_BLOCKSIZE);
|
memcpy( c->iv, inbuf, CAST5_BLOCKSIZE);
|
||||||
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
if( is_aligned ) {
|
||||||
encrypted_block( c, c->eniv, c->iv );
|
#if SIZEOF_UNSIGNED_LONG == CAST5_BLOCKSIZE
|
||||||
|
*(ulong*)outbuf = *(ulong*)c->eniv ^ *(ulong*)inbuf;
|
||||||
|
#elif (2*SIZEOF_UNSIGNED_LONG) == CAST5_BLOCKSIZE
|
||||||
|
((ulong*)outbuf)[0] = ((ulong*)c->eniv)[0] ^ ((ulong*)inbuf)[0];
|
||||||
|
((ulong*)outbuf)[1] = ((ulong*)c->eniv)[1] ^ ((ulong*)inbuf)[1];
|
||||||
|
#elif (4*SIZEOF_UNSIGNED_LONG) == CAST5_BLOCKSIZE
|
||||||
|
((ulong*)outbuf)[0] = ((ulong*)c->eniv)[0] ^ ((ulong*)inbuf)[0];
|
||||||
|
((ulong*)outbuf)[1] = ((ulong*)c->eniv)[1] ^ ((ulong*)inbuf)[1];
|
||||||
|
((ulong*)outbuf)[2] = ((ulong*)c->eniv)[2] ^ ((ulong*)inbuf)[2];
|
||||||
|
((ulong*)outbuf)[3] = ((ulong*)c->eniv)[3] ^ ((ulong*)inbuf)[3];
|
||||||
|
#else
|
||||||
|
#error Please remove this info line.
|
||||||
|
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
else /* not aligned */
|
||||||
|
xorblock( outbuf, c->eniv, inbuf, CAST5_BLOCKSIZE);
|
||||||
|
encrypt_block( c, c->eniv, c->iv );
|
||||||
nbytes -= CAST5_BLOCKSIZE;
|
nbytes -= CAST5_BLOCKSIZE;
|
||||||
inbuf += CAST5_BLOCKSIZE;
|
inbuf += CAST5_BLOCKSIZE;
|
||||||
outbuf += CAST5_BLOCKSIZE;
|
outbuf += CAST5_BLOCKSIZE;
|
||||||
@ -613,3 +749,16 @@ cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
cast5_sync_cfb( CAST5_context *c )
|
||||||
|
{
|
||||||
|
if( c->count ) {
|
||||||
|
memmove(c->iv + c->count, c->iv, CAST5_BLOCKSIZE - c->count );
|
||||||
|
memcpy(c->iv, c->eniv + CAST5_BLOCKSIZE - c->count, c->count);
|
||||||
|
c->count = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -25,11 +25,8 @@
|
|||||||
#define CAST5_BLOCKSIZE 8
|
#define CAST5_BLOCKSIZE 8
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
u32 s0[256];
|
u32 Km[16];
|
||||||
u32 s1[256];
|
byte Kr[16];
|
||||||
u32 s2[256];
|
|
||||||
u32 s3[256];
|
|
||||||
u32 p[16+2];
|
|
||||||
byte iv[CAST5_BLOCKSIZE];
|
byte iv[CAST5_BLOCKSIZE];
|
||||||
byte eniv[CAST5_BLOCKSIZE];
|
byte eniv[CAST5_BLOCKSIZE];
|
||||||
int count;
|
int count;
|
||||||
@ -45,6 +42,7 @@ void cast5_encode_cfb( CAST5_context *c, byte *outbuf,
|
|||||||
byte *inbuf, unsigned nbytes);
|
byte *inbuf, unsigned nbytes);
|
||||||
void cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
void cast5_decode_cfb( CAST5_context *c, byte *outbuf,
|
||||||
byte *inbuf, unsigned nbytes);
|
byte *inbuf, unsigned nbytes);
|
||||||
|
void cast5_sync_cfb( CAST5_context *c );
|
||||||
|
|
||||||
|
|
||||||
#endif /*G10_CAST5_H*/
|
#endif /*G10_CAST5_H*/
|
||||||
|
@ -162,6 +162,7 @@ check_cipher_algo( int algo )
|
|||||||
switch( algo ) {
|
switch( algo ) {
|
||||||
case CIPHER_ALGO_BLOWFISH128:
|
case CIPHER_ALGO_BLOWFISH128:
|
||||||
case CIPHER_ALGO_BLOWFISH:
|
case CIPHER_ALGO_BLOWFISH:
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
return 0;
|
return 0;
|
||||||
default:
|
default:
|
||||||
return G10ERR_CIPHER_ALGO;
|
return G10ERR_CIPHER_ALGO;
|
||||||
|
49
doc/DETAILS
49
doc/DETAILS
@ -234,3 +234,52 @@ There is one enhavement used ith the old style packet headers:
|
|||||||
+ another packet version to tell the application that it can not assume,
|
+ another packet version to tell the application that it can not assume,
|
||||||
+ that this is the last packet.
|
+ that this is the last packet.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Keyserver Message Format
|
||||||
|
-------------------------
|
||||||
|
|
||||||
|
The keyserver may be contacted by a Unix Domain socket or via TCP.
|
||||||
|
|
||||||
|
The Format of a request is:
|
||||||
|
|
||||||
|
----
|
||||||
|
command-tag
|
||||||
|
"Content-length:" digits
|
||||||
|
CRLF
|
||||||
|
------
|
||||||
|
|
||||||
|
Where command-tag is
|
||||||
|
|
||||||
|
GET <user-name>
|
||||||
|
PUT
|
||||||
|
DELETE <user-name>
|
||||||
|
|
||||||
|
|
||||||
|
The format of a response is:
|
||||||
|
|
||||||
|
------
|
||||||
|
"GNUPG/1.0" status-code status-text
|
||||||
|
"Content-length:" digits
|
||||||
|
CRLF
|
||||||
|
------------
|
||||||
|
followed by <digits> bytes of data
|
||||||
|
|
||||||
|
|
||||||
|
Status codes are:
|
||||||
|
|
||||||
|
o 1xx: Informational - Request received, continuing process
|
||||||
|
|
||||||
|
o 2xx: Success - The action was successfully received, understood,
|
||||||
|
and accepted
|
||||||
|
|
||||||
|
o 4xx: Client Error - The request contains bad syntax or cannot be
|
||||||
|
fulfilled
|
||||||
|
|
||||||
|
o 5xx: Server Error - The server failed to fulfill an apparently
|
||||||
|
valid request
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,3 +1,14 @@
|
|||||||
|
Sat Apr 4 20:07:01 1998 Werner Koch (wk@isil.d.shuttle.de)
|
||||||
|
|
||||||
|
* cipher.c (cipher_filter): Support for CAST5
|
||||||
|
* encr-data.c (decode_filter): Ditto.
|
||||||
|
(decrypt_data): Ditto.
|
||||||
|
* seskey.c (make_session_key): Ditto.
|
||||||
|
* seckey-cert.c (check_elg, check_dsa): Ditto,
|
||||||
|
(protect_secret_key): Ditto.
|
||||||
|
* pubkey-enc.c (get_session_key): Ditto.
|
||||||
|
* passphrase.c (hash_passphrase): Ditto.
|
||||||
|
|
||||||
Thu Apr 2 20:22:35 1998 Werner Koch (wk@isil.d.shuttle.de)
|
Thu Apr 2 20:22:35 1998 Werner Koch (wk@isil.d.shuttle.de)
|
||||||
|
|
||||||
* gpgd.c: New
|
* gpgd.c: New
|
||||||
|
@ -289,7 +289,8 @@ do_secret_cert( IOBUF out, int ctb, PKT_secret_cert *skc )
|
|||||||
mpi_write(a, skc->d.rsa.rsa_n );
|
mpi_write(a, skc->d.rsa.rsa_n );
|
||||||
mpi_write(a, skc->d.rsa.rsa_e );
|
mpi_write(a, skc->d.rsa.rsa_e );
|
||||||
if( skc->is_protected ) {
|
if( skc->is_protected ) {
|
||||||
assert( skc->protect.algo == CIPHER_ALGO_BLOWFISH );
|
assert( skc->protect.algo == CIPHER_ALGO_BLOWFISH
|
||||||
|
|| skc->protect.algo == CIPHER_ALGO_CAST );
|
||||||
iobuf_put(a, skc->protect.algo );
|
iobuf_put(a, skc->protect.algo );
|
||||||
iobuf_write(a, skc->protect.iv, 8 );
|
iobuf_write(a, skc->protect.iv, 8 );
|
||||||
}
|
}
|
||||||
|
12
g10/cipher.c
12
g10/cipher.c
@ -74,6 +74,13 @@ cipher_filter( void *opaque, int control,
|
|||||||
blowfish_setiv( cfx->bf_ctx, NULL );
|
blowfish_setiv( cfx->bf_ctx, NULL );
|
||||||
blowfish_encode_cfb( cfx->bf_ctx, temp, temp, 10);
|
blowfish_encode_cfb( cfx->bf_ctx, temp, temp, 10);
|
||||||
}
|
}
|
||||||
|
else if( cfx->dek->algo == CIPHER_ALGO_CAST ) {
|
||||||
|
cfx->cast5_ctx = m_alloc_secure( sizeof *cfx->cast5_ctx );
|
||||||
|
cast5_setkey( cfx->cast5_ctx, cfx->dek->key, cfx->dek->keylen );
|
||||||
|
cast5_setiv( cfx->cast5_ctx, NULL );
|
||||||
|
cast5_encode_cfb( cfx->cast5_ctx, temp, temp, 10);
|
||||||
|
cast5_sync_cfb( cfx->cast5_ctx );
|
||||||
|
}
|
||||||
else
|
else
|
||||||
log_bug("no cipher algo %d\n", cfx->dek->algo);
|
log_bug("no cipher algo %d\n", cfx->dek->algo);
|
||||||
|
|
||||||
@ -84,6 +91,9 @@ cipher_filter( void *opaque, int control,
|
|||||||
if( cfx->dek->algo == CIPHER_ALGO_BLOWFISH
|
if( cfx->dek->algo == CIPHER_ALGO_BLOWFISH
|
||||||
|| cfx->dek->algo == CIPHER_ALGO_BLOWFISH128 )
|
|| cfx->dek->algo == CIPHER_ALGO_BLOWFISH128 )
|
||||||
blowfish_encode_cfb( cfx->bf_ctx, buf, buf, size);
|
blowfish_encode_cfb( cfx->bf_ctx, buf, buf, size);
|
||||||
|
else if( cfx->dek->algo == CIPHER_ALGO_CAST )
|
||||||
|
cast5_encode_cfb( cfx->cast5_ctx, buf, buf, size);
|
||||||
|
|
||||||
if( iobuf_write( a, buf, size ) )
|
if( iobuf_write( a, buf, size ) )
|
||||||
rc = G10ERR_WRITE_FILE;
|
rc = G10ERR_WRITE_FILE;
|
||||||
}
|
}
|
||||||
@ -91,6 +101,8 @@ cipher_filter( void *opaque, int control,
|
|||||||
if( cfx->dek->algo == CIPHER_ALGO_BLOWFISH
|
if( cfx->dek->algo == CIPHER_ALGO_BLOWFISH
|
||||||
|| cfx->dek->algo == CIPHER_ALGO_BLOWFISH128 )
|
|| cfx->dek->algo == CIPHER_ALGO_BLOWFISH128 )
|
||||||
m_free(cfx->bf_ctx);
|
m_free(cfx->bf_ctx);
|
||||||
|
else if( cfx->dek->algo == CIPHER_ALGO_CAST )
|
||||||
|
m_free(cfx->cast5_ctx);
|
||||||
}
|
}
|
||||||
else if( control == IOBUFCTRL_DESC ) {
|
else if( control == IOBUFCTRL_DESC ) {
|
||||||
*(char**)buf = "cipher_filter";
|
*(char**)buf = "cipher_filter";
|
||||||
|
@ -28,13 +28,16 @@
|
|||||||
#include "packet.h"
|
#include "packet.h"
|
||||||
#include "mpi.h"
|
#include "mpi.h"
|
||||||
#include "cipher.h"
|
#include "cipher.h"
|
||||||
|
#include "options.h"
|
||||||
|
|
||||||
|
|
||||||
static int decode_filter( void *opaque, int control, IOBUF a,
|
static int decode_filter( void *opaque, int control, IOBUF a,
|
||||||
byte *buf, size_t *ret_len);
|
byte *buf, size_t *ret_len);
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
int is_cast5;
|
||||||
BLOWFISH_context *bf_ctx;
|
BLOWFISH_context *bf_ctx;
|
||||||
|
CAST5_context *cast5_ctx;
|
||||||
} decode_filter_ctx_t;
|
} decode_filter_ctx_t;
|
||||||
|
|
||||||
|
|
||||||
@ -50,16 +53,32 @@ decrypt_data( PKT_encrypted *ed, DEK *dek )
|
|||||||
int c, i;
|
int c, i;
|
||||||
byte temp[16];
|
byte temp[16];
|
||||||
|
|
||||||
|
if( opt.verbose ) {
|
||||||
|
const char *s = cipher_algo_to_string( dek->algo );
|
||||||
|
if( s )
|
||||||
|
log_info("%s encrypted data\n", s );
|
||||||
|
else
|
||||||
|
log_info("encrypted with unknown algorithm %d\n", dek->algo );
|
||||||
|
}
|
||||||
if( dek->algo != CIPHER_ALGO_BLOWFISH
|
if( dek->algo != CIPHER_ALGO_BLOWFISH
|
||||||
&& dek->algo != CIPHER_ALGO_BLOWFISH128 )
|
&& dek->algo != CIPHER_ALGO_BLOWFISH128
|
||||||
|
&& dek->algo != CIPHER_ALGO_CAST )
|
||||||
return G10ERR_CIPHER_ALGO;
|
return G10ERR_CIPHER_ALGO;
|
||||||
if( ed->len && ed->len < 10 )
|
if( ed->len && ed->len < 10 )
|
||||||
log_bug("Nanu\n"); /* oops: found a bug */
|
log_bug("Nanu\n"); /* oops: found a bug */
|
||||||
|
|
||||||
dfx.bf_ctx = m_alloc_secure( sizeof *dfx.bf_ctx );
|
if( dek->algo == CIPHER_ALGO_CAST ) {
|
||||||
blowfish_setkey( dfx.bf_ctx, dek->key, dek->keylen );
|
dfx.is_cast5 = 1;
|
||||||
blowfish_setiv( dfx.bf_ctx, NULL );
|
dfx.cast5_ctx = m_alloc_secure( sizeof *dfx.cast5_ctx );
|
||||||
|
cast5_setkey( dfx.cast5_ctx, dek->key, dek->keylen );
|
||||||
|
cast5_setiv( dfx.cast5_ctx, NULL );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
dfx.is_cast5 = 0;
|
||||||
|
dfx.bf_ctx = m_alloc_secure( sizeof *dfx.bf_ctx );
|
||||||
|
blowfish_setkey( dfx.bf_ctx, dek->key, dek->keylen );
|
||||||
|
blowfish_setiv( dfx.bf_ctx, NULL );
|
||||||
|
}
|
||||||
|
|
||||||
if( ed->len ) {
|
if( ed->len ) {
|
||||||
iobuf_set_limit( ed->buf, ed->len );
|
iobuf_set_limit( ed->buf, ed->len );
|
||||||
@ -74,7 +93,12 @@ decrypt_data( PKT_encrypted *ed, DEK *dek )
|
|||||||
else
|
else
|
||||||
temp[i] = c;
|
temp[i] = c;
|
||||||
}
|
}
|
||||||
blowfish_decode_cfb( dfx.bf_ctx, temp, temp, 10);
|
if( dfx.is_cast5 ) {
|
||||||
|
cast5_decode_cfb( dfx.cast5_ctx, temp, temp, 10);
|
||||||
|
cast5_sync_cfb( dfx.cast5_ctx );
|
||||||
|
}
|
||||||
|
else
|
||||||
|
blowfish_decode_cfb( dfx.bf_ctx, temp, temp, 10);
|
||||||
p = temp;
|
p = temp;
|
||||||
if( p[6] != p[8] || p[7] != p[9] ) {
|
if( p[6] != p[8] || p[7] != p[9] ) {
|
||||||
m_free(dfx.bf_ctx);
|
m_free(dfx.bf_ctx);
|
||||||
@ -108,8 +132,12 @@ decode_filter( void *opaque, int control, IOBUF a, byte *buf, size_t *ret_len)
|
|||||||
buf[n] = c;
|
buf[n] = c;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( n )
|
if( n ) {
|
||||||
blowfish_decode_cfb( fc->bf_ctx, buf, buf, n);
|
if( fc->is_cast5 )
|
||||||
|
cast5_decode_cfb( fc->cast5_ctx, buf, buf, n);
|
||||||
|
else
|
||||||
|
blowfish_decode_cfb( fc->bf_ctx, buf, buf, n);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
rc = -1; /* eof */
|
rc = -1; /* eof */
|
||||||
*ret_len = n;
|
*ret_len = n;
|
||||||
|
@ -61,6 +61,7 @@ typedef struct {
|
|||||||
DEK *dek;
|
DEK *dek;
|
||||||
u32 datalen;
|
u32 datalen;
|
||||||
BLOWFISH_context *bf_ctx;
|
BLOWFISH_context *bf_ctx;
|
||||||
|
CAST5_context *cast5_ctx;
|
||||||
int header;
|
int header;
|
||||||
} cipher_filter_context_t;
|
} cipher_filter_context_t;
|
||||||
|
|
||||||
|
@ -156,6 +156,19 @@ hash_passphrase( DEK *dek, char *pw, byte *salt )
|
|||||||
memcpy( dek->key, md_read(md,0), dek->keylen );
|
memcpy( dek->key, md_read(md,0), dek->keylen );
|
||||||
md_close(md);
|
md_close(md);
|
||||||
}
|
}
|
||||||
|
else if( dek->algo == CIPHER_ALGO_CAST ) {
|
||||||
|
MD_HANDLE md;
|
||||||
|
|
||||||
|
md = md_open(DIGEST_ALGO_SHA1, 1);
|
||||||
|
if( salt )
|
||||||
|
md_write( md, salt, 8 );
|
||||||
|
md_write( md, pw, strlen(pw) );
|
||||||
|
md_final( md );
|
||||||
|
/* use only the low 128 bits */
|
||||||
|
dek->keylen = 16;
|
||||||
|
memcpy( dek->key, md_read(md,0), dek->keylen );
|
||||||
|
md_close(md);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
rc = G10ERR_UNSUPPORTED;
|
rc = G10ERR_UNSUPPORTED;
|
||||||
return rc;
|
return rc;
|
||||||
|
@ -135,13 +135,16 @@ get_session_key( PKT_pubkey_enc *k, DEK *dek )
|
|||||||
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
||||||
break;
|
break;
|
||||||
case CIPHER_ALGO_BLOWFISH128:
|
case CIPHER_ALGO_BLOWFISH128:
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
if( dek->keylen != 16 )
|
if( dek->keylen != 16 )
|
||||||
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
||||||
break;
|
break;
|
||||||
|
#if 0
|
||||||
case CIPHER_ALGO_CAST:
|
case CIPHER_ALGO_CAST:
|
||||||
if( dek->keylen < 5 || dek->keylen > 16 )
|
if( dek->keylen < 5 || dek->keylen > 16 )
|
||||||
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
{ rc = G10ERR_WRONG_SECKEY; goto leave; }
|
||||||
break;
|
break;
|
||||||
|
#endif
|
||||||
default:
|
default:
|
||||||
dek->algo = 0;
|
dek->algo = 0;
|
||||||
rc = G10ERR_CIPHER_ALGO;
|
rc = G10ERR_CIPHER_ALGO;
|
||||||
|
@ -31,7 +31,10 @@
|
|||||||
#include "cipher.h"
|
#include "cipher.h"
|
||||||
|
|
||||||
#if BLOWFISH_BLOCKSIZE != 8
|
#if BLOWFISH_BLOCKSIZE != 8
|
||||||
#error unsupportted blocksize
|
#error unsupported blocksize
|
||||||
|
#endif
|
||||||
|
#if CAST5_BLOCKSIZE != 8
|
||||||
|
#error unsupported blocksize
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static u16
|
static u16
|
||||||
@ -71,10 +74,12 @@ check_elg( PKT_secret_cert *cert )
|
|||||||
DEK *dek = NULL;
|
DEK *dek = NULL;
|
||||||
MPI test_x;
|
MPI test_x;
|
||||||
BLOWFISH_context *blowfish_ctx=NULL;
|
BLOWFISH_context *blowfish_ctx=NULL;
|
||||||
|
CAST5_context *cast5_ctx=NULL;
|
||||||
|
|
||||||
switch( cert->protect.algo ) {
|
switch( cert->protect.algo ) {
|
||||||
case CIPHER_ALGO_NONE: BUG(); break;
|
case CIPHER_ALGO_NONE: BUG(); break;
|
||||||
case CIPHER_ALGO_BLOWFISH:
|
case CIPHER_ALGO_BLOWFISH:
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
keyid_from_skc( cert, keyid );
|
keyid_from_skc( cert, keyid );
|
||||||
if( cert->protect.s2k == 1 || cert->protect.s2k == 3 )
|
if( cert->protect.s2k == 1 || cert->protect.s2k == 3 )
|
||||||
dek = get_passphrase_hash( keyid, NULL,
|
dek = get_passphrase_hash( keyid, NULL,
|
||||||
@ -82,23 +87,41 @@ check_elg( PKT_secret_cert *cert )
|
|||||||
else
|
else
|
||||||
dek = get_passphrase_hash( keyid, NULL, NULL );
|
dek = get_passphrase_hash( keyid, NULL, NULL );
|
||||||
|
|
||||||
blowfish_ctx = m_alloc_secure( sizeof *blowfish_ctx );
|
if( cert->protect.algo == CIPHER_ALGO_CAST )
|
||||||
blowfish_setkey( blowfish_ctx, dek->key, dek->keylen );
|
cast5_ctx = m_alloc_secure( sizeof *cast5_ctx );
|
||||||
|
else
|
||||||
|
blowfish_ctx = m_alloc_secure( sizeof *blowfish_ctx );
|
||||||
|
|
||||||
|
if( blowfish_ctx ) {
|
||||||
|
blowfish_setkey( blowfish_ctx, dek->key, dek->keylen );
|
||||||
|
blowfish_setiv( blowfish_ctx, NULL );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
cast5_setkey( cast5_ctx, dek->key, dek->keylen );
|
||||||
|
cast5_setiv( cast5_ctx, NULL );
|
||||||
|
}
|
||||||
m_free(dek); /* pw is in secure memory, so m_free() burns it */
|
m_free(dek); /* pw is in secure memory, so m_free() burns it */
|
||||||
blowfish_setiv( blowfish_ctx, NULL );
|
|
||||||
memcpy(save_iv, cert->protect.iv, 8 );
|
memcpy(save_iv, cert->protect.iv, 8 );
|
||||||
blowfish_decode_cfb( blowfish_ctx, cert->protect.iv,
|
if( blowfish_ctx )
|
||||||
cert->protect.iv, 8 );
|
blowfish_decode_cfb( blowfish_ctx, cert->protect.iv,
|
||||||
|
cert->protect.iv, 8 );
|
||||||
|
else
|
||||||
|
cast5_decode_cfb( cast5_ctx, cert->protect.iv,
|
||||||
|
cert->protect.iv, 8 );
|
||||||
mpi_set_secure(cert->d.elg.x );
|
mpi_set_secure(cert->d.elg.x );
|
||||||
/*fixme: maybe it is better to set the buffer secure with a
|
/*fixme: maybe it is better to set the buffer secure with a
|
||||||
* new get_buffer_secure() function */
|
* new get_buffer_secure() function */
|
||||||
buffer = mpi_get_buffer( cert->d.elg.x, &nbytes, NULL );
|
buffer = mpi_get_buffer( cert->d.elg.x, &nbytes, NULL );
|
||||||
csum = checksum_u16( nbytes*8 );
|
csum = checksum_u16( nbytes*8 );
|
||||||
blowfish_decode_cfb( blowfish_ctx, buffer, buffer, nbytes );
|
if( blowfish_ctx )
|
||||||
|
blowfish_decode_cfb( blowfish_ctx, buffer, buffer, nbytes );
|
||||||
|
else
|
||||||
|
cast5_decode_cfb( cast5_ctx, buffer, buffer, nbytes );
|
||||||
csum += checksum( buffer, nbytes );
|
csum += checksum( buffer, nbytes );
|
||||||
test_x = mpi_alloc_secure( mpi_get_nlimbs(cert->d.elg.x) );
|
test_x = mpi_alloc_secure( mpi_get_nlimbs(cert->d.elg.x) );
|
||||||
mpi_set_buffer( test_x, buffer, nbytes, 0 );
|
mpi_set_buffer( test_x, buffer, nbytes, 0 );
|
||||||
m_free( buffer );
|
m_free( buffer );
|
||||||
|
m_free( cast5_ctx );
|
||||||
m_free( blowfish_ctx );
|
m_free( blowfish_ctx );
|
||||||
/* now let's see wether we have used the right passphrase */
|
/* now let's see wether we have used the right passphrase */
|
||||||
if( csum != cert->csum ) {
|
if( csum != cert->csum ) {
|
||||||
@ -155,10 +178,12 @@ check_dsa( PKT_secret_cert *cert )
|
|||||||
DEK *dek = NULL;
|
DEK *dek = NULL;
|
||||||
MPI test_x;
|
MPI test_x;
|
||||||
BLOWFISH_context *blowfish_ctx=NULL;
|
BLOWFISH_context *blowfish_ctx=NULL;
|
||||||
|
CAST5_context *cast5_ctx=NULL;
|
||||||
|
|
||||||
switch( cert->protect.algo ) {
|
switch( cert->protect.algo ) {
|
||||||
case CIPHER_ALGO_NONE: BUG(); break;
|
case CIPHER_ALGO_NONE: BUG(); break;
|
||||||
case CIPHER_ALGO_BLOWFISH:
|
case CIPHER_ALGO_BLOWFISH:
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
keyid_from_skc( cert, keyid );
|
keyid_from_skc( cert, keyid );
|
||||||
if( cert->protect.s2k == 1 || cert->protect.s2k == 3 )
|
if( cert->protect.s2k == 1 || cert->protect.s2k == 3 )
|
||||||
dek = get_passphrase_hash( keyid, NULL,
|
dek = get_passphrase_hash( keyid, NULL,
|
||||||
@ -166,24 +191,38 @@ check_dsa( PKT_secret_cert *cert )
|
|||||||
else
|
else
|
||||||
dek = get_passphrase_hash( keyid, NULL, NULL );
|
dek = get_passphrase_hash( keyid, NULL, NULL );
|
||||||
|
|
||||||
blowfish_ctx = m_alloc_secure( sizeof *blowfish_ctx );
|
if( cert->protect.algo == CIPHER_ALGO_CAST ) {
|
||||||
blowfish_setkey( blowfish_ctx, dek->key, dek->keylen );
|
cast5_ctx = m_alloc_secure( sizeof *cast5_ctx );
|
||||||
|
cast5_setkey( cast5_ctx, dek->key, dek->keylen );
|
||||||
|
cast5_setiv( cast5_ctx, NULL );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
blowfish_ctx = m_alloc_secure( sizeof *blowfish_ctx );
|
||||||
|
blowfish_setkey( blowfish_ctx, dek->key, dek->keylen );
|
||||||
|
blowfish_setiv( blowfish_ctx, NULL );
|
||||||
|
}
|
||||||
m_free(dek); /* pw is in secure memory, so m_free() burns it */
|
m_free(dek); /* pw is in secure memory, so m_free() burns it */
|
||||||
blowfish_setiv( blowfish_ctx, NULL );
|
|
||||||
memcpy(save_iv, cert->protect.iv, 8 );
|
memcpy(save_iv, cert->protect.iv, 8 );
|
||||||
blowfish_decode_cfb( blowfish_ctx,
|
if( blowfish_ctx )
|
||||||
cert->protect.iv,
|
blowfish_decode_cfb( blowfish_ctx, cert->protect.iv,
|
||||||
cert->protect.iv, 8 );
|
cert->protect.iv, 8 );
|
||||||
|
else
|
||||||
|
cast5_decode_cfb( cast5_ctx, cert->protect.iv,
|
||||||
|
cert->protect.iv, 8 );
|
||||||
mpi_set_secure(cert->d.dsa.x );
|
mpi_set_secure(cert->d.dsa.x );
|
||||||
/*fixme: maybe it is better to set the buffer secure with a
|
/*fixme: maybe it is better to set the buffer secure with a
|
||||||
* new get_buffer_secure() function */
|
* new get_buffer_secure() function */
|
||||||
buffer = mpi_get_buffer( cert->d.dsa.x, &nbytes, NULL );
|
buffer = mpi_get_buffer( cert->d.dsa.x, &nbytes, NULL );
|
||||||
csum = checksum_u16( nbytes*8 );
|
csum = checksum_u16( nbytes*8 );
|
||||||
blowfish_decode_cfb( blowfish_ctx, buffer, buffer, nbytes );
|
if( blowfish_ctx )
|
||||||
|
blowfish_decode_cfb( blowfish_ctx, buffer, buffer, nbytes );
|
||||||
|
else
|
||||||
|
cast5_decode_cfb( cast5_ctx, buffer, buffer, nbytes );
|
||||||
csum += checksum( buffer, nbytes );
|
csum += checksum( buffer, nbytes );
|
||||||
test_x = mpi_alloc_secure( mpi_get_nlimbs(cert->d.dsa.x) );
|
test_x = mpi_alloc_secure( mpi_get_nlimbs(cert->d.dsa.x) );
|
||||||
mpi_set_buffer( test_x, buffer, nbytes, 0 );
|
mpi_set_buffer( test_x, buffer, nbytes, 0 );
|
||||||
m_free( buffer );
|
m_free( buffer );
|
||||||
|
m_free( cast5_ctx );
|
||||||
m_free( blowfish_ctx );
|
m_free( blowfish_ctx );
|
||||||
/* now let's see wether we have used the right passphrase */
|
/* now let's see wether we have used the right passphrase */
|
||||||
if( csum != cert->csum ) {
|
if( csum != cert->csum ) {
|
||||||
@ -399,6 +438,7 @@ protect_secret_key( PKT_secret_cert *cert, DEK *dek )
|
|||||||
|
|
||||||
if( !cert->is_protected ) { /* okay, apply the protection */
|
if( !cert->is_protected ) { /* okay, apply the protection */
|
||||||
BLOWFISH_context *blowfish_ctx=NULL;
|
BLOWFISH_context *blowfish_ctx=NULL;
|
||||||
|
CAST5_context *cast5_ctx=NULL;
|
||||||
|
|
||||||
switch( cert->protect.algo ) {
|
switch( cert->protect.algo ) {
|
||||||
case CIPHER_ALGO_NONE: BUG(); break;
|
case CIPHER_ALGO_NONE: BUG(); break;
|
||||||
@ -414,6 +454,18 @@ protect_secret_key( PKT_secret_cert *cert, DEK *dek )
|
|||||||
m_free( blowfish_ctx );
|
m_free( blowfish_ctx );
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
|
cast5_ctx = m_alloc_secure( sizeof *cast5_ctx );
|
||||||
|
cast5_setkey( cast5_ctx, dek->key, dek->keylen );
|
||||||
|
cast5_setiv( cast5_ctx, NULL );
|
||||||
|
cast5_encode_cfb( cast5_ctx, cert->protect.iv,
|
||||||
|
cert->protect.iv, 8 );
|
||||||
|
if( !do_protect( (void (*)(void*,byte*,byte*,unsigned))
|
||||||
|
&cast5_encode_cfb, cast5_ctx, cert ) )
|
||||||
|
cert->is_protected = 1;
|
||||||
|
m_free( cast5_ctx );
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
rc = G10ERR_CIPHER_ALGO; /* unsupport protection algorithm */
|
rc = G10ERR_CIPHER_ALGO; /* unsupport protection algorithm */
|
||||||
break;
|
break;
|
||||||
|
@ -41,6 +41,7 @@ make_session_key( DEK *dek )
|
|||||||
randomize_buffer( dek->key, dek->keylen, 1 );
|
randomize_buffer( dek->key, dek->keylen, 1 );
|
||||||
break;
|
break;
|
||||||
case CIPHER_ALGO_BLOWFISH128:
|
case CIPHER_ALGO_BLOWFISH128:
|
||||||
|
case CIPHER_ALGO_CAST:
|
||||||
dek->keylen = 16;
|
dek->keylen = 16;
|
||||||
randomize_buffer( dek->key, dek->keylen, 1 );
|
randomize_buffer( dek->key, dek->keylen, 1 );
|
||||||
break;
|
break;
|
||||||
|
@ -33,6 +33,7 @@
|
|||||||
#include "../cipher/rsa.h"
|
#include "../cipher/rsa.h"
|
||||||
#endif
|
#endif
|
||||||
#include "../cipher/blowfish.h"
|
#include "../cipher/blowfish.h"
|
||||||
|
#include "../cipher/cast5.h"
|
||||||
#include "../cipher/elgamal.h"
|
#include "../cipher/elgamal.h"
|
||||||
#include "../cipher/dsa.h"
|
#include "../cipher/dsa.h"
|
||||||
#include "../cipher/random.h"
|
#include "../cipher/random.h"
|
||||||
|
@ -1,19 +1,23 @@
|
|||||||
## Process this file with automake to produce Makefile.in
|
## Process this file with automake to produce Makefile.in
|
||||||
|
|
||||||
INCLUDES = -I$(top_srcdir)/include -I$(top_srcdir)/intl -I../intl
|
INCLUDES = -I$(top_srcdir)/include -I$(top_srcdir)/intl -I../intl
|
||||||
needed_libs = ../cipher/libcipher.a ../util/libutil.a ../mpi/libmpi.a ../util/libutil.a
|
needed_libs = ../cipher/libcipher.a ../util/libutil.a \
|
||||||
|
../mpi/libmpi.a ../util/libutil.a
|
||||||
|
|
||||||
noinst_PROGRAMS = mpicalc bftest clean-sat
|
noinst_PROGRAMS = mpicalc bftest cast5test clean-sat
|
||||||
|
|
||||||
mpicalc_SOURCES = mpicalc.c
|
mpicalc_SOURCES = mpicalc.c
|
||||||
|
|
||||||
bftest_SOURCES = bftest.c
|
bftest_SOURCES = bftest.c
|
||||||
|
|
||||||
|
cast5test_SOURCES = cast5test.c
|
||||||
|
|
||||||
clean_sat_SOURCES = clean-sat.c
|
clean_sat_SOURCES = clean-sat.c
|
||||||
|
|
||||||
|
|
||||||
mpicalc_LDADD = @INTLLIBS@ $(needed_libs)
|
mpicalc_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
bftest_LDADD = @INTLLIBS@ $(needed_libs)
|
bftest_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
|
cast5test_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
|
|
||||||
mpicalc bftest: $(needed_libs)
|
mpicalc bftest cast5test: $(needed_libs)
|
||||||
|
|
||||||
|
@ -93,18 +93,22 @@ ZLIBS = @ZLIBS@
|
|||||||
l = @l@
|
l = @l@
|
||||||
|
|
||||||
INCLUDES = -I$(top_srcdir)/include -I$(top_srcdir)/intl -I../intl
|
INCLUDES = -I$(top_srcdir)/include -I$(top_srcdir)/intl -I../intl
|
||||||
needed_libs = ../cipher/libcipher.a ../util/libutil.a ../mpi/libmpi.a ../util/libutil.a
|
needed_libs = ../cipher/libcipher.a ../util/libutil.a \
|
||||||
|
../mpi/libmpi.a ../util/libutil.a
|
||||||
|
|
||||||
noinst_PROGRAMS = mpicalc bftest clean-sat
|
noinst_PROGRAMS = mpicalc bftest cast5test clean-sat
|
||||||
|
|
||||||
mpicalc_SOURCES = mpicalc.c
|
mpicalc_SOURCES = mpicalc.c
|
||||||
|
|
||||||
bftest_SOURCES = bftest.c
|
bftest_SOURCES = bftest.c
|
||||||
|
|
||||||
|
cast5test_SOURCES = cast5test.c
|
||||||
|
|
||||||
clean_sat_SOURCES = clean-sat.c
|
clean_sat_SOURCES = clean-sat.c
|
||||||
|
|
||||||
mpicalc_LDADD = @INTLLIBS@ $(needed_libs)
|
mpicalc_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
bftest_LDADD = @INTLLIBS@ $(needed_libs)
|
bftest_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
|
cast5test_LDADD = @INTLLIBS@ $(needed_libs)
|
||||||
mkinstalldirs = $(SHELL) $(top_srcdir)/scripts/mkinstalldirs
|
mkinstalldirs = $(SHELL) $(top_srcdir)/scripts/mkinstalldirs
|
||||||
CONFIG_HEADER = ../config.h
|
CONFIG_HEADER = ../config.h
|
||||||
CONFIG_CLEAN_FILES =
|
CONFIG_CLEAN_FILES =
|
||||||
@ -123,6 +127,10 @@ bftest_OBJECTS = bftest.o
|
|||||||
bftest_DEPENDENCIES = ../cipher/libcipher.a ../util/libutil.a \
|
bftest_DEPENDENCIES = ../cipher/libcipher.a ../util/libutil.a \
|
||||||
../mpi/libmpi.a ../util/libutil.a
|
../mpi/libmpi.a ../util/libutil.a
|
||||||
bftest_LDFLAGS =
|
bftest_LDFLAGS =
|
||||||
|
cast5test_OBJECTS = cast5test.o
|
||||||
|
cast5test_DEPENDENCIES = ../cipher/libcipher.a ../util/libutil.a \
|
||||||
|
../mpi/libmpi.a ../util/libutil.a
|
||||||
|
cast5test_LDFLAGS =
|
||||||
clean_sat_OBJECTS = clean-sat.o
|
clean_sat_OBJECTS = clean-sat.o
|
||||||
clean_sat_LDADD = $(LDADD)
|
clean_sat_LDADD = $(LDADD)
|
||||||
clean_sat_DEPENDENCIES =
|
clean_sat_DEPENDENCIES =
|
||||||
@ -137,9 +145,10 @@ DISTFILES = $(DIST_COMMON) $(SOURCES) $(HEADERS) $(TEXINFOS) $(EXTRA_DIST)
|
|||||||
|
|
||||||
TAR = tar
|
TAR = tar
|
||||||
GZIP = --best
|
GZIP = --best
|
||||||
DEP_FILES = .deps/bftest.P .deps/clean-sat.P .deps/mpicalc.P
|
DEP_FILES = .deps/bftest.P .deps/cast5test.P .deps/clean-sat.P \
|
||||||
SOURCES = $(mpicalc_SOURCES) $(bftest_SOURCES) $(clean_sat_SOURCES)
|
.deps/mpicalc.P
|
||||||
OBJECTS = $(mpicalc_OBJECTS) $(bftest_OBJECTS) $(clean_sat_OBJECTS)
|
SOURCES = $(mpicalc_SOURCES) $(bftest_SOURCES) $(cast5test_SOURCES) $(clean_sat_SOURCES)
|
||||||
|
OBJECTS = $(mpicalc_OBJECTS) $(bftest_OBJECTS) $(cast5test_OBJECTS) $(clean_sat_OBJECTS)
|
||||||
|
|
||||||
default: all
|
default: all
|
||||||
|
|
||||||
@ -186,6 +195,10 @@ bftest: $(bftest_OBJECTS) $(bftest_DEPENDENCIES)
|
|||||||
@rm -f bftest
|
@rm -f bftest
|
||||||
$(LINK) $(bftest_LDFLAGS) $(bftest_OBJECTS) $(bftest_LDADD) $(LIBS)
|
$(LINK) $(bftest_LDFLAGS) $(bftest_OBJECTS) $(bftest_LDADD) $(LIBS)
|
||||||
|
|
||||||
|
cast5test: $(cast5test_OBJECTS) $(cast5test_DEPENDENCIES)
|
||||||
|
@rm -f cast5test
|
||||||
|
$(LINK) $(cast5test_LDFLAGS) $(cast5test_OBJECTS) $(cast5test_LDADD) $(LIBS)
|
||||||
|
|
||||||
clean-sat: $(clean_sat_OBJECTS) $(clean_sat_DEPENDENCIES)
|
clean-sat: $(clean_sat_OBJECTS) $(clean_sat_DEPENDENCIES)
|
||||||
@rm -f clean-sat
|
@rm -f clean-sat
|
||||||
$(LINK) $(clean_sat_LDFLAGS) $(clean_sat_OBJECTS) $(clean_sat_LDADD) $(LIBS)
|
$(LINK) $(clean_sat_LDFLAGS) $(clean_sat_OBJECTS) $(clean_sat_LDADD) $(LIBS)
|
||||||
@ -320,7 +333,7 @@ installdirs mostlyclean-generic distclean-generic clean-generic \
|
|||||||
maintainer-clean-generic clean mostlyclean distclean maintainer-clean
|
maintainer-clean-generic clean mostlyclean distclean maintainer-clean
|
||||||
|
|
||||||
|
|
||||||
mpicalc bftest: $(needed_libs)
|
mpicalc bftest cast5test: $(needed_libs)
|
||||||
|
|
||||||
# Tell versions [3.59,3.63) of GNU make to not export all variables.
|
# Tell versions [3.59,3.63) of GNU make to not export all variables.
|
||||||
# Otherwise a system limit (for SysV at least) may be exceeded.
|
# Otherwise a system limit (for SysV at least) may be exceeded.
|
||||||
|
108
tools/cast5test.c
Normal file
108
tools/cast5test.c
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
/* cast5test.c - CAST5 test program
|
||||||
|
* Copyright (C) 1998 Free Software Foundation, Inc.
|
||||||
|
*
|
||||||
|
* This file is part of GNUPG.
|
||||||
|
*
|
||||||
|
* GNUPG is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* GNUPG is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <config.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
#ifdef __MINGW32__
|
||||||
|
#include <io.h>
|
||||||
|
#include <fcntl.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include "util.h"
|
||||||
|
#include "cipher.h"
|
||||||
|
#include "i18n.h"
|
||||||
|
|
||||||
|
static void
|
||||||
|
my_usage(void)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "usage: cast5test [-e][-d] key\n");
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
const char *
|
||||||
|
strusage( int level )
|
||||||
|
{
|
||||||
|
return default_strusage(level);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
i18n_init(void)
|
||||||
|
{
|
||||||
|
#ifdef ENABLE_NLS
|
||||||
|
#ifdef HAVE_LC_MESSAGES
|
||||||
|
setlocale( LC_MESSAGES, "" );
|
||||||
|
#else
|
||||||
|
setlocale( LC_ALL, "" );
|
||||||
|
#endif
|
||||||
|
bindtextdomain( PACKAGE, G10_LOCALEDIR );
|
||||||
|
textdomain( PACKAGE );
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
main(int argc, char **argv)
|
||||||
|
{
|
||||||
|
int encode=0;
|
||||||
|
CAST5_context ctx;
|
||||||
|
char buf[100];
|
||||||
|
int n, size=100;
|
||||||
|
|
||||||
|
#ifdef __MINGW32__
|
||||||
|
setmode( fileno(stdin), O_BINARY );
|
||||||
|
setmode( fileno(stdout), O_BINARY );
|
||||||
|
#endif
|
||||||
|
|
||||||
|
i18n_init();
|
||||||
|
if( argc > 1 && !strcmp(argv[1], "-e") ) {
|
||||||
|
encode++;
|
||||||
|
argc--; argv++;
|
||||||
|
}
|
||||||
|
else if( argc > 1 && !strcmp(argv[1], "-E") ) {
|
||||||
|
encode++;
|
||||||
|
argc--; argv++;
|
||||||
|
size = 10;
|
||||||
|
}
|
||||||
|
else if( argc > 1 && !strcmp(argv[1], "-d") ) {
|
||||||
|
argc--; argv++;
|
||||||
|
}
|
||||||
|
else if( argc > 1 && !strcmp(argv[1], "-D") ) {
|
||||||
|
argc--; argv++;
|
||||||
|
size = 10;
|
||||||
|
}
|
||||||
|
if( argc != 2 )
|
||||||
|
my_usage();
|
||||||
|
argc--; argv++;
|
||||||
|
|
||||||
|
cast5_setkey( &ctx, *argv, strlen(*argv) );
|
||||||
|
cast5_setiv( &ctx, NULL );
|
||||||
|
while( (n = fread( buf, 1, size, stdin )) > 0 ) {
|
||||||
|
if( encode )
|
||||||
|
cast5_encode_cfb( &ctx, buf, buf, n );
|
||||||
|
else
|
||||||
|
cast5_decode_cfb( &ctx, buf, buf, n );
|
||||||
|
if( fwrite( buf, 1, n, stdout) != n )
|
||||||
|
log_fatal("write error\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
Loading…
x
Reference in New Issue
Block a user