From 3bc4fa5822cc0917d131055e286d46d90421e0b0 Mon Sep 17 00:00:00 2001 From: Christopher Jeffrey Date: Wed, 9 Nov 2016 18:24:34 -0800 Subject: [PATCH] schnorr: fix issues mentioned in #89. --- lib/crypto/schnorr.js | 36 ++++++++++++++++++++++++++---------- 1 file changed, 26 insertions(+), 10 deletions(-) diff --git a/lib/crypto/schnorr.js b/lib/crypto/schnorr.js index 8814cc0b..f4c79ded 100644 --- a/lib/crypto/schnorr.js +++ b/lib/crypto/schnorr.js @@ -11,6 +11,7 @@ var elliptic = require('elliptic'); var Signature = require('elliptic/lib/elliptic/ec/signature'); var hmacDRBG = require('elliptic/lib/elliptic/hmac-drbg'); var crypto = require('./crypto'); +var curves = elliptic.curves; var curve = elliptic.ec('secp256k1').curve; var sha256 = require('./crypto').sha256; @@ -76,6 +77,9 @@ schnorr._sign = function _sign(msg, prv, k, hash, pubnonce) { h = schnorr.hash(msg, r.getX(), hash); + if (h.cmpn(0) === 0) + return; + if (h.cmp(curve.n) >= 0) return; @@ -100,7 +104,7 @@ schnorr._sign = function _sign(msg, prv, k, hash, pubnonce) { schnorr.sign = function sign(msg, key, hash, pubnonce) { var prv = new BN(key); - var k, sig; + var k, sig, drbg; if (prv.cmpn(0) === 0) throw new Error('Bad private key.'); @@ -108,8 +112,10 @@ schnorr.sign = function sign(msg, key, hash, pubnonce) { if (prv.cmp(curve.n) >= 0) throw new Error('Bad private key.'); + drbg = schnorr.drbg(msg, key, pubnonce); + while (!sig) { - k = new BN(crypto.randomBytes(32)); + k = new BN(drbg.generate(curve.n.byteLength())); sig = schnorr._sign(msg, prv, k, hash, pubnonce); } @@ -304,16 +310,16 @@ schnorr.partialSign = function partialSign(msg, priv, privnonce, pubs, hash) { schnorr.alg = new Buffer('Schnorr+SHA256 ', 'ascii'); /** - * Perform hmac drbg according to rfc6979. + * Instantiate an HMAC-DRBG. * @param {Buffer} msg * @param {Buffer} priv * @param {Buffer} data - * @returns {Buffer} + * @returns {HmacDRBG} */ -schnorr.rfc6979 = function rfc6979(msg, priv, data) { +schnorr.drbg = function drbg(msg, priv, data) { var kdata = new Buffer(112); - var drbg, prv, pers; + var prv, pers; kdata.fill(0); @@ -329,16 +335,26 @@ schnorr.rfc6979 = function rfc6979(msg, priv, data) { msg = toArray(kdata.slice(32, 64)); pers = toArray(kdata.slice(64)); - drbg = new hmacDRBG({ - hash: require('hash.js').sha256, + return new hmacDRBG({ + hash: curves.secp256k1.hash, entropy: prv, nonce: msg, pers: pers }); +}; - drbg = drbg.generate(curve.n.byteLength()); +/** + * Perform hmac drbg according to rfc6979. + * @param {Buffer} msg + * @param {Buffer} priv + * @param {Buffer} data + * @returns {Buffer} + */ - return new Buffer(drbg); +schnorr.rfc6979 = function rfc6979(msg, priv, data) { + var drbg = schnorr.drbg(msg, priv, data); + var bytes = drbg.generate(curve.n.byteLength()); + return new Buffer(bytes); }; /**