New DES random number generation. For regular DES, it is nearly equivalent
authorRichard Basch <probe@mit.edu>
Tue, 7 May 1996 20:17:36 +0000 (20:17 +0000)
committerRichard Basch <probe@mit.edu>
Tue, 7 May 1996 20:17:36 +0000 (20:17 +0000)
(an extra DES encryption now happens).  For 3des, it is a substantially
better setup (the original one was a placeholder); it may not be the final
one, but at least it is not as weak as the previous version.  (This checkin
does not include the proposed API changes.)

git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@7911 dc483132-0cff-0310-8789-dd5450dbe970

src/lib/crypto/des/ChangeLog
src/lib/crypto/des/Makefile.in
src/lib/crypto/des/d3_rndky.c [deleted file]
src/lib/crypto/des/des_int.h
src/lib/crypto/des/fin_rndkey.c
src/lib/crypto/des/new_rn_key.c [deleted file]
src/lib/crypto/des/random_key.c
src/lib/crypto/des/u_rn_key.c [new file with mode: 0644]

index 15219e3ae5996cc1243a9c2a6ade1b58089481d4..70063be98d0435765b9d92e446f2a3de6465fc22 100644 (file)
@@ -1,3 +1,28 @@
+Thu May  2 18:29:01 1996  Richard Basch  <basch@lehman.com>
+
+       * d3_rndky.c new_rn_key.c: Removed (obsolete).
+
+       * u_rn_key.c: New file
+               Support routines to set the seed/sequence number of the
+               random stream.
+
+       * Makefile.in: new/removed file changes
+
+       * des_int.h: Changed prototypes for all the random routines.
+
+       * fin_rndkey.c: rewrote mit_des_finish_random_key to use the new
+               random state structure and to accept an eblock as arg 1.
+
+       * init_rkey.c: rewritten to be a common DES, 3-DES random stream
+               initialization routine.  it uses the eblock to determine
+               the random key type to generate.
+               
+       * random_key.c: rewritten to be a common DES, 3-DES random stream
+               generator, using the former DES algorithm (encrypting an
+               incrementing sequence number with a unique key schedule)
+               [3-DES uses DES3-CBC-CRC to increment a 192 bit sequence
+               number, instead of being only as secure as DES.]
+
 Wed Apr 10 17:46:40 1996  Theodore Y. Ts'o  <tytso@dcl>
 
        * Makefile.in (SRCS,OBJS): Added afsstring2key.c to the list of
index 281f449c98e7ed15e4c2b440516b991e7f3f865b..6875c762ddb144da7d3306f241bdf72c2c4f6903 100644 (file)
@@ -21,7 +21,6 @@ OBJS= afsstring2key.$(OBJEXT) \
        process_ky.$(OBJEXT)    \
        random_key.$(OBJEXT)    \
        string2key.$(OBJEXT)    \
-       new_rn_key.$(OBJEXT)    \
        key_sched.$(OBJEXT)     \
        weak_key.$(OBJEXT)      \
        f_cbc.$(OBJEXT)         \
@@ -34,9 +33,9 @@ OBJS= afsstring2key.$(OBJEXT) \
        d3_ecb.$(OBJEXT)        \
        d3_kysched.$(OBJEXT)    \
        d3_procky.$(OBJEXT)     \
-       d3_rndky.$(OBJEXT)      \
-       d3_str2ky.$(OBJEXT) \
-       u_nfold.$(OBJEXT)
+       d3_str2ky.$(OBJEXT)     \
+       u_nfold.$(OBJEXT)       \
+       u_rn_key.$(OBJEXT)
 
 SRCS=  $(srcdir)/afsstring2key.c \
        $(srcdir)/cs_entry.c    \
@@ -47,7 +46,6 @@ SRCS= $(srcdir)/afsstring2key.c \
        $(srcdir)/process_ky.c  \
        $(srcdir)/random_key.c  \
        $(srcdir)/string2key.c  \
-       $(srcdir)/new_rn_key.c  \
        $(srcdir)/key_sched.c   \
        $(srcdir)/weak_key.c    \
        $(srcdir)/f_cbc.c \
@@ -60,9 +58,9 @@ SRCS= $(srcdir)/afsstring2key.c \
        $(srcdir)/d3_ecb.c \
        $(srcdir)/d3_kysched.c \
        $(srcdir)/d3_procky.c \
-       $(srcdir)/d3_rndky.c \
        $(srcdir)/d3_str2ky.c \
