]> git.immae.eu Git - perso/Immae/Projets/Cryptomonnaies/BIP39.git/commitdiff
xpub key can be used as bip32 root key
authorIan Coleman <coleman.ian@gmail.com>
Mon, 19 Dec 2016 02:54:51 +0000 (13:54 +1100)
committerIan Coleman <coleman.ian@gmail.com>
Mon, 19 Dec 2016 02:55:21 +0000 (13:55 +1100)
bip39-standalone.html
src/js/index.js
tests.js

index 0f7d7d08a10bf2759a9683bd2623cf69141908d4..367d9a2fdc1d923728b3cf88e45a1c2f18a0f0c6 100644 (file)
@@ -18868,11 +18868,11 @@ window.Entropy = new (function() {
         // Calculate and display
         calcBip32RootKeyFromBase58(rootKeyBase58);
         calcForDerivationPath();
-        hidePending();
     }
 
     function calcForDerivationPath() {
         showPending();
+        clearAddressesList();
         hideValidationError();
         // Get the derivation path
         var derivationPath = getDerivationPath();
@@ -18974,7 +18974,12 @@ window.Entropy = new (function() {
                 continue;
             }
             var hardened = bit[bit.length-1] == "'";
-            if (hardened) {
+            var isPriv = "privKey" in extendedKey;
+            var invalidDerivationPath = hardened && !isPriv;
+            if (invalidDerivationPath) {
+                extendedKey = null;
+            }
+            else if (hardened) {
                 extendedKey = extendedKey.deriveHardened(index);
             }
             else {
@@ -19093,6 +19098,12 @@ window.Entropy = new (function() {
                 }
             }
         }
+        // Check no hardened derivation path when using xpub keys
+        var hardened = path.indexOf("'") > -1;
+        var isXpubkey = !("privKey" in bip32RootKey);
+        if (hardened && isXpubkey) {
+            return "Hardened derivation path is invalid with xpub key";
+        }
         return false;
     }
 
@@ -19119,7 +19130,11 @@ window.Entropy = new (function() {
         DOM.seed.val(seed);
         var rootKey = bip32RootKey.toBase58();
         DOM.rootKey.val(rootKey);
-        var extendedPrivKey = bip32ExtendedKey.toBase58();
+        var xprvkeyB58 = "NA";
+        if (bip32ExtendedKey.privKey) {
+            xprvkeyB58 = bip32ExtendedKey.toBase58();
+        }
+        var extendedPrivKey = xprvkeyB58;
         DOM.extendedPrivKey.val(extendedPrivKey);
         var extendedPubKey = bip32ExtendedKey.toBase58(false);
         DOM.extendedPubKey.val(extendedPubKey);
@@ -19153,7 +19168,10 @@ window.Entropy = new (function() {
                     key = bip32ExtendedKey.derive(index);
                 }
                 var address = key.getAddress().toString();
-                var privkey = key.privKey.toWIF(network);
+                var privkey = "NA";
+                if (key.privKey) {
+                    privkey = key.privKey.toWIF(network);
+                }
                 var pubkey = key.pubKey.toHex();
                 var indexText = getDerivationPath() + "/" + index;
                 if (useHardenedAddresses) {
index cac420ecc398b7d97359ab1abd62e416883051c3..45edea8477b835245c3a03b34183310f226ebbc3 100644 (file)
         // Calculate and display
         calcBip32RootKeyFromBase58(rootKeyBase58);
         calcForDerivationPath();
-        hidePending();
     }
 
     function calcForDerivationPath() {
         showPending();
+        clearAddressesList();
         hideValidationError();
         // Get the derivation path
         var derivationPath = getDerivationPath();
                 continue;
             }
             var hardened = bit[bit.length-1] == "'";
-            if (hardened) {
+            var isPriv = "privKey" in extendedKey;
+            var invalidDerivationPath = hardened && !isPriv;
+            if (invalidDerivationPath) {
+                extendedKey = null;
+            }
+            else if (hardened) {
                 extendedKey = extendedKey.deriveHardened(index);
             }
             else {
                 }
             }
         }
+        // Check no hardened derivation path when using xpub keys
+        var hardened = path.indexOf("'") > -1;
+        var isXpubkey = !("privKey" in bip32RootKey);
+        if (hardened && isXpubkey) {
+            return "Hardened derivation path is invalid with xpub key";
+        }
         return false;
     }
 
         DOM.seed.val(seed);
         var rootKey = bip32RootKey.toBase58();
         DOM.rootKey.val(rootKey);
-        var extendedPrivKey = bip32ExtendedKey.toBase58();
+        var xprvkeyB58 = "NA";
+        if (bip32ExtendedKey.privKey) {
+            xprvkeyB58 = bip32ExtendedKey.toBase58();
+        }
+        var extendedPrivKey = xprvkeyB58;
         DOM.extendedPrivKey.val(extendedPrivKey);
         var extendedPubKey = bip32ExtendedKey.toBase58(false);
         DOM.extendedPubKey.val(extendedPubKey);
                     key = bip32ExtendedKey.derive(index);
                 }
                 var address = key.getAddress().toString();
-                var privkey = key.privKey.toWIF(network);
+                var privkey = "NA";
+                if (key.privKey) {
+                    privkey = key.privKey.toWIF(network);
+                }
                 var pubkey = key.pubKey.toHex();
                 var indexText = getDerivationPath() + "/" + index;
                 if (useHardenedAddresses) {
index d5a73f6cee83cf1939b08ddfea962184b6952e2d..19a371272c705a51c786a8ca10495ae57580c0cc 100644 (file)
--- a/tests.js
+++ b/tests.js
@@ -3138,6 +3138,109 @@ page.open(url, function(status) {
 });
 },
 
+// github issue 40
+// BIP32 root key can be set as an xpub
+function() {
+page.open(url, function(status) {
+    // set the phrase
+    page.evaluate(function() {
+        // set xpub for account 0 of bip44 for 'abandon abandon ability'
+        var bip44AccountXpub = "xpub6CzDCPbtLrrn4VpVbyyQLHbdSMpZoHN4iuW64VswCyEpfjM2mJGdaHJ2DyuZwtst96E16VvcERb8BBeJdHSCVmAq9RhtRQg6eAZFrTKCNqf";
+        $("#root-key").val(bip44AccountXpub);
+        $("#root-key").trigger("input");
+    });
+    waitForFeedback(function() {
+        page.evaluate(function() {
+            // Use bip32 tab
+            $("#bip32-tab a").click();
+        });
+        waitForGenerate(function() {
+            page.evaluate(function() {
+                // derive external addresses for this xpub
+                var firstAccountDerivationPath = "m/0";
+                $("#bip32-path").val(firstAccountDerivationPath);
+                $("#bip32-path").trigger("input");
+            });
+            waitForGenerate(function() {
+                // check the addresses are generated
+                var expected = "1Di3Vp7tBWtyQaDABLAjfWtF6V7hYKJtug";
+                var actual = page.evaluate(function() {
+                    return $(".address:first").text();
+                });
+                if (actual != expected) {
+                    console.log("xpub key does not generate addresses in table");
+                    console.log("Expected: " + expected);
+                    console.log("Actual: " + actual);
+                    fail();
+                }
+                // check the xprv key is not set
+                var expected = "NA";
+                var actual = page.evaluate(function() {
+                    return $(".extended-priv-key").val();
+                });
+                if (actual != expected) {
+                    console.log("xpub key as root shows derived bip32 xprv key");
+                    console.log("Expected: " + expected);
+                    console.log("Actual: " + actual);
+                    fail();
+                }
+                // check the private key is not set
+                var expected = "NA";
+                var actual = page.evaluate(function() {
+                    return $(".privkey:first").text();
+                });
+                if (actual != expected) {
+                    console.log("xpub key generates private key in addresses table");
+                    console.log("Expected: " + expected);
+                    console.log("Actual: " + actual);
+                    fail();
+                }
+                next();
+            });
+        });
+    });
+});
+},
+
+// github issue 40
+// xpub for bip32 root key will not work with hardened derivation paths
+function() {
+page.open(url, function(status) {
+    // set the phrase
+    page.evaluate(function() {
+        // set xpub for account 0 of bip44 for 'abandon abandon ability'
+        var bip44AccountXpub = "xpub6CzDCPbtLrrn4VpVbyyQLHbdSMpZoHN4iuW64VswCyEpfjM2mJGdaHJ2DyuZwtst96E16VvcERb8BBeJdHSCVmAq9RhtRQg6eAZFrTKCNqf";
+        $("#root-key").val(bip44AccountXpub);
+        $("#root-key").trigger("input");
+    });
+    waitForFeedback(function() {
+        // Check feedback is correct
+        var expected = "Hardened derivation path is invalid with xpub key";
+        var actual = page.evaluate(function() {
+            return $(".feedback").text();
+        });
+        if (actual != expected) {
+            console.log("xpub key with hardened derivation path does not show feedback");
+            console.log("Expected: " + expected);
+            console.log("Actual: " + actual);
+            fail();
+        }
+        // Check no addresses are shown
+        var expected = 0;
+        var actual = page.evaluate(function() {
+            return $(".addresses tr").length;
+        });
+        if (actual != expected) {
+            console.log("addresses still show after setting xpub key with hardened derivation path");
+            console.log("Expected: " + expected);
+            console.log("Actual: " + actual);
+            fail();
+        }
+        next();
+    });
+});
+},
+
 
 // If you wish to add more tests, do so here...