| 'use strict'; |
| |
| var utils = exports; |
| var BN = require('bn.js'); |
| var minAssert = require('minimalistic-assert'); |
| var minUtils = require('minimalistic-crypto-utils'); |
| |
| utils.assert = minAssert; |
| utils.toArray = minUtils.toArray; |
| utils.zero2 = minUtils.zero2; |
| utils.toHex = minUtils.toHex; |
| utils.encode = minUtils.encode; |
| |
| // Represent num in a w-NAF form |
| function getNAF(num, w) { |
| var naf = []; |
| var ws = 1 << (w + 1); |
| var k = num.clone(); |
| while (k.cmpn(1) >= 0) { |
| var z; |
| if (k.isOdd()) { |
| var mod = k.andln(ws - 1); |
| if (mod > (ws >> 1) - 1) |
| z = (ws >> 1) - mod; |
| else |
| z = mod; |
| k.isubn(z); |
| } else { |
| z = 0; |
| } |
| naf.push(z); |
| |
| // Optimization, shift by word if possible |
| var shift = (k.cmpn(0) !== 0 && k.andln(ws - 1) === 0) ? (w + 1) : 1; |
| for (var i = 1; i < shift; i++) |
| naf.push(0); |
| k.iushrn(shift); |
| } |
| |
| return naf; |
| } |
| utils.getNAF = getNAF; |
| |
| // Represent k1, k2 in a Joint Sparse Form |
| function getJSF(k1, k2) { |
| var jsf = [ |
| [], |
| [] |
| ]; |
| |
| k1 = k1.clone(); |
| k2 = k2.clone(); |
| var d1 = 0; |
| var d2 = 0; |
| while (k1.cmpn(-d1) > 0 || k2.cmpn(-d2) > 0) { |
| |
| // First phase |
| var m14 = (k1.andln(3) + d1) & 3; |
| var m24 = (k2.andln(3) + d2) & 3; |
| if (m14 === 3) |
| m14 = -1; |
| if (m24 === 3) |
| m24 = -1; |
| var u1; |
| if ((m14 & 1) === 0) { |
| u1 = 0; |
| } else { |
| var m8 = (k1.andln(7) + d1) & 7; |
| if ((m8 === 3 || m8 === 5) && m24 === 2) |
| u1 = -m14; |
| else |
| u1 = m14; |
| } |
| jsf[0].push(u1); |
| |
| var u2; |
| if ((m24 & 1) === 0) { |
| u2 = 0; |
| } else { |
| var m8 = (k2.andln(7) + d2) & 7; |
| if ((m8 === 3 || m8 === 5) && m14 === 2) |
| u2 = -m24; |
| else |
| u2 = m24; |
| } |
| jsf[1].push(u2); |
| |
| // Second phase |
| if (2 * d1 === u1 + 1) |
| d1 = 1 - d1; |
| if (2 * d2 === u2 + 1) |
| d2 = 1 - d2; |
| k1.iushrn(1); |
| k2.iushrn(1); |
| } |
| |
| return jsf; |
| } |
| utils.getJSF = getJSF; |
| |
| function cachedProperty(obj, name, computer) { |
| var key = '_' + name; |
| obj.prototype[name] = function cachedProperty() { |
| return this[key] !== undefined ? this[key] : |
| this[key] = computer.call(this); |
| }; |
| } |
| utils.cachedProperty = cachedProperty; |
| |
| function parseBytes(bytes) { |
| return typeof bytes === 'string' ? utils.toArray(bytes, 'hex') : |
| bytes; |
| } |
| utils.parseBytes = parseBytes; |
| |
| function intFromLE(bytes) { |
| return new BN(bytes, 'hex', 'le'); |
| } |
| utils.intFromLE = intFromLE; |
| |