-       $(srcdir)/u_nfold.c
+       $(srcdir)/u_nfold.c \
+       $(srcdir)/u_rn_key.c
 
 
 all:: $(OBJS)
diff --git a/src/lib/crypto/des/d3_rndky.c b/src/lib/crypto/des/d3_rndky.c
deleted file mode 100644 (file)
index 5edcf4d..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 1995 by Richard P. Basch.  All Rights Reserved.
- * Copyright 1995 by Lehman Brothers, Inc.  All Rights Reserved.
- *
- * Export of this software from the United States of America may
- *   require a specific license from the United States Government.
- *   It is the responsibility of any person or organization contemplating
- *   export to obtain such a license before exporting.
- * 
- * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
- * distribute this software and its documentation for any purpose and
- * without fee is hereby granted, provided that the above copyright
- * notice appear in all copies and that both that copyright notice and
- * this permission notice appear in supporting documentation, and that
- * the name of Richard P. Basch, Lehman Brothers and M.I.T. not be used
- * in advertising or publicity pertaining to distribution of the software
- * without specific, written prior permission.  Richard P. Basch,
- * Lehman Brothers and M.I.T. make no representations about the suitability
- * of this software for any purpose.  It is provided "as is" without
- * express or implied warranty.
- */
-
-#include "k5-int.h"
-#include "des_int.h"
-
-krb5_error_code
-mit_des3_random_key (eblock, seed, keyblock)
-    const krb5_encrypt_block * eblock;
-    krb5_pointer seed;
-    krb5_keyblock ** keyblock;
-{
-    krb5_keyblock *randkey;
-
-    if (!(randkey = (krb5_keyblock *)malloc(sizeof(*randkey))))
-       return ENOMEM;
-    if (!(randkey->contents=(krb5_octet *)malloc(sizeof(mit_des3_cblock)))) {
-       krb5_xfree(randkey);
-       return ENOMEM;
-    }
-    randkey->magic = KV5M_KEYBLOCK;
-    randkey->length = sizeof(mit_des3_cblock);
-    randkey->enctype = eblock->crypto_entry->proto_enctype;
-    mit_des_new_random_key(*(mit_des_cblock *)randkey->contents,
-                          (mit_des_random_key_seed *) seed);
-    mit_des_new_random_key(*((mit_des_cblock *)randkey->contents + 1),
-                          (mit_des_random_key_seed *) seed);
-    mit_des_new_random_key(*((mit_des_cblock *)randkey->contents + 2),
-                          (mit_des_random_key_seed *) seed);
-    *keyblock = randkey;
-    return 0;
-}
index 04332f706a43f2c8cc2609e415dd16bd74e21b25..db1a6b9b3d416f307ba54a470cc47b82d06addfa 100644 (file)
@@ -57,9 +57,9 @@ typedef mit_des_key_schedule  mit_des3_key_schedule[3];
 #define MIT_DES_DECRYPT        0
 
 typedef struct mit_des_ran_key_seed {
-    krb5_octet sequence_number[8];
-    mit_des_key_schedule random_sequence_key;
-} mit_des_random_key_seed;
+    krb5_encrypt_block eblock;
+    krb5_data sequence;
+} mit_des_random_state;
 
 /* the first byte of the key is already in the keyblock */
 
@@ -118,7 +118,8 @@ extern int mit_des_cbc_encrypt
     
 /* fin_rndkey.c */
 extern krb5_error_code mit_des_finish_random_key
-    PROTOTYPE(( krb5_pointer FAR *));
+    PROTOTYPE(( const krb5_encrypt_block FAR *,
+               krb5_pointer FAR *));
 
 /* finish_key.c */
 extern krb5_error_code mit_des_finish_key
@@ -126,7 +127,9 @@ extern krb5_error_code mit_des_finish_key
 
 /* init_rkey.c */
 extern krb5_error_code mit_des_init_random_key
-    PROTOTYPE(( const krb5_keyblock FAR *,  krb5_pointer FAR *));
+    PROTOTYPE(( const krb5_encrypt_block FAR *,
+               const krb5_keyblock FAR *,
+               krb5_pointer FAR *));
 
 /* key_parity.c */
 extern void mit_des_fixup_key_parity PROTOTYPE((mit_des_cblock ));
@@ -136,18 +139,6 @@ extern int mit_des_check_key_parity PROTOTYPE((mit_des_cblock ));
 extern int mit_des_key_sched
     PROTOTYPE((mit_des_cblock , mit_des_key_schedule ));
 
