aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorlloyd <[email protected]>2010-03-09 14:31:07 +0000
committerlloyd <[email protected]>2010-03-09 14:31:07 +0000
commit535eb4d66574a0a6d49554de40c277512c7fada1 (patch)
treea24cb69cd155a111e9e3aa75d820f87f55157a0a
parent80a3459993c6b4531617f5c4f8b32cbe98d15529 (diff)
DSA and NR require certain parameters (which depend on the randomly
choosen nonce) not be 0. Previously it would just check and throw an exception if this was the case. Change to generate a new nonce and retry if this happens.
-rw-r--r--src/pubkey/dsa/dsa.cpp21
-rw-r--r--src/pubkey/nr/nr.cpp21
2 files changed, 24 insertions, 18 deletions
diff --git a/src/pubkey/dsa/dsa.cpp b/src/pubkey/dsa/dsa.cpp
index feac712b8..d1f721084 100644
--- a/src/pubkey/dsa/dsa.cpp
+++ b/src/pubkey/dsa/dsa.cpp
@@ -9,6 +9,8 @@
#include <botan/numthry.h>
#include <botan/keypair.h>
+#include <stdio.h>
+
namespace Botan {
/*
@@ -90,18 +92,19 @@ DSA_Signature_Operation::sign(const byte msg[], u32bit msg_len,
{
rng.add_entropy(msg, msg_len);
- BigInt k;
- do
- k.randomize(rng, q.bits());
- while(k >= q);
-
BigInt i(msg, msg_len);
+ BigInt r = 0, s = 0;
- BigInt r = mod_q.reduce(powermod_g_p(k));
- BigInt s = mod_q.multiply(inverse_mod(k, q), mul_add(x, r, i));
+ while(r == 0 || s == 0)
+ {
+ BigInt k;
+ do
+ k.randomize(rng, q.bits());
+ while(k >= q);
- if(r.is_zero() || s.is_zero())
- throw Internal_Error("DSA signature gen failure: r or s was zero");
+ r = mod_q.reduce(powermod_g_p(k));
+ s = mod_q.multiply(inverse_mod(k, q), mul_add(x, r, i));
+ }
SecureVector<byte> output(2*q.bytes());
r.binary_encode(output + (output.size() / 2 - r.bytes()));
diff --git a/src/pubkey/nr/nr.cpp b/src/pubkey/nr/nr.cpp
index cf59615da..f9ba37c41 100644
--- a/src/pubkey/nr/nr.cpp
+++ b/src/pubkey/nr/nr.cpp
@@ -99,20 +99,23 @@ NR_Signature_Operation::sign(const byte msg[], u32bit msg_len,
{
rng.add_entropy(msg, msg_len);
- BigInt k;
- do
- k.randomize(rng, q.bits());
- while(k >= q);
-
BigInt f(msg, msg_len);
if(f >= q)
throw Invalid_Argument("NR_Signature_Operation: Input is out of range");
- BigInt c = mod_q.reduce(powermod_g_p(k) + f);
- if(c.is_zero())
- throw Internal_Error("NR_Signature_Operation: c was zero");
- BigInt d = mod_q.reduce(k - x * c);
+ BigInt c, d;
+
+ while(c == 0)
+ {
+ BigInt k;
+ do
+ k.randomize(rng, q.bits());
+ while(k >= q);
+
+ c = mod_q.reduce(powermod_g_p(k) + f);
+ d = mod_q.reduce(k - x * c);
+ }
SecureVector<byte> output(2*q.bytes());
c.binary_encode(output + (output.size() / 2 - c.bytes()));