1
0
mirror of https://github.com/bitcoinbook/bitcoinbook synced 2024-12-27 08:58:08 +00:00

Merge branch 'develop' with libbitcoin and bx updates, misc edits and typo fixes

This commit is contained in:
Andreas M. Antonopoulos 2015-02-23 17:21:09 -05:00
commit 733bde3e65
10 changed files with 295 additions and 266 deletions

View File

@ -2,12 +2,15 @@
Mastering Bitcoin is a book for developers, but the first two chapters cover bitcoin at a level that is approachable to non-programmers. Anyone with a basic understanding of technology can read the first two chapters and get a great understanding of bitcoin. Mastering Bitcoin is a book for developers, but the first two chapters cover bitcoin at a level that is approachable to non-programmers. Anyone with a basic understanding of technology can read the first two chapters and get a great understanding of bitcoin.
# Contributing # Published
To contribute to this book, please fork and make changes to your forked copy, then submit a pull request. Or alternatively, if you cannot use the github.com pull request system, submit an Issue from the menu on the right. Major contributions will receive an acknowledgment in the preface of the book. "Mastering Bitcoin" is now available in print and e-book formats by many book sellers including [Amazon](http://www.amazon.com/Mastering-Bitcoin-Unlocking-Digital-Crypto-Currencies/dp/1449374042)
, [Barnes & Nobles](http://www.barnesandnoble.com/w/mastering-bitcoin-andreas-m-antonopoulos/1119253039?ean=9781449374044
) and [O'Reilly Media](http://shop.oreilly.com/product/0636920032281.do). For a limited time, the book is also sold for bitcoin at the [author's site](http://bitcoinbook.info)
# Purchasing # Source
"Mastering Bitcoin" will be available in print and e-book format in Fall 2014. To pre-order your copy, please visit: The book's source code, found in this repository, is a near-final draft before the publisher's editorial process. Please do not submit changes here, instead use the [errata](http://www.oreilly.com/catalog/errata.csp?isbn=0636920032281) page on the publisher's site.
http://bitcoinbook.info
<a rel="license" href="http://creativecommons.org/licenses/by-nc-nd/4.0/"><img alt="Creative Commons License" style="border-width:0" src="https://i.creativecommons.org/l/by-nc-nd/4.0/88x31.png" /></a><br /><span xmlns:dct="http://purl.org/dc/terms/" property="dct:title">Mastering Bitcoin: Unlocking digital crypto-currencies</span> by <a xmlns:cc="http://creativecommons.org/ns#" href="http://antonopoulos.com/" property="cc:attributionName" rel="cc:attributionURL">Andreas M. Antonopoulos LLC</a> is licensed under a <a rel="license" href="http://creativecommons.org/licenses/by-nc-nd/4.0/">Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License</a>.

186
appdx-bx.asciidoc Normal file
View File

@ -0,0 +1,186 @@
[[appdx_bx]]
[appendix]
== Available Bitcoin Explorer Commands
((("Bitcoin Explorer commands","commands in", id="ix_appdx-bx-asciidoc0", range="startofrange")))
----
Usage: bx COMMAND [--help]
Info: The bx commands are:
address-decode
address-embed
address-encode
address-validate
base16-decode
base16-encode
base58-decode
base58-encode
base58check-decode
base58check-encode
base64-decode
base64-encode
bitcoin160
bitcoin256
btc-to-satoshi
ec-add
ec-add-secrets
ec-multiply
ec-multiply-secrets
ec-new
ec-to-address
ec-to-public
ec-to-wif
fetch-balance
fetch-header
fetch-height
fetch-history
fetch-stealth
fetch-tx
fetch-tx-index
hd-new
hd-private
hd-public
hd-to-address
hd-to-ec
hd-to-public
hd-to-wif
help
input-set
input-sign
input-validate
message-sign
message-validate
mnemonic-decode
mnemonic-encode
ripemd160
satoshi-to-btc
script-decode
script-encode
script-to-address
seed
send-tx
send-tx-node
send-tx-p2p
settings
sha160
sha256
sha512
stealth-decode
stealth-encode
stealth-public
stealth-secret
stealth-shared
tx-decode
tx-encode
uri-decode
uri-encode
validate-tx
watch-address
wif-to-ec
wif-to-public
wrap-decode
wrap-encode
Bitcoin Explorer home page:
https://github.com/libbitcoin/libbitcoin-explorer
Bitcoin Explorer user documentation:
https://github.com/libbitcoin/libbitcoin-explorer/wiki
----
Next, we look at some examples of using Bitcoin Explorer commands to experiment with keys and addresses.
Generate a random "seed" value using the((("Bitcoin Explorer","seed command")))((("seed command (bx)"))) +seed+ command, which uses the operating system's random number generator. Pass the seed to the((("Bitcoin Explorer","ec-new command")))((("ec-new command (bx)"))) +ec-new+ command to generate a new private key. We save the standard output into the file _private_key_:
----
$ bx seed | bx ec-new > private_key
$ cat private_key
73096ed11ab9f1db6135857958ece7d73ea7c30862145bcc4bbc7649075de474
----
Now, generate the public key from that private key using the((("Bitcoin Explorer","ec-to-public command")))((("ec-to-public command (bx)"))) +ec-to-public+ command. We pass the _private_key_ file into the standard input and save the standard output of the command into a new file _public_key_:
----
$ bx ec-to-public < private_key > public_key
$ cat public_key
02fca46a6006a62dfdd2dbb2149359d0d97a04f430f12a7626dd409256c12be500
----
We can reformat the +public_key+ as an address using the((("Bitcoin Explorer","ec-to-address command")))((("ec-to-address command (bx)"))) +ec-to-address+ command. We pass the _public_key_ into standard input:
----
$ bx ec-to-address < public_key
17re1S4Q8ZHyCP8Kw7xQad1Lr6XUzWUnkG
----
Keys generated in this manner produce a type-0 nondeterministic wallet. That means that each key is generated from an independent seed. Bitcoin Explorer commands can also generate keys deterministically, in accordance with BIP0032. In this case a "master" key is created from a seed and then extended deterministically to produce a tree of subkeys, resulting in a type-2 deterministic wallet.
First, we we use the((("Bitcoin Explorer","seed command")))((("seed command (bx)"))) +seed+ and((("Bitcoin Explorer","hd-new command")))((("hd-new command (bx)"))) +hd-new+ commands to generate a master key that will be used as the basis to derive a hierarchy of keys.
----
$ bx seed > seed
$ cat seed
eb68ee9f3df6bd4441a9feadec179ff1
$ bx hd-new < seed > master
$ cat master
xprv9s21ZrQH143K2BEhMYpNQoUvAgiEjArAVaZaCTgsaGe6LsAnwubeiTcDzd23mAoyizm9cApe51gNfLMkBqkYoWWMCRwzfuJk8RwF1SVEpAQ
----
We now use the((("Bitcoin Explorer","hd-private command")))((("hd-private command (bx)"))) +hd-private+ command to generate a hardened "account" key and a sequence of two private keys within the account.
----
$ bx hd-private --hard < master > account
$ cat account
xprv9vkDLt81dTKjwHB8fsVB5QK8cGnzveChzSrtCfvu3aMWvQaThp59ueufuyQ8Qi3qpjk4aKsbmbfxwcgS8PYbgoR2NWHeLyvg4DhoEE68A1n
$ bx hd-private --index 0 < account
xprv9xHfb6w1vX9xgZyPNXVgAhPxSsEkeRcPHEUV5iJcVEsuUEACvR3NRY3fpGhcnBiDbvG4LgndirDsia1e9F3DWPkX7Tp1V1u97HKG1FJwUpU
$ bx hd-private --index 1 < account
xprv9xHfb6w1vX9xjc8XbN4GN86jzNAZ6xHEqYxzbLB4fzHFd6VqCLPGRZFsdjsuMVERadbgDbziCRJru9n6tzEWrASVpEdrZrFidt1RDfn4yA3
----
Next we use the((("Bitcoin Explorer","hd-public command")))((("hd-public command (bx)"))) +hd-public+ command to generate the corresponding sequence of two public keys.
----
$ bx hd-public --index 0 < account
xpub6BH1zcTuktiFu43rUZ2gXqLgzu5F3tLEeTQ5t6iE3aQtM2VMTxMcyLN9fYHiGhGpQe9QQYmqL2eYPFJ3vezHz5wzaSW4FiGrseNDR4LKqTy
$ bx hd-public --index 1 < account
xpub6BH1zcTuktiFx6CzhPbGjG3UYQ13WR16CmtbPiagEKpEVtpyjshWyMaMV1cn7nUPUkgQHPVXJVqsrA8xWbGQDhohEcDFTEYMvYzwRD7Juf8
----
The public keys can also be derived from their corresponding private keys using the((("Bitcoin Explorer","hd-to-public command")))((("hd-to-public command (bx)"))) +hd-to-public+ command.
----
$ bx hd-private --index 0 < account | bx hd-to-public
xpub6BH1zcTuktiFu43rUZ2gXqLgzu5F3tLEeTQ5t6iE3aQtM2VMTxMcyLN9fYHiGhGpQe9QQYmqL2eYPFJ3vezHz5wzaSW4FiGrseNDR4LKqTy
$ bx hd-private --index 1 < account | bx hd-to-public
xpub6BH1zcTuktiFx6CzhPbGjG3UYQ13WR16CmtbPiagEKpEVtpyjshWyMaMV1cn7nUPUkgQHPVXJVqsrA8xWbGQDhohEcDFTEYMvYzwRD7Juf8
----
We can generate a practically limitless number of keys in a deterministic chain, all derived from a single seed. This technique is used in many wallet applications to generate keys that can be backed up and restored with a single seed value. This is easier than having to back up the wallet with all its randomly generated keys every time a new key is created.
The seed can be encoded using the((("Bitcoin Explorer","mnemonic-encode command")))((("mnemonic-encode command (bx)"))) +mnemonic-encode+ command.
----
$ bx hd-mnemonic < seed > words
adore repeat vision worst especially veil inch woman cast recall dwell appreciate
----
The seed can then be decoded using the((("Bitcoin Explorer","mnemonic-decode command")))((("mnemonic-decode command (bx)"))) +mnemonic-decode+ command.
----
$ bx mnemonic-decode < words
eb68ee9f3df6bd4441a9feadec179ff1
----
Mnemonic encoding can make the seed easier to record and even remember.(((range="endofrange", startref="ix_appdx-bx-asciidoc0")))

View File

@ -1,211 +0,0 @@
[[appdx_sx]]
[appendix]
== Available Commands with sx Tools
((("sx tools","commands in", id="ix_appdx-sx-asciidoc0", range="startofrange")))
----
The sx commands are:
DEPRECATED
ELECTRUM STYLE DETERMINISTIC KEYS AND ADDRESSES
genaddr Generate a Bitcoin address deterministically from a wallet
seed or master public key.
genpriv Generate a private key deterministically from a seed.
genpub Generate a public key deterministically from a wallet
seed or master public key.
mpk Extract a master public key from a deterministic wallet seed.
newseed Create a new deterministic wallet seed.
EXPERIMENTAL
APPS
wallet Experimental command-line wallet.
OFFLINE BLOCKCHAIN
HEADERS
showblkhead Show the details of a block header.
OFFLINE KEYS AND ADDRESSES
BASIC
addr See Bitcoin address of a public or private key.
embed-addr Generate an address used for embedding record of data into the
blockchain
get-pubkey Get the pubkey of an address if available.
newkey Create a new private key.
pubkey See the public part of a private key.
validaddr Validate an address.
BRAIN STORAGE
brainwallet Make 256 bit bitcoin private key from an arbitrary passphrase.
mnemonic Make 12 word mnemonic out of 128 bit electrum or bip32 seed.
HD / BIP32
hd-priv Create a private HD key from another HD private key.
hd-pub Create an HD public key from another HD private or public key.
hd-seed Create a random new HD key.
hd-to-address Convert an HD public or private key to a Bitcoin address.
hd-to-wif Convert an HD private key to a WIF private key.
MULTISIG ADDRESSES
scripthash Create BIP 16 script hash address from raw script hex.
STEALTH
stealth-addr See a stealth address from given input.
stealth-initiate Initiate a new stealth payment.
stealth-newkey Generate new stealth keys and an address.
stealth-show-addr Show details for a stealth address.
stealth-uncover Uncover a stealth address.
stealth-uncover-secret Uncover a stealth secret.
OFFLINE TRANSACTIONS
SCRIPTING
mktx Create an unsigned tx.
rawscript Create the raw hex representation from a script.
set-input Set a transaction input.
showscript Show the details of a raw script.
showtx Show the details of a transaction.
sign-input Sign a transaction input.
unwrap Validates checksum and recovers version byte and original data
from hexstring.
validsig Validate a transaction input's signature.
wrap Adds version byte and checksum to hexstring.
ONLINE (BITCOIN P2P)
BLOCKCHAIN UPDATES
sendtx-node Send transaction to a single node.
sendtx-p2p Send tx to bitcoin network.
ONLINE (BLOCKCHAIN.INFO)
BLOCKCHAIN QUERIES (blockchain.info)
bci-fetch-last-height Fetch the last block height using blockchain.info.
bci-history Get list of output points, values, and their spends
from blockchain.info
BLOCKCHAIN UPDATES
sendtx-bci Send tx to blockchain.info/pushtx.
ONLINE (BLOCKEXPLORER.COM)
BLOCKCHAIN QUERIES (blockexplorer.com)
blke-fetch-transaction Fetches a transaction from blockexplorer.com
ONLINE (OBELISK)
BLOCKCHAIN QUERIES
balance Show balance of a Bitcoin address in satoshis.
fetch-block-header Fetch raw block header.
fetch-last-height Fetch the last block height.
fetch-stealth Fetch a stealth information using a network connection
to make requests against the obelisk load balancer backend.
fetch-transaction Fetch a raw transaction using a network connection to
make requests against the obelisk load balancer
backend.
fetch-transaction-index
Fetch block height and index in block of transaction.
get-utxo Get enough unspent transaction outputs from a given set
of addresses to pay a given number of satoshis.
history Get list of output points, values, and their spends for
an address. grep can filter for just unspent outputs which can
be fed into mktx.
validtx Validate a transaction.
BLOCKCHAIN UPDATES
sendtx-obelisk Send tx to obelisk server.
BLOCKCHAIN WATCHING
monitor Monitor an address.
watchtx Watch transactions from the network searching for a certain
hash.
OBELISK ADMIN
initchain Initialize a new blockchain.
UTILITY
EC MATH
ec-add-modp Calculate the result of INTEGER + INTEGER.
ec-multiply Multiply an integer and a point together.
ec-tweak-add Calculate the result of POINT + INTEGER * G.
FORMAT (BASE 58)
base58-decode Convert from base58 to hex.
base58-encode Convert from hex to base58.
FORMAT (BASE58CHECK)
base58check-decode Convert from base58check to hex.
base58check-encode Convert from hex to base58check.
decode-addr Decode a address from base58check form to internal RIPEMD
representation.
encode-addr Encode an address from internal RIPEMD representation to
base58check form.
FORMAT (WIF)
secret-to-wif Convert a secret exponent value to Wallet Import Format.
wif-to-secret Convert a Wallet Import Format to secret exponent value.
HASHES
ripemd-hash RIPEMD hash data from STDIN.
sha256 Perform SHA256 hash of data.
MISC
qrcode Generate Bitcoin QR codes offline.
SATOSHI MATH
btc Convert Satoshis into Bitcoins.
satoshi Convert Bitcoins into Satoshis.
See 'sx help COMMAND' for more information on a specific command.
----
Next, we look at some examples of using sx tools to experiment with keys and addresses.
Generate a new private key with the operating system's random number generator by using the +newkey+ command. We save the standard output into the file _private_key_:
----
$ sx newkey > private_key
$ cat private_key
5Jgx3UAaXw8AcCQCi1j7uaTaqpz2fqNR9K3r4apxdYn6rTzR1PL
----
Now, generate the public key from that private key using the +pubkey+ command. Pass the _private_key_ file into the standard input and save the standard output of the command into a new file _public_key_:
----
$ sx pubkey < private_key > public_key
$ cat public_key
02fca46a6006a62dfdd2dbb2149359d0d97a04f430f12a7626dd409256c12be500
----
We can reformat the +public_key+ as an address using the +addr+ command. We pass the +public_key+ into standard input:
----
$ sx addr < public_key
17re1S4Q8ZHyCP8Kw7xQad1Lr6XUzWUnkG
----
The keys generated are so called type-0 nondeterministic keys. That means that each one is generated from a random number generator. The sx tools also support type-2 deterministic keys, where a "master" key is created and then extended to produce a chain or tree of subkeys.
First, we generate a "seed" that will be used as the basis to derive a chain of keys, compatible with the Electrum wallet and other similar implementations. We use the +newseed+ command to produce a seed value:
----
$ sx newseed > seed
$ cat seed
eb68ee9f3df6bd4441a9feadec179ff1
----
The seed value can also be exported as a word mnemonic that is human readable and easier to store and type than a hexadecimal string
using the +mnemonic+ command:
----
$ sx mnemonic < seed > words
$ cat words
adore repeat vision worst especially veil inch woman cast recall dwell appreciate
----
The mnemonic words can be used to reproduce the seed using the +mnemonic+ command again:
----
$ sx mnemonic < words
eb68ee9f3df6bd4441a9feadec179ff1
----
With the seed, we can now generate a sequence of private and public keys, a key chain. We use the +genpriv+ command to generate a sequence of private keys from a seed and the +addr+ command to generate the corresponding public key:
[source,bash]
----
$ sx genpriv 0 < seed
5JzY2cPZGViPGgXZ4Syb9Y4eUGjJpVt6sR8noxrpEcqgyj7LK7i
$ sx genpriv 0 < seed | sx addr
1esVQV2vR9JZPhFeRaeWkAhzmWq7Fi7t7
$ sx genpriv 1 < seed
5JdtL7ckAn3iFBFyVG1Bs3A5TqziFTaB9f8NeyNo8crnE2Sw5Mz
$ sx genpriv 1 < seed | sx addr
1G1oTeXitk76c2fvQWny4pryTdH1RTqSPW
----
With deterministic keys we can generate and regenerate thousands of keys, all derived from a single seed in a deterministic chain. This technique is used in many wallet applications to generate keys that can be backed up and restored with a simple multiword mnemonic. This is easier than having to back up the wallet with all its randomly generated keys every time a new key is created.(((range="endofrange", startref="ix_appdx-sx-asciidoc0")))

View File

@ -34,7 +34,7 @@ include::appdx-bips.asciidoc[]
include::appdx-pycoin.asciidoc[] include::appdx-pycoin.asciidoc[]
include::appdx-sx.asciidoc[] include::appdx-bx.asciidoc[]
include::index.asciidoc[] include::index.asciidoc[]

View File

@ -1131,7 +1131,9 @@ As before, we can also examine this in more detail using the +getrawtransaction+
Alternative implementations include: Alternative implementations include:
https://libbitcoin.dyne.org/[libbitcoin and sx tools]:: A C++ multithreaded full-node client and library with command-line tools https://github.com/libbitcoin/libbitcoin[libbitcoin]:: ((("libbitcoin library")))Bitcoin Cross-Platform C++ Development Toolkit
https://github.com/libbitcoin/libbitcoin-explorer[bitcoin explorer]:: ((("Bitcoin Explorer")))Bitcoin Command Line Tool
https://github.com/libbitcoin/libbitcoin-server[bitcoin server]:: ((("Bitcoin Server")))Bitcoin Full Node and Query Server
https://code.google.com/p/bitcoinj/[bitcoinj]:: ((("BitcoinJ library")))A Java full-node client library https://code.google.com/p/bitcoinj/[bitcoinj]:: ((("BitcoinJ library")))A Java full-node client library
https://opensource.conformal.com/wiki/btcd[btcd]:: ((("btcd","client")))A Go language full-node bitcoin client https://opensource.conformal.com/wiki/btcd[btcd]:: ((("btcd","client")))A Go language full-node bitcoin client
https://bitsofproof.com[Bits of Proof (BOP)]:: ((("Bits of Proof (BOP)")))A Java enterprise-class implementation of bitcoin https://bitsofproof.com[Bits of Proof (BOP)]:: ((("Bits of Proof (BOP)")))A Java enterprise-class implementation of bitcoin
@ -1141,26 +1143,39 @@ https://github.com/richardkiss/pycoin[pycoin]:: ((("pycoin library")))Another Py
Many more libraries exist in a variety of other programming languages and more are created all the time. Many more libraries exist in a variety of other programming languages and more are created all the time.
[[sx_tools]] [[libbitcoin]]
==== Libbitcoin and sx Tools ==== Libbitcoin and Bitcoin Explorer
((("libbitcoin library")))((("libraries, alternative","libbitcoin library")))((("sx tools")))The libbitcoin library is a C++ scalable multithreaded and modular implementation that supports a full-node client and a command-line toolset called sx, which offers many of the same capabilities as the bitcoind client commands we illustrated in this chapter. The sx tools also offer some key management and manipulation tools that are not offered by bitcoind, including type-2 deterministic keys and key mnemonics. The ((("libbitcoin library")))((("libraries, alternative","libbitcoin library")))libbitcoin library is a cross-platform C++ development toolkit that supports the ((("Bitcoin Server")))((("libraries, alternative","Bitcoin Server")))libbitcoin-server full node and the ((("Bitcoin Explorer")))((("libraries, alternative","Bitcoin Explorer")))Bitcoin Explorer (bx) command line tool.
===== Installing sx The bx commands offer many of the same capabilities as the bitcoind client commands we illustrated in this chapter. The bx commands also offer some key management and manipulation tools that are not offered by bitcoind, including type-2 deterministic keys and mnemonic key encoding, as well as stealth address, payment and query support.
((("sx tools","installing")))To install sx and the supporting library libbitcoin, download and run the online installer on a Linux system: ===== Installing Bitcoin Explorer
[source,bash] ((("Bitcoin Explorer","installing")))To use Bitcoin Explorer simply download the signed executable for your operating system. Builds are available for mainnet and testnet for Linux, OSX and Windows.
----
$ wget http://sx.dyne.org/install-sx.sh
$ sudo bash ./install-sx.sh
----
You should now have the sx tools installed. Type +sx+ with no parameters to display the help text, which lists all the available commands (see <<appdx_sx>>). https://github.com/libbitcoin/libbitcoin-explorer/wiki/Download
Type +bx+ with no parameters to display the list of all available commands (see <<appdx_bx>>).
Bitcoin Explorer also provides an installer for building from sources on Linux and OSX as well as Visual Studio projects for Windows. Sources can also be built manually using Autotools. These also install the ((("libbitcoin library","installing")))libbitcoin library dependency.
https://github.com/libbitcoin/libbitcoin-explorer/wiki/Build
[TIP] [TIP]
==== ====
The sx toolkit offers many useful commands for encoding and decoding addresses, and converting to and from different formats and representations. Use them to explore the various formats such as Base58, Base58Check, hex, etc. Bitcoin Explorer offers many useful commands for encoding and decoding addresses, and converting to and from different formats and representations. Use them to explore the various formats such as Base16 (hex), Base58, Base58Check, Base64, etc.
====
===== Installing Libbitcoin
((("libbitcoin library","installing")))The libbitcoin library provides an installer for building from sources on Linux and OSX as well as Visual Studio projects for Windows. Sources can also be built manually using Autotools.
https://github.com/libbitcoin/libbitcoin/wiki/Build
[TIP]
====
The Bitcoin Explorer installer installs both bx and the libbitcoin library, so if you have built bx from sources you can skip this step.
==== ====
==== pycoin ==== pycoin

View File

@ -87,10 +87,10 @@ The +dumpprivkey+ command opens the wallet and extracts the private key that was
The +dumpprivkey+ command is not generating a private key from a public key, as this is impossible. The command simply reveals the private key that is already known to the wallet and which was generated by the getnewaddress command. The +dumpprivkey+ command is not generating a private key from a public key, as this is impossible. The command simply reveals the private key that is already known to the wallet and which was generated by the getnewaddress command.
===================================================================== =====================================================================
You can also use the command-line sx tools (see <<sx_tools>>) to generate and display private keys with the sx command +newkey+: (((range="endofrange", startref="ix_ch04-asciidoc3")))(((range="endofrange", startref="ix_ch04-asciidoc2")))(((range="endofrange", startref="ix_ch04-asciidoc1"))) You can also use the Bitcoin Explorer command-line tool (see <<libbitcoin>>) to generate and display private keys with the commands((("Bitcoin Explorer","seed command")))((("seed command (bx)"))) +seed+,((("Bitcoin Explorer","ec-new command")))((("ec-new command (bx)"))) +ec-new+ and((("Bitcoin Explorer","ec-to-wif command")))((("ec-to-wif command (bx)"))) +ec-to-wif+: (((range="endofrange", startref="ix_ch04-asciidoc3")))(((range="endofrange", startref="ix_ch04-asciidoc2")))(((range="endofrange", startref="ix_ch04-asciidoc1")))
---- ----
$ sx newkey $ bx seed | bx ec-new | bx ec-to-wif
5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn
---- ----
@ -340,7 +340,7 @@ Address: 1PRTTaJesdNovgne6Ehcdu1fpEdX7913CK
[[priv_formats]] [[priv_formats]]
===== Private key formats ===== Private key formats
((("private keys","format")))((("sx tools","modifying private key formats with")))The private key can be represented in a number of different formats, all of which correspond to the same 256-bit number. <<table_4-2>> shows three common formats used to represent private keys. ((("private keys","format")))((("Bitcoin Explorer","modifying private key formats with")))The private key can be represented in a number of different formats, all of which correspond to the same 256-bit number. <<table_4-2>> shows three common formats used to represent private keys.
[[table_4-2]] [[table_4-2]]
.Private key representations (encoding formats) .Private key representations (encoding formats)
@ -359,38 +359,63 @@ Address: 1PRTTaJesdNovgne6Ehcdu1fpEdX7913CK
[options="header"] [options="header"]
|======= |=======
|Format | Private Key |Format | Private Key
| Hex | 1E99423A4ED27608A15A2616A2B0E9E52CED330AC530EDCC32C8FFC6A526AEDD | Hex | 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd
| WIF | 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn | WIF | 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn
| WIF-compressed | KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ | WIF-compressed | KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ
|======= |=======
All of these representations are different ways of showing the same number, the same private key. They look different, but any one format can easily be converted to any other format. All of these representations are different ways of showing the same number, the same private key. They look different, but any one format can easily be converted to any other format.
===== Decode from Base58Check to hex We use the((("Bitcoin Explorer","wif-to-ec command")))((("wif-to-ec command (bx)"))) +wif-to-ec+ command from Bitcoin Explorer (see <<libbitcoin>>) to show that both WIF keys represent the same private key:
((("Base58Check encoding","decoding to hex")))((("sx tools","decoding Base58Check to/from hex")))The sx tools package (See <<sx_tools>>) makes it easy to write shell scripts and command-line "pipes" that manipulate bitcoin keys, addresses, and transactions. You can use sx tools to decode the Base58Check format on the command line.
We use the((("base58check-decode command (sx tools)"))) +base58check-decode+ command:
---- ----
$ sx base58check-decode 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn $ bx wif-to-ec 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn
1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd 128 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd
$ bx wif-to-ec KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ
1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd
---- ----
The result is the hexadecimal key, followed by the Wallet Import Format (WIF) version prefix 128. ===== Decode from Base58Check
((("Base58Check encoding","decoding to hex")))The Bitcoin Explorer commands (see <<libbitcoin>>) make it easy to write shell scripts and command-line "pipes" that manipulate bitcoin keys, addresses, and transactions. You can use Bitcoin Explorer to decode the Base58Check format on the command line.
We use the((("Bitcoin Explorer","base58check-decode command")))((("base58check-decode command (bx)"))) +base58check-decode+ command to decode the uncompressed key:
----
$ bx base58check-decode 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn
wrapper
{
checksum 4286807748
payload 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd
version 128
}
----
The result contains the key as payload, the Wallet Import Format (WIF) version prefix 128, and a checksum.
Notice that the "payload" of the compressed key is appended with the suffix +01+, signalling that the derived public key is to be compressed.
----
$ bx base58check-decode KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ
wrapper
{
checksum 2339607926
payload 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd01
version 128
}
----
===== Encode from hex to Base58Check ===== Encode from hex to Base58Check
((("Base58Check encoding","from hex")))To encode into Base58Check (the opposite of the previous command), we provide the hex private key, followed by the((("Base58Check encoding","WIF prefix for")))((("Wallet Import Format (WIF)"))) Wallet Import Format (WIF) version prefix 128: ((("Base58Check encoding","from hex")))To encode into Base58Check (the opposite of the previous command), we use the((("Bitcoin Explorer","base58check-encode command")))((("base58check-encode command (bx)"))) +base58check-encode+ command from Bitcoin Explorer (see <<libbitcoin>>) and provide the hex private key, followed by the((("Base58Check encoding","WIF prefix for")))((("Wallet Import Format (WIF)"))) Wallet Import Format (WIF) version prefix 128:
---- ----
$ sx base58check-encode 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd 128 bx base58check-encode 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd --version 128
5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn 5J3mBbAH58CpQ3Y5RNJpUKPE62SQ5tfcvU2JpbnkeyhfsYB1Jcn
---- ----
===== Encode from hex (compressed key) to Base58Check encoding ===== Encode from hex (compressed key) to Base58Check
((("compressed keys","encoding/decoding from Base58Check")))To encode into Base58Check as a "compressed" private key (see <<comp_priv>>), we add the suffix +01+ to the end of the hex key and then encode as above: ((("compressed keys","encoding/decoding from Base58Check")))To encode into Base58Check as a "compressed" private key (see <<comp_priv>>), we append the suffix +01+ to the hex key and then encode as above:
---- ----
$ sx base58check-encode 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd01 128 $ bx base58check-encode 1e99423a4ed27608a15a2616a2b0e9e52ced330ac530edcc32c8ffc6a526aedd01 --version 128
KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ KxFC1jmwwCoACiCAWZ3eXa96mBM6tb3TYzGmf6YwgdGWZgawvrtJ
---- ----
@ -626,7 +651,7 @@ fce540af281bf7cdeade0dd2c1c795bd02f1e4049e205a0158906c343
((("deterministic wallets","hierarchical", id="ix_ch04-asciidoc24", range="startofrange")))((("hierarchical deterministic wallets (HD wallets)", id="ix_ch04-asciidoc25", range="startofrange")))((("BIP0032", id="ix_ch04-asciidoc25a", range="startofrange")))((("BIP0044", id="ix_ch04-asciidoc25b", range="startofrange")))Deterministic wallets were developed to make it easy to derive many keys from a single "seed." The most advanced form of deterministic wallets is the _hierarchical deterministic wallet_ or _HD wallet_ defined by the BIP0032 standard. Hierarchical deterministic wallets contain keys derived in a tree structure, such that a parent key can derive a sequence of children keys, each of which can derive a sequence of grandchildren keys, and so on, to an infinite depth. This tree structure is illustrated in <<Type2_wallet>>.((("hierarchical deterministic wallets (HD wallets)","tree structure for"))) ((("deterministic wallets","hierarchical", id="ix_ch04-asciidoc24", range="startofrange")))((("hierarchical deterministic wallets (HD wallets)", id="ix_ch04-asciidoc25", range="startofrange")))((("BIP0032", id="ix_ch04-asciidoc25a", range="startofrange")))((("BIP0044", id="ix_ch04-asciidoc25b", range="startofrange")))Deterministic wallets were developed to make it easy to derive many keys from a single "seed." The most advanced form of deterministic wallets is the _hierarchical deterministic wallet_ or _HD wallet_ defined by the BIP0032 standard. Hierarchical deterministic wallets contain keys derived in a tree structure, such that a parent key can derive a sequence of children keys, each of which can derive a sequence of grandchildren keys, and so on, to an infinite depth. This tree structure is illustrated in <<Type2_wallet>>.((("hierarchical deterministic wallets (HD wallets)","tree structure for")))
[[Type2_wallet]] [[Type2_wallet]]
.Type-2 hierarchical deterministic wallet: a tree of keys generated from a seed .Type-2 hierarchical deterministic wallet: a tree of keys generated from a single seed
image::images/msbt_0409.png["HD wallet"] image::images/msbt_0409.png["HD wallet"]
[TIP] [TIP]
@ -796,25 +821,25 @@ BIP0044 specifies the structure as consisting of five predefined tree levels:
| m/44'/2'/0'/0/1 | The second private key in the Litecoin main account, for signing transactions | m/44'/2'/0'/0/1 | The second private key in the Litecoin main account, for signing transactions
|======= |=======
===== Experimenting with HD wallets using sx tools ===== Experimenting with HD wallets using Bitcoin Explorer
((("hierarchical deterministic wallets (HD wallets)","sx tools and")))((("sx tools","HD wallets and")))Using the command-line tool +sx+, introduced in <<ch03_bitcoin_client>>, you can experiment with generating and extending BIP0032 deterministic keys, as well as displaying them in different formats: (((range="endofrange", startref="ix_ch04-asciidoc25b")))(((range="endofrange", startref="ix_ch04-asciidoc25a")))(((range="endofrange", startref="ix_ch04-asciidoc25")))(((range="endofrange", startref="ix_ch04-asciidoc24")))(((range="endofrange", startref="ix_ch04-asciidoc23"))) ((("hierarchical deterministic wallets (HD wallets)","Bitcoin Explorer and")))((("Bitcoin Explorer","HD wallets and")))Using the Bitcoin Explorer command-line tool introduced in <<ch03_bitcoin_client>>, you can experiment with generating and extending BIP0032 deterministic keys, as well as displaying them in different formats((("Bitcoin Explorer","seed command")))((("seed command (bx)")))((("Bitcoin Explorer","hd-seed command")))((("hd-seed command (bx)")))((("Bitcoin Explorer","hd-public command")))((("hd-public command (bx)")))((("Bitcoin Explorer","hd-private command")))((("hd-private command (bx)")))((("Bitcoin Explorer","hd-to-address command")))((("hd-to-address command (bx)")))((("Bitcoin Explorer","hd-to-wif command")))((("hd-to-wif command (bx)"))): (((range="endofrange", startref="ix_ch04-asciidoc25b")))(((range="endofrange", startref="ix_ch04-asciidoc25a")))(((range="endofrange", startref="ix_ch04-asciidoc25")))(((range="endofrange", startref="ix_ch04-asciidoc24")))(((range="endofrange", startref="ix_ch04-asciidoc23")))
==== ====
[source, bash] [source, bash]
---- ----
$ sx hd-seed > m # create a new master private key from a seed and store in file "m" $ bx seed | bx hd-seed > m # create a new master private key from a seed and store in file "m"
$ cat m # show the master extended private key $ cat m # show the master extended private key
xprv9s21ZrQH143K38iQ9Y5p6qoB8C75TE71NfpyQPdfGvzghDt39DHPFpovvtWZaRgY5uPwV7RpEgHs7cvdgfiSjLjjbuGKGcjRyU7RGGSS8Xa xprv9s21ZrQH143K38iQ9Y5p6qoB8C75TE71NfpyQPdfGvzghDt39DHPFpovvtWZaRgY5uPwV7RpEgHs7cvdgfiSjLjjbuGKGcjRyU7RGGSS8Xa
$ cat m | sx hd-pub 0 # generate the M/0 extended public key $ cat m | bx hd-public # generate the M/0 extended public key
xpub67xpozcx8pe95XVuZLHXZeG6XWXHpGq6Qv5cmNfi7cS5mtjJ2tgypeQbBs2UAR6KECeeMVKZBPLrtJunSDMstweyLXhRgPxdp14sk9tJPW9 xpub67xpozcx8pe95XVuZLHXZeG6XWXHpGq6Qv5cmNfi7cS5mtjJ2tgypeQbBs2UAR6KECeeMVKZBPLrtJunSDMstweyLXhRgPxdp14sk9tJPW9
$ cat m | sx hd-priv 0 # generate the m/0 extended private key $ cat m | bx hd-private # generate the m/0 extended private key
xprv9tyUQV64JT5qs3RSTJkXCWKMyUgoQp7F3hA1xzG6ZGu6u6Q9VMNjGr67Lctvy5P8oyaYAL9CAWrUE9i6GoNMKUga5biW6Hx4tws2six3b9c xprv9tyUQV64JT5qs3RSTJkXCWKMyUgoQp7F3hA1xzG6ZGu6u6Q9VMNjGr67Lctvy5P8oyaYAL9CAWrUE9i6GoNMKUga5biW6Hx4tws2six3b9c
$ cat m | sx hd-priv 0 | sx hd-to-wif # show the private key of m/0 as a WIF $ cat m | bx hd-private | bx hd-to-wif # show the private key of m/0 as a WIF
L1pbvV86crAGoDzqmgY85xURkz3c435Z9nirMt52UbnGjYMzKBUN L1pbvV86crAGoDzqmgY85xURkz3c435Z9nirMt52UbnGjYMzKBUN
$ cat m | sx hd-pub 0 | sx hd-to-address # show the bitcoin address of M/0 $ cat m | bx hd-public | bx hd-to-address # show the bitcoin address of M/0
1CHCnCjgMNb6digimckNQ6TBVcTWBAmPHK 1CHCnCjgMNb6digimckNQ6TBVcTWBAmPHK
$ cat m | sx hd-priv 0 | sx hd-priv 12 --hard | sx hd-priv 4 # generate m/0/12'/4 $ cat m | bx hd-private | bx hd-private --index 12 --hard | bx hd-private --index 4 # generate m/0/12'/4
xprv9yL8ndfdPVeDWJenF18oiHguRUj8jHmVrqqD97YQHeTcR3LCeh53q5PXPkLsy2kRaqgwoS6YZBLatRZRyUeAkRPe1kLR1P6Mn7jUrXFquUt xprv9yL8ndfdPVeDWJenF18oiHguRUj8jHmVrqqD97YQHeTcR3LCeh53q5PXPkLsy2kRaqgwoS6YZBLatRZRyUeAkRPe1kLR1P6Mn7jUrXFquUt
---- ----
==== ====
@ -857,8 +882,13 @@ A pay-to-script hash address is created from a transaction script, which defines
script hash = RIPEMD160(SHA256(script)) script hash = RIPEMD160(SHA256(script))
---- ----
((("script hashes")))The resulting "script hash" is encoded with Base58Check with a version prefix of 5, which results in an encoded address starting with a +3+. An example of a P2SH address is +32M8ednmuyZ2zVbes4puqe44NZumgG92sM+. ((("script hashes")))The resulting "script hash" is encoded with Base58Check with a version prefix of 5, which results in an encoded address starting with a +3+. An example of a P2SH address is +3F6i6kwkevjR7AsAd4te2YB2zZyASEm1HM+, which can be derived using the Bitcoin Explorer commands((("Bitcoin Explorer","script-encode command")))((("script-encode command (bx)"))) +script-encode+,((("Bitcoin Explorer","sha256 command")))((("sha256 command (bx)"))) +sha256+,((("Bitcoin Explorer","ripemd160 command")))((("ripemd160 command (bx)"))) +ripemd160+ and((("Bitcoin Explorer","base58check-encode command")))((("base58check-encode command (bx)"))) +base58check-encode+ (see <<libbitcoin>>) as follows:
----
$ echo dup hash160 [ 89abcdefabbaabbaabbaabbaabbaabbaabbaabba ] equalverify checksig > script
$ bx script-encode < script | bx sha256 | bx ripemd160 | bx base58check-encode --version 5
3F6i6kwkevjR7AsAd4te2YB2zZyASEm1HM
----
[TIP] [TIP]
==== ====

View File

@ -3,8 +3,10 @@
int main() int main()
{ {
// Private secret key. // Private secret key.
bc::ec_secret secret = bc::decode_hash( bc::ec_secret secret;
bool success = bc::decode_base16(secret,
"038109007313a5807b2eccc082c8c3fbb988a973cacf1a7df9ce725c31b14776"); "038109007313a5807b2eccc082c8c3fbb988a973cacf1a7df9ce725c31b14776");
assert(success);
// Get public key. // Get public key.
bc::ec_point public_key = bc::secret_to_public_key(secret); bc::ec_point public_key = bc::secret_to_public_key(secret);
std::cout << "Public key: " << bc::encode_hex(public_key) << std::endl; std::cout << "Public key: " << bc::encode_hex(public_key) << std::endl;

View File

@ -1,5 +1,6 @@
import ecdsa import ecdsa
import random import random
import time
from ecdsa.util import string_to_number, number_to_string from ecdsa.util import string_to_number, number_to_string
# secp256k1, http://www.oid-info.com/get/1.3.132.0.10 # secp256k1, http://www.oid-info.com/get/1.3.132.0.10
@ -37,6 +38,9 @@ def get_point_pubkey_uncompressed(point):
'%064x' % point.y() '%064x' % point.y()
return key.decode('hex') return key.decode('hex')
# Seed random number generator.
random.seed(time.time())
# Generate a new private key. # Generate a new private key.
secret = random_secret() secret = random_secret()
print "Secret: ", secret print "Secret: ", secret

View File

@ -1,6 +1,6 @@
#include <bitcoin/bitcoin.hpp> #include <bitcoin/bitcoin.hpp>
bc::hash_digest create_merkle(bc::hash_digest_list& merkle) bc::hash_digest create_merkle(bc::hash_list& merkle)
{ {
// Stop if hash list is empty. // Stop if hash list is empty.
if (merkle.empty()) if (merkle.empty())
@ -18,7 +18,7 @@ bc::hash_digest create_merkle(bc::hash_digest_list& merkle)
assert(merkle.size() % 2 == 0); assert(merkle.size() % 2 == 0);
// New hash list. // New hash list.
bc::hash_digest_list new_merkle; bc::hash_list new_merkle;
// Loop through hashes 2 at a time. // Loop through hashes 2 at a time.
for (auto it = merkle.begin(); it != merkle.end(); it += 2) for (auto it = merkle.begin(); it != merkle.end(); it += 2)
{ {
@ -50,10 +50,10 @@ bc::hash_digest create_merkle(bc::hash_digest_list& merkle)
int main() int main()
{ {
// Replace these hashes with ones from a block to reproduce the same merkle root. // Replace these hashes with ones from a block to reproduce the same merkle root.
bc::hash_digest_list tx_hashes{{ bc::hash_list tx_hashes{{
bc::decode_hash("0000000000000000000000000000000000000000000000000000000000000000"), bc::hash_literal("0000000000000000000000000000000000000000000000000000000000000000"),
bc::decode_hash("0000000000000000000000000000000000000000000000000000000000000011"), bc::hash_literal("0000000000000000000000000000000000000000000000000000000000000011"),
bc::decode_hash("0000000000000000000000000000000000000000000000000000000000000022"), bc::hash_literal("0000000000000000000000000000000000000000000000000000000000000022"),
}}; }};
const bc::hash_digest merkle_root = create_merkle(tx_hashes); const bc::hash_digest merkle_root = create_merkle(tx_hashes);
std::cout << "Result: " << bc::encode_hex(merkle_root) << std::endl; std::cout << "Result: " << bc::encode_hex(merkle_root) << std::endl;

View File

@ -123,7 +123,7 @@ During the development of the book, I made early drafts available on GitHub and
Once the book was drafted, it went through several rounds of technical review. Thanks to Cricket Liu and Lorne Lantz for their thorough review, comments, and support. Once the book was drafted, it went through several rounds of technical review. Thanks to Cricket Liu and Lorne Lantz for their thorough review, comments, and support.
Several bitcoin developers contributed code samples, reviews, comments, and encouragement. Thanks to Amir Taaki for example code snippets and many great comments; Vitalik Buterin and Richard Kiss for help with elliptic curve math and code contributions; Gavin Andresen for corrections, comments, and encouragement; and Michalis Kargakis for comments, contributions, and btcd writeup. Several bitcoin developers contributed code samples, reviews, comments, and encouragement. Thanks to Amir Taaki and Eric Voskuil for example code snippets and many great comments; Vitalik Buterin and Richard Kiss for help with elliptic curve math and code contributions; Gavin Andresen for corrections, comments, and encouragement; and Michalis Kargakis for comments, contributions, and btcd writeup.
I owe my love of words and books to my mother, Theresa, who raised me in a house with books lining every wall. My mother also bought me my first computer in 1982, despite being a self-described technophobe. My father, Menelaos, a civil engineer who just published his first book at 80 years old, was the one who taught me logical and analytical thinking and a love of science and engineering. I owe my love of words and books to my mother, Theresa, who raised me in a house with books lining every wall. My mother also bought me my first computer in 1982, despite being a self-described technophobe. My father, Menelaos, a civil engineer who just published his first book at 80 years old, was the one who taught me logical and analytical thinking and a love of science and engineering.