-/* new_rnd_key.c */
-extern int mit_des_new_random_key
-    PROTOTYPE((mit_des_cblock , mit_des_random_key_seed FAR *));
-extern void mit_des_init_random_number_generator
-    PROTOTYPE((mit_des_cblock, mit_des_random_key_seed FAR *));
-extern void mit_des_set_random_generator_seed
-    PROTOTYPE((mit_des_cblock , mit_des_random_key_seed FAR *));
-extern void mit_des_set_sequence_number
-    PROTOTYPE((mit_des_cblock , mit_des_random_key_seed FAR *));
-extern void mit_des_generate_random_block
-    PROTOTYPE((mit_des_cblock , mit_des_random_key_seed FAR *));
-
 /* process_ky.c */
 extern krb5_error_code mit_des_process_key
     PROTOTYPE(( krb5_encrypt_block FAR *,  const krb5_keyblock FAR *));
@@ -218,12 +209,6 @@ extern krb5_error_code mit_des3_process_key
        PROTOTYPE((krb5_encrypt_block * eblock,
                   const krb5_keyblock * keyblock));
 
-/* d3_rndkey.c */
-extern krb5_error_code mit_des3_random_key
-       PROTOTYPE((const krb5_encrypt_block * eblock,
-                  krb5_pointer seed,
-                  krb5_keyblock ** keyblock));
-
 /* d3_kysched.c */
 extern int mit_des3_key_sched
        PROTOTYPE((mit_des3_cblock key,
@@ -243,4 +228,13 @@ extern krb5_error_code mit_des_n_fold
                   krb5_octet * output,
                   const size_t out_len));
 
+/* u_rn_key.c */
+extern krb5_error_code mit_des_set_random_generator_seed
+       PROTOTYPE((const krb5_data * seed,
+                  krb5_pointer random_state));
+
+extern krb5_error_code mit_des_set_random_sequence_number
+       PROTOTYPE((const krb5_data * sequence,
+                  krb5_pointer random_state));
+
 #endif /*DES_INTERNAL_DEFS*/
index 943a27c5b012e9c1a4dfe74da526205ddd96631b..7b8a2c385c101b6ed95ce14851431ff4a3261279 100644 (file)
@@ -2,6 +2,7 @@
  * lib/crypto/des/fin_rndkey.c
  *
  * Copyright 1990,1991 by the Massachusetts Institute of Technology.
+ * Copyright 1996 by Lehman Brothers, Inc.
  * All Rights Reserved.
  *
  * Export of this software from the United States of America may
  * without fee is hereby granted, provided that the above copyright
  * notice appear in all copies and that both that copyright notice and
  * this permission notice appear in supporting documentation, and that
- * the name of M.I.T. not be used in advertising or publicity pertaining
- * to distribution of the software without specific, written prior
- * permission.  M.I.T. makes no representations about the suitability of
- * this software for any purpose.  It is provided "as is" without express
- * or implied warranty.
- * 
- *
+ * the name of M.I.T. or Lehman Brothers not be used in advertising or
+ * publicity pertaining to distribution of the software without
+ * specific, written prior permission.  M.I.T. and Lehman Brothers
+ * make no representations about the suitability of this software for
+ * any purpose.  It is provided "as is" without express or implied
+ * warranty.
  */
 
 #include "k5-int.h"
         free any resources held by "seed" and assigned by init_random_key()
  */
 
-krb5_error_code mit_des_finish_random_key (seed)
-    krb5_pointer * seed;
+krb5_error_code mit_des_finish_random_key (eblock, p_state)
+    const krb5_encrypt_block * eblock;
+    krb5_pointer * p_state;
 {
-    memset((char *)*seed, 0, sizeof(mit_des_random_key_seed) );
-    krb5_xfree(*seed);
-    *seed = 0;
+    mit_des_random_state * state = *p_state;
+
+    if (! state) return 0;
+
+    if (state->sequence.data) {
+       memset((char *)state->sequence.data, 0, state->sequence.length);
+       krb5_xfree(state->sequence.data);
+    }
+
+    mit_des_finish_key(&state->eblock);
+
+    krb5_xfree(state);
+    *p_state = 0;
     return 0;
 }
