aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/index.html56
-rw-r--r--src/js/entropy.js1774
-rw-r--r--src/js/index.js106
3 files changed, 1929 insertions, 7 deletions
diff --git a/src/index.html b/src/index.html
index 3ec4aa9..cb7a781 100644
--- a/src/index.html
+++ b/src/index.html
@@ -65,12 +65,14 @@
65 <div class="col-md-12"> 65 <div class="col-md-12">
66 <h2>Mnemonic</h2> 66 <h2>Mnemonic</h2>
67 <form class="form-horizontal" role="form"> 67 <form class="form-horizontal" role="form">
68 <div class="col-sm-2"></div>
69 <div class="col-sm-10">
70 <p>You can enter an existing BIP39 mnemonic, or generate a new random one. Typing your own twelve words will probably not work how you expect, since the words require a particular structure (the last word is a checksum)</p>
71 <p>For more info see the <a href="https://github.com/bitcoin/bips/blob/master/bip-0039.mediawiki" target="_blank">BIP39 spec</a></p>
72 </div>
73 <div class="form-group"> 68 <div class="form-group">
69 <div class="col-sm-2"></div>
70 <div class="col-sm-10">
71 <p>You can enter an existing BIP39 mnemonic, or generate a new random one. Typing your own twelve words will probably not work how you expect, since the words require a particular structure (the last word is a checksum)</p>
72 <p>For more info see the <a href="https://github.com/bitcoin/bips/blob/master/bip-0039.mediawiki" target="_blank">BIP39 spec</a></p>
73 </div>
74 </div>
75 <div class="form-group generate-container">
74 <label class="col-sm-2 control-label"></label> 76 <label class="col-sm-2 control-label"></label>
75 <div class="col-sm-10"> 77 <div class="col-sm-10">
76 <div class="form-inline"> 78 <div class="form-inline">
@@ -92,7 +94,30 @@
92 </div> 94 </div>
93 </div> 95 </div>
94 </div> 96 </div>
95 <div class="form-group"> 97 <div class="entropy-container hidden">
98 <label for="entropy" class="col-sm-2 control-label">Entropy</label>
99 <div class="col-sm-10">
100 <input id="entropy" class="entropy form-control" placeholder="Accepts binary, base 6, 6-sided dice, base 10, hexadecimal">
101 <span class="help-block">
102 <div class="text-danger">
103 This is an advanced feature.
104 Your mnemonic may be insecure if this feature is used incorrectly.
105 <a href="#entropy-notes">Read more</a>
106 </div>
107 <div class="text-danger entropy-error"></div>
108 </span>
109 </div>
110 </div>
111 <div class="form-group">
112 <div class="col-sm-2"></div>
113 <div class="col-sm-10 checkbox">
114 <label>
115 <input type="checkbox" class="use-entropy">
116 Supply my own source of entropy
117 </label>
118 </div>
119 </div>
120 <div class="form-group">
96 <label class="col-sm-2 control-label"></label> 121 <label class="col-sm-2 control-label"></label>
97 <div class="col-sm-10 languages"> 122 <div class="col-sm-10 languages">
98 <a href="#english">English</a> 123 <a href="#english">English</a>
@@ -353,6 +378,24 @@
353 but be careful - it can be easy to make mistakes if you 378 but be careful - it can be easy to make mistakes if you
354 don't know what you're doing 379 don't know what you're doing
355 </p> 380 </p>
381 <h3 id="entropy-notes">Entropy</h3>
382 <p>
383 Entropy values must be sourced from a
384 <a href="https://en.wikipedia.org/wiki/Random_number_generation" target="_blank">strong source of randomness</a>.
385 This means flipping a fair coin, rolling a fair dice, noise measurements etc. Do <strong>NOT</strong> use
386 phrases from books, lyrics from songs, your birthday or steet address, keyboard mashing, or anything you <i>think</i>
387 is random, because chances are <em>overwhelming</em> that it isn't random enough for the needs of this tool.
388 </p>
389 <p>
390 The random mnemonic generator on this page uses a
391 <a href="https://developer.mozilla.org/en-US/docs/Web/API/RandomSource/getRandomValues" target="_blank">cryptographically secure random number generator</a>,
392 and can generally be trusted more than your own intuition about randomness.
393 If cryptographic randomness isn't available in your browser, this page will show a warning and <i>will not generate
394 random mnemonics</i>.
395 </p>
396 <p>
397 <a href="https://bitcointalk.org/index.php?topic=311000.msg3345309#msg3345309" target="_blank">You are not a good source of entropy.</a>
398 </p>
356 </div> 399 </div>
357 </div> 400 </div>
358 401
@@ -465,6 +508,7 @@
465 <script src="js/wordlist_french.js"></script> 508 <script src="js/wordlist_french.js"></script>
466 <script src="js/wordlist_italian.js"></script> 509 <script src="js/wordlist_italian.js"></script>
467 <script src="js/jsbip39.js"></script> 510 <script src="js/jsbip39.js"></script>
511 <script src="js/entropy.js"></script>
468 <script src="js/index.js"></script> 512 <script src="js/index.js"></script>
469 </body> 513 </body>
470</html> 514</html>
diff --git a/src/js/entropy.js b/src/js/entropy.js
new file mode 100644
index 0000000..1e556ce
--- /dev/null
+++ b/src/js/entropy.js
@@ -0,0 +1,1774 @@
1window.Entropy = new (function() {
2
3 var matchers = {
4 binary: /[0-1]/gi,
5 base6: /[0-5]/gi,
6 dice: /[1-6]/gi, // ie dice numbers
7 base10: /[0-9]/gi,
8 hex: /[0-9A-F]/gi,
9 }
10
11 this.fromString = function(rawEntropyStr) {
12 // Find type of entropy being used (binary, hex, dice etc)
13 var base = getBase(rawEntropyStr);
14 // Convert dice to base6 entropy (ie 1-6 to 0-5)
15 if (base.str == "dice") {
16 var newRawEntropyStr = "";
17 for (var i=0; i<rawEntropyStr.length; i++) {
18 var c = rawEntropyStr[i];
19 if ("123456".indexOf(c) > -1) {
20 newRawEntropyStr += (parseInt(c) - 1).toString();
21 }
22 else {
23 newRawEntropyStr += c
24 }
25 }
26 rawEntropyStr = newRawEntropyStr;
27 base.str = "base 6 (dice)";
28 base.matcher = matchers.base6;
29 }
30 var entropyParts = rawEntropyStr.match(base.matcher) || [];
31 var entropyStr = entropyParts.join("");
32 // Detect empty entropy
33 if (entropyStr.length == 0) {
34 return {
35 binaryStr: "",
36 hexStr: "",
37 cleanStr: "",
38 base: base,
39 };
40 }
41 // Pull leading zeros off
42 var leadingZeros = "";
43 while (entropyStr[0] == "0") {
44 leadingZeros += "0";
45 entropyStr = entropyStr.substring(1);
46 }
47 // Convert leading zeros to binary equivalent
48 var numBinLeadingZeros = Math.ceil(Math.log2(base.asInt) * leadingZeros.length);
49 var binLeadingZeros = "";
50 for (var i=0; i<numBinLeadingZeros; i++) {
51 binLeadingZeros += "0";
52 }
53 // Convert leading zeros to hex equivalent
54 var numHexLeadingZeros = Math.floor(numBinLeadingZeros / 4);
55 var hexLeadingZeros = "";
56 for (var i=0; i<numHexLeadingZeros; i++) {
57 hexLeadingZeros += "0";
58 }
59 // Handle entropy of zero
60 if (entropyStr == "") {
61 return {
62 binaryStr: binLeadingZeros,
63 hexStr: hexLeadingZeros || "0",
64 cleanStr: leadingZeros,
65 base: base,
66 }
67 }
68 // If using hex, should always be multiples of 4 bits, which can get
69 // out of sync if first number has leading 0 bits, eg 2 in hex is 0010
70 // which would show up as 10, thus missing 2 bits it should have.
71 if (base.asInt == 16) {
72 var firstDigit = parseInt(entropyStr[0], 16);
73 if (firstDigit >= 4 && firstDigit < 8) {
74 binLeadingZeros += "0";
75 }
76 else if (firstDigit >= 2 && firstDigit < 4) {
77 binLeadingZeros += "00";
78 }
79 else if (firstDigit >= 1 && firstDigit < 2) {
80 binLeadingZeros += "000";
81 }
82 }
83 // Convert entropy to different foramts
84 var entropyInt = BigInteger.parse(entropyStr, base.asInt);
85 var entropyBin = binLeadingZeros + entropyInt.toString(2);
86 var entropyHex = hexLeadingZeros + entropyInt.toString(16);
87 var entropyClean = leadingZeros + entropyStr;
88 var e = {
89 binaryStr: entropyBin,
90 hexStr: entropyHex,
91 cleanStr: entropyClean,
92 base: base,
93 }
94 return e;
95 }
96
97 function getBase(str) {
98 // Need to get the lowest base for the supplied entropy.
99 // This prevents interpreting, say, dice rolls as hexadecimal.
100 var binaryMatches = str.match(matchers.binary) || [];
101 var base6Matches = str.match(matchers.base6) || [];
102 var diceMatches = str.match(matchers.dice) || [];
103 var base10Matches = str.match(matchers.base10) || [];
104 var hexMatches = str.match(matchers.hex) || [];
105 // Find the lowest base that can be used, whilst ignoring any irrelevant chars
106 if (binaryMatches.length == hexMatches.length) {
107 return {
108 matcher: matchers.binary,
109 asInt: 2,
110 str: "binary",
111 }
112 }
113 if (diceMatches.length == hexMatches.length) {
114 return {
115 matcher: matchers.dice,
116 asInt: 6,
117 str: "dice",
118 }
119 }
120 if (base6Matches.length == hexMatches.length) {
121 return {
122 matcher: matchers.base6,
123 asInt: 6,
124 str: "base 6",
125 }
126 }
127 if (base10Matches.length == hexMatches.length) {
128 return {
129 matcher: matchers.base10,
130 asInt: 10,
131 str: "base 10",
132 }
133 }
134 return {
135 matcher: matchers.hex,
136 asInt: 16,
137 str: "hexadecimal",
138 }
139 }
140
141 // Polyfill for Math.log2
142 // See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/log2#Polyfill
143 Math.log2 = Math.log2 || function(x) {
144 return Math.log(x) * Math.LOG2E;
145 };
146
147})();
148
149
150// BigInteger library included here because
151// only the entropy library depends on it
152// so if entropy detection is removed so is the dependency
153
154
155/*
156 JavaScript BigInteger library version 0.9.1
157 http://silentmatt.com/biginteger/
158
159 Copyright (c) 2009 Matthew Crumley <email@matthewcrumley.com>
160 Copyright (c) 2010,2011 by John Tobey <John.Tobey@gmail.com>
161 Licensed under the MIT license.
162
163 Support for arbitrary internal representation base was added by
164 Vitaly Magerya.
165*/
166
167/*
168 File: biginteger.js
169
170 Exports:
171
172 <BigInteger>
173*/
174(function(exports) {
175"use strict";
176/*
177 Class: BigInteger
178 An arbitrarily-large integer.
179
180 <BigInteger> objects should be considered immutable. None of the "built-in"
181 methods modify *this* or their arguments. All properties should be
182 considered private.
183
184 All the methods of <BigInteger> instances can be called "statically". The
185 static versions are convenient if you don't already have a <BigInteger>
186 object.
187
188 As an example, these calls are equivalent.
189
190 > BigInteger(4).multiply(5); // returns BigInteger(20);
191 > BigInteger.multiply(4, 5); // returns BigInteger(20);
192
193 > var a = 42;
194 > var a = BigInteger.toJSValue("0b101010"); // Not completely useless...
195*/
196
197var CONSTRUCT = {}; // Unique token to call "private" version of constructor
198
199/*
200 Constructor: BigInteger()
201 Convert a value to a <BigInteger>.
202
203 Although <BigInteger()> is the constructor for <BigInteger> objects, it is
204 best not to call it as a constructor. If *n* is a <BigInteger> object, it is
205 simply returned as-is. Otherwise, <BigInteger()> is equivalent to <parse>
206 without a radix argument.
207
208 > var n0 = BigInteger(); // Same as <BigInteger.ZERO>
209 > var n1 = BigInteger("123"); // Create a new <BigInteger> with value 123
210 > var n2 = BigInteger(123); // Create a new <BigInteger> with value 123
211 > var n3 = BigInteger(n2); // Return n2, unchanged
212
213 The constructor form only takes an array and a sign. *n* must be an
214 array of numbers in little-endian order, where each digit is between 0
215 and BigInteger.base. The second parameter sets the sign: -1 for
216 negative, +1 for positive, or 0 for zero. The array is *not copied and
217 may be modified*. If the array contains only zeros, the sign parameter
218 is ignored and is forced to zero.
219
220 > new BigInteger([5], -1): create a new BigInteger with value -5
221
222 Parameters:
223
224 n - Value to convert to a <BigInteger>.
225
226 Returns:
227
228 A <BigInteger> value.
229
230 See Also:
231
232 <parse>, <BigInteger>
233*/
234function BigInteger(n, s, token) {
235 if (token !== CONSTRUCT) {
236 if (n instanceof BigInteger) {
237 return n;
238 }
239 else if (typeof n === "undefined") {
240 return ZERO;
241 }
242 return BigInteger.parse(n);
243 }
244
245 n = n || []; // Provide the nullary constructor for subclasses.
246 while (n.length && !n[n.length - 1]) {
247 --n.length;
248 }
249 this._d = n;
250 this._s = n.length ? (s || 1) : 0;
251}
252
253BigInteger._construct = function(n, s) {
254 return new BigInteger(n, s, CONSTRUCT);
255};
256
257// Base-10 speedup hacks in parse, toString, exp10 and log functions
258// require base to be a power of 10. 10^7 is the largest such power
259// that won't cause a precision loss when digits are multiplied.
260var BigInteger_base = 10000000;
261var BigInteger_base_log10 = 7;
262
263BigInteger.base = BigInteger_base;
264BigInteger.base_log10 = BigInteger_base_log10;
265
266var ZERO = new BigInteger([], 0, CONSTRUCT);
267// Constant: ZERO
268// <BigInteger> 0.
269BigInteger.ZERO = ZERO;
270
271var ONE = new BigInteger([1], 1, CONSTRUCT);
272// Constant: ONE
273// <BigInteger> 1.
274BigInteger.ONE = ONE;
275
276var M_ONE = new BigInteger(ONE._d, -1, CONSTRUCT);
277// Constant: M_ONE
278// <BigInteger> -1.
279BigInteger.M_ONE = M_ONE;
280
281// Constant: _0
282// Shortcut for <ZERO>.
283BigInteger._0 = ZERO;
284
285// Constant: _1
286// Shortcut for <ONE>.
287BigInteger._1 = ONE;
288
289/*
290 Constant: small
291 Array of <BigIntegers> from 0 to 36.
292
293 These are used internally for parsing, but useful when you need a "small"
294 <BigInteger>.
295
296 See Also:
297
298 <ZERO>, <ONE>, <_0>, <_1>
299*/
300BigInteger.small = [
301 ZERO,
302 ONE,
303 /* Assuming BigInteger_base > 36 */
304 new BigInteger( [2], 1, CONSTRUCT),
305 new BigInteger( [3], 1, CONSTRUCT),
306 new BigInteger( [4], 1, CONSTRUCT),
307 new BigInteger( [5], 1, CONSTRUCT),
308 new BigInteger( [6], 1, CONSTRUCT),
309 new BigInteger( [7], 1, CONSTRUCT),
310 new BigInteger( [8], 1, CONSTRUCT),
311 new BigInteger( [9], 1, CONSTRUCT),
312 new BigInteger([10], 1, CONSTRUCT),
313 new BigInteger([11], 1, CONSTRUCT),
314 new BigInteger([12], 1, CONSTRUCT),
315 new BigInteger([13], 1, CONSTRUCT),
316 new BigInteger([14], 1, CONSTRUCT),
317 new BigInteger([15], 1, CONSTRUCT),
318 new BigInteger([16], 1, CONSTRUCT),
319 new BigInteger([17], 1, CONSTRUCT),
320 new BigInteger([18], 1, CONSTRUCT),
321 new BigInteger([19], 1, CONSTRUCT),
322 new BigInteger([20], 1, CONSTRUCT),
323 new BigInteger([21], 1, CONSTRUCT),
324 new BigInteger([22], 1, CONSTRUCT),
325 new BigInteger([23], 1, CONSTRUCT),
326 new BigInteger([24], 1, CONSTRUCT),
327 new BigInteger([25], 1, CONSTRUCT),
328 new BigInteger([26], 1, CONSTRUCT),
329 new BigInteger([27], 1, CONSTRUCT),
330 new BigInteger([28], 1, CONSTRUCT),
331 new BigInteger([29], 1, CONSTRUCT),
332 new BigInteger([30], 1, CONSTRUCT),
333 new BigInteger([31], 1, CONSTRUCT),
334 new BigInteger([32], 1, CONSTRUCT),
335 new BigInteger([33], 1, CONSTRUCT),
336 new BigInteger([34], 1, CONSTRUCT),
337 new BigInteger([35], 1, CONSTRUCT),
338 new BigInteger([36], 1, CONSTRUCT)
339];
340
341// Used for parsing/radix conversion
342BigInteger.digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ".split("");
343
344/*
345 Method: toString
346 Convert a <BigInteger> to a string.
347
348 When *base* is greater than 10, letters are upper case.
349
350 Parameters:
351
352 base - Optional base to represent the number in (default is base 10).
353 Must be between 2 and 36 inclusive, or an Error will be thrown.
354
355 Returns:
356
357 The string representation of the <BigInteger>.
358*/
359BigInteger.prototype.toString = function(base) {
360 base = +base || 10;
361 if (base < 2 || base > 36) {
362 throw new Error("illegal radix " + base + ".");
363 }
364 if (this._s === 0) {
365 return "0";
366 }
367 if (base === 10) {
368 var str = this._s < 0 ? "-" : "";
369 str += this._d[this._d.length - 1].toString();
370 for (var i = this._d.length - 2; i >= 0; i--) {
371 var group = this._d[i].toString();
372 while (group.length < BigInteger_base_log10) group = '0' + group;
373 str += group;
374 }
375 return str;
376 }
377 else {
378 var numerals = BigInteger.digits;
379 base = BigInteger.small[base];
380 var sign = this._s;
381
382 var n = this.abs();
383 var digits = [];
384 var digit;
385
386 while (n._s !== 0) {
387 var divmod = n.divRem(base);
388 n = divmod[0];
389 digit = divmod[1];
390 // TODO: This could be changed to unshift instead of reversing at the end.
391 // Benchmark both to compare speeds.
392 digits.push(numerals[digit.valueOf()]);
393 }
394 return (sign < 0 ? "-" : "") + digits.reverse().join("");
395 }
396};
397
398// Verify strings for parsing
399BigInteger.radixRegex = [
400 /^$/,
401 /^$/,
402 /^[01]*$/,
403 /^[012]*$/,
404 /^[0-3]*$/,
405 /^[0-4]*$/,
406 /^[0-5]*$/,
407 /^[0-6]*$/,
408 /^[0-7]*$/,
409 /^[0-8]*$/,
410 /^[0-9]*$/,
411 /^[0-9aA]*$/,
412 /^[0-9abAB]*$/,
413 /^[0-9abcABC]*$/,
414 /^[0-9a-dA-D]*$/,
415 /^[0-9a-eA-E]*$/,
416 /^[0-9a-fA-F]*$/,
417 /^[0-9a-gA-G]*$/,
418 /^[0-9a-hA-H]*$/,
419 /^[0-9a-iA-I]*$/,
420 /^[0-9a-jA-J]*$/,
421 /^[0-9a-kA-K]*$/,
422 /^[0-9a-lA-L]*$/,
423 /^[0-9a-mA-M]*$/,
424 /^[0-9a-nA-N]*$/,
425 /^[0-9a-oA-O]*$/,
426 /^[0-9a-pA-P]*$/,
427 /^[0-9a-qA-Q]*$/,
428 /^[0-9a-rA-R]*$/,
429 /^[0-9a-sA-S]*$/,
430 /^[0-9a-tA-T]*$/,
431 /^[0-9a-uA-U]*$/,
432 /^[0-9a-vA-V]*$/,
433 /^[0-9a-wA-W]*$/,
434 /^[0-9a-xA-X]*$/,
435 /^[0-9a-yA-Y]*$/,
436 /^[0-9a-zA-Z]*$/
437];
438
439/*
440 Function: parse
441 Parse a string into a <BigInteger>.
442
443 *base* is optional but, if provided, must be from 2 to 36 inclusive. If
444 *base* is not provided, it will be guessed based on the leading characters
445 of *s* as follows:
446
447 - "0x" or "0X": *base* = 16
448 - "0c" or "0C": *base* = 8
449 - "0b" or "0B": *base* = 2
450 - else: *base* = 10
451
452 If no base is provided, or *base* is 10, the number can be in exponential
453 form. For example, these are all valid:
454
455 > BigInteger.parse("1e9"); // Same as "1000000000"
456 > BigInteger.parse("1.234*10^3"); // Same as 1234
457 > BigInteger.parse("56789 * 10 ** -2"); // Same as 567
458
459 If any characters fall outside the range defined by the radix, an exception
460 will be thrown.
461
462 Parameters:
463
464 s - The string to parse.
465 base - Optional radix (default is to guess based on *s*).
466
467 Returns:
468
469 a <BigInteger> instance.
470*/
471BigInteger.parse = function(s, base) {
472 // Expands a number in exponential form to decimal form.
473 // expandExponential("-13.441*10^5") === "1344100";
474 // expandExponential("1.12300e-1") === "0.112300";
475 // expandExponential(1000000000000000000000000000000) === "1000000000000000000000000000000";
476 function expandExponential(str) {
477 str = str.replace(/\s*[*xX]\s*10\s*(\^|\*\*)\s*/, "e");
478
479 return str.replace(/^([+\-])?(\d+)\.?(\d*)[eE]([+\-]?\d+)$/, function(x, s, n, f, c) {
480 c = +c;
481 var l = c < 0;
482 var i = n.length + c;
483 x = (l ? n : f).length;
484 c = ((c = Math.abs(c)) >= x ? c - x + l : 0);
485 var z = (new Array(c + 1)).join("0");
486 var r = n + f;
487 return (s || "") + (l ? r = z + r : r += z).substr(0, i += l ? z.length : 0) + (i < r.length ? "." + r.substr(i) : "");
488 });
489 }
490
491 s = s.toString();
492 if (typeof base === "undefined" || +base === 10) {
493 s = expandExponential(s);
494 }
495
496 var prefixRE;
497 if (typeof base === "undefined") {
498 prefixRE = '0[xcb]';
499 }
500 else if (base == 16) {
501 prefixRE = '0x';
502 }
503 else if (base == 8) {
504 prefixRE = '0c';
505 }
506 else if (base == 2) {
507 prefixRE = '0b';
508 }
509 else {
510 prefixRE = '';
511 }
512 var parts = new RegExp('^([+\\-]?)(' + prefixRE + ')?([0-9a-z]*)(?:\\.\\d*)?$', 'i').exec(s);
513 if (parts) {
514 var sign = parts[1] || "+";
515 var baseSection = parts[2] || "";
516 var digits = parts[3] || "";
517
518 if (typeof base === "undefined") {
519 // Guess base
520 if (baseSection === "0x" || baseSection === "0X") { // Hex
521 base = 16;
522 }
523 else if (baseSection === "0c" || baseSection === "0C") { // Octal
524 base = 8;
525 }
526 else if (baseSection === "0b" || baseSection === "0B") { // Binary
527 base = 2;
528 }
529 else {
530 base = 10;
531 }
532 }
533 else if (base < 2 || base > 36) {
534 throw new Error("Illegal radix " + base + ".");
535 }
536
537 base = +base;
538
539 // Check for digits outside the range
540 if (!(BigInteger.radixRegex[base].test(digits))) {
541 throw new Error("Bad digit for radix " + base);
542 }
543
544 // Strip leading zeros, and convert to array
545 digits = digits.replace(/^0+/, "").split("");
546 if (digits.length === 0) {
547 return ZERO;
548 }
549
550 // Get the sign (we know it's not zero)
551 sign = (sign === "-") ? -1 : 1;
552
553 // Optimize 10
554 if (base == 10) {
555 var d = [];
556 while (digits.length >= BigInteger_base_log10) {
557 d.push(parseInt(digits.splice(digits.length-BigInteger.base_log10, BigInteger.base_log10).join(''), 10));
558 }
559 d.push(parseInt(digits.join(''), 10));
560 return new BigInteger(d, sign, CONSTRUCT);
561 }
562
563 // Do the conversion
564 var d = ZERO;
565 base = BigInteger.small[base];
566 var small = BigInteger.small;
567 for (var i = 0; i < digits.length; i++) {
568 d = d.multiply(base).add(small[parseInt(digits[i], 36)]);
569 }
570 return new BigInteger(d._d, sign, CONSTRUCT);
571 }
572 else {
573 throw new Error("Invalid BigInteger format: " + s);
574 }
575};
576
577/*
578 Function: add
579 Add two <BigIntegers>.
580
581 Parameters:
582
583 n - The number to add to *this*. Will be converted to a <BigInteger>.
584
585 Returns:
586
587 The numbers added together.
588
589 See Also:
590
591 <subtract>, <multiply>, <quotient>, <next>
592*/
593BigInteger.prototype.add = function(n) {
594 if (this._s === 0) {
595 return BigInteger(n);
596 }
597
598 n = BigInteger(n);
599 if (n._s === 0) {
600 return this;
601 }
602 if (this._s !== n._s) {
603 n = n.negate();
604 return this.subtract(n);
605 }
606
607 var a = this._d;
608 var b = n._d;
609 var al = a.length;
610 var bl = b.length;
611 var sum = new Array(Math.max(al, bl) + 1);
612 var size = Math.min(al, bl);
613 var carry = 0;
614 var digit;
615
616 for (var i = 0; i < size; i++) {
617 digit = a[i] + b[i] + carry;
618 sum[i] = digit % BigInteger_base;
619 carry = (digit / BigInteger_base) | 0;
620 }
621 if (bl > al) {
622 a = b;
623 al = bl;
624 }
625 for (i = size; carry && i < al; i++) {
626 digit = a[i] + carry;
627 sum[i] = digit % BigInteger_base;
628 carry = (digit / BigInteger_base) | 0;
629 }
630 if (carry) {
631 sum[i] = carry;
632 }
633
634 for ( ; i < al; i++) {
635 sum[i] = a[i];
636 }
637
638 return new BigInteger(sum, this._s, CONSTRUCT);
639};
640
641/*
642 Function: negate
643 Get the additive inverse of a <BigInteger>.
644
645 Returns:
646
647 A <BigInteger> with the same magnatude, but with the opposite sign.
648
649 See Also:
650
651 <abs>
652*/
653BigInteger.prototype.negate = function() {
654 return new BigInteger(this._d, (-this._s) | 0, CONSTRUCT);
655};
656
657/*
658 Function: abs
659 Get the absolute value of a <BigInteger>.
660
661 Returns:
662
663 A <BigInteger> with the same magnatude, but always positive (or zero).
664
665 See Also:
666
667 <negate>
668*/
669BigInteger.prototype.abs = function() {
670 return (this._s < 0) ? this.negate() : this;
671};
672
673/*
674 Function: subtract
675 Subtract two <BigIntegers>.
676
677 Parameters:
678
679 n - The number to subtract from *this*. Will be converted to a <BigInteger>.
680
681 Returns:
682
683 The *n* subtracted from *this*.
684
685 See Also:
686
687 <add>, <multiply>, <quotient>, <prev>
688*/
689BigInteger.prototype.subtract = function(n) {
690 if (this._s === 0) {
691 return BigInteger(n).negate();
692 }
693
694 n = BigInteger(n);
695 if (n._s === 0) {
696 return this;
697 }
698 if (this._s !== n._s) {
699 n = n.negate();
700 return this.add(n);
701 }
702
703 var m = this;
704 // negative - negative => -|a| - -|b| => -|a| + |b| => |b| - |a|
705 if (this._s < 0) {
706 m = new BigInteger(n._d, 1, CONSTRUCT);
707 n = new BigInteger(this._d, 1, CONSTRUCT);
708 }
709
710 // Both are positive => a - b
711 var sign = m.compareAbs(n);
712 if (sign === 0) {
713 return ZERO;
714 }
715 else if (sign < 0) {
716 // swap m and n
717 var t = n;
718 n = m;
719 m = t;
720 }
721
722 // a > b
723 var a = m._d;
724 var b = n._d;
725 var al = a.length;
726 var bl = b.length;
727 var diff = new Array(al); // al >= bl since a > b
728 var borrow = 0;
729 var i;
730 var digit;
731
732 for (i = 0; i < bl; i++) {
733 digit = a[i] - borrow - b[i];
734 if (digit < 0) {
735 digit += BigInteger_base;
736 borrow = 1;
737 }
738 else {
739 borrow = 0;
740 }
741 diff[i] = digit;
742 }
743 for (i = bl; i < al; i++) {
744 digit = a[i] - borrow;
745 if (digit < 0) {
746 digit += BigInteger_base;
747 }
748 else {
749 diff[i++] = digit;
750 break;
751 }
752 diff[i] = digit;
753 }
754 for ( ; i < al; i++) {
755 diff[i] = a[i];
756 }
757
758 return new BigInteger(diff, sign, CONSTRUCT);
759};
760
761(function() {
762 function addOne(n, sign) {
763 var a = n._d;
764 var sum = a.slice();
765 var carry = true;
766 var i = 0;
767
768 while (true) {
769 var digit = (a[i] || 0) + 1;
770 sum[i] = digit % BigInteger_base;
771 if (digit <= BigInteger_base - 1) {
772 break;
773 }
774 ++i;
775 }
776
777 return new BigInteger(sum, sign, CONSTRUCT);
778 }
779
780 function subtractOne(n, sign) {
781 var a = n._d;
782 var sum = a.slice();
783 var borrow = true;
784 var i = 0;
785
786 while (true) {
787 var digit = (a[i] || 0) - 1;
788 if (digit < 0) {
789 sum[i] = digit + BigInteger_base;
790 }
791 else {
792 sum[i] = digit;
793 break;
794 }
795 ++i;
796 }
797
798 return new BigInteger(sum, sign, CONSTRUCT);
799 }
800
801 /*
802 Function: next
803 Get the next <BigInteger> (add one).
804
805 Returns:
806
807 *this* + 1.
808
809 See Also:
810
811 <add>, <prev>
812 */
813 BigInteger.prototype.next = function() {
814 switch (this._s) {
815 case 0:
816 return ONE;
817 case -1:
818 return subtractOne(this, -1);
819 // case 1:
820 default:
821 return addOne(this, 1);
822 }
823 };
824
825 /*
826 Function: prev
827 Get the previous <BigInteger> (subtract one).
828
829 Returns:
830
831 *this* - 1.
832
833 See Also:
834
835 <next>, <subtract>
836 */
837 BigInteger.prototype.prev = function() {
838 switch (this._s) {
839 case 0:
840 return M_ONE;
841 case -1:
842 return addOne(this, -1);
843 // case 1:
844 default:
845 return subtractOne(this, 1);
846 }
847 };
848})();
849
850/*
851 Function: compareAbs
852 Compare the absolute value of two <BigIntegers>.
853
854 Calling <compareAbs> is faster than calling <abs> twice, then <compare>.
855
856 Parameters:
857
858 n - The number to compare to *this*. Will be converted to a <BigInteger>.
859
860 Returns:
861
862 -1, 0, or +1 if *|this|* is less than, equal to, or greater than *|n|*.
863
864 See Also:
865
866 <compare>, <abs>
867*/
868BigInteger.prototype.compareAbs = function(n) {
869 if (this === n) {
870 return 0;
871 }
872
873 if (!(n instanceof BigInteger)) {
874 if (!isFinite(n)) {
875 return(isNaN(n) ? n : -1);
876 }
877 n = BigInteger(n);
878 }
879
880 if (this._s === 0) {
881 return (n._s !== 0) ? -1 : 0;
882 }
883 if (n._s === 0) {
884 return 1;
885 }
886
887 var l = this._d.length;
888 var nl = n._d.length;
889 if (l < nl) {
890 return -1;
891 }
892 else if (l > nl) {
893 return 1;
894 }
895
896 var a = this._d;
897 var b = n._d;
898 for (var i = l-1; i >= 0; i--) {
899 if (a[i] !== b[i]) {
900 return a[i] < b[i] ? -1 : 1;
901 }
902 }
903
904 return 0;
905};
906
907/*
908 Function: compare
909 Compare two <BigIntegers>.
910
911 Parameters:
912
913 n - The number to compare to *this*. Will be converted to a <BigInteger>.
914
915 Returns:
916
917 -1, 0, or +1 if *this* is less than, equal to, or greater than *n*.
918
919 See Also:
920
921 <compareAbs>, <isPositive>, <isNegative>, <isUnit>
922*/
923BigInteger.prototype.compare = function(n) {
924 if (this === n) {
925 return 0;
926 }
927
928 n = BigInteger(n);
929
930 if (this._s === 0) {
931 return -n._s;
932 }
933
934 if (this._s === n._s) { // both positive or both negative
935 var cmp = this.compareAbs(n);
936 return cmp * this._s;
937 }
938 else {
939 return this._s;
940 }
941};
942
943/*
944 Function: isUnit
945 Return true iff *this* is either 1 or -1.
946
947 Returns:
948
949 true if *this* compares equal to <BigInteger.ONE> or <BigInteger.M_ONE>.
950
951 See Also:
952
953 <isZero>, <isNegative>, <isPositive>, <compareAbs>, <compare>,
954 <BigInteger.ONE>, <BigInteger.M_ONE>
955*/
956BigInteger.prototype.isUnit = function() {
957 return this === ONE ||
958 this === M_ONE ||
959 (this._d.length === 1 && this._d[0] === 1);
960};
961
962/*
963 Function: multiply
964 Multiply two <BigIntegers>.
965
966 Parameters:
967
968 n - The number to multiply *this* by. Will be converted to a
969 <BigInteger>.
970
971 Returns:
972
973 The numbers multiplied together.
974
975 See Also:
976
977 <add>, <subtract>, <quotient>, <square>
978*/
979BigInteger.prototype.multiply = function(n) {
980 // TODO: Consider adding Karatsuba multiplication for large numbers
981 if (this._s === 0) {
982 return ZERO;
983 }
984
985 n = BigInteger(n);
986 if (n._s === 0) {
987 return ZERO;
988 }
989 if (this.isUnit()) {
990 if (this._s < 0) {
991 return n.negate();
992 }
993 return n;
994 }
995 if (n.isUnit()) {
996 if (n._s < 0) {
997 return this.negate();
998 }
999 return this;
1000 }
1001 if (this === n) {
1002 return this.square();
1003 }
1004
1005 var r = (this._d.length >= n._d.length);
1006 var a = (r ? this : n)._d; // a will be longer than b
1007 var b = (r ? n : this)._d;
1008 var al = a.length;
1009 var bl = b.length;
1010
1011 var pl = al + bl;
1012 var partial = new Array(pl);
1013 var i;
1014 for (i = 0; i < pl; i++) {
1015 partial[i] = 0;
1016 }
1017
1018 for (i = 0; i < bl; i++) {
1019 var carry = 0;
1020 var bi = b[i];
1021 var jlimit = al + i;
1022 var digit;
1023 for (var j = i; j < jlimit; j++) {
1024 digit = partial[j] + bi * a[j - i] + carry;
1025 carry = (digit / BigInteger_base) | 0;
1026 partial[j] = (digit % BigInteger_base) | 0;
1027 }
1028 if (carry) {
1029 digit = partial[j] + carry;
1030 carry = (digit / BigInteger_base) | 0;
1031 partial[j] = digit % BigInteger_base;
1032 }
1033 }
1034 return new BigInteger(partial, this._s * n._s, CONSTRUCT);
1035};
1036
1037// Multiply a BigInteger by a single-digit native number
1038// Assumes that this and n are >= 0
1039// This is not really intended to be used outside the library itself
1040BigInteger.prototype.multiplySingleDigit = function(n) {
1041 if (n === 0 || this._s === 0) {
1042 return ZERO;
1043 }
1044 if (n === 1) {
1045 return this;
1046 }
1047
1048 var digit;
1049 if (this._d.length === 1) {
1050 digit = this._d[0] * n;
1051 if (digit >= BigInteger_base) {
1052 return new BigInteger([(digit % BigInteger_base)|0,
1053 (digit / BigInteger_base)|0], 1, CONSTRUCT);
1054 }
1055 return new BigInteger([digit], 1, CONSTRUCT);
1056 }
1057
1058 if (n === 2) {
1059 return this.add(this);
1060 }
1061 if (this.isUnit()) {
1062 return new BigInteger([n], 1, CONSTRUCT);
1063 }
1064
1065 var a = this._d;
1066 var al = a.length;
1067
1068 var pl = al + 1;
1069 var partial = new Array(pl);
1070 for (var i = 0; i < pl; i++) {
1071 partial[i] = 0;
1072 }
1073
1074 var carry = 0;
1075 for (var j = 0; j < al; j++) {
1076 digit = n * a[j] + carry;
1077 carry = (digit / BigInteger_base) | 0;
1078 partial[j] = (digit % BigInteger_base) | 0;
1079 }
1080 if (carry) {
1081 partial[j] = carry;
1082 }
1083
1084 return new BigInteger(partial, 1, CONSTRUCT);
1085};
1086
1087/*
1088 Function: square
1089 Multiply a <BigInteger> by itself.
1090
1091 This is slightly faster than regular multiplication, since it removes the
1092 duplicated multiplcations.
1093
1094 Returns:
1095
1096 > this.multiply(this)
1097
1098 See Also:
1099 <multiply>
1100*/
1101BigInteger.prototype.square = function() {
1102 // Normally, squaring a 10-digit number would take 100 multiplications.
1103 // Of these 10 are unique diagonals, of the remaining 90 (100-10), 45 are repeated.
1104 // This procedure saves (N*(N-1))/2 multiplications, (e.g., 45 of 100 multiplies).
1105 // Based on code by Gary Darby, Intellitech Systems Inc., www.DelphiForFun.org
1106
1107 if (this._s === 0) {
1108 return ZERO;
1109 }
1110 if (this.isUnit()) {
1111 return ONE;
1112 }
1113
1114 var digits = this._d;
1115 var length = digits.length;
1116 var imult1 = new Array(length + length + 1);
1117 var product, carry, k;
1118 var i;
1119
1120 // Calculate diagonal
1121 for (i = 0; i < length; i++) {
1122 k = i * 2;
1123 product = digits[i] * digits[i];
1124 carry = (product / BigInteger_base) | 0;
1125 imult1[k] = product % BigInteger_base;
1126 imult1[k + 1] = carry;
1127 }
1128
1129 // Calculate repeating part
1130 for (i = 0; i < length; i++) {
1131 carry = 0;
1132 k = i * 2 + 1;
1133 for (var j = i + 1; j < length; j++, k++) {
1134 product = digits[j] * digits[i] * 2 + imult1[k] + carry;
1135 carry = (product / BigInteger_base) | 0;
1136 imult1[k] = product % BigInteger_base;
1137 }
1138 k = length + i;
1139 var digit = carry + imult1[k];
1140 carry = (digit / BigInteger_base) | 0;
1141 imult1[k] = digit % BigInteger_base;
1142 imult1[k + 1] += carry;
1143 }
1144
1145 return new BigInteger(imult1, 1, CONSTRUCT);
1146};
1147
1148/*
1149 Function: quotient
1150 Divide two <BigIntegers> and truncate towards zero.
1151
1152 <quotient> throws an exception if *n* is zero.
1153
1154 Parameters:
1155
1156 n - The number to divide *this* by. Will be converted to a <BigInteger>.
1157
1158 Returns:
1159
1160 The *this* / *n*, truncated to an integer.
1161
1162 See Also:
1163
1164 <add>, <subtract>, <multiply>, <divRem>, <remainder>
1165*/
1166BigInteger.prototype.quotient = function(n) {
1167 return this.divRem(n)[0];
1168};
1169
1170/*
1171 Function: divide
1172 Deprecated synonym for <quotient>.
1173*/
1174BigInteger.prototype.divide = BigInteger.prototype.quotient;
1175
1176/*
1177 Function: remainder
1178 Calculate the remainder of two <BigIntegers>.
1179
1180 <remainder> throws an exception if *n* is zero.
1181
1182 Parameters:
1183
1184 n - The remainder after *this* is divided *this* by *n*. Will be
1185 converted to a <BigInteger>.
1186
1187 Returns:
1188
1189 *this* % *n*.
1190
1191 See Also:
1192
1193 <divRem>, <quotient>
1194*/
1195BigInteger.prototype.remainder = function(n) {
1196 return this.divRem(n)[1];
1197};
1198
1199/*
1200 Function: divRem
1201 Calculate the integer quotient and remainder of two <BigIntegers>.
1202
1203 <divRem> throws an exception if *n* is zero.
1204
1205 Parameters:
1206
1207 n - The number to divide *this* by. Will be converted to a <BigInteger>.
1208
1209 Returns:
1210
1211 A two-element array containing the quotient and the remainder.
1212
1213 > a.divRem(b)
1214
1215 is exactly equivalent to
1216
1217 > [a.quotient(b), a.remainder(b)]
1218
1219 except it is faster, because they are calculated at the same time.
1220
1221 See Also:
1222
1223 <quotient>, <remainder>
1224*/
1225BigInteger.prototype.divRem = function(n) {
1226 n = BigInteger(n);
1227 if (n._s === 0) {
1228 throw new Error("Divide by zero");
1229 }
1230 if (this._s === 0) {
1231 return [ZERO, ZERO];
1232 }
1233 if (n._d.length === 1) {
1234 return this.divRemSmall(n._s * n._d[0]);
1235 }
1236
1237 // Test for easy cases -- |n1| <= |n2|
1238 switch (this.compareAbs(n)) {
1239 case 0: // n1 == n2
1240 return [this._s === n._s ? ONE : M_ONE, ZERO];
1241 case -1: // |n1| < |n2|
1242 return [ZERO, this];
1243 }
1244
1245 var sign = this._s * n._s;
1246 var a = n.abs();
1247 var b_digits = this._d;
1248 var b_index = b_digits.length;
1249 var digits = n._d.length;
1250 var quot = [];
1251 var guess;
1252
1253 var part = new BigInteger([], 0, CONSTRUCT);
1254
1255 while (b_index) {
1256 part._d.unshift(b_digits[--b_index]);
1257 part = new BigInteger(part._d, 1, CONSTRUCT);
1258
1259 if (part.compareAbs(n) < 0) {
1260 quot.push(0);
1261 continue;
1262 }
1263 if (part._s === 0) {
1264 guess = 0;
1265 }
1266 else {
1267 var xlen = part._d.length, ylen = a._d.length;
1268 var highx = part._d[xlen-1]*BigInteger_base + part._d[xlen-2];
1269 var highy = a._d[ylen-1]*BigInteger_base + a._d[ylen-2];
1270 if (part._d.length > a._d.length) {
1271 // The length of part._d can either match a._d length,
1272 // or exceed it by one.
1273 highx = (highx+1)*BigInteger_base;
1274 }
1275 guess = Math.ceil(highx/highy);
1276 }
1277 do {
1278 var check = a.multiplySingleDigit(guess);
1279 if (check.compareAbs(part) <= 0) {
1280 break;
1281 }
1282 guess--;
1283 } while (guess);
1284
1285 quot.push(guess);
1286 if (!guess) {
1287 continue;
1288 }
1289 var diff = part.subtract(check);
1290 part._d = diff._d.slice();
1291 }
1292
1293 return [new BigInteger(quot.reverse(), sign, CONSTRUCT),
1294 new BigInteger(part._d, this._s, CONSTRUCT)];
1295};
1296
1297// Throws an exception if n is outside of (-BigInteger.base, -1] or
1298// [1, BigInteger.base). It's not necessary to call this, since the
1299// other division functions will call it if they are able to.
1300BigInteger.prototype.divRemSmall = function(n) {
1301 var r;
1302 n = +n;
1303 if (n === 0) {
1304 throw new Error("Divide by zero");
1305 }
1306
1307 var n_s = n < 0 ? -1 : 1;
1308 var sign = this._s * n_s;
1309 n = Math.abs(n);
1310
1311 if (n < 1 || n >= BigInteger_base) {
1312 throw new Error("Argument out of range");
1313 }
1314
1315 if (this._s === 0) {
1316 return [ZERO, ZERO];
1317 }
1318
1319 if (n === 1 || n === -1) {
1320 return [(sign === 1) ? this.abs() : new BigInteger(this._d, sign, CONSTRUCT), ZERO];
1321 }
1322
1323 // 2 <= n < BigInteger_base
1324
1325 // divide a single digit by a single digit
1326 if (this._d.length === 1) {
1327 var q = new BigInteger([(this._d[0] / n) | 0], 1, CONSTRUCT);
1328 r = new BigInteger([(this._d[0] % n) | 0], 1, CONSTRUCT);
1329 if (sign < 0) {
1330 q = q.negate();
1331 }
1332 if (this._s < 0) {
1333 r = r.negate();
1334 }
1335 return [q, r];
1336 }
1337
1338 var digits = this._d.slice();
1339 var quot = new Array(digits.length);
1340 var part = 0;
1341 var diff = 0;
1342 var i = 0;
1343 var guess;
1344
1345 while (digits.length) {
1346 part = part * BigInteger_base + digits[digits.length - 1];
1347 if (part < n) {
1348 quot[i++] = 0;
1349 digits.pop();
1350 diff = BigInteger_base * diff + part;
1351 continue;
1352 }
1353 if (part === 0) {
1354 guess = 0;
1355 }
1356 else {
1357 guess = (part / n) | 0;
1358 }
1359
1360 var check = n * guess;
1361 diff = part - check;
1362 quot[i++] = guess;
1363 if (!guess) {
1364 digits.pop();
1365 continue;
1366 }
1367
1368 digits.pop();
1369 part = diff;
1370 }
1371
1372 r = new BigInteger([diff], 1, CONSTRUCT);
1373 if (this._s < 0) {
1374 r = r.negate();
1375 }
1376 return [new BigInteger(quot.reverse(), sign, CONSTRUCT), r];
1377};
1378
1379/*
1380 Function: isEven
1381 Return true iff *this* is divisible by two.
1382
1383 Note that <BigInteger.ZERO> is even.
1384
1385 Returns:
1386
1387 true if *this* is even, false otherwise.
1388
1389 See Also:
1390
1391 <isOdd>
1392*/
1393BigInteger.prototype.isEven = function() {
1394 var digits = this._d;
1395 return this._s === 0 || digits.length === 0 || (digits[0] % 2) === 0;
1396};
1397
1398/*
1399 Function: isOdd
1400 Return true iff *this* is not divisible by two.
1401
1402 Returns:
1403
1404 true if *this* is odd, false otherwise.
1405
1406 See Also:
1407
1408 <isEven>
1409*/
1410BigInteger.prototype.isOdd = function() {
1411 return !this.isEven();
1412};
1413
1414/*
1415 Function: sign
1416 Get the sign of a <BigInteger>.
1417
1418 Returns:
1419
1420 * -1 if *this* < 0
1421 * 0 if *this* == 0
1422 * +1 if *this* > 0
1423
1424 See Also:
1425
1426 <isZero>, <isPositive>, <isNegative>, <compare>, <BigInteger.ZERO>
1427*/
1428BigInteger.prototype.sign = function() {
1429 return this._s;
1430};
1431
1432/*
1433 Function: isPositive
1434 Return true iff *this* > 0.
1435
1436 Returns:
1437
1438 true if *this*.compare(<BigInteger.ZERO>) == 1.
1439
1440 See Also:
1441
1442 <sign>, <isZero>, <isNegative>, <isUnit>, <compare>, <BigInteger.ZERO>
1443*/
1444BigInteger.prototype.isPositive = function() {
1445 return this._s > 0;
1446};
1447
1448/*
1449 Function: isNegative
1450 Return true iff *this* < 0.
1451
1452 Returns:
1453
1454 true if *this*.compare(<BigInteger.ZERO>) == -1.
1455
1456 See Also:
1457
1458 <sign>, <isPositive>, <isZero>, <isUnit>, <compare>, <BigInteger.ZERO>
1459*/
1460BigInteger.prototype.isNegative = function() {
1461 return this._s < 0;
1462};
1463
1464/*
1465 Function: isZero
1466 Return true iff *this* == 0.
1467
1468 Returns:
1469
1470 true if *this*.compare(<BigInteger.ZERO>) == 0.
1471
1472 See Also:
1473
1474 <sign>, <isPositive>, <isNegative>, <isUnit>, <BigInteger.ZERO>
1475*/
1476BigInteger.prototype.isZero = function() {
1477 return this._s === 0;
1478};
1479
1480/*
1481 Function: exp10
1482 Multiply a <BigInteger> by a power of 10.
1483
1484 This is equivalent to, but faster than
1485
1486 > if (n >= 0) {
1487 > return this.multiply(BigInteger("1e" + n));
1488 > }
1489 > else { // n <= 0
1490 > return this.quotient(BigInteger("1e" + -n));
1491 > }
1492
1493 Parameters:
1494
1495 n - The power of 10 to multiply *this* by. *n* is converted to a
1496 javascipt number and must be no greater than <BigInteger.MAX_EXP>
1497 (0x7FFFFFFF), or an exception will be thrown.
1498
1499 Returns:
1500
1501 *this* * (10 ** *n*), truncated to an integer if necessary.
1502
1503 See Also:
1504
1505 <pow>, <multiply>
1506*/
1507BigInteger.prototype.exp10 = function(n) {
1508 n = +n;
1509 if (n === 0) {
1510 return this;
1511 }
1512 if (Math.abs(n) > Number(MAX_EXP)) {
1513 throw new Error("exponent too large in BigInteger.exp10");
1514 }
1515 // Optimization for this == 0. This also keeps us from having to trim zeros in the positive n case
1516 if (this._s === 0) {
1517 return ZERO;
1518 }
1519 if (n > 0) {
1520 var k = new BigInteger(this._d.slice(), this._s, CONSTRUCT);
1521
1522 for (; n >= BigInteger_base_log10; n -= BigInteger_base_log10) {
1523 k._d.unshift(0);
1524 }
1525 if (n == 0)
1526 return k;
1527 k._s = 1;
1528 k = k.multiplySingleDigit(Math.pow(10, n));
1529 return (this._s < 0 ? k.negate() : k);
1530 } else if (-n >= this._d.length*BigInteger_base_log10) {
1531 return ZERO;
1532 } else {
1533 var k = new BigInteger(this._d.slice(), this._s, CONSTRUCT);
1534
1535 for (n = -n; n >= BigInteger_base_log10; n -= BigInteger_base_log10) {
1536 k._d.shift();
1537 }
1538 return (n == 0) ? k : k.divRemSmall(Math.pow(10, n))[0];
1539 }
1540};
1541
1542/*
1543 Function: pow
1544 Raise a <BigInteger> to a power.
1545
1546 In this implementation, 0**0 is 1.
1547
1548 Parameters:
1549
1550 n - The exponent to raise *this* by. *n* must be no greater than
1551 <BigInteger.MAX_EXP> (0x7FFFFFFF), or an exception will be thrown.
1552
1553 Returns:
1554
1555 *this* raised to the *nth* power.
1556
1557 See Also:
1558
1559 <modPow>
1560*/
1561BigInteger.prototype.pow = function(n) {
1562 if (this.isUnit()) {
1563 if (this._s > 0) {
1564 return this;
1565 }
1566 else {
1567 return BigInteger(n).isOdd() ? this : this.negate();
1568 }
1569 }
1570
1571 n = BigInteger(n);
1572 if (n._s === 0) {
1573 return ONE;
1574 }
1575 else if (n._s < 0) {
1576 if (this._s === 0) {
1577 throw new Error("Divide by zero");
1578 }
1579 else {
1580 return ZERO;
1581 }
1582 }
1583 if (this._s === 0) {
1584 return ZERO;
1585 }
1586 if (n.isUnit()) {
1587 return this;
1588 }
1589
1590 if (n.compareAbs(MAX_EXP) > 0) {
1591 throw new Error("exponent too large in BigInteger.pow");
1592 }
1593 var x = this;
1594 var aux = ONE;
1595 var two = BigInteger.small[2];
1596
1597 while (n.isPositive()) {
1598 if (n.isOdd()) {
1599 aux = aux.multiply(x);
1600 if (n.isUnit()) {
1601 return aux;
1602 }
1603 }
1604 x = x.square();
1605 n = n.quotient(two);
1606 }
1607
1608 return aux;
1609};
1610
1611/*
1612 Function: modPow
1613 Raise a <BigInteger> to a power (mod m).
1614
1615 Because it is reduced by a modulus, <modPow> is not limited by
1616 <BigInteger.MAX_EXP> like <pow>.
1617
1618 Parameters:
1619
1620 exponent - The exponent to raise *this* by. Must be positive.
1621 modulus - The modulus.
1622
1623 Returns:
1624
1625 *this* ^ *exponent* (mod *modulus*).
1626
1627 See Also:
1628
1629 <pow>, <mod>
1630*/
1631BigInteger.prototype.modPow = function(exponent, modulus) {
1632 var result = ONE;
1633 var base = this;
1634
1635 while (exponent.isPositive()) {
1636 if (exponent.isOdd()) {
1637 result = result.multiply(base).remainder(modulus);
1638 }
1639
1640 exponent = exponent.quotient(BigInteger.small[2]);
1641 if (exponent.isPositive()) {
1642 base = base.square().remainder(modulus);
1643 }
1644 }
1645
1646 return result;
1647};
1648
1649/*
1650 Function: log
1651 Get the natural logarithm of a <BigInteger> as a native JavaScript number.
1652
1653 This is equivalent to
1654
1655 > Math.log(this.toJSValue())
1656
1657 but handles values outside of the native number range.
1658
1659 Returns:
1660
1661 log( *this* )
1662
1663 See Also:
1664
1665 <toJSValue>
1666*/
1667BigInteger.prototype.log = function() {
1668 switch (this._s) {
1669 case 0: return -Infinity;
1670 case -1: return NaN;
1671 default: // Fall through.
1672 }
1673
1674 var l = this._d.length;
1675
1676 if (l*BigInteger_base_log10 < 30) {
1677 return Math.log(this.valueOf());
1678 }
1679
1680 var N = Math.ceil(30/BigInteger_base_log10);
1681 var firstNdigits = this._d.slice(l - N);
1682 return Math.log((new BigInteger(firstNdigits, 1, CONSTRUCT)).valueOf()) + (l - N) * Math.log(BigInteger_base);
1683};
1684
1685/*
1686 Function: valueOf
1687 Convert a <BigInteger> to a native JavaScript integer.
1688
1689 This is called automatically by JavaScipt to convert a <BigInteger> to a
1690 native value.
1691
1692 Returns:
1693
1694 > parseInt(this.toString(), 10)
1695
1696 See Also:
1697
1698 <toString>, <toJSValue>
1699*/
1700BigInteger.prototype.valueOf = function() {
1701 return parseInt(this.toString(), 10);
1702};
1703
1704/*
1705 Function: toJSValue
1706 Convert a <BigInteger> to a native JavaScript integer.
1707
1708 This is the same as valueOf, but more explicitly named.
1709
1710 Returns:
1711
1712 > parseInt(this.toString(), 10)
1713
1714 See Also:
1715
1716 <toString>, <valueOf>
1717*/
1718BigInteger.prototype.toJSValue = function() {
1719 return parseInt(this.toString(), 10);
1720};
1721
1722var MAX_EXP = BigInteger(0x7FFFFFFF);
1723// Constant: MAX_EXP
1724// The largest exponent allowed in <pow> and <exp10> (0x7FFFFFFF or 2147483647).
1725BigInteger.MAX_EXP = MAX_EXP;
1726
1727(function() {
1728 function makeUnary(fn) {
1729 return function(a) {
1730 return fn.call(BigInteger(a));
1731 };
1732 }
1733
1734 function makeBinary(fn) {
1735 return function(a, b) {
1736 return fn.call(BigInteger(a), BigInteger(b));
1737 };
1738 }
1739
1740 function makeTrinary(fn) {
1741 return function(a, b, c) {
1742 return fn.call(BigInteger(a), BigInteger(b), BigInteger(c));
1743 };
1744 }
1745
1746 (function() {
1747 var i, fn;
1748 var unary = "toJSValue,isEven,isOdd,sign,isZero,isNegative,abs,isUnit,square,negate,isPositive,toString,next,prev,log".split(",");
1749 var binary = "compare,remainder,divRem,subtract,add,quotient,divide,multiply,pow,compareAbs".split(",");
1750 var trinary = ["modPow"];
1751
1752 for (i = 0; i < unary.length; i++) {
1753 fn = unary[i];
1754 BigInteger[fn] = makeUnary(BigInteger.prototype[fn]);
1755 }
1756
1757 for (i = 0; i < binary.length; i++) {
1758 fn = binary[i];
1759 BigInteger[fn] = makeBinary(BigInteger.prototype[fn]);
1760 }
1761
1762 for (i = 0; i < trinary.length; i++) {
1763 fn = trinary[i];
1764 BigInteger[fn] = makeTrinary(BigInteger.prototype[fn]);
1765 }
1766
1767 BigInteger.exp10 = function(x, n) {
1768 return BigInteger(x).exp10(n);
1769 };
1770 })();
1771})();
1772
1773exports.BigInteger = BigInteger;
1774})(typeof exports !== 'undefined' ? exports : this);
diff --git a/src/js/index.js b/src/js/index.js
index 0e4cc05..cd7f281 100644
--- a/src/js/index.js
+++ b/src/js/index.js
@@ -14,14 +14,20 @@
14 var showPubKey = true; 14 var showPubKey = true;
15 var showPrivKey = true; 15 var showPrivKey = true;
16 16
17 var entropyChangeTimeoutEvent = null;
17 var phraseChangeTimeoutEvent = null; 18 var phraseChangeTimeoutEvent = null;
18 var rootKeyChangedTimeoutEvent = null; 19 var rootKeyChangedTimeoutEvent = null;
19 20
20 var DOM = {}; 21 var DOM = {};
21 DOM.network = $(".network"); 22 DOM.network = $(".network");
22 DOM.phraseNetwork = $("#network-phrase"); 23 DOM.phraseNetwork = $("#network-phrase");
24 DOM.useEntropy = $(".use-entropy");
25 DOM.entropyContainer = $(".entropy-container");
26 DOM.entropy = $(".entropy");
27 DOM.entropyError = $(".entropy-error");
23 DOM.phrase = $(".phrase"); 28 DOM.phrase = $(".phrase");
24 DOM.passphrase = $(".passphrase"); 29 DOM.passphrase = $(".passphrase");
30 DOM.generateContainer = $(".generate-container");
25 DOM.generate = $(".generate"); 31 DOM.generate = $(".generate");
26 DOM.seed = $(".seed"); 32 DOM.seed = $(".seed");
27 DOM.rootKey = $(".root-key"); 33 DOM.rootKey = $(".root-key");
@@ -53,6 +59,8 @@
53 function init() { 59 function init() {
54 // Events 60 // Events
55 DOM.network.on("change", networkChanged); 61 DOM.network.on("change", networkChanged);
62 DOM.useEntropy.on("change", setEntropyVisibility);
63 DOM.entropy.on("input", delayedEntropyChanged);
56 DOM.phrase.on("input", delayedPhraseChanged); 64 DOM.phrase.on("input", delayedPhraseChanged);
57 DOM.passphrase.on("input", delayedPhraseChanged); 65 DOM.passphrase.on("input", delayedPhraseChanged);
58 DOM.generate.on("click", generateClicked); 66 DOM.generate.on("click", generateClicked);
@@ -89,6 +97,21 @@
89 } 97 }
90 } 98 }
91 99
100 function setEntropyVisibility() {
101 if (isUsingOwnEntropy()) {
102 DOM.entropyContainer.removeClass("hidden");
103 DOM.generateContainer.addClass("hidden");
104 DOM.phrase.prop("readonly", true);
105 DOM.entropy.focus();
106 entropyChanged();
107 }
108 else {
109 DOM.entropyContainer.addClass("hidden");
110 DOM.generateContainer.removeClass("hidden");
111 DOM.phrase.prop("readonly", false);
112 }
113 }
114
92 function delayedPhraseChanged() { 115 function delayedPhraseChanged() {
93 hideValidationError(); 116 hideValidationError();
94 showPending(); 117 showPending();
@@ -116,6 +139,20 @@
116 hidePending(); 139 hidePending();
117 } 140 }
118 141
142 function delayedEntropyChanged() {
143 hideValidationError();
144 showPending();
145 if (entropyChangeTimeoutEvent != null) {
146 clearTimeout(entropyChangeTimeoutEvent);
147 }
148 entropyChangeTimeoutEvent = setTimeout(entropyChanged, 400);
149 }
150
151 function entropyChanged() {
152 setMnemonicFromEntropy();
153 phraseChanged();
154 }
155
119 function delayedRootKeyChanged() { 156 function delayedRootKeyChanged() {
120 // Warn if there is an existing mnemonic or passphrase. 157 // Warn if there is an existing mnemonic or passphrase.
121 if (DOM.phrase.val().length > 0 || DOM.passphrase.val().length > 0) { 158 if (DOM.phrase.val().length > 0 || DOM.passphrase.val().length > 0) {
@@ -168,6 +205,9 @@
168 } 205 }
169 206
170 function generateClicked() { 207 function generateClicked() {
208 if (isUsingOwnEntropy()) {
209 return;
210 }
171 clearDisplay(); 211 clearDisplay();
172 showPending(); 212 showPending();
173 setTimeout(function() { 213 setTimeout(function() {
@@ -599,7 +639,12 @@
599 } 639 }
600 640
601 function getLanguageFromUrl() { 641 function getLanguageFromUrl() {
602 return window.location.hash.substring(1); 642 for (var language in WORDLISTS) {
643 if (window.location.hash.indexOf(language) > -1) {
644 return language;
645 }
646 }
647 return "";
603 } 648 }
604 649
605 function setMnemonicLanguage() { 650 function setMnemonicLanguage() {
@@ -650,6 +695,65 @@
650 return phrase; 695 return phrase;
651 } 696 }
652 697
698 function isUsingOwnEntropy() {
699 return DOM.useEntropy.prop("checked");
700 }
701
702 function setMnemonicFromEntropy() {
703 hideEntropyError();
704 // Work out minimum base for entropy
705 var entropyStr = DOM.entropy.val();
706 var entropy = Entropy.fromString(entropyStr);
707 if (entropy.hexStr.length == 0) {
708 return;
709 }
710 // Show entropy details
711 var extraBits = 32 - (entropy.binaryStr.length % 32);
712 var extraChars = Math.ceil(extraBits * Math.log(2) / Math.log(entropy.base.asInt));
713 var strength = "an extremely weak";
714 if (entropy.hexStr.length >= 8) {
715 strength = "a very weak";
716 }
717 if (entropy.hexStr.length >= 12) {
718 strength = "a weak";
719 }
720 if (entropy.hexStr.length >= 24) {
721 strength = "a strong";
722 }
723 if (entropy.hexStr.length >= 32) {
724 strength = "a very strong";
725 }
726 if (entropy.hexStr.length >= 40) {
727 strength = "an extremely strong";
728 }
729 if (entropy.hexStr.length >=48) {
730 strength = "an even stronger"
731 }
732 var msg = "Have " + entropy.binaryStr.length + " bits of entropy, " + extraChars + " more " + entropy.base.str + " chars required to generate " + strength + " mnemonic: " + entropy.cleanStr;
733 showEntropyError(msg);
734 // Discard trailing entropy
735 var hexStr = entropy.hexStr.substring(0, Math.floor(entropy.hexStr.length / 8) * 8);
736 // Convert entropy string to numeric array
737 var entropyArr = [];
738 for (var i=0; i<hexStr.length / 2; i++) {
739 var entropyByte = parseInt(hexStr[i*2].concat(hexStr[i*2+1]), 16);
740 entropyArr.push(entropyByte)
741 }
742 // Convert entropy array to mnemonic
743 var phrase = mnemonic.toMnemonic(entropyArr);
744 // Set the mnemonic in the UI
745 DOM.phrase.val(phrase);
746 }
747
748 function hideEntropyError() {
749 DOM.entropyError.addClass("hidden");
750 }
751
752 function showEntropyError(msg) {
753 DOM.entropyError.text(msg);
754 DOM.entropyError.removeClass("hidden");
755 }
756
653 var networks = [ 757 var networks = [
654 { 758 {
655 name: "Bitcoin", 759 name: "Bitcoin",