Merge commit 'refs/pull/462/head' of github.com:bitcoindevkit/bdk
This commit is contained in:
		
						commit
						16e832533c
					
				
							
								
								
									
										11
									
								
								Cargo.toml
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								Cargo.toml
									
									
									
									
									
								
							| @ -34,14 +34,7 @@ cc = { version = ">=1.0.64", optional = true } | |||||||
| socks = { version = "0.3", optional = true } | socks = { version = "0.3", optional = true } | ||||||
| lazy_static = { version = "1.4", optional = true } | lazy_static = { version = "1.4", optional = true } | ||||||
| 
 | 
 | ||||||
| # the latest 0.8 version of tiny-bip39 depends on zeroize_derive 1.2 which has MSRV 1.51 and our  | bip39 = { version = "1.0.1", optional = true } | ||||||
| # MSRV is 1.46, to fix this until we update our MSRV or replace the tiny-bip39  |  | ||||||
| # dependency https://github.com/bitcoindevkit/bdk/issues/399 we can only use an older version |  | ||||||
| tiny-bip39 = { version = "< 0.8", optional = true } |  | ||||||
| # backtrace > 0.3.61 includes object v0.27 which doesn't compile on 1.46. this is used by |  | ||||||
| # tiny-bip39 |  | ||||||
| backtrace = { version = "=0.3.61", optional = true } |  | ||||||
| 
 |  | ||||||
| bitcoinconsensus = { version = "0.19.0-3", optional = true } | bitcoinconsensus = { version = "0.19.0-3", optional = true } | ||||||
| 
 | 
 | ||||||
| # Needed by bdk_blockchain_tests macro | # Needed by bdk_blockchain_tests macro | ||||||
| @ -65,7 +58,7 @@ sqlite = ["rusqlite", "ahash"] | |||||||
| compact_filters = ["rocksdb", "socks", "lazy_static", "cc"] | compact_filters = ["rocksdb", "socks", "lazy_static", "cc"] | ||||||
| key-value-db = ["sled"] | key-value-db = ["sled"] | ||||||
| all-keys = ["keys-bip39"] | all-keys = ["keys-bip39"] | ||||||
| keys-bip39 = ["tiny-bip39", "backtrace"] | keys-bip39 = ["bip39"] | ||||||
| rpc = ["bitcoincore-rpc"] | rpc = ["bitcoincore-rpc"] | ||||||
| 
 | 
 | ||||||
| # We currently provide mulitple implementations of `Blockchain`, all are | # We currently provide mulitple implementations of `Blockchain`, all are | ||||||
|  | |||||||
| @ -19,7 +19,23 @@ use bitcoin::Network; | |||||||
| 
 | 
 | ||||||
| use miniscript::ScriptContext; | use miniscript::ScriptContext; | ||||||
| 
 | 
 | ||||||
| pub use bip39::{Language, Mnemonic, MnemonicType, Seed}; | pub use bip39::{Language, Mnemonic}; | ||||||
|  | 
 | ||||||
|  | type Seed = [u8; 64]; | ||||||
|  | 
 | ||||||
|  | /// Type describing entropy length (aka word count) in the mnemonic
 | ||||||
|  | pub enum WordsCount { | ||||||
|  |     /// 12 words mnemonic (128 bits entropy)
 | ||||||
|  |     Words12 = 128, | ||||||
|  |     /// 15 words mnemonic (160 bits entropy)
 | ||||||
|  |     Words15 = 160, | ||||||
|  |     /// 18 words mnemonic (192 bits entropy)
 | ||||||
|  |     Words18 = 192, | ||||||
|  |     /// 21 words mnemonic (224 bits entropy)
 | ||||||
|  |     Words21 = 224, | ||||||
|  |     /// 24 words mnemonic (256 bits entropy)
 | ||||||
|  |     Words24 = 256, | ||||||
|  | } | ||||||
| 
 | 
 | ||||||
