bitcoin-ruby 0.0.18 → 0.0.19
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/.gitignore +8 -0
- data/.rspec +1 -0
- data/.rubocop.yml +46 -0
- data/.travis.yml +5 -1
- data/Gemfile +11 -9
- data/Gemfile.lock +64 -12
- data/README.rdoc +17 -4
- data/Rakefile +58 -83
- data/bitcoin-ruby.gemspec +5 -2
- data/lib/bitcoin.rb +31 -14
- data/lib/bitcoin/bech32.rb +126 -132
- data/lib/bitcoin/bloom_filter.rb +24 -21
- data/lib/bitcoin/builder.rb +168 -126
- data/lib/bitcoin/connection.rb +21 -24
- data/lib/bitcoin/contracthash.rb +20 -24
- data/lib/bitcoin/dogecoin.rb +79 -77
- data/lib/bitcoin/electrum/mnemonic.rb +28 -25
- data/lib/bitcoin/ext_key.rb +3 -3
- data/lib/bitcoin/ffi/bitcoinconsensus.rb +17 -13
- data/lib/bitcoin/ffi/openssl.rb +355 -338
- data/lib/bitcoin/ffi/secp256k1.rb +97 -64
- data/lib/bitcoin/protocol.rb +6 -3
- data/lib/bitcoin/protocol/address.rb +15 -13
- data/lib/bitcoin/protocol/aux_pow.rb +12 -15
- data/lib/bitcoin/protocol/block.rb +102 -76
- data/lib/bitcoin/protocol/handler.rb +2 -4
- data/lib/bitcoin/protocol/parser.rb +108 -92
- data/lib/bitcoin/protocol/partial_merkle_tree.rb +59 -47
- data/lib/bitcoin/protocol/reject.rb +26 -28
- data/lib/bitcoin/protocol/script_witness.rb +3 -8
- data/lib/bitcoin/protocol/tx.rb +250 -137
- data/lib/bitcoin/protocol/txin.rb +44 -38
- data/lib/bitcoin/protocol/txout.rb +27 -20
- data/lib/bitcoin/protocol/version.rb +47 -34
- data/lib/bitcoin/script.rb +18 -17
- data/lib/bitcoin/trezor/mnemonic.rb +113 -98
- data/lib/bitcoin/version.rb +1 -1
- data/spec/examples.txt +399 -0
- data/spec/{bitcoin/fixtures → fixtures}/000000000000056b1a3d84a1e2b33cde8915a4b61c0cae14fca6d3e1490b4f98.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/03d7e1fa4d5fefa169431f24f7798552861b255cd55d377066fedcd088fb0e99.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/0961c660358478829505e16a1f028757e54b5bbf9758341a7546573738f31429.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/0f24294a1d23efbb49c1765cf443fba7930702752aba6d765870082fe4f13cae.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/156e6e1b84c5c3bd3a0927b25e4119fadce6e6d5186f363317511d1d680fae9a.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/23b397edccd3740a74adb603c9756370fafcde9bcc4483eb271ecad09a94dd63.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/315ac7d4c26d69668129cc352851d9389b4a6868f1509c6c8b66bead11e2619f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/35e2001b428891fefa0bfb73167c7360669d3cbd7b3aa78e7cad125ddfc51131.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/3a17dace09ffb919ed627a93f1873220f4c975c1248558b18d16bce25d38c4b7.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/3e58b7eed0fdb599019af08578effea25c8666bbe8e200845453cacce6314477.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/514c46f0b61714092f15c8dfcb576c9f79b3f959989b98de3944b19d98832b58.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/51bf528ecf3c161e7c021224197dbe84f9a8564212f6207baa014c01a1668e1e.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/60a20bd93aa49ab4b28d514ec10b06e1829ce6818ec06cd3aabd013ebcdc4bb1.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/69216b8aaa35b76d6613e5f527f4858640d986e1046238583bdad79b35e938dc.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/7208e5edf525f04e705fb3390194e316205b8f995c8c9fcd8c6093abe04fa27d.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/761d8c5210fdfd505f6dff38f740ae3728eb93d7d0971fb433f685d40a4c04f6.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/8d0b238a06b5a70be75d543902d02d7a514d68d3252a949a513865ac3538874c.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/aea682d68a3ea5e3583e088dcbd699a5d44d4b083f02ad0aaf2598fe1fa4dfd4.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/base58_keys_invalid.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/base58_keys_valid.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/bc179baab547b7d7c1d5d8d6f8b0cc6318eaa4b0dd0a093ad6ac7f5a1cb6b3ba.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/bd1715f1abfdc62bea3f605bdb461b3ba1f2cca6ec0d73a18a548b7717ca8531.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/block-testnet-0000000000ac85bb2530a05a4214a387e6be02b22d3348abc5e7a5d9c4ce8dab.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/cd874fa8cb0e2ec2d385735d5e1fd482c4fe648533efb4c50ee53bda58e15ae2.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/ce5fad9b4ef094d8f4937b0707edaf0a6e6ceeaf67d5edbfd51f660eac8f398b.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/coinbase-toshi.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/coinbase.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/dogecoin-block-60323982f9c5ff1b5a954eac9dc1269352835f47c2c5222691d80f0d50dcf053.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/f003f0c1193019db2497a675fd05d9f2edddf9b67c59e677c48d3dbd4ed5f00b.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/filteredblock-0.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/litecoin-block-80ca095ed10b02e53d769eb6eaf92cd04e9e0759e5be4a8477b42911ba49c78f.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/litecoin-block-80ca095ed10b02e53d769eb6eaf92cd04e9e0759e5be4a8477b42911ba49c78f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/litecoin-genesis-block-12a765e31ffd4059bada1e25190f6e98c99d9714d334efa41a195a7e7e04bfe2.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/litecoin-genesis-block-12a765e31ffd4059bada1e25190f6e98c99d9714d334efa41a195a7e7e04bfe2.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/litecoin-tx-f5aa30f574e3b6f1a3d99c07a6356ba812aabb9661e1d5f71edff828cbd5c996.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-0.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-0.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-1.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-1.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-131025.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-131025.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-170.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-9.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-auxpow.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-testnet-1151351.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-testnet-26478.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-testnet-26478.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawblock-testnet-265322.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-01-toshi.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-01.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-01.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-02-toshi.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-02.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-02.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-03-toshi.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-03.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-03.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-04.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-0437cd7f8525ceed2324359c2d0ba26006d92d856a9c20fa0241106ee5a597c9.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-05.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-14be6fff8c6014f7c9493b4a6e4a741699173f39d74431b6b844fcb41ebb9984.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-2f4a2717ec8c9f077a87dde6cbe0274d5238793a3f3f492b63c744837285e58a.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-2f4a2717ec8c9f077a87dde6cbe0274d5238793a3f3f492b63c744837285e58a.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-406b2b06bcd34d3c8733e6b79f7a394c8a431fbf4ff5ac705c93f4076bb77602.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-52250a162c7d03d2e1fbc5ebd1801a88612463314b55102171c5b5d817d2d7b2.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-b5d4e8883533f99e5903ea2cf001a133a322fa6b1370b18a16c57c946a40823d.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-ba1ff5cd66713133c062a871a8adab92416f1e38d17786b2bf56ac5f6ffdfdf5.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-c99c49da4c38af669dea436d3e73780dfdb6c1ecf9958baa52960e8baee30e73.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-de35d060663750b3975b7997bde7fb76307cec5b270d12fcd9c4ad98b279c28c.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-p2wpkh.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-p2wpkh.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-04fdc38d6722ab4b12d79113fc4b2896bdcc5169710690ee4e78541b98e467b4.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-0b294c7d11dd21bcccb8393e6744fed7d4d1981a08c00e3e88838cc421f33c9f.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-3bc52ac063291ad92d95ddda5fd776a342083b95607ad32ed8bc6f8f7d30449e.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-6f0bbdd4e71a8af4305018d738184df32dbb6f27284fdebd5b56d16947f7c181.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-a220adf1902c46a39db25a24bc4178b6a88440f977a7e2cabfdd8b5c1dd35cfb.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-a7c9b06e275e8674cc19a5f7d3e557c72c6d93576e635b33212dbe08ab7cdb60.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-e232e0055dbdca88bbaa79458683195a0b7c17c5b6c524a8d146721d4d4d652f.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-e232e0055dbdca88bbaa79458683195a0b7c17c5b6c524a8d146721d4d4d652f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/rawtx-testnet-f80acbd2f594d04ddb0e1cacba662132104909157dff526935a3c88abe9201a5.bin +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/script_tests.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/sighash.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-0295028ef826b2a188409cb905b631faebb9bb3cdf14510571c5f4bd8591338f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-03339a725007a279484fb6f5361f522dd1cf4d0923d30e6b973290dba4275f92.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-0a6a357e2f7796444e02638749d9611c008b253fb55f5dc88b739b230ed0c4c3.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-0ce7e5238fbdb6c086cf1b384b21b827e91cc23f360417265874a5a0d86ce367.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-0ef34c49f630aea17df0080728b0fc67bf5f87fbda936934a4b11b4a69d7821e.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-1129d2a8bd5bb3a81e54dc96a90f1f6b2544575748caa17243470935c5dd91b7.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-19aa42fee0fa57c45d3b16488198b27caaacc4ff5794510d0c17f173f05587ff.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-1a4f3b9dc4494aeedeb39f30dd37e60541b2abe3ed4977992017cc0ad4f44956.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-1f9191dcf2b1844ca28c6ef4b969e1d5fab70a5e3c56b7007949e55851cb0c4f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-22cd5fef23684d7b304e119bedffde6f54538d3d54a5bfa237e20dc2d9b4b5ad.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-28204cad1d7fc1d199e8ef4fa22f182de6258a3eaafe1bbe56ebdcacd3069a5f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-2958fb00b4fd6fe0353503b886eb9a193d502f4fd5fc042d5e03216ba918bbd6.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-29f277145749ad6efbed3ae6ce301f8d33c585ec26b7c044ad93c2f866e9e942.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-2c5e5376c20e9cc78d0fb771730e5d840cc2096eff0ef045b599fe92475ace1c.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-2c63aa814701cef5dbd4bbaddab3fea9117028f2434dddcdab8339141e9b14d1.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-313897799b1e37e9ecae15010e56156dddde4e683c96b0e713af95272c38aee0.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-326882a7f22b5191f1a0cc9962ca4b878cd969cf3b3a70887aece4d801a0ba5e.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-345bed8785c3282a264ffb0dbee61cde54854f10e16f1b3e75b7f2d9f62946f2.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-39ba7440b7103557560cc8ce258009936796485aaf8b478e66ab4cb97c66e31b.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-3a04d57a833367f1655cc5ec3beb587888ef4977a86caa8c8ad4ba7cc717eae7.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-3da75972766f0ad13319b0b461fd16823a731e44f6e9de4eb3c52d6a6fb6c8ae.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-4142ee4877eb116abf955a7ec6ef2dc38133b793df762b76d75e3d7d4d8badc9.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-44b833074e671120ba33106877b49e86ece510824b9af477a3853972bcd8d06a.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-46224764c7870f95b58f155bce1e38d4da8e99d42dbb632d0dd7c07e092ee5aa.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-5df1375ffe61ac35ca178ebb0cab9ea26dedbd0e96005dfcee7e379fa513232f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-62d9a565bd7b5344c5352e3e9e5f40fa4bbd467fa19c87357216ec8777ba1cce.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-6327783a064d4e350c454ad5cd90201aedf65b1fc524e73709c52f0163739190.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-6606c366a487bff9e412d0b6c09c14916319932db5954bf5d8719f43f828a3ba.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-6aaf18b9f1283b939d8e5d40ff5f8a435229f4178372659cc3a0bce4e262bf78.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-6b48bba6f6d2286d7ec0883c0fc3085955090813a4c94980466611c798b868cc.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-70cfbc6690f9ab46712db44e3079ac227962b2771a9341d4233d898b521619ef.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-7a1a9db42f065f75110fcdb1bc415549c8ef7670417ba1d35a67f1b8adc562c1.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-9a768fc7d0c4bdc86e25154357ef7c0063ca21310e5740a2f12f90b7455184a7.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-9cad8d523a0694f2509d092c39cebc8046adae62b4e4297102d568191d9478d8.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-9e052eb694bd7e15906433f064dff0161a12fd325c1124537766377004023c6f.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-9fb65b7304aaa77ac9580823c2c06b259cc42591e5cce66d76a81b6f51cc5c28.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-a6ce7081addade7676cd2af75c4129eba6bf5e179a19c40c7d4cf6a5fe595954.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-a955032f4d6b0c9bfe8cad8f00a8933790b9c1dc28c82e0f48e75b35da0e4944.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-aab7ef280abbb9cc6fbaf524d2645c3daf4fcca2b3f53370e618d9cedf65f1f8.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-ab9805c6d57d7070d9a42c5176e47bb705023e6b67249fb6760880548298e742.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-ad4bcf3241e5d2ad140564e20db3567d41594cf4c2012433fe46a2b70e0d87b8.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-b5b598de91787439afd5938116654e0b16b7a0d0f82742ba37564219c5afcbf9.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-b8fd633e7713a43d5ac87266adc78444669b987a56b3a65fb92d58c2c4b0e84d.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-bbca0628c42cb8bf7c3f4b2ad688fa56da5308dd2a10255da89fb1f46e6e413d.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-bc7fd132fcf817918334822ee6d9bd95c889099c96e07ca2c1eb2cc70db63224.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-c192b74844e4837a34c4a5a97b438f1c111405b01b99e2d12b7c96d07fc74c04.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-d3d77d63709e47d9ef58f0b557800115a6b676c6a423012fbb96f45d8fcef830.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-e335562f7e297aadeed88e5954bc4eeb8dc00b31d829eedb232e39d672b0c009.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-eb3b82c0884e3efa6d8b0be55b4915eb20be124c9766245bcc7f34fdac32bccb.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/tx-fee1b9b85531c8fb6cd7831f83490c7f2aa768b6eefe29854ef5e89ce7b9ecb1.json +0 -0
- data/spec/{bitcoin/fixtures → fixtures}/txscript-invalid-too-many-sigops-followed-by-invalid-pushdata.bin +0 -0
- data/spec/helpers/block_helpers.rb +58 -0
- data/spec/helpers/fixture_helpers.rb +20 -0
- data/spec/helpers/library_helpers.rb +15 -0
- data/spec/spec_helper.rb +109 -0
- data/spec/unit/bitcoin/bech32_spec.rb +187 -0
- data/spec/unit/bitcoin/bitcoin_spec.rb +1079 -0
- data/spec/unit/bitcoin/bloom_filter_spec.rb +33 -0
- data/spec/unit/bitcoin/builder_spec.rb +559 -0
- data/spec/unit/bitcoin/contracthash_spec.rb +52 -0
- data/spec/unit/bitcoin/ext_key_spec.rb +281 -0
- data/spec/unit/bitcoin/key_spec.rb +457 -0
- data/spec/unit/bitcoin/network_spec.rb +71 -0
- data/spec/unit/bitcoin/protocol/addr_spec.rb +90 -0
- data/spec/unit/bitcoin/protocol/aux_pow_spec.rb +45 -0
- data/spec/unit/bitcoin/protocol/bip143_spec.rb +334 -0
- data/spec/unit/bitcoin/protocol/block_spec.rb +280 -0
- data/spec/unit/bitcoin/protocol/getblocks_spec.rb +44 -0
- data/spec/unit/bitcoin/protocol/inv_spec.rb +166 -0
- data/spec/unit/bitcoin/protocol/notfound_spec.rb +44 -0
- data/spec/unit/bitcoin/protocol/parser_spec.rb +69 -0
- data/spec/unit/bitcoin/protocol/partial_merkle_tree_spec.rb +47 -0
- data/spec/unit/bitcoin/protocol/ping_spec.rb +62 -0
- data/spec/unit/bitcoin/protocol/tx_spec.rb +1515 -0
- data/spec/unit/bitcoin/protocol/txin_spec.rb +47 -0
- data/spec/unit/bitcoin/protocol/txout_spec.rb +36 -0
- data/spec/unit/bitcoin/protocol/version_spec.rb +121 -0
- data/spec/unit/bitcoin/script/opcodes_spec.rb +864 -0
- data/spec/unit/bitcoin/script/script_spec.rb +1610 -0
- data/spec/unit/bitcoin/secp256k1_spec.rb +138 -0
- data/spec/unit/bitcoin/trezor/mnemonic_spec.rb +193 -0
- data/spec/unit/integrations/dogecoin_spec.rb +215 -0
- metadata +381 -372
- data/lib/bitcoin/logger.rb +0 -86
- data/lib/bitcoin/protocol/alert.rb +0 -46
- data/spec/bitcoin/bech32_spec.rb +0 -160
- data/spec/bitcoin/bitcoin_spec.rb +0 -666
- data/spec/bitcoin/bloom_filter_spec.rb +0 -23
- data/spec/bitcoin/builder_spec.rb +0 -375
- data/spec/bitcoin/contracthash_spec.rb +0 -45
- data/spec/bitcoin/dogecoin_spec.rb +0 -176
- data/spec/bitcoin/ext_key_spec.rb +0 -180
- data/spec/bitcoin/ffi_openssl.rb +0 -45
- data/spec/bitcoin/fixtures/rawblock-170.json +0 -68
- data/spec/bitcoin/fixtures/rawblock-9.json +0 -39
- data/spec/bitcoin/fixtures/reorg/blk_0_to_4.dat +0 -0
- data/spec/bitcoin/fixtures/reorg/blk_3A.dat +0 -0
- data/spec/bitcoin/fixtures/reorg/blk_4A.dat +0 -0
- data/spec/bitcoin/fixtures/reorg/blk_5A.dat +0 -0
- data/spec/bitcoin/fixtures/testnet/block_0.bin +0 -0
- data/spec/bitcoin/fixtures/testnet/block_1.bin +0 -0
- data/spec/bitcoin/fixtures/testnet/block_2.bin +0 -0
- data/spec/bitcoin/fixtures/testnet/block_3.bin +0 -0
- data/spec/bitcoin/fixtures/testnet/block_4.bin +0 -0
- data/spec/bitcoin/fixtures/testnet/block_5.bin +0 -0
- data/spec/bitcoin/fixtures/txdp-1.txt +0 -32
- data/spec/bitcoin/fixtures/txdp-2-signed.txt +0 -19
- data/spec/bitcoin/fixtures/txdp-2-unsigned.txt +0 -14
- data/spec/bitcoin/helpers/fake_blockchain.rb +0 -183
- data/spec/bitcoin/key_spec.rb +0 -326
- data/spec/bitcoin/network_spec.rb +0 -50
- data/spec/bitcoin/performance/storage_spec.rb +0 -41
- data/spec/bitcoin/protocol/addr_spec.rb +0 -82
- data/spec/bitcoin/protocol/alert_spec.rb +0 -22
- data/spec/bitcoin/protocol/aux_pow_spec.rb +0 -45
- data/spec/bitcoin/protocol/bip143_spec.rb +0 -116
- data/spec/bitcoin/protocol/block_spec.rb +0 -208
- data/spec/bitcoin/protocol/getblocks_spec.rb +0 -32
- data/spec/bitcoin/protocol/inv_spec.rb +0 -134
- data/spec/bitcoin/protocol/notfound_spec.rb +0 -31
- data/spec/bitcoin/protocol/parser_spec.rb +0 -50
- data/spec/bitcoin/protocol/partial_merkle_tree_spec.rb +0 -38
- data/spec/bitcoin/protocol/ping_spec.rb +0 -51
- data/spec/bitcoin/protocol/reject.rb +0 -17
- data/spec/bitcoin/protocol/tx_spec.rb +0 -894
- data/spec/bitcoin/protocol/txin_spec.rb +0 -45
- data/spec/bitcoin/protocol/txout_spec.rb +0 -33
- data/spec/bitcoin/protocol/version_spec.rb +0 -110
- data/spec/bitcoin/script/opcodes_spec.rb +0 -773
- data/spec/bitcoin/script/script_spec.rb +0 -977
- data/spec/bitcoin/secp256k1_spec.rb +0 -78
- data/spec/bitcoin/spec_helper.rb +0 -108
- data/spec/bitcoin/trezor/mnemonic_spec.rb +0 -161
data/lib/bitcoin/connection.rb
CHANGED
|
@@ -6,7 +6,7 @@ require 'bitcoin'
|
|
|
6
6
|
require 'resolv'
|
|
7
7
|
|
|
8
8
|
module Bitcoin
|
|
9
|
-
|
|
9
|
+
# Handle messages received from node
|
|
10
10
|
module ConnectionHandler
|
|
11
11
|
def on_inv_transaction(hash)
|
|
12
12
|
p ['inv transaction', hash.hth]
|
|
@@ -38,13 +38,13 @@ module Bitcoin
|
|
|
38
38
|
|
|
39
39
|
def on_block(block)
|
|
40
40
|
p ['block', block.hash]
|
|
41
|
-
#p block.payload.each_byte.map{|i| "%02x" % [i] }.join(" ")
|
|
42
|
-
#puts block.to_json
|
|
41
|
+
# p block.payload.each_byte.map{|i| "%02x" % [i] }.join(" ")
|
|
42
|
+
# puts block.to_json
|
|
43
43
|
end
|
|
44
44
|
|
|
45
45
|
def on_version(version)
|
|
46
46
|
p [@sockaddr, 'version', version, version.time - Time.now.to_i]
|
|
47
|
-
send_data(
|
|
47
|
+
send_data(Protocol.verack_pkt)
|
|
48
48
|
end
|
|
49
49
|
|
|
50
50
|
def on_verack
|
|
@@ -59,17 +59,17 @@ module Bitcoin
|
|
|
59
59
|
end
|
|
60
60
|
|
|
61
61
|
def query_blocks
|
|
62
|
-
start = ("\x00"*32)
|
|
63
|
-
stop = ("\x00"*32)
|
|
64
|
-
pkt = Protocol.pkt(
|
|
62
|
+
start = ("\x00" * 32)
|
|
63
|
+
stop = ("\x00" * 32)
|
|
64
|
+
pkt = Protocol.pkt('getblocks', "\x00" + start + stop)
|
|
65
65
|
send_data(pkt)
|
|
66
66
|
end
|
|
67
67
|
|
|
68
68
|
def on_handshake_begin
|
|
69
|
-
block =
|
|
70
|
-
from =
|
|
69
|
+
block = 127_953
|
|
70
|
+
from = '127.0.0.1:8333'
|
|
71
71
|
from_id = Bitcoin::Protocol::Uniq
|
|
72
|
-
to = @sockaddr.reverse.join(
|
|
72
|
+
to = @sockaddr.reverse.join(':')
|
|
73
73
|
# p "==", from_id, from, to, block
|
|
74
74
|
pkt = Protocol.version_pkt(from_id, from, to, block)
|
|
75
75
|
p ['sending version pkt', pkt]
|
|
@@ -77,19 +77,19 @@ module Bitcoin
|
|
|
77
77
|
end
|
|
78
78
|
end
|
|
79
79
|
|
|
80
|
-
|
|
80
|
+
# Establish connection to node
|
|
81
81
|
class Connection < EM::Connection
|
|
82
82
|
include ConnectionHandler
|
|
83
83
|
|
|
84
84
|
def initialize(host, port, connections)
|
|
85
85
|
@sockaddr = [port, host]
|
|
86
86
|
@connections = connections
|
|
87
|
-
@parser = Bitcoin::Protocol::Parser.new(
|
|
87
|
+
@parser = Bitcoin::Protocol::Parser.new(self)
|
|
88
88
|
end
|
|
89
89
|
|
|
90
90
|
def post_init
|
|
91
91
|
p ['connected', @sockaddr]
|
|
92
|
-
EM.schedule{ on_handshake_begin }
|
|
92
|
+
EM.schedule { on_handshake_begin }
|
|
93
93
|
end
|
|
94
94
|
|
|
95
95
|
def receive_data(data)
|
|
@@ -107,24 +107,21 @@ module Bitcoin
|
|
|
107
107
|
|
|
108
108
|
def self.connect_random_from_dns(connections)
|
|
109
109
|
seeds = Bitcoin.network[:dns_seeds]
|
|
110
|
-
if seeds.
|
|
111
|
-
|
|
112
|
-
connect(host, Bitcoin::network[:default_port], connections)
|
|
113
|
-
else
|
|
114
|
-
raise "No DNS seeds available. Provide IP, configure seeds, or use different network."
|
|
110
|
+
if seeds.empty?
|
|
111
|
+
raise 'No DNS seeds available. Provide IP, configure seeds, or use different network.'
|
|
115
112
|
end
|
|
113
|
+
|
|
114
|
+
host = Resolv::DNS.new.getaddresses(seeds.sample).map(&:to_s).sample
|
|
115
|
+
connect(host, Bitcoin.network[:default_port], connections)
|
|
116
116
|
end
|
|
117
117
|
end
|
|
118
118
|
end
|
|
119
119
|
|
|
120
|
-
|
|
121
|
-
if $0 == __FILE__
|
|
120
|
+
if $PROGRAM_NAME == __FILE__
|
|
122
121
|
EM.run do
|
|
123
|
-
|
|
124
122
|
connections = []
|
|
125
|
-
#Bitcoin::Connection.connect('127.0.0.1', 8333, connections)
|
|
126
|
-
#Bitcoin::Connection.connect('217.157.1.202', 8333, connections)
|
|
123
|
+
# Bitcoin::Connection.connect('127.0.0.1', 8333, connections)
|
|
124
|
+
# Bitcoin::Connection.connect('217.157.1.202', 8333, connections)
|
|
127
125
|
Bitcoin::Connection.connect_random_from_dns(connections)
|
|
128
|
-
|
|
129
126
|
end
|
|
130
127
|
end
|
data/lib/bitcoin/contracthash.rb
CHANGED
|
@@ -1,43 +1,39 @@
|
|
|
1
|
-
#
|
|
2
|
-
# Ruby port of https://github.com/Blockstream/contracthashtool
|
|
3
|
-
#
|
|
4
|
-
|
|
5
1
|
module Bitcoin
|
|
2
|
+
# Ruby port of https://github.com/Blockstream/contracthashtool
|
|
6
3
|
module ContractHash
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
EC_GROUP = OpenSSL::PKey::EC::Group.new("secp256k1")
|
|
4
|
+
HMAC_DIGEST = OpenSSL::Digest.new('SHA256')
|
|
5
|
+
EC_GROUP = OpenSSL::PKey::EC::Group.new('secp256k1')
|
|
10
6
|
|
|
11
7
|
def self.hmac(pubkey, data)
|
|
12
8
|
OpenSSL::HMAC.hexdigest(HMAC_DIGEST, pubkey, data)
|
|
13
9
|
end
|
|
14
10
|
|
|
15
11
|
# generate a contract address
|
|
16
|
-
def self.generate(redeem_script_hex, payee_address_or_ascii, nonce_hex=nil)
|
|
17
|
-
redeem_script = Bitcoin::Script.new([redeem_script_hex].pack(
|
|
18
|
-
raise
|
|
12
|
+
def self.generate(redeem_script_hex, payee_address_or_ascii, nonce_hex = nil)
|
|
13
|
+
redeem_script = Bitcoin::Script.new([redeem_script_hex].pack('H*'))
|
|
14
|
+
raise 'only multisig redeem scripts are currently supported' unless redeem_script.is_multisig?
|
|
19
15
|
nonce_hex, data = compute_data(payee_address_or_ascii, nonce_hex)
|
|
20
16
|
|
|
21
17
|
derived_keys = []
|
|
22
18
|
redeem_script.get_multisig_pubkeys.each do |pubkey|
|
|
23
19
|
tweak = hmac(pubkey, data).to_i(16)
|
|
24
|
-
raise
|
|
20
|
+
raise 'order exceeded, pick a new nonce' if tweak >= EC_GROUP.order.to_i
|
|
25
21
|
tweak = OpenSSL::BN.new(tweak.to_s)
|
|
26
22
|
|
|
27
|
-
key = Bitcoin::Key.new(nil, pubkey.unpack(
|
|
23
|
+
key = Bitcoin::Key.new(nil, pubkey.unpack('H*')[0])
|
|
28
24
|
key = key.instance_variable_get(:@key)
|
|
29
25
|
point = EC_GROUP.generator.mul(tweak).ec_add(key.public_key).to_bn.to_i
|
|
30
|
-
raise
|
|
26
|
+
raise 'infinity' if point == 1 / 0.0
|
|
31
27
|
|
|
32
28
|
key = Bitcoin::Key.new(nil, point.to_s(16))
|
|
33
|
-
key.instance_eval{ @pubkey_compressed = true }
|
|
29
|
+
key.instance_eval { @pubkey_compressed = true }
|
|
34
30
|
derived_keys << key.pub
|
|
35
31
|
end
|
|
36
32
|
|
|
37
33
|
m = redeem_script.get_signatures_required
|
|
38
34
|
p2sh_script, redeem_script = Bitcoin::Script.to_p2sh_multisig_script(m, *derived_keys)
|
|
39
35
|
|
|
40
|
-
[
|
|
36
|
+
[nonce_hex, redeem_script.unpack('H*')[0], Bitcoin::Script.new(p2sh_script).get_p2sh_address]
|
|
41
37
|
end
|
|
42
38
|
|
|
43
39
|
# claim a contract
|
|
@@ -45,32 +41,32 @@ module Bitcoin
|
|
|
45
41
|
key = Bitcoin::Key.from_base58(private_key_wif)
|
|
46
42
|
data = compute_data(payee_address_or_ascii, nonce_hex)[1]
|
|
47
43
|
|
|
48
|
-
pubkey = [key.pub].pack(
|
|
44
|
+
pubkey = [key.pub].pack('H*')
|
|
49
45
|
tweak = hmac(pubkey, data).to_i(16)
|
|
50
|
-
raise
|
|
46
|
+
raise 'order exceeded, verify parameters' if tweak >= EC_GROUP.order.to_i
|
|
51
47
|
|
|
52
48
|
derived_key = (tweak + key.priv.to_i(16)) % EC_GROUP.order.to_i
|
|
53
|
-
raise
|
|
49
|
+
raise 'zero' if derived_key.zero?
|
|
54
50
|
|
|
55
51
|
Bitcoin::Key.new(derived_key.to_s(16))
|
|
56
52
|
end
|
|
57
53
|
|
|
58
54
|
# compute HMAC data
|
|
59
55
|
def self.compute_data(address_or_ascii, nonce_hex)
|
|
60
|
-
nonce = nonce_hex ? [nonce_hex].pack(
|
|
56
|
+
nonce = nonce_hex ? [nonce_hex].pack('H32') : SecureRandom.random_bytes(16)
|
|
61
57
|
if Bitcoin.valid_address?(address_or_ascii)
|
|
62
58
|
address_type = case Bitcoin.address_type(address_or_ascii)
|
|
63
|
-
when :hash160
|
|
64
|
-
when :p2sh
|
|
59
|
+
when :hash160 then 'P2PH'
|
|
60
|
+
when :p2sh then 'P2SH'
|
|
65
61
|
else
|
|
66
62
|
raise "unsupported address type #{address_type}"
|
|
67
63
|
end
|
|
68
|
-
contract_bytes = [
|
|
64
|
+
contract_bytes = [Bitcoin.hash160_from_address(address_or_ascii)].pack('H*')
|
|
69
65
|
else
|
|
70
|
-
address_type =
|
|
66
|
+
address_type = 'TEXT'
|
|
71
67
|
contract_bytes = address_or_ascii
|
|
72
68
|
end
|
|
73
|
-
[
|
|
69
|
+
[nonce.unpack('H*')[0], address_type + nonce + contract_bytes]
|
|
74
70
|
end
|
|
75
71
|
end
|
|
76
72
|
end
|
data/lib/bitcoin/dogecoin.rb
CHANGED
|
@@ -1,97 +1,99 @@
|
|
|
1
1
|
# encoding: ascii-8bit
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
#
|
|
5
|
-
#
|
|
6
|
-
#
|
|
7
|
-
#
|
|
8
|
-
# the
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
# fixed reward past the 600k block
|
|
16
|
-
POST_600K_REWARD = 10000 * Bitcoin::COIN
|
|
17
|
-
|
|
18
|
-
# Dogecoin-specific Script methods for parsing and creating of dogecoin scripts,
|
|
19
|
-
# as well as methods to extract address, doge_hash, doge and value.
|
|
20
|
-
module Util
|
|
21
|
-
|
|
22
|
-
def self.included(base)
|
|
23
|
-
base.constants.each {|c| const_set(c, base.const_get(c)) unless constants.include?(c) }
|
|
24
|
-
base.class_eval do
|
|
3
|
+
module Bitcoin
|
|
4
|
+
# This module includes (almost) everything necessary to add dogecoin support
|
|
5
|
+
# to bitcoin-ruby. When switching to a :dogecoin network, it will load its
|
|
6
|
+
# functionality into the Script class.
|
|
7
|
+
# The only things not included here should be parsing the AuxPow, which is
|
|
8
|
+
# done in Protocol::Block directly, and passing the txout to #store_doge from
|
|
9
|
+
# the storage backend.
|
|
10
|
+
module Dogecoin
|
|
11
|
+
def self.load
|
|
12
|
+
Bitcoin::Util.class_eval { include Util }
|
|
13
|
+
end
|
|
25
14
|
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
15
|
+
# fixed reward past the 600k block
|
|
16
|
+
POST_600K_REWARD = 10_000 * Bitcoin::COIN
|
|
17
|
+
|
|
18
|
+
# Dogecoin-specific Script methods for parsing and creating of dogecoin scripts,
|
|
19
|
+
# as well as methods to extract address, doge_hash, doge and value.
|
|
20
|
+
module Util
|
|
21
|
+
# rubocop:disable CyclomaticComplexity,PerceivedComplexity
|
|
22
|
+
def self.included(base)
|
|
23
|
+
base.constants.each { |c| const_set(c, base.const_get(c)) unless constants.include?(c) }
|
|
24
|
+
base.class_eval do
|
|
25
|
+
def block_creation_reward(block_height)
|
|
26
|
+
reward_scaler = 2**(block_height / Bitcoin.network[:reward_halving].to_f).floor
|
|
27
|
+
if block_height < Bitcoin.network[:difficulty_change_block]
|
|
28
|
+
# Dogecoin early rewards were random, using part of the hash of the
|
|
29
|
+
# previous block as the seed for the Mersenne Twister algorithm.
|
|
30
|
+
# Given we don't have previous block hash available, and this value is
|
|
31
|
+
# functionally a maximum (not exact value), I'm using the maximum the random
|
|
32
|
+
# reward generator can produce and calling it good enough.
|
|
33
|
+
Bitcoin.network[:reward_base] / reward_scaler * 2
|
|
34
|
+
elsif block_height < 600_000
|
|
35
|
+
Bitcoin.network[:reward_base] / reward_scaler
|
|
36
|
+
else
|
|
37
|
+
POST_600K_REWARD
|
|
38
|
+
end
|
|
38
39
|
end
|
|
39
|
-
end
|
|
40
|
-
|
|
41
|
-
def block_new_target(prev_height, prev_block_time, prev_block_bits, last_retarget_time)
|
|
42
|
-
new_difficulty_protocol = (prev_height + 1) >= Bitcoin.network[:difficulty_change_block]
|
|
43
40
|
|
|
44
|
-
|
|
45
|
-
|
|
41
|
+
def block_new_target(prev_height, prev_block_time, prev_block_bits, last_retarget_time)
|
|
42
|
+
new_difficulty_protocol = (prev_height + 1) >= Bitcoin.network[:difficulty_change_block]
|
|
46
43
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
retarget_time = Bitcoin.network[:retarget_time_new]
|
|
50
|
-
end
|
|
44
|
+
# target interval for block interval in seconds
|
|
45
|
+
retarget_time = Bitcoin.network[:retarget_time]
|
|
51
46
|
|
|
52
|
-
|
|
53
|
-
|
|
47
|
+
if new_difficulty_protocol
|
|
48
|
+
# what is the ideal interval between the blocks
|
|
49
|
+
retarget_time = Bitcoin.network[:retarget_time_new]
|
|
50
|
+
end
|
|
54
51
|
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
if
|
|
59
|
-
|
|
52
|
+
# actual time elapsed since last retarget
|
|
53
|
+
actual_time = prev_block_time - last_retarget_time
|
|
54
|
+
|
|
55
|
+
if new_difficulty_protocol
|
|
56
|
+
# DigiShield implementation - thanks to RealSolid & WDC for this code
|
|
57
|
+
# We round always towards zero to match the C++ version
|
|
58
|
+
actual_time = if actual_time < retarget_time
|
|
59
|
+
retarget_time + ((actual_time - retarget_time) / 8.0).ceil
|
|
60
|
+
else
|
|
61
|
+
retarget_time + ((actual_time - retarget_time) / 8.0).floor
|
|
62
|
+
end
|
|
63
|
+
# amplitude filter - thanks to daft27 for this code
|
|
64
|
+
min = retarget_time - (retarget_time / 4)
|
|
65
|
+
max = retarget_time + (retarget_time / 2)
|
|
66
|
+
elsif prev_height + 1 > 10_000
|
|
67
|
+
min = retarget_time / 4
|
|
68
|
+
max = retarget_time * 4
|
|
69
|
+
elsif prev_height + 1 > 5000
|
|
70
|
+
min = retarget_time / 8
|
|
71
|
+
max = retarget_time * 4
|
|
60
72
|
else
|
|
61
|
-
|
|
73
|
+
min = retarget_time / 16
|
|
74
|
+
max = retarget_time * 4
|
|
62
75
|
end
|
|
63
|
-
# amplitude filter - thanks to daft27 for this code
|
|
64
|
-
min = retarget_time - (retarget_time/4)
|
|
65
|
-
max = retarget_time + (retarget_time/2)
|
|
66
|
-
elsif prev_height+1 > 10000
|
|
67
|
-
min = retarget_time / 4
|
|
68
|
-
max = retarget_time * 4
|
|
69
|
-
elsif prev_height+1 > 5000
|
|
70
|
-
min = retarget_time / 8
|
|
71
|
-
max = retarget_time * 4
|
|
72
|
-
else
|
|
73
|
-
min = retarget_time / 16
|
|
74
|
-
max = retarget_time * 4
|
|
75
|
-
end
|
|
76
76
|
|
|
77
|
-
|
|
78
|
-
|
|
77
|
+
actual_time = min if actual_time < min
|
|
78
|
+
actual_time = max if actual_time > max
|
|
79
79
|
|
|
80
|
-
|
|
81
|
-
|
|
80
|
+
# It could be a bit confusing: we are adjusting difficulty of the previous block,
|
|
81
|
+
# while logically we should use difficulty of the previous 2016th block ("first")
|
|
82
82
|
|
|
83
|
-
|
|
83
|
+
prev_target = decode_compact_bits(prev_block_bits).to_i(16)
|
|
84
84
|
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
85
|
+
new_target = prev_target * actual_time / retarget_time
|
|
86
|
+
if new_target < Bitcoin.decode_compact_bits(
|
|
87
|
+
Bitcoin.network[:proof_of_work_limit]
|
|
88
|
+
).to_i(16)
|
|
89
|
+
encode_compact_bits(new_target.to_s(16))
|
|
90
|
+
else
|
|
91
|
+
Bitcoin.network[:proof_of_work_limit]
|
|
92
|
+
end
|
|
90
93
|
end
|
|
91
94
|
end
|
|
92
95
|
end
|
|
96
|
+
# rubocop:enable CyclomaticComplexity,PerceivedComplexity
|
|
93
97
|
end
|
|
94
|
-
|
|
95
98
|
end
|
|
96
|
-
|
|
97
99
|
end
|
|
@@ -1,10 +1,9 @@
|
|
|
1
1
|
# encoding: ascii-8bit
|
|
2
2
|
|
|
3
|
+
# ruby version of: https://github.com/spesmilo/electrum/blob/master/lib/mnemonic.py
|
|
3
4
|
class Mnemonic
|
|
4
|
-
# ruby version of: https://github.com/spesmilo/electrum/blob/master/lib/mnemonic.py
|
|
5
|
-
|
|
6
5
|
# list of words from http://en.wiktionary.org/wiki/Wiktionary:Frequency_lists/Contemporary_poetry
|
|
7
|
-
|
|
6
|
+
WORDS = <<-TEXT.split
|
|
8
7
|
like just love know never want time out there make look eye down only think
|
|
9
8
|
heart back then into about more away still them take thing even through long always
|
|
10
9
|
world too friend tell try hand thought over here other need smile again much cry
|
|
@@ -116,47 +115,51 @@ class Mnemonic
|
|
|
116
115
|
thigh throne total unseen weapon weary
|
|
117
116
|
TEXT
|
|
118
117
|
|
|
119
|
-
def self.encode(hex, words=
|
|
118
|
+
def self.encode(hex, words = WORDS)
|
|
120
119
|
n = words.size
|
|
121
|
-
[hex].pack(
|
|
120
|
+
[hex].pack('H*').unpack('N*').map do |x|
|
|
122
121
|
w1 = x % n
|
|
123
122
|
w2 = ((x / n) + w1) % n
|
|
124
123
|
w3 = ((x / n / n) + w2) % n
|
|
125
|
-
[
|
|
126
|
-
|
|
124
|
+
[words[w1], words[w2], words[w3]]
|
|
125
|
+
end.flatten
|
|
127
126
|
end
|
|
128
127
|
|
|
129
|
-
def self.decode(word_list, words=
|
|
128
|
+
def self.decode(word_list, words = WORDS)
|
|
130
129
|
n = words.size
|
|
131
|
-
word_list.each_slice(3).map
|
|
132
|
-
w1, w2, w3 = three_words.map{|word| words.index(word) % n }
|
|
133
|
-
'%08x'
|
|
134
|
-
|
|
130
|
+
word_list.each_slice(3).map do |three_words|
|
|
131
|
+
w1, w2, w3 = three_words.map { |word| words.index(word) % n }
|
|
132
|
+
format('%08x', (w1 + n * ((w2 - w1) % n) + n * n * ((w3 - w2) % n)))
|
|
133
|
+
end.join
|
|
135
134
|
end
|
|
136
|
-
|
|
137
135
|
end
|
|
138
136
|
|
|
137
|
+
if $PROGRAM_NAME == __FILE__
|
|
138
|
+
hex = '4c7d10656aa55383a5d88e3f63300af5e169918f4058bf349d99b20239909b61'
|
|
139
|
+
expected_words = %w[horse love nose speak diamond gaze wash drag glance
|
|
140
|
+
money cease soft complete huge aside confusion touch
|
|
141
|
+
grass pie play bread exactly bubble great]
|
|
139
142
|
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
hex = "4c7d10656aa55383a5d88e3f63300af5e169918f4058bf349d99b20239909b61"
|
|
143
|
-
expected_words = ['horse', 'love', 'nose', 'speak', 'diamond', 'gaze', 'wash', 'drag', 'glance',
|
|
144
|
-
'money', 'cease', 'soft', 'complete', 'huge', 'aside', 'confusion', 'touch',
|
|
145
|
-
'grass', 'pie', 'play', 'bread', 'exactly', 'bubble', 'great']
|
|
143
|
+
p Mnemonic.encode(hex) == expected_words
|
|
144
|
+
p Mnemonic.decode(expected_words) == hex
|
|
146
145
|
|
|
147
146
|
# from http://brainwallet.org/#chains
|
|
148
|
-
hex =
|
|
147
|
+
hex = 'ff64b72c431f75799f0c5ebe438e46dd'
|
|
149
148
|
expected_words = %w[muscle lot sea got revenge crack wait yeah gas study embrace spend]
|
|
150
|
-
hex
|
|
149
|
+
p Mnemonic.encode(hex) == expected_words
|
|
150
|
+
p Mnemonic.decode(expected_words) == hex
|
|
151
|
+
|
|
152
|
+
hex = '18cfaf96961750c7a4e4e39c861d1415'
|
|
151
153
|
expected_words = %w[example poor twice expect decision master blame rub forward easy jump carve]
|
|
154
|
+
p Mnemonic.encode(hex) == expected_words
|
|
155
|
+
p Mnemonic.decode(expected_words) == hex
|
|
152
156
|
|
|
153
157
|
# from https://en.bitcoin.it/wiki/Electrum#Brain_Wallet
|
|
154
|
-
hex =
|
|
158
|
+
hex = '431a62f1c86555d3c45e5c4d9e10c8c7'
|
|
155
159
|
expected_words = %w[constant forest adore false green weave stop guy fur freeze giggle clock]
|
|
156
160
|
|
|
157
|
-
#p Mnemonic.encode(hex)
|
|
161
|
+
# p Mnemonic.encode(hex)
|
|
158
162
|
p Mnemonic.encode(hex) == expected_words
|
|
159
|
-
#p Mnemonic.decode(expected_words)
|
|
163
|
+
# p Mnemonic.decode(expected_words)
|
|
160
164
|
p Mnemonic.decode(expected_words) == hex
|
|
161
165
|
end
|
|
162
|
-
|