diff --git a/src/lib/crypto/des/new_rn_key.c b/src/lib/crypto/des/new_rn_key.c
deleted file mode 100644 (file)
index e100602..0000000
+++ /dev/null
@@ -1,235 +0,0 @@
-/*
- * lib/crypto/des/new_rn_key.c
- *
- * Copyright 1988,1990 by the Massachusetts Institute of Technology.
- * All Rights Reserved.
- *
- * Export of this software from the United States of America may
- *   require a specific license from the United States Government.
- *   It is the responsibility of any person or organization contemplating
- *   export to obtain such a license before exporting.
- * 
- * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
- * distribute this software and its documentation for any purpose and
- * without fee is hereby granted, provided that the above copyright
- * notice appear in all copies and that both that copyright notice and
- * this permission notice appear in supporting documentation, and that
- * the name of M.I.T. not be used in advertising or publicity pertaining
- * to distribution of the software without specific, written prior
- * permission.  M.I.T. makes no representations about the suitability of
- * this software for any purpose.  It is provided "as is" without express
- * or implied warranty.
- * 
- *
- * New pseudo-random key generator, using DES encryption to make the
- * pseudo-random cycle as hard to break as DES.
- *
- * Written by Mark Lillibridge, MIT Project Athena
- *
- * Under U.S. law, this software may not be exported outside the US
- * without license from the U.S. Commerce department.
- */
-
-#include "k5-int.h"
-#include "des_int.h"
-
-#ifndef min
-#define min(a,b) (((a) < (b)) ? (a) : (b))
-#endif
-
-/*
- * mit_des_new_random_key: create a random des key
- *
- * Requires: mit_des_set_random_number_generater_seed must be at called least
- *           once before this routine is called.
- *
- * Notes: the returned key has correct parity and is guarenteed not
- *        to be a weak des key.  Mit_Des_generate_random_block is used to
- *        provide the random bits.
- */
-int
-mit_des_new_random_key(key, p_seed)
-    mit_des_cblock key;
-    mit_des_random_key_seed    *p_seed;
-{
-    do {
-       mit_des_generate_random_block(key, p_seed);
-       mit_des_fixup_key_parity(key);
-    } while (mit_des_is_weak_key(key));
-
-    return(0);
-}
-
-/*
- * mit_des_init_random_number_generator:
- *
- *    This routine takes a secret key possibly shared by a number
- * of servers and uses it to generate a random number stream that is
- * not shared by any of the other servers.  It does this by using the current
- * process id, host id, and the current time to the nearest second.  The
- * resulting stream seed is not useful information for cracking the secret
- * key.   Moreover, this routine keeps no copy of the secret key.
- * This routine is used for example, by the kerberos server(s) with the
- * key in question being the kerberos master key.
- *
- * Note: this routine calls mit_des_set_random_generator_seed.
- */
-
-void
-mit_des_init_random_number_generator(key,p_seed)
-    mit_des_cblock key;
-    mit_des_random_key_seed    *p_seed;
-{
-    mit_des_cblock seed; /* This must be 64 bits exactly */
-    struct tval {
-       krb5_int32 seconds;
-       krb5_int32 microseconds;
-    } timenow;
-    mit_des_cblock new_key;
-
-    krb5_address **addrs = 0;
-
-    /*
-     * use a host id in generating the seed to ensure
-     * that different servers have different streams:
-     */
-    memset((char *)seed, 0, sizeof(seed));
-    if (!krb5_crypto_os_localaddr(&addrs) && addrs && *addrs) {
-       memcpy((char *)seed, (char *)addrs[0]->contents,
-             min(sizeof(seed), addrs[0]->length));
-       /* XXX may not do all of the seed. */
-    }
-    if (addrs) {
-       /* can't use krb5_free_addresses due to circular dependencies in
-          libraries */
-       register krb5_address **addr2;
-       for (addr2 = addrs; *addr2; addr2++) {
-           krb5_xfree((*addr2)->contents);
-           krb5_xfree(*addr2);
-       }
-       krb5_xfree(addrs);
-    }
-    /*
-     * Generate a temporary value that depends on the key and host_id
-     * such that it gives no useful information about the key:
-     */
-    mit_des_set_random_generator_seed(key, p_seed);
-    mit_des_set_sequence_number(seed, p_seed);
-    mit_des_new_random_key(new_key, p_seed);
-
-    /*
-     * use it to select a random stream:
-     */      
-    mit_des_set_random_generator_seed(new_key, p_seed);
-
-    /*
-     * use a time stamp to ensure that a server started later does not reuse
-     * an old stream:
-     */
-    /* XXX return value */
-    (void) krb5_crypto_us_timeofday(&timenow.seconds,
-                                   &timenow.microseconds);
-    mit_des_set_sequence_number((unsigned char *)&timenow, p_seed);
-
-    /*
-     * use the time stamp finally to select the final seed using the
-     * current random number stream:
-     */
-    mit_des_new_random_key(new_key, p_seed);
-    mit_des_set_random_generator_seed(new_key, p_seed);
-}
-
-/*
- * This module implements a random number generator faculty such that the next
- * number in any random number stream is very hard to predict without knowing
- * the seed for that stream even given the preceeding random numbers.
- */
-
-/*
- * mit_des_set_random_generator_seed: this routine is used to select a random
- *                                number stream.  The stream that results is
- *                                totally determined by the passed in key.
- *                                (I.e., calling this routine again with the
- *                                same key allows repeating a sequence of
- *                                random numbers)
- *
- * Requires: key is a valid des key.  I.e., has correct parity and is not a
- *           weak des key.
- *     [Note: I have changed this so that even if it is not a valid
- *     DES key, this function will do something rational --- that is,
- *     we fix up the key parity and make it a non-weak key.  This
- *     still won't help us if the input value is guessable, but at
- *     least we won't get screwed if the key-parity is wrong... --- TYT]
- */
-void
-mit_des_set_random_generator_seed(key, p_seed)
-    mit_des_cblock key;
-    mit_des_random_key_seed    *p_seed;
-{
-    register int i;
-    mit_des_cblock fixed_key;
-
-    memcpy(fixed_key, key, sizeof(mit_des_cblock));
-    mit_des_fixup_key_parity(fixed_key);
-    if (mit_des_is_weak_key(fixed_key)) {
-           fixed_key[0] ^= 0xF0;
-           mit_des_fixup_key_parity(fixed_key);
-    }
-
-    /* select the new stream: (note errors are not possible here...) */
-    mit_des_key_sched(fixed_key, p_seed->random_sequence_key);
-
-    /* "seek" to the start of the stream: */
-    for (i=0; i<8; i++)
-      p_seed->sequence_number[i] = 0;
-}
-
-/*
- * mit_des_set_sequence_number: this routine is used to set the sequence number
- *                          of the current random number stream.  This routine
- *                          may be used to "seek" within the current random
- *                          number stream.
- *
- * Note that mit_des_set_random_generator_seed resets the sequence number to 0.
- */
-void
-mit_des_set_sequence_number(new_sequence_number, p_seed)
-    mit_des_cblock new_sequence_number;
-    mit_des_random_key_seed    *p_seed;
-{
-    memcpy((char *)p_seed->sequence_number, (char *)new_sequence_number,
-         sizeof(p_seed->sequence_number));
-}
-
-/*
- * mit_des_generate_random_block: routine to return the next random number
- *                            from the current random number stream.
- *                            The returned number is 64 bits long.
- *
- * Requires: mit_des_set_random_generator_seed must have been called at least once
- *           before this routine is called.
- */
-void
-mit_des_generate_random_block(block, p_seed)
-    mit_des_cblock block;
-    mit_des_random_key_seed    *p_seed;
-{
-    int i;
-
-    /*
-     * Encrypt the sequence number to get the new random block:
-     */
-    mit_des_ecb_encrypt((const mit_des_cblock *)p_seed->sequence_number, 
-                   (mit_des_cblock *)block, 
-                   p_seed->random_sequence_key, 1);
-
-    /*
-     * Increment the sequence number as an 8 byte unsigned number with wrap:
-     * (using LSB here)
-     */
-    for (i=0; i<8; i++) {
-       p_seed->sequence_number[i] = (p_seed->sequence_number[i] + 1) & 0xff;
-       if (p_seed->sequence_number[i])
-         break;
-    }
-}
index 3a8758f2b3b21105149061ca0410a386455a00e0..b24ec51efaad946756cb3342b2af12966f7744c2 100644 (file)
@@ -2,6 +2,7 @@
  * lib/crypto/des/random_key.c
  *
  * Copyright 1990,1991 by the Massachusetts Institute of Technology.