| use super::{ | use super::{ | ||||||
|     any_network, DerivableKey, DescriptorKey, ExtendedKey, GeneratableKey, GeneratedKey, KeyError, |     any_network, DerivableKey, DescriptorKey, ExtendedKey, GeneratableKey, GeneratedKey, KeyError, | ||||||
| @ -40,7 +56,7 @@ pub type MnemonicWithPassphrase = (Mnemonic, Option<String>); | |||||||
| #[cfg_attr(docsrs, doc(cfg(feature = "keys-bip39")))] | #[cfg_attr(docsrs, doc(cfg(feature = "keys-bip39")))] | ||||||
| impl<Ctx: ScriptContext> DerivableKey<Ctx> for Seed { | impl<Ctx: ScriptContext> DerivableKey<Ctx> for Seed { | ||||||
|     fn into_extended_key(self) -> Result<ExtendedKey<Ctx>, KeyError> { |     fn into_extended_key(self) -> Result<ExtendedKey<Ctx>, KeyError> { | ||||||
|         Ok(bip32::ExtendedPrivKey::new_master(Network::Bitcoin, self.as_bytes())?.into()) |         Ok(bip32::ExtendedPrivKey::new_master(Network::Bitcoin, &self[..])?.into()) | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     fn into_descriptor_key( |     fn into_descriptor_key( | ||||||
| @ -60,7 +76,7 @@ impl<Ctx: ScriptContext> DerivableKey<Ctx> for Seed { | |||||||
| impl<Ctx: ScriptContext> DerivableKey<Ctx> for MnemonicWithPassphrase { | impl<Ctx: ScriptContext> DerivableKey<Ctx> for MnemonicWithPassphrase { | ||||||
|     fn into_extended_key(self) -> Result<ExtendedKey<Ctx>, KeyError> { |     fn into_extended_key(self) -> Result<ExtendedKey<Ctx>, KeyError> { | ||||||
|         let (mnemonic, passphrase) = self; |         let (mnemonic, passphrase) = self; | ||||||
|         let seed = Seed::new(&mnemonic, passphrase.as_deref().unwrap_or("")); |         let seed: Seed = mnemonic.to_seed(passphrase.as_deref().unwrap_or("")); | ||||||
| 
 | 
 | ||||||
|         seed.into_extended_key() |         seed.into_extended_key() | ||||||
|     } |     } | ||||||
| @ -101,15 +117,15 @@ impl<Ctx: ScriptContext> DerivableKey<Ctx> for Mnemonic { | |||||||
| impl<Ctx: ScriptContext> GeneratableKey<Ctx> for Mnemonic { | impl<Ctx: ScriptContext> GeneratableKey<Ctx> for Mnemonic { | ||||||
|     type Entropy = [u8; 32]; |     type Entropy = [u8; 32]; | ||||||
| 
 | 
 | ||||||
|     type Options = (MnemonicType, Language); |     type Options = (WordsCount, Language); | ||||||
|     type Error = Option<bip39::ErrorKind>; |     type Error = Option<bip39::Error>; | ||||||
| 
 | 
 | ||||||
|     fn generate_with_entropy( |     fn generate_with_entropy( | ||||||
|         (mnemonic_type, language): Self::Options, |         (word_count, language): Self::Options, | ||||||
|         entropy: Self::Entropy, |         entropy: Self::Entropy, | ||||||
|     ) -> Result<GeneratedKey<Self, Ctx>, Self::Error> { |     ) -> Result<GeneratedKey<Self, Ctx>, Self::Error> { | ||||||
|         let entropy = &entropy.as_ref()[..(mnemonic_type.entropy_bits() / 8)]; |         let entropy = &entropy.as_ref()[..(word_count as usize / 8)]; | ||||||
|         let mnemonic = Mnemonic::from_entropy(entropy, language).map_err(|e| e.downcast().ok())?; |         let mnemonic = Mnemonic::from_entropy_in(language, entropy)?; | ||||||
| 
 | 
 | ||||||
|         Ok(GeneratedKey::new(mnemonic, any_network())) |         Ok(GeneratedKey::new(mnemonic, any_network())) | ||||||
|     } |     } | ||||||
| @ -121,15 +137,17 @@ mod test { | |||||||
| 
 | 
 | ||||||
|     use bitcoin::util::bip32; |     use bitcoin::util::bip32; | ||||||
| 
 | 
 | ||||||
|     use bip39::{Language, Mnemonic, MnemonicType}; |     use bip39::{Language, Mnemonic}; | ||||||
| 
 | 
 | ||||||
|     use crate::keys::{any_network, GeneratableKey, GeneratedKey}; |     use crate::keys::{any_network, GeneratableKey, GeneratedKey}; | ||||||
| 
 | 
 | ||||||
|  |     use super::WordsCount; | ||||||
|  | 
 | ||||||
|     #[test] |     #[test] | ||||||
|     fn test_keys_bip39_mnemonic() { |     fn test_keys_bip39_mnemonic() { | ||||||
|         let mnemonic = |         let mnemonic = | ||||||
|             "aim bunker wash balance finish force paper analyst cabin spoon stable organ"; |             "aim bunker wash balance finish force paper analyst cabin spoon stable organ"; | ||||||
|         let mnemonic = Mnemonic::from_phrase(mnemonic, Language::English).unwrap(); |         let mnemonic = Mnemonic::parse_in(Language::English, mnemonic).unwrap(); | ||||||
|         let path = bip32::DerivationPath::from_str("m/44'/0'/0'/0").unwrap(); |         let path = bip32::DerivationPath::from_str("m/44'/0'/0'/0").unwrap(); | ||||||
| 
 | 
 | ||||||
|         let key = (mnemonic, path); |         let key = (mnemonic, path); | ||||||
| @ -143,7 +161,7 @@ mod test { | |||||||
|     fn test_keys_bip39_mnemonic_passphrase() { |     fn test_keys_bip39_mnemonic_passphrase() { | ||||||
|         let mnemonic = |         let mnemonic = | ||||||
|             "aim bunker wash balance finish force paper analyst cabin spoon stable organ"; |             "aim bunker wash balance finish force paper analyst cabin spoon stable organ"; | ||||||
|         let mnemonic = Mnemonic::from_phrase(mnemonic, Language::English).unwrap(); |         let mnemonic = Mnemonic::parse_in(Language::English, mnemonic).unwrap(); | ||||||
|         let path = bip32::DerivationPath::from_str("m/44'/0'/0'/0").unwrap(); |         let path = bip32::DerivationPath::from_str("m/44'/0'/0'/0").unwrap(); | ||||||
| 
 | 
 | ||||||
|         let key = ((mnemonic, Some("passphrase".into())), path); |         let key = ((mnemonic, Some("passphrase".into())), path); | ||||||
| @ -157,7 +175,7 @@ mod test { | |||||||
|     fn test_keys_generate_bip39() { |     fn test_keys_generate_bip39() { | ||||||
|         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = |         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = | ||||||
|             Mnemonic::generate_with_entropy( |             Mnemonic::generate_with_entropy( | ||||||
|                 (MnemonicType::Words12, Language::English), |                 (WordsCount::Words12, Language::English), | ||||||
|                 crate::keys::test::TEST_ENTROPY, |                 crate::keys::test::TEST_ENTROPY, | ||||||
|             ) |             ) | ||||||
|             .unwrap(); |             .unwrap(); | ||||||
| @ -169,7 +187,7 @@ mod test { | |||||||
| 
 | 
 | ||||||
|         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = |         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = | ||||||
|             Mnemonic::generate_with_entropy( |             Mnemonic::generate_with_entropy( | ||||||
|                 (MnemonicType::Words24, Language::English), |                 (WordsCount::Words24, Language::English), | ||||||
|                 crate::keys::test::TEST_ENTROPY, |                 crate::keys::test::TEST_ENTROPY, | ||||||
|             ) |             ) | ||||||
|             .unwrap(); |             .unwrap(); | ||||||
| @ -180,11 +198,11 @@ mod test { | |||||||
|     #[test] |     #[test] | ||||||
|     fn test_keys_generate_bip39_random() { |     fn test_keys_generate_bip39_random() { | ||||||
|         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = |         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = | ||||||
|             Mnemonic::generate((MnemonicType::Words12, Language::English)).unwrap(); |             Mnemonic::generate((WordsCount::Words12, Language::English)).unwrap(); | ||||||
|         assert_eq!(generated_mnemonic.valid_networks, any_network()); |         assert_eq!(generated_mnemonic.valid_networks, any_network()); | ||||||
| 
 | 
 | ||||||
|         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = |         let generated_mnemonic: GeneratedKey<_, miniscript::Segwitv0> = | ||||||
|             Mnemonic::generate((MnemonicType::Words24, Language::English)).unwrap(); |             Mnemonic::generate((WordsCount::Words24, Language::English)).unwrap(); | ||||||
|         assert_eq!(generated_mnemonic.valid_networks, any_network()); |         assert_eq!(generated_mnemonic.valid_networks, any_network()); | ||||||
|     } |     } | ||||||
| } | } | ||||||
|  | |||||||
| @ -460,9 +460,9 @@ use bdk::keys::bip39::{Mnemonic, Language}; | |||||||
| 
 | 
 | ||||||
| # fn main() -> Result<(), Box<dyn std::error::Error>> { | # fn main() -> Result<(), Box<dyn std::error::Error>> { | ||||||
| let xkey: ExtendedKey = | let xkey: ExtendedKey = | ||||||
|     Mnemonic::from_phrase( |     Mnemonic::parse_in( | ||||||
|  |         Language::English, | ||||||
|         "jelly crash boy whisper mouse ecology tuna soccer memory million news short", |         "jelly crash boy whisper mouse ecology tuna soccer memory million news short", | ||||||
|         Language::English |  | ||||||
|     )? |     )? | ||||||
|     .into_extended_key()?; |     .into_extended_key()?; | ||||||
| let xprv = xkey.into_xprv(Network::Bitcoin).unwrap(); | let xprv = xkey.into_xprv(Network::Bitcoin).unwrap(); | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user