[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

[or-cvs] Be smarter about getting key matter from DH.



Update of /home/or/cvsroot/src/common
In directory moria.mit.edu:/tmp/cvs-serv27166/src/common

Modified Files:
	crypto.c crypto.h 
Log Message:
Be smarter about getting key matter from DH.

Formerly, once we had g^xy, we took the last N bytes from g^xy.

Now, we take SHA(g^xy || [0]) || SHA1(g^xy || [1]) || ... , in order
to use all bits from g^xy equally, and generate as much key material
as we need.



Index: crypto.c
===================================================================
RCS file: /home/or/cvsroot/src/common/crypto.c,v
retrieving revision 1.27
retrieving revision 1.28
diff -u -d -r1.27 -r1.28
--- crypto.c	30 Jun 2003 19:18:32 -0000	1.27
+++ crypto.c	30 Jul 2003 19:10:20 -0000	1.28
@@ -798,22 +798,41 @@
 
   return 0;
 }
+
+#undef MIN
+#define MIN(a,b) ((a)<(b)?(a):(b))
 int crypto_dh_compute_secret(crypto_dh_env_t *dh, 
 			     char *pubkey, int pubkey_len,
-			     char *secret_out)
+			     char *secret_out, int secret_bytes_out)
 {
-  BIGNUM *pubkey_bn;
+  unsigned char hash[20];
+  unsigned char *secret_tmp = NULL;
+  BIGNUM *pubkey_bn = NULL;
   int secret_len;
+  int i;
   assert(dh);
-  
+  assert(secret_bytes_out/20 <= 255);
+
   if (!(pubkey_bn = BN_bin2bn(pubkey, pubkey_len, NULL)))
-    return -1;
-  
-  secret_len = DH_compute_key(secret_out, pubkey_bn, dh->dh);  
-  BN_free(pubkey_bn);
-  if (secret_len == -1)
-    return -1;
+    goto error;
+  secret_tmp = tor_malloc(crypto_dh_get_bytes(dh)+1);
+  secret_len = DH_compute_key(secret_tmp, pubkey_bn, dh->dh);
+  for (i = 0; i < secret_bytes_out; i += 20) {
+    secret_tmp[secret_len] = (unsigned char) i/20;
+    if (crypto_SHA_digest(secret_tmp, secret_len+1, hash))
+      goto error;
+    memcpy(secret_out+i, hash, MIN(20, secret_bytes_out-i));
+  }
+  secret_len = secret_bytes_out;
 
+  goto done;
+ error:
+  secret_len = -1;
+ done:
+  if (pubkey_bn)
+    BN_free(pubkey_bn);
+  if (secret_tmp)
+    free(secret_tmp);
   return secret_len;
 }
 void crypto_dh_free(crypto_dh_env_t *dh)

Index: crypto.h
===================================================================
RCS file: /home/or/cvsroot/src/common/crypto.h,v
retrieving revision 1.13
retrieving revision 1.14
diff -u -d -r1.13 -r1.14
--- crypto.h	30 Jun 2003 19:18:32 -0000	1.13
+++ crypto.h	30 Jul 2003 19:10:20 -0000	1.14
@@ -81,7 +81,7 @@
 			 int pubkey_out_len);
 int crypto_dh_compute_secret(crypto_dh_env_t *dh, 
 			     char *pubkey, int pubkey_len,
-			     char *secret_out);
+			     char *secret_out, int secret_out_len);
 void crypto_dh_free(crypto_dh_env_t *dh);
 
 /* symmetric crypto */