+ * Copyright 1996 by Lehman Brothers, Inc.
  * All Rights Reserved.
  *
  * Export of this software from the United States of America may
  * without fee is hereby granted, provided that the above copyright
  * notice appear in all copies and that both that copyright notice and
  * this permission notice appear in supporting documentation, and that
- * the name of M.I.T. not be used in advertising or publicity pertaining
- * to distribution of the software without specific, written prior
- * permission.  M.I.T. makes no representations about the suitability of
- * this software for any purpose.  It is provided "as is" without express
- * or implied warranty.
+ * the name of M.I.T. or Lehman Brothers not be used in advertising or
+ * publicity pertaining to distribution of the software without
+ * specific, written prior permission.  M.I.T. and Lehman Brothers
+ * make no representations about the suitability of this software for
+ * any purpose.  It is provided "as is" without express or implied
+ * warranty.
  */
 
 #include "k5-int.h"
 #include "des_int.h"
 
+static void mit_des_generate_random_key
+       PROTOTYPE((mit_des_random_state * state, krb5_keyblock * randkey));
+
+
 /*
         generate a random encryption key, allocating storage for it and
         filling in the keyblock address in *keyblock
  */
 
 krb5_error_code
-mit_des_random_key (eblock, seed, keyblock)
+mit_des_random_key (eblock, state, keyblock)
     const krb5_encrypt_block * eblock;
-    krb5_pointer seed;
+    krb5_pointer state;
     krb5_keyblock ** keyblock;
 {
     krb5_keyblock *randkey;
+    int keysize = ((mit_des_random_state *)state)->eblock.crypto_entry->keysize;
+
+    if (eblock == NULL)
+       /* We are being called from the random number initialization routine */
+       eblock = &((mit_des_random_state *)state)->eblock;
 
     if (!(randkey = (krb5_keyblock *)malloc(sizeof(*randkey))))
        return ENOMEM;
-    if (!(randkey->contents = (krb5_octet *)malloc(sizeof(mit_des_cblock)))) {
+    if (!(randkey->contents = (krb5_octet *)malloc(keysize))) {
        krb5_xfree(randkey);
        return ENOMEM;
     }
     randkey->magic = KV5M_KEYBLOCK;
-    randkey->length = sizeof(mit_des_cblock);
+    randkey->length = keysize;
     randkey->enctype = eblock->crypto_entry->proto_enctype;
-    mit_des_new_random_key(randkey->contents, (mit_des_random_key_seed *) seed);
+
+    do {
+       mit_des_generate_random_key(state, randkey);
+       mit_des_fixup_keyblock_parity(randkey);
+    } while (mit_des_is_weak_keyblock(randkey));
+
     *keyblock = randkey;
     return 0;
 }
+
+static mit_des_cblock zero_ivec = { 0, 0, 0, 0, 0, 0, 0, 0 };
+
+static void
+mit_des_generate_random_key(state, randkey)
+    mit_des_random_state * state;
+    krb5_keyblock * randkey;
+{
+    krb5_encrypt_block *eblock = &state->eblock;
+    int i;
+
+    (* state->eblock.crypto_entry->encrypt_func)
+       (state->sequence.data /*in*/, randkey->contents /*out*/,
+        state->sequence.length, eblock, zero_ivec);
+    (* state->eblock.crypto_entry->encrypt_func)
+       (randkey->contents /*in*/, randkey->contents /*out*/,
+        randkey->length, eblock,
+        randkey->contents + randkey->length - sizeof(mit_des_cblock));
+
+    /* Increment the sequence number, with wraparound (LSB) */
+    for (i = 0; i < state->sequence.length; i++) {
+       state->sequence.data[i] = (state->sequence.data[i] + 1) & 0xff;
+       if (state->sequence.data[i])
+           break;
+    }
+}
diff --git a/src/lib/crypto/des/u_rn_key.c b/src/lib/crypto/des/u_rn_key.c
new file mode 100644 (file)
index 0000000..44d3c73
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright 1996 by Richard P. Basch.  All Rights Reserved.
+ * Copyright 1996 by Lehman Brothers, Inc.  All Rights Reserved.
+ *
+ * Export of this software from the United States of America may
+ *   require a specific license from the United States Government.
+ *   It is the responsibility of any person or organization contemplating
+ *   export to obtain such a license before exporting.
+ * 
+ * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and
+ * distribute this software and its documentation for any purpose and
+ * without fee is hereby granted, provided that the above copyright
+ * notice appear in all copies and that both that copyright notice and
+ * this permission notice appear in supporting documentation, and that
+ * the name of Richard P. Basch, Lehman Brothers and M.I.T. not be used
+ * in advertising or publicity pertaining to distribution of the software
+ * without specific, written prior permission.  Richard P. Basch,
+ * Lehman Brothers and M.I.T. make no representations about the suitability
+ * of this software for any purpose.  It is provided "as is" without
+ * express or implied warranty.
+ *
+ *
+ * Based on the version written by Mark Lillibridge, MIT Project Athena.
+ *
+ * Under U.S. law, this software may not be exported outside the US
+ * without license from the U.S. Commerce department.
+ */
+
+#include "k5-int.h"
+#include "des_int.h"
+
+int
+mit_des_is_weak_keyblock(keyblock)
+    krb5_keyblock * keyblock;
+{
+    int i;
+    
+    for (i = 0; i < keyblock->length/sizeof(mit_des_cblock); i++)
+       if (mit_des_is_weak_key(*((mit_des_cblock *)keyblock->contents + i)))
+           return 1;
+    return 0;
+}
+
+void
+mit_des_fixup_keyblock_parity(keyblock)
+    krb5_keyblock * keyblock;
+{
+    int i;
+    
+    for (i = 0; i < keyblock->length/sizeof(mit_des_cblock); i++)
+       mit_des_fixup_key_parity(*((mit_des_cblock *)keyblock->contents + i));
+}
+
+/*
+ * mit_des_set_random_generator_seed: this routine is used to select a random
+ *                                number stream.  The stream that results is
+ *                                totally determined by the passed in key.
+ *                                (I.e., calling this routine again with the
+ *                                same key allows repeating a sequence of
+ *                                random numbers)
+ */
+krb5_error_code
+mit_des_set_random_generator_seed(seed, p_state)
+    const krb5_data * seed;
+    krb5_pointer p_state;
+{
+    krb5_error_code kret;
+    register int i;
+    mit_des_cblock *new_key;
+    mit_des_random_state *state = p_state;
+
+    if (state->eblock.key) {
+       if (state->eblock.key->contents) {
+           memset(state->eblock.key->contents, 0, state->eblock.key->length);
+           krb5_xfree(state->eblock.key->contents);
+       }
+    }
+
+    state->eblock.key = (krb5_keyblock *)malloc(sizeof(krb5_keyblock));
+    if (! state->eblock.key)
+       return ENOMEM;
+
+    state->eblock.key->enctype = state->eblock.crypto_entry->proto_enctype;
+    state->eblock.key->length = state->eblock.crypto_entry->keysize;
+    state->eblock.key->contents = (krb5_octet *)malloc(state->eblock.key->length);
+    if (! state->eblock.key->contents) {
+       krb5_xfree(state->eblock.key);
+       state->eblock.key = 0;
+       return ENOMEM;
+    }
+
+    kret = mit_des_n_fold(seed->data, seed->length,
+               state->eblock.key->contents, state->eblock.key->length);
+    if (kret) return kret;
+
+    mit_des_fixup_keyblock_parity(state->eblock.key);
+
+    for (i = 0; i < state->eblock.key->length/sizeof(mit_des_cblock); i++) {
+       new_key = (mit_des_cblock *)state->eblock.key->contents + i;
+       if (mit_des_is_weak_key(*new_key)) {
+           (*new_key)[0] ^= 0xF0;
+           mit_des_fixup_key_parity(*new_key);
+       }
+    }
+
+    /* destroy any old key schedule */
+    mit_des_finish_key(&state->eblock);
+    
+    /* compute the key schedule */
+    (* state->eblock.crypto_entry->process_key)
+       (&state->eblock, state->eblock.key);
+
+    /* now we can destroy the key... */
+    memset(state->eblock.key->contents, 0, state->eblock.key->length);
+    krb5_xfree(state->eblock.key->contents);
+    krb5_xfree(state->eblock.key);
+    state->eblock.key = (krb5_keyblock *) 0;
+
+    /* "seek" to the start of the stream: */
+    memset(state->sequence.data, 0, state->sequence.length);
+
+    return 0;
+}
+
+krb5_error_code
+mit_des_set_random_sequence_number(sequence, p_state)
+    const krb5_data *sequence;
+    krb5_pointer p_state;
+{
+    mit_des_random_state *state = p_state;
+    int length = state->eblock.crypto_entry->keysize;
+
+    if (length > sequence->length)
+       length = sequence->length;
+
+    memcpy(state->sequence.data, sequence->data, length);
+    
+    return 0;
+}