Search in sources :

Example 1 with KeyDerivation

use of com.sparrowwallet.drongo.KeyDerivation in project drongo by sparrowwallet.

the class PSBT method parseGlobalEntries.

private void parseGlobalEntries(List<PSBTEntry> globalEntries) throws PSBTParseException {
    PSBTEntry duplicate = findDuplicateKey(globalEntries);
    if (duplicate != null) {
        throw new PSBTParseException("Found duplicate key for PSBT global: " + Utils.bytesToHex(duplicate.getKey()));
    }
    for (PSBTEntry entry : globalEntries) {
        switch(entry.getKeyType()) {
            case PSBT_GLOBAL_UNSIGNED_TX:
                entry.checkOneByteKey();
                Transaction transaction = new Transaction(entry.getData());
                transaction.verify();
                inputs = transaction.getInputs().size();
                outputs = transaction.getOutputs().size();
                log.debug("Transaction with txid: " + transaction.getTxId() + " version " + transaction.getVersion() + " size " + transaction.getMessageSize() + " locktime " + transaction.getLocktime());
                for (TransactionInput input : transaction.getInputs()) {
                    if (input.getScriptSig().getProgram().length != 0) {
                        throw new PSBTParseException("Unsigned tx input does not have empty scriptSig");
                    }
                    log.debug(" Transaction input references txid: " + input.getOutpoint().getHash() + " vout " + input.getOutpoint().getIndex() + " with script " + input.getScriptSig());
                }
                for (TransactionOutput output : transaction.getOutputs()) {
                    try {
                        log.debug(" Transaction output value: " + output.getValue() + " to addresses " + Arrays.asList(output.getScript().getToAddresses()) + " with script hex " + Utils.bytesToHex(output.getScript().getProgram()) + " to script " + output.getScript());
                    } catch (NonStandardScriptException e) {
                        log.debug(" Transaction output value: " + output.getValue() + " with script hex " + Utils.bytesToHex(output.getScript().getProgram()) + " to script " + output.getScript());
                    }
                }
                this.transaction = transaction;
                break;
            case PSBT_GLOBAL_BIP32_PUBKEY:
                entry.checkOneBytePlusXpubKey();
                KeyDerivation keyDerivation = parseKeyDerivation(entry.getData());
                ExtendedKey pubKey = ExtendedKey.fromDescriptor(Base58.encodeChecked(entry.getKeyData()));
                this.extendedPublicKeys.put(pubKey, keyDerivation);
                log.debug("Pubkey with master fingerprint " + keyDerivation.getMasterFingerprint() + " at path " + keyDerivation.getDerivationPath() + ": " + pubKey.getExtendedKey());
                break;
            case PSBT_GLOBAL_VERSION:
                entry.checkOneByteKey();
                int version = (int) Utils.readUint32(entry.getData(), 0);
                this.version = version;
                log.debug("PSBT version: " + version);
                break;
            case PSBT_GLOBAL_PROPRIETARY:
                globalProprietary.put(Utils.bytesToHex(entry.getKeyData()), Utils.bytesToHex(entry.getData()));
                log.debug("PSBT global proprietary data: " + Utils.bytesToHex(entry.getData()));
                break;
            default:
                log.warn("PSBT global not recognized key type: " + entry.getKeyType());
        }
    }
}
Also used : KeyDerivation(com.sparrowwallet.drongo.KeyDerivation) PSBTEntry(com.sparrowwallet.drongo.psbt.PSBTEntry) ExtendedKey(com.sparrowwallet.drongo.ExtendedKey)

Example 2 with KeyDerivation

use of com.sparrowwallet.drongo.KeyDerivation in project drongo by sparrowwallet.

the class PSBTTest method creatorBip.

@Test
public void creatorBip() throws PSBTParseException {
    Transaction transaction = new Transaction();
    transaction.setVersion(2);
    transaction.addOutput(149990000L, new Script(Utils.hexToBytes("0014d85c2b71d0060b09c9886aeb815e50991dda124d")));
    transaction.addOutput(100000000L, new Script(Utils.hexToBytes("001400aea9a2e5f0f876a588df5546e8742d1d87008f")));
    transaction.addInput(Sha256Hash.wrap("75ddabb27b8845f5247975c8a5ba7c6f336c4570708ebe230caf6db5217ae858"), 0, new Script(new byte[0]));
    transaction.addInput(Sha256Hash.wrap("1dea7cd05979072a3578cab271c02244ea8a090bbb46aa680a65ecd027048d83"), 1, new Script(new byte[0]));
    PSBT psbt = new PSBT(transaction);
    Assert.assertEquals("70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f000000000000000000", psbt.toString());
    psbt.getPsbtInputs().get(0).setRedeemScript(new Script(Utils.hexToBytes("5221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae")));
    psbt.getPsbtInputs().get(1).setRedeemScript(new Script(Utils.hexToBytes("00208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903")));
    psbt.getPsbtInputs().get(1).setWitnessScript(new Script(Utils.hexToBytes("522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae")));
    Transaction utxo1 = new Transaction(Utils.hexToBytes("0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000"));
    psbt.getPsbtInputs().get(0).setNonWitnessUtxo(utxo1);
    Transaction utxo2 = new Transaction(Utils.hexToBytes("0200000000010158e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd7501000000171600145f275f436b09a8cc9a2eb2a2f528485c68a56323feffffff02d8231f1b0100000017a914aed962d6654f9a2b36608eb9d64d2b260db4f1118700c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e88702483045022100a22edcc6e5bc511af4cc4ae0de0fcd75c7e04d8c1c3a8aa9d820ed4b967384ec02200642963597b9b1bc22c75e9f3e117284a962188bf5e8a74c895089046a20ad770121035509a48eb623e10aace8bfd0212fdb8a8e5af3c94b0b133b95e114cab89e4f7965000000"));
    psbt.getPsbtInputs().get(1).setWitnessUtxo(utxo2.getOutputs().get(1));
    psbt.getPsbtInputs().get(0).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f")), new KeyDerivation("d90c6a4f", "m/0'/0'/0'"));
    psbt.getPsbtInputs().get(0).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("02dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d7")), new KeyDerivation("d90c6a4f", "m/0'/0'/1'"));
    psbt.getPsbtInputs().get(1).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e73")), new KeyDerivation("d90c6a4f", "m/0'/0'/3'"));
    psbt.getPsbtInputs().get(1).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("03089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc")), new KeyDerivation("d90c6a4f", "m/0'/0'/2'"));
    psbt.getPsbtOutputs().get(0).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("03a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca58771")), new KeyDerivation("d90c6a4f", "m/0'/0'/4'"));
    psbt.getPsbtOutputs().get(1).getDerivedPublicKeys().put(ECKey.fromPublicOnly(Utils.hexToBytes("027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b50051096")), new KeyDerivation("d90c6a4f", "m/0'/0'/5'"));
    Assert.assertEquals("70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f6187650000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e88701042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000", psbt.toString());
    for (PSBTInput psbtInput : psbt.getPsbtInputs()) {
        psbtInput.setSigHash(SigHash.ALL);
    }
    Assert.assertEquals("70736274ff01009a020000000258e87a21b56daf0c23be8e7070456c336f7cbaa5c8757924f545887bb2abdd750000000000ffffffff838d0427d0ec650a68aa46bb0b098aea4422c071b2ca78352a077959d07cea1d0100000000ffffffff0270aaf00800000000160014d85c2b71d0060b09c9886aeb815e50991dda124d00e1f5050000000016001400aea9a2e5f0f876a588df5546e8742d1d87008f00000000000100bb0200000001aad73931018bd25f84ae400b68848be09db706eac2ac18298babee71ab656f8b0000000048473044022058f6fc7c6a33e1b31548d481c826c015bd30135aad42cd67790dab66d2ad243b02204a1ced2604c6735b6393e5b41691dd78b00f0c5942fb9f751856faa938157dba01feffffff0280f0fa020000000017a9140fb9463421696b82c833af241c78c17ddbde493487d0f20a270100000017a91429ca74f8a08f81999428185c97b5d852e4063f618765000000010304010000000104475221029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f2102dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d752ae2206029583bf39ae0a609747ad199addd634fa6108559d6c5cd39b4c2183f1ab96e07f10d90c6a4f000000800000008000000080220602dab61ff49a14db6a7d02b0cd1fbb78fc4b18312b5b4e54dae4dba2fbfef536d710d90c6a4f0000008000000080010000800001012000c2eb0b0000000017a914b7f5faf40e3d40a5a459b1db3535f2b72fa921e8870103040100000001042200208c2353173743b595dfb4a07b72ba8e42e3797da74e87fe7d9d7497e3b2028903010547522103089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc21023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7352ae2206023add904f3d6dcf59ddb906b0dee23529b7ffb9ed50e5e86151926860221f0e7310d90c6a4f000000800000008003000080220603089dc10c7ac6db54f91329af617333db388cead0c231f723379d1b99030b02dc10d90c6a4f00000080000000800200008000220203a9a4c37f5996d3aa25dbac6b570af0650394492942460b354753ed9eeca5877110d90c6a4f000000800000008004000080002202027f6399757d2eff55a136ad02c684b1838b6556e5f1b6b34282a94b6b5005109610d90c6a4f00000080000000800500008000", psbt.toString());
}
Also used : KeyDerivation(com.sparrowwallet.drongo.KeyDerivation) Test(org.junit.Test)

Example 3 with KeyDerivation

use of com.sparrowwallet.drongo.KeyDerivation in project sparrow by sparrowwallet.

the class MessageSignDialog method signUsbKeystore.

private void signUsbKeystore(Wallet usbWallet) {
    List<String> fingerprints = List.of(usbWallet.getKeystores().get(0).getKeyDerivation().getMasterFingerprint());
    KeyDerivation fullDerivation = usbWallet.getKeystores().get(0).getKeyDerivation().extend(walletNode.getDerivation());
    DeviceSignMessageDialog deviceSignMessageDialog = new DeviceSignMessageDialog(fingerprints, usbWallet, message.getText().trim(), fullDerivation);
    Optional<String> optSignature = deviceSignMessageDialog.showAndWait();
    if (optSignature.isPresent()) {
        signature.clear();
        signature.appendText(optSignature.get());
    }
}
Also used : KeyDerivation(com.sparrowwallet.drongo.KeyDerivation) SecureString(com.sparrowwallet.drongo.SecureString)

Example 4 with KeyDerivation

use of com.sparrowwallet.drongo.KeyDerivation in project sparrow by sparrowwallet.

the class CaravanMultisig method importWallet.

@Override
public Wallet importWallet(InputStream inputStream, String password) throws ImportException {
    try {
        InputStreamReader reader = new InputStreamReader(inputStream, StandardCharsets.UTF_8);
        CaravanFile cf = JsonPersistence.getGson().fromJson(reader, CaravanFile.class);
        Wallet wallet = new Wallet();
        wallet.setName(cf.name);
        wallet.setPolicyType(PolicyType.MULTI);
        ScriptType scriptType = ScriptType.valueOf(cf.addressType.replace('-', '_'));
        for (ExtPublicKey extKey : cf.extendedPublicKeys) {
            Keystore keystore = new Keystore(extKey.name);
            try {
                keystore.setKeyDerivation(new KeyDerivation(extKey.xfp, extKey.bip32Path));
            } catch (NumberFormatException e) {
                keystore.setKeyDerivation(new KeyDerivation(extKey.xfp, scriptType.getDefaultDerivationPath()));
            }
            keystore.setExtendedPublicKey(ExtendedKey.fromDescriptor(extKey.xpub));
            WalletModel walletModel = WalletModel.fromType(extKey.method);
            if (walletModel == null) {
                keystore.setWalletModel(WalletModel.SPARROW);
                keystore.setSource(KeystoreSource.SW_WATCH);
            } else {
                keystore.setWalletModel(walletModel);
                keystore.setSource(KeystoreSource.HW_USB);
            }
            wallet.getKeystores().add(keystore);
        }
        wallet.setScriptType(scriptType);
        wallet.setDefaultPolicy(Policy.getPolicy(PolicyType.MULTI, scriptType, wallet.getKeystores(), cf.quorum.requiredSigners));
        return wallet;
    } catch (Exception e) {
        throw new ImportException("Error importing " + getName() + " wallet", e);
    }
}
Also used : Keystore(com.sparrowwallet.drongo.wallet.Keystore) ScriptType(com.sparrowwallet.drongo.protocol.ScriptType) WalletModel(com.sparrowwallet.drongo.wallet.WalletModel) InputStreamReader(java.io.InputStreamReader) Wallet(com.sparrowwallet.drongo.wallet.Wallet) KeyDerivation(com.sparrowwallet.drongo.KeyDerivation)

Example 5 with KeyDerivation

use of com.sparrowwallet.drongo.KeyDerivation in project sparrow by sparrowwallet.

the class CoboVaultSinglesig method getKeystore.

@Override
public Keystore getKeystore(ScriptType scriptType, InputStream inputStream, String password) throws ImportException {
    try {
        Gson gson = new Gson();
        CoboVaultSinglesigKeystore coboKeystore = gson.fromJson(new InputStreamReader(inputStream, StandardCharsets.UTF_8), CoboVaultSinglesigKeystore.class);
        if (coboKeystore.MasterFingerprint == null || coboKeystore.AccountKeyPath == null || coboKeystore.ExtPubKey == null) {
            throw new ImportException("Not a valid " + getName() + " keystore export");
        }
        Keystore keystore = new Keystore();
        keystore.setLabel(getName());
        keystore.setSource(KeystoreSource.HW_AIRGAPPED);
        keystore.setWalletModel(WalletModel.COBO_VAULT);
        keystore.setKeyDerivation(new KeyDerivation(coboKeystore.MasterFingerprint.toLowerCase(), "m/" + coboKeystore.AccountKeyPath));
        keystore.setExtendedPublicKey(ExtendedKey.fromDescriptor(coboKeystore.ExtPubKey));
        ExtendedKey.Header header = ExtendedKey.Header.fromExtendedKey(coboKeystore.ExtPubKey);
        if (header.getDefaultScriptType() != scriptType) {
            throw new ImportException("This wallet's script type (" + scriptType + ") does not match the " + getName() + " script type (" + header.getDefaultScriptType() + ")");
        }
        return keystore;
    } catch (Exception e) {
        throw new ImportException("Error getting " + getName() + " keystore", e);
    }
}
Also used : InputStreamReader(java.io.InputStreamReader) KeyDerivation(com.sparrowwallet.drongo.KeyDerivation) Gson(com.google.gson.Gson) ExtendedKey(com.sparrowwallet.drongo.ExtendedKey)

Aggregations

KeyDerivation (com.sparrowwallet.drongo.KeyDerivation)17 ExtendedKey (com.sparrowwallet.drongo.ExtendedKey)8 ScriptType (com.sparrowwallet.drongo.protocol.ScriptType)4 Keystore (com.sparrowwallet.drongo.wallet.Keystore)4 InputStreamReader (java.io.InputStreamReader)4 PolicyType (com.sparrowwallet.drongo.policy.PolicyType)3 Test (org.junit.Test)3 Gson (com.google.gson.Gson)2 KeyPurpose (com.sparrowwallet.drongo.KeyPurpose)2 Wallet (com.sparrowwallet.drongo.wallet.Wallet)2 Type (java.lang.reflect.Type)2 ArrayList (java.util.ArrayList)2 JsonElement (com.google.gson.JsonElement)1 OutputDescriptor (com.sparrowwallet.drongo.OutputDescriptor)1 SecureString (com.sparrowwallet.drongo.SecureString)1 Utils (com.sparrowwallet.drongo.Utils)1 Address (com.sparrowwallet.drongo.address.Address)1 PaymentAddress (com.sparrowwallet.drongo.bip47.PaymentAddress)1 PaymentCode (com.sparrowwallet.drongo.bip47.PaymentCode)1 com.sparrowwallet.drongo.crypto (com.sparrowwallet.drongo.crypto)1