Contributions by @harding to devel docs

Thanks also (in alphabetical order) to @cbeams, @mikehearn, and
@tgeller, among others.

The last pre-squash commit was: c2b8d562aa107c7b68c60946cea14cdccc5159ad
This commit is contained in:
David Harding 2014-05-09 22:13:59 -04:00
parent 82378ddcb4
commit ffde087f02
90 changed files with 13524 additions and 0 deletions

296
_autocrossref.yaml Normal file
View file

@ -0,0 +1,296 @@
---
## List of words to match with references in _includes/references.md
## in developer documentation, used by autocrossref.rb plugin.
## "pattern to match in file" => "reference to give it"
51 percent attack:
address:
addresses: address
'`amount`': pp amount
base-58: base58check
base58: base58check
base58check:
## bitcoin -- Recommend against bitcoin (singular) because of confusion between protocol, software, denomination
bitcoins:
bitcoin QR code: URI QR code
bitcoin QR codes: URI QR code
'`bitcoin:` URI': bitcoin uri
'`bitcoin:` URIs': bitcoin uri
block:
block chain:
block-chain: block chain
block header:
block height:
block reward:
block time:
block version:
blocks: block
broadcast:
broadcasts: broadcast
broadcasting:
certificate chain:
chain code:
change address:
change addresses: change address
change output:
change outputs: change output
child extended key:
child extended keys: child extended key
child key:
child keys: child key
child public key:
child public keys: child public key
coinbase: coinbase transaction
coinbase transaction:
coinbase transactions: coinbase transaction
coinbase field:
confirm:
confirmed:
confirmation:
confirmations:
confirmed transactions:
denomination:
denominations: denomination
DER format: der
DER-formatted: der
difficulty:
double spend:
double-spend: double spend
double spending: double spend
double-spent: double spend
ECDSA:
escrow contract:
'`expires`': pp expires
extended key:
extended keys: extended key
extended private key:
extended public key:
fiat:
fork: accidental fork
genesis block:
hardened extended private key:
HD protocol:
header nonce:
high-priority transaction: high-priority transactions
high-priority transactions:
inputs: input
input:
intermediate certificate:
intermediate certificates: intermediate certificate
key index:
key pair:
'`label`': label
leaf certificate:
locktime:
long-term fork:
mainnet:
master chain code:
master private key:
'`memo`': pp memo
'`message`': message
'`merchant_data`': pp merchant data
merkle root:
merkle tree:
merge:
Merge avoidance:
micropayment channel:
micropayment channels: micropayment channel
mine:
miner:
miners: miner
minimum fee:
mining: mine
millibit: millibits
millibits:
multisig:
network:
null data:
'`op_checkmultisig`': op_checkmultisig
'`op_checksig`': op_checksig
op code:
op codes: op code
'`op_dup`': op_dup
'`op_equal`': op_equal
'`op_equalverify`': op_equalverify
'`op_hash160`': op_hash160
'`op_return`': op_return
'`op_verify`': op_verify
orphan:
orphan: orphaned
outputs: output
output:
output index:
p2ph:
p2sh:
p2sh multisig:
parent chain code:
parent private key:
parent public key:
Payment message: pp payment
payment protocol:
"payment protocol's": payment protocol
PaymentACK:
PaymentDetails:
PaymentRequest:
PaymentRequests: paymentrequest
'`payment_url`': pp payment url
peer:
peers: peer
peer-to-peer network: network
pki:
'`pki_type`': pp pki type
'`point()`': point function
private key:
private keys: private key
proof of work:
proof-of-work: proof of work
protocol buffer: protobuf
protocol buffers: protobuf
pubkey hash:
pubkey hashes: pubkey hash
public key:
public keys: public key
public key infrastructure: pki
'`r`': r
raw format:
rawtransaction format: raw format
receipt:
recurrent rebilling:
redeemScript:
refund:
refunds: refund
'`refund_to`': pp refund to
root certificate:
root seed:
RPCs: rpc
RPC:
satoshi:
satoshis: satoshi
script:
'`script`': pp script
script hash:
scripts: script
scriptSig:
scriptSigs: scriptSig
secp256k1:
sequence number:
sequence numbers: sequence number
SIGHASH: signature hash
'`SIGHASH_ANYONECANPAY`': shacp
'`SIGHASH_ALL`': sighash_all
'`SIGHASH_ALL|SIGHASH_ANYONECANPAY`': sha_shacp
'`SIGHASH_NONE`': sighash_none
'`SIGHASH_NONE|SIGHASH_ANYONECANPAY`': shn_shacp
'`SIGHASH_SINGLE|SIGHASH_ANYONECANPAY`': shs_shacp
signature:
signature hash:
signatures: signature
SPV:
stack:
standard script:
standard scripts: standard script
standard transaction: standard script
standard transactions: standard script
target:
testnet:
#transaction -- Recommend we don't autocrossref this; it occurs too often
transaction fee:
transaction fees: transaction fee
transaction malleability:
transaction object format:
transaction version number:
'`transactions`': pp transactions
txid:
txids: txid
unconfirmed:
unconfirmed transactions:
unique address: unique addresses
unique addresses:
utxo:
utxos: utxo
verified payments:
version 2 blocks: v2 block
wallet:
wallets: wallet
wallet import format:
x.509: x509
X509Certificates:
## BIPS in numerical order; don't use padding zeros (e.g. BIP70 not BIP0070)
BIP21:
BIP32:
BIP39:
BIP70:
## RPCs
'`addmultisigaddress`': rpc addmultisigaddress
'`addnode`': rpc addnode
'`backupwallet`': rpc backupwallet
'`createmultisig`': rpc createmultisig
'`createrawtransaction`': rpc createrawtransaction
'`decoderawtransaction`': rpc decoderawtransaction
'`decodescript`': rpc decodescript
'`dumpprivkey`': rpc dumpprivkey
'`dumpwallet`': rpc dumpwallet
'`getaccount`': rpc getaccount
'`getaccountaddress`': rpc getaccountaddress
'`getaddednodeinfo`': rpc getaddednodeinfo
'`getaddressesbyaccount`': rpc getaddressesbyaccount
'`getbalance`': rpc getbalance
'`getbestblockhash`': rpc getbestblockhash
'`getblock`': rpc getblock
'`getblockcount`': rpc getblockcount
'`getblockhash`': rpc getblockhash
'`getblocktemplate`': rpc getblocktemplate
'`getconnectioncount`': rpc getconnectioncount
'`getdifficulty`': rpc getdifficulty
'`getgenerate`': rpc getgenerate
'`gethashespersec`': rpc gethashespersec
'`getinfo`': rpc getinfo
'`getmininginfo`': rpc getmininginfo
'`getnettotals`': rpc getnettotals
'`getnetworkhashps`': rpc getnetworkhashps
'`getnewaddress`': rpc getnewaddress
'`getpeerinfo`': rpc getpeerinfo
'`getrawchangeaddress`': rpc getrawchangeaddress
'`getrawmempool`': rpc getrawmempool
'`getrawtransaction`': rpc getrawtransaction
'`getreceivedbyaccount`': rpc getreceivedbyaccount
'`getreceivedbyaddress`': rpc getreceivedbyaddress
'`gettransaction`': rpc gettransaction
'`gettxout`': rpc gettxout
'`gettxoutsetinfo`': rpc gettxoutsetinfo
'`getunconfirmedbalance`': rpc getunconfirmedbalance
'`getwork`': rpc getwork
'`help`': rpc help
'`importprivkey`': rpc importprivkey
'`importwallet`': rpc importwallet
'`keypoolrefill`': rpc keypoolrefill
'`listaccounts`': rpc listaccounts
'`listaddressgroupings`': rpc listaddressgroupings
'`listlockunspent`': rpc listlockunspent
'`listreceivedbyaccount`': rpc listreceivedbyaccount
'`listreceivedbyaddress`': rpc listreceivedbyaddress
'`listsinceblock`': rpc listsinceblock
'`listtransactions`': rpc listtransactions
'`listunspent`': rpc listunspent
'`lockunspent`': rpc lockunspent
'`move`': rpc move
'`ping`': rpc ping
'`sendfrom`': rpc sendfrom
'`sendmany`': rpc sendmany
'`sendrawtransaction`': rpc sendrawtransaction
'`sendtoaddress`': rpc sendtoaddress
'`setaccount`': rpc setaccount
'`setgenerate`': rpc setgenerate
'`settxfee`': rpc settxfee
'`signmessage`': rpc signmessage
'`signrawtransaction`': rpc signrawtransaction
'`stop`': rpc stop
'`submitblock`': rpc submitblock
'`validateaddress`': rpc validateaddress
'`verifychain`': rpc verifychain
'`verifymessage`': rpc verifymessage
'`walletlock`': rpc walletlock
'`walletpassphrase`': rpc walletpassphrase
'`walletpassphrasechange`': rpc walletpassphrasechange

View file

@ -0,0 +1,242 @@
## Block Chain
{% autocrossref %}
The block chain provides Bitcoin's public ledger, a timestamped record
of all confirmed transactions. This system is used to protect against double spending
and modification of previous transaction records, using proof of
work verified by the peer-to-peer network to maintain a global consensus.
{% endautocrossref %}
### Block Chain Overview
{% autocrossref %}
![Block Chain Overview](/img/dev/en-blockchain-overview.svg)
The illustration above shows a simplified version of a block chain.
A [block][]{:#term-block}{:.term} of one or more new transactions
is collected into the transaction data part of a block.
Copies of each transaction are hashed, and the hashes are then paired,
hashed, paired again, and hashed again until a single hash remains, the
[Merkle root][]{:#term-merkle-root}{:.term} of a Merkle tree.
The Merkle root is stored in the block header. Each block also
stores the hash of the previous block's header, chaining the blocks
together. This ensures a transaction cannot be modified without
modifying the block that records it and all following blocks.
Transactions are also chained together. Bitcoin wallet software gives
the impression that satoshis are sent from and to addresses, but
bitcoins really move from transaction to transaction. Each standard
transaction spends the satoshis previously spent in one or more earlier
transactions, so the input of one transaction is the output of a
previous transaction.
![Transaction Propagation](/img/dev/en-transaction-propagation.svg)
A single transaction can spend bitcoins to multiple outputs, as would be
the case when sending satoshis to multiple addresses, but each output of
a particular transaction can only be used as an input once in the
block chain. Any subsequent reference is a forbidden double
spend---an attempt to spend the same satoshis twice.
Outputs are not the same as Bitcoin addresses. You can use the same
address in multiple transactions, but you can only use each output once.
Outputs are tied to [transaction identifiers (TXIDs)][txid]{:#term-txid}{:.term}, which are the hashes
of signed transactions.
Because each output of a particular transaction can only be spent once,
all transactions included in the block chain can be categorized as either
[Unspent Transaction Outputs (UTXOs)][utxo]{:#term-utxo}{:.term} or spent transaction outputs. For a
payment to be valid, it must only use UTXOs as inputs.
Satoshis cannot be left in a UTXO after a transaction or they will be
irretrievably lost, so any difference between the number of satoshis in a
transaction's inputs and outputs is given as a [transaction fee][]{:#term-transaction-fee}{:.term} to
the Bitcoin [miner][]{:#term-miner}{:.term} who creates the block containing that transaction.
For example, in the illustration above, each transaction spends 10,000 satoshis
fewer than it receives from its combined inputs, effectively paying a 10,000
satoshi transaction fee.
{% endautocrossref %}
### Proof Of Work
{% autocrossref %}
The block chain is collaboratively maintained on a peer-to-peer network, so
Bitcoin requires each block prove a significant amount of work was invested in
its creation to ensure that untrustworthy peers who want to modify past blocks have
to work harder than trustworthy peers who only want to add new blocks to the
block chain.
Chaining blocks together makes it impossible to modify transactions included
in any block without modifying all following blocks. As a
result, the cost to modify a particular block increases with every new block
added to the block chain, magnifying the effect of the proof of work.
The [proof of work][]{:#term-proof-of-work}{:.term} used in Bitcoin
takes advantage of the apparently random nature of cryptographic hashes.
A good cryptographic hash algorithm converts arbitrary data into a
seemingly-random number. If the data is modified in any way and
the hash re-run, a new seemingly-random number is produced, so there is
no way to modify the data to make the hash number predictable.
To prove you did some extra work to create a block, you must create a
hash of the block header which does not exceed a certain value. For
example, if the maximum possible hash value is <span
class="math">2<sup>256</sup>1</span>, you can prove that you
tried up to two combinations by producing a hash value less than <span
class="math">2<sup>256</sup>1</span>.
In the example given above, you will almost certainly produce a
successful hash on your first try. You can even estimate the probability
that a given hash attempt will generate a number below the [target][]{:#term-target}{:.term}
threshold. Bitcoin itself does not track probabilities but instead
simply assumes that the lower it makes the target threshold, the more
hash attempts, on average, will need to be tried.
New blocks will only be added to the block chain if their hash is at
least as challenging as a [difficulty][]{:#term-difficulty}{:.term} value expected by the peer-to-peer
network. Every 2,016 blocks, the network uses timestamps stored in each
block header to calculate the number of seconds elapsed between generation
of the first and last of those last 2,016 blocks. The ideal value is
1,209,600 seconds (two weeks).
* If it took fewer than two weeks to generate the 2,016 blocks,
the expected difficulty value is increased proportionally (by as much
as 300%) so that the next 2,016 blocks should take exactly two weeks
to generate if hashes are checked at the same rate.
* If it took more than two weeks to generate the blocks, the expected
difficulty value is decreased proportionally (by as much as 75%) for
the same reason.
(Note: an off-by-one error in the Bitcoin Core implementation causes the
difficulty to be updated every 2,01*6* blocks using timestamps from only
2,01*5* blocks, creating a slight skew.)
Because each block header must hash to a value below the target
threshold, and because each block is linked to the block that
preceded it, it requires (on average) as much hashing power to
propagate a modified block as the entire Bitcoin network expended
between the time the original block was created and the present time.
Only if you acquired a majority of the network's hashing power
could you reliably execute such a [51 percent attack][]{:#term-51-attack}{:.term} against
transaction history.
The block header provides several easy-to-modify fields, such as a
dedicated nonce field, so obtaining new hashes doesn't require waiting
for new transactions. Also, only the 80-byte block header is hashed for
proof-of-work, so adding more bytes of transaction data to
a block does not slow down hashing with extra I/O.
{% endautocrossref %}
### Block Height And Forking
{% autocrossref %}
Any Bitcoin miner who successfully hashes a block header to a value
below the target threshold can add the entire block to the block chain.
(Assuming the block is otherwise valid.) These blocks are commonly addressed
by their [block height][]{:#term-block-height}{:.term}---the number of blocks between them and the first Bitcoin
block (block 0, most commonly known as the [genesis block]{:#term-genesis-block}{:.term}). For example,
block 2016 is where difficulty could have been first adjusted.
![Common And Uncommon Block Chain Forks](/img/dev/en-blockchain-fork.svg)
Multiple blocks can all have the same block height, as is common when
two or more miners each produce a block at roughly the same time. This
creates an apparent [fork][accidental fork]{:#term-accidental-fork}{:.term} in the block chain, as shown in the
illustration above.
When miners produce simultaneous blocks at the end of the block chain, each
peer individually chooses which block to trust. (In the absence of
other considerations, discussed below, peers usually trust the first
block they see.)
Eventually a miner produces another block which attaches to only one of
the competing simultaneously-mined blocks. This makes that side of
the fork longer than the other side. Assuming a fork only contains valid
blocks, normal peers always follow the longest fork (the most difficult chain
to recreate) and throw away ([orphan][]{:#term-orphan}{:.term}) blocks belonging to shorter forks.
[Long-term forks][long-term fork]{:#term-long-term-fork}{:.term} are possible if different miners work at cross-purposes,
such as some miners diligently working to extend the block chain at the
same time other miners are attempting a 51 percent attack to revise
transaction history.
Since multiple blocks can have the same height during a block chain fork, block
height should not be used as a globally unique identifier. Instead, blocks
are usually referenced by the SHA256(SHA256()) hash of their header.
{% endautocrossref %}
### Transaction Data
{% autocrossref %}
Every block must include one or more transactions. Exactly one of these
transactions must be a coinbase transaction which should collect and
spend the block reward and any transaction fees paid by transactions included in this block.
The UTXO of a coinbase transaction has the special condition that
it cannot be spent (used as an input) for at least 100 blocks. This temporarily
prevents a miner from spending the transaction fees and block reward from a
block that may later be orphaned (destroyed) after a block chain fork.
Blocks are not required to include any non-coinbase transactions, but
miners almost always do include additional transactions in order to
collect their transaction fees.
All transactions, including the coinbase transaction, are encoded into
blocks in binary rawtransaction format prefixed by a block transaction
sequence number.
The rawtransaction format is hashed to create the transaction
identifier (txid). From these txids, the [Merkle tree][]{:#term-merkle-tree}{:.term} is constructed by pairing each
txid with one other txid and then hashing them together. If there are
an odd number of txids, the txid without a partner is hashed with a
copy of itself.
The resulting hashes themselves are each paired with one other hash and
hashed together. Any hash without a partner is hashed with itself. The
process repeats until only one hash remains, the Merkle root.
For example, if transactions were merely joined (not hashed), a
five-transaction Merkle tree would look like the following text diagram:
{% endautocrossref %}
~~~
ABCDEEEE .......Merkle root
/ \
ABCD EEEE
/ \ /
AB CD EE .......E is paired with itself
/ \ / \ /
A B C D E .........Transactions
~~~
{% autocrossref %}
As discussed in the Simplified Payment Verification (SPV) subsection,
the Merkle tree allows clients to verify for
themselves that a transaction was included in a block by obtaining the
Merkle root from a block header and a list of the intermediate hashes
from a full peer. The full peer does not need to be trusted: it is
expensive to fake block headers and the intermediate hashes cannot be faked or
the verification will fail.
For example, to verify transaction D was added to the
block, an SPV client only needs a copy of the C, AB, and EEEE hashes in addition to the
Merkle root; the client doesn't need to know anything about any of the
other transactions. If the five transactions in this block were all at
the maximum size, downloading the entire block would require over
500,000 bytes---but downloading three hashes plus the block header
requires only 140 bytes.
{% endautocrossref %}

View file

@ -0,0 +1,288 @@
## Contracts
{% autocrossref %}
By making the system hard to understand, the complexity of transactions
has so far worked against you. That changes with contracts. Contracts are
transactions which use the decentralized Bitcoin system to enforce financial
agreements.
Bitcoin contracts can often be crafted to minimize dependency on outside
agents, such as the court system, which significantly decreases the risk
of dealing with unknown entities in financial transactions. For example,
Alice and Bob might only know each other casually over the Internet;
they would never open a checking account together---one of them could
pass bad checks, leaving the other on the hook. But with Bitcoin
contracts, they can nearly eliminate the risk from their relationship
and start a business even though they hardly know each other.
The following subsections will describe a variety of Bitcoin contracts
already in use. Because contracts deal with real people, not just
transactions, they are framed below in story format.
Besides the contract types described below, many other contract types
have been proposed. Several of them are collected on the [Contracts
page](https://en.bitcoin.it/wiki/Contracts) of the Bitcoin Wiki.
{% endautocrossref %}
### Escrow And Arbitration
{% autocrossref %}
Charlie-the-customer wants to buy a product from Bob-the-businessman,
but neither of them trusts the other person, so they use a contract to
help ensure Charlie gets his merchandise and Bob gets his payment.
A simple contract could say that Charlie will spend satoshis to an
output which can only be spent if Charlie and Bob both sign the input
spending it. That means Bob won't get paid unless Charlie gets his
merchandise, but Charlie can't get the merchandise and keep his payment.
This simple contract isn't much help if there's a dispute, so Bob and
Charlie enlist the help of Alice-the-arbitrator to create an [escrow
contract][]{:#term-escrow-contract}{:.term}. Charlie spends his satoshis
to an output which can only be spent if two of the three people sign the
input. Now Charlie can pay Bob if everything is ok, Bob can refund
Charlie's money if there's a problem, or Alice can arbitrate and decide
who should get the satoshis if there's a dispute.
To create a multiple-signature ([multisig][]{:#term-multisig}{:.term})
output, they each give the others a public key. Then Bob creates the
following [P2SH multisig][]{:#term-p2sh-multisig}{:.term} redeemScript:
{% endautocrossref %}
~~~
OP_2 [A's pubkey] [B's pubkey] [C's pubkey] OP_3 OP_CHECKMULTISIG
~~~
{% autocrossref %}
(Op codes to push the public keys onto the stack are not shown.)
`OP_2` and `OP_3` push the actual numbers 2 and 3 onto the
stack. `OP_2`
specifies that 2 signatures are required to sign; `OP_3` specifies that
3 public keys (unhashed) are being provided. This is a 2-of-3 multisig
script, more generically called a m-of-n script (where *m* is the
*minimum* matching signatures required and *n* in the *number* of public
keys provided).
Bob gives the redeemScript to Charlie, who checks to make sure his
public key and Alice's public key are included. Then he hashes the
redeemScript, puts it in a P2SH output, and pays the satoshis to it. Bob
sees the payment get added to the block chain and ships the merchandise.
Unfortunately, the merchandise gets slightly damaged in transit. Charlie
wants a full refund, but Bob thinks a 10% refund is sufficient. They
turn to Alice to resolve the issue. Alice asks for photo evidence from
Charlie along with a copy of the unhashed redeemScript Bob created and
Charlie checked.
After looking at the evidence, Alice thinks a 40% refund is sufficient,
so she creates and signs a transaction with two outputs, one that spends 60%
of the satoshis to Bob's public key and one that spends the remaining
40% to Charlie's public key.
In the input section of the script, Alice puts her signature, a 0x00
placeholder byte, and a copy of the unhashed serialized redeemScript
that Bob created. She gives a copy of the incomplete transaction to
both Bob and Charlie. Either one of them can complete it by replacing
the placeholder byte with his signature, creating the following input
script:
{% endautocrossref %}
~~~
OP_0 [A's signature] [B's or C's signature] [serialized redeemScript]
~~~
{% autocrossref %}
(Op codes to push the signatures and redeemScript onto the stack are
not shown. `OP_0` is a workaround for an off-by-one error in the original
implementation which must be preserved for compatibility.)
When the transaction is broadcast to the network, each peer checks the
input script against the P2SH output Charlie previously paid,
ensuring that the redeemScript matches the redeemScript hash previously
provided. Then the redeemScript is evaluated, with the two signatures
being used as input<!--noref--> data. Assuming the redeemScript
validates, the two transaction outputs show up in Bob's and Charlie's
wallets as spendable balances.
However, if Alice created and signed a transaction neither of them would
agree to, such as spending all the satoshis to herself, Bob and Charlie
can find a new arbitrator and sign a transaction spending the satoshis
to another 2-of-3 multisig redeemScript hash, this one including a public
key from that second arbitrator. This means that Bob and Charlie never
need to worry about their arbitrator stealing their money.
**Resource:** [BitRated](https://www.bitrated.com/) provides a multisig arbitration
service interface using HTML/JavaScript on a GNU AGPL-licensed website.
{% endautocrossref %}
### Micropayment Channel
{% autocrossref %}
<!-- SOMEDAY: try to rewrite using a more likely real-world example without
making the text or illustration more complicated -->
Alice also works part-time moderating forum posts for Bob. Every time
someone posts to Bob's busy forum, Alice skims the post to make sure it
isn't offensive or spam. Alas, Bob often forgets to pay her, so Alice
demands to be paid immediately after each post she approves or rejects.
Bob says he can't do that because hundreds of small payments will cost
him thousands of satoshis in transaction fees, so Alice suggests they use a
[micropayment channel][]{:#term-micropayment-channel}{:.term}.
Bob asks Alice for her public key and then creates two transactions.
The first transaction pays 100 millibits to a P2SH output whose
2-of-2 multisig redeemScript requires signatures from both Alice and Bob.
This is the bond transaction.
Broadcasting this transaction would let Alice hold the millibits
hostage, so Bob keeps this transaction private for now and creates a
second transaction.
The second transaction spends all of the first transaction's millibits
(minus a transaction fee) back to Bob after a 24 hour delay enforced
by locktime. This is the refund transaction. Bob can't sign the refund transaction by himself, so he gives
it to Alice to sign, as shown in the
illustration below.
![Micropayment Channel Example](/img/dev/en-micropayment-channel.svg)
Alice checks that the refund transaction's locktime is 24 hours in the
future, signs it, and gives a copy of it back to Bob. She then asks Bob
for the bond transaction and checks that the refund transaction spends
the output of the bond transaction. She can now broadcast the bond
transaction to the network to ensure Bob has to wait for the time lock
to expire before further spending his millibits. Bob hasn't actually
spent anything so far, except possibly a small transaction fee, and
he'll be able to broadcast the refund transaction in 24 hours for a
full refund.
Now, when Alice does some work worth 1 millibit, she asks Bob to create
and sign a new version of the refund transaction. Version two of the
transaction spends 1 millibit to Alice and the other 99 back to Bob; it does
not have a locktime, so Alice can sign it and spend it whenever she
wants. (But she doesn't do that immediately.)
Alice and Bob repeat these work-and-pay steps until Alice finishes for
the day, or until the time lock is about to expire. Alice signs the
final version of the refund transaction and broadcasts it, paying
herself and refunding any remaining balance to Bob. The next day, when
Alice starts work, they create a new micropayment channel.
If Alice fails to broadcast a version of the refund transaction before
its time lock expires, Bob can broadcast the first version and receive a
full refund. This is one reason micropayment channels are best suited to
small payments---if Alice's Internet service goes out for a few hours
near the time lock expiry, she could be cheated out of her payment.
Transaction malleability, discussed above in the Transactions section,
is another reason to limit the value of micropayment channels.
If someone uses transaction malleability to break the link between the
two transactions, Alice could hold Bob's 100 millibits hostage even if she
hadn't done any work.
For larger payments, Bitcoin transaction fees are very low as a
percentage of the total transaction value, so it makes more sense to
protect payments with immediately-broadcast separate transactions.
**Resource:** The [bitcoinj](http://bitcoinj.org) Java library
provides a complete set of micropayment functions, an example
implementation, and [a
tutorial](https://bitcoinj.github.io/working-with-micropayments)
all under an Apache license.
{% endautocrossref %}
### CoinJoin
{% autocrossref %}
Alice is concerned about her privacy. She knows every transaction gets
added to the public block chain, so when Bob and Charlie pay her, they
can each easily track those satoshis to learn what Bitcoin
addresses she pays, how much she pays them, and possibly how many
satoshis she has left.
Because Alice isn't a criminal, she doesn't want to use some shady
Bitcoin laundering service; she just wants plausible deniability about
where she has spent her satoshis and how many she has left, so she
starts up the Tor anonymity service on her computer and logs into an
IRC chatroom as "AnonGirl."
Also in the chatroom are "Nemo" and "Neminem." They collectively
agree to transfer satoshis between each other so no one besides them
can reliably determine who controls which satoshis. But they're faced
with a dilemma: who transfers their satoshis to one of the other two
pseudonymous persons first? The CoinJoin-style contract, shown in the
illustration below, makes this decision easy: they create a single
transaction which does all of the spending simultaneously, ensuring none
of them can steal the others' satoshis.
![Example CoinJoin Transaction](/img/dev/en-coinjoin.svg)
Each contributor looks through their collection of Unspent Transaction
Outputs (UTXOs) for 100 millibits they can spend. They then each generate
a brand new public key and give UTXO details and pubkey hashes to the
facilitator. In this case, the facilitator is AnonGirl; she creates
a transaction spending each of the UTXOs to three equally-sized outputs.
One output goes to each of the contributors' pubkey hashes.
AnonGirl then signs her inputs using `SIGHASH_ALL` to ensure nobody can
change the input or output details. She gives the partially-signed
transaction to Nemo who signs his inputs the same way and passes it
to Neminem, who also signs it the same way. Neminem then broadcasts
the transaction to the peer-to-peer network, mixing all of the millibits in
a single transaction.
As you can see in the illustration, there's no way for anyone besides
AnonGirl, Nemo, and Neminem to confidently determine who received
which output, so they can each spend their output with plausible
deniability.
Now when Bob or Charlie try to track Alice's transactions through the
block chain, they'll also see transactions made by Nemo and
Neminem. If Alice does a few more CoinJoins, Bob and Charlie might
have to guess which transactions made by dozens or hundreds of people
were actually made by Alice.
The complete history of Alice's satoshis is still in the block chain,
so a determined investigator could talk to the people AnonGirl
CoinJoined with to find out the ultimate origin of her satoshis and
possibly reveal AnonGirl as Alice. But against anyone casually browsing
block chain history, Alice gains plausible deniability.
The CoinJoin technique described above costs the participants a small
amount of satoshis to pay the transaction fee. An alternative
technique, purchaser CoinJoin, can actually save them satoshis and
improve their privacy at the same time.
AnonGirl waits in the IRC chatroom until she wants to make a purchase.
She announces her intention to spend satoshis and waits until someone
else wants to make a purchase, likely from a different merchant. Then
they combine their inputs the same way as before but set the outputs
to the separate merchant addresses so nobody will be able to figure
out solely from block chain history which one of them bought what from
the merchants.
Since they would've had to pay a transaction fee to make their purchases
anyway, AnonGirl and her co-spenders don't pay anything extra---but
because they reduced overhead by combining multiple transactions, saving
bytes, they may be able to pay a smaller aggregate transaction fee,
saving each one of them a tiny amount of satoshis.
**Resource:** An alpha-quality (as of this writing) implementation of decentralized
CoinJoin is [CoinMux](http://coinmux.com/), available under the Apache
license. A centralized version of purchaser CoinJoin is available at the
[SharedCoin](https://sharedcoin.com/) website (part of Blockchain.info),
whose [implementation](https://github.com/blockchain/Sharedcoin) is
available under the 4-clause BSD license.
{% endautocrossref %}

62
_includes/guide_intro.md Normal file
View file

@ -0,0 +1,62 @@
{% autocrossref %}
The Developer Guide aims to provide the information you need to start
building Bitcoin-based applications. To make the best use of this guide,
you may want to install the current version of Bitcoin Core, either from
[source][core git] or from a [pre-compiled executable][core executable].
Once installed, you'll have access to three programs: `bitcoind`,
`bitcoin-qt`, and `bitcoin-cli`. When run with no arguments, all three
programs default to Bitcoin's main network ([mainnet][mainnet]{:#term-mainnet}{:.term}) which will require
you purchase satoshis in order to generate transactions.
However, for development, it's safer and cheaper to use Bitcoin's test
network ([testnet][testnet]{:#term-testnet}{:.term}) where the satoshis spent have no real-world value.
Testnet also relaxes some restrictions (such as standard transaction
checks) so you can test functions which might currently be disabled by
default on mainnet.
To use testnet, use the argument `-testnet`<!--noref--> with each program or add
`testnet=1`<!--noref--> to your `bitcoin.conf` file. To get
free satoshis for testing, use [Piotr Piasecki's testnet faucet][].
Testnet is a public resource provided for free by members of the
community, so please don't abuse it.
You can speed up development further using the [regression test mode][]
which creates a new testnet local to your computer. This regtest mode
will let you generate blocks almost instantly with a RPC command so you
can generate your own satoshis and add transactions to the block chain
immediately.
* `bitcoin-qt` provides a combination full Bitcoin peer and wallet
frontend. From the Help menu, you can access a console where you can
enter the RPC commands used throughout this document.
* `bitcoind` is more useful for programming: it provides a full peer
which you can interact with through RPCs to port 8332 (or 18332
for testnet).
* `bitcoin-cli` allows you to send RPC commands to `bitcoind` from the
command line. For example, `bitcoin-cli help`
All three programs get settings from `bitcoin.conf` in the `Bitcoin`
application directiory:
* Windows: `%APPDATA%\Bitcoin\`
* OSX: `$HOME/Library/Application Support/Bitcoin/`
* Linux: `$HOME/.bitcoin/`
Questions about Bitcoin development are best sent to the Bitcoin [Forum][forum
tech support] and [IRC channels][]. Errors or suggestions related to
documentation on Bitcoin.org can be [submitted as an issue][docs issue]
or posted to the [bitcoin-documentation mailing list][].
In the following guide,
some strings have been shortened or wrapped: "[...]" indicates extra data was removed, and lines ending in a single backslash "\\" are continued below.
If you hover your mouse over a paragraph, cross-reference links will be
shown in blue. If you hover over a cross-reference link, a brief
definition of the term will be displayed in a tooltip.
{% endautocrossref %}

202
_includes/guide_mining.md Normal file
View file

@ -0,0 +1,202 @@
## Mining
{% autocrossref %}
Mining adds new blocks to the block chain, making transaction history
hard to modify. Mining today takes on two forms:
* Solo mining, where the miner attempts to generate new blocks on his
own, with the proceeds from the block reward and transaction fees
going entirely to himself, allowing him to receive large payments with
a higher variance (longer time between payments)
* Pooled mining, where the miner pools resources with other miners to
find blocks more often, with the proceeds being shared among the pool
miners in rough correlation to the amount of hashing power
they each contributed, allowing the miner to receive small
payments with a lower variance (shorter time between payments).
{% endautocrossref %}
### Solo Mining
{% autocrossref %}
As illustrated below, solo miners typically use `bitcoind` to get new
transactions from the network. Their mining software periodically polls
`bitcoind` for new transactions using the `getblocktemplate` RPC, which
provides the list of new transactions plus the public key to which the
coinbase transaction should be sent.
![Solo Bitcoin Mining](/img/dev/en-solo-mining-overview.svg)
The mining software constructs a block using the template (described below) and creates a
block header. It then sends the 80-byte block header to its mining
hardware (an ASIC) along with a target threshold (difficulty setting).
The mining hardware iterates through every possible value for the block
header nonce and generates the corresponding hash.
If none of the hashes are below the threshold, the mining hardware gets
an updated block header with a new Merkle root from the mining software;
this new block header is created by adding extra nonce data to the
coinbase field of the coinbase transaction.
On the other hand, if a hash is found below the target threshold, the
mining hardware returns the block header with the successful nonce to
the mining software. The mining software combines the header with the
block and sends the completed block to `bitcoind` to be broadcast to the network for addition to the
block chain.
{% endautocrossref %}
### Pool Mining
{% autocrossref %}
Pool miners follow a similar workflow, illustrated below, which allows
mining pool operators to pay miners based on their share of the work
done. The mining pool gets new transactions from the network using
`bitcoind`. Using one of the methods discussed later, each miner's mining
software connects to the pool and requests the information it needs to
construct block headers.
![Pooled Bitcoin Mining](/img/dev/en-pooled-mining-overview.svg)
In pooled mining, the mining pool sets the target threshold a few orders
of magnitude higher (less difficult) than the network
difficulty. This causes the mining hardware to return many block headers
which don't hash to a value eligible for inclusion on the block chain
but which do hash below the pool's target, proving (on average) that the
miner checked a percentage of the possible hash values.
The miner then sends to the pool a copy of the information the pool
needs to validate that the header will hash below the target and that
the the block of transactions referred to by the header Merkle root field
is valid for the pool's purposes. (This usually means that the coinbase
transaction must pay the pool.)
The information the miner sends to the pool is called a share because it
proves the miner did a share of the work. By chance, some shares the
pool receives will also be below the network target---the mining pool
sends these to the network to be added to the block chain.
The block reward and transaction fees that come from mining that block
are paid to the mining pool. The mining pool pays out a portion of
these proceeds to individual miners based on how many shares they generated. For
example, if the mining pool's target threshold is 100 times lower than
the network target threshold, 100 shares will need to be generated on
average to create a successful block, so the mining pool can pay 1/100th
of its payout for each share received. Different mining pools use
different reward distribution systems based on this basic share system.
{% endautocrossref %}
### Block Prototypes
{% autocrossref %}
In both solo and pool mining, the mining software needs to get the
information necessary to construct block headers. This subsection
describes, in a linear way, how that information is transmitted and
used. However, in actual implementations, parallel threads and queuing
are used to keep ASIC hashers working at maximum capacity,
{% endautocrossref %}
#### getwork RPC
{% autocrossref %}
The simplest and earliest method was the now-deprecated Bitcoin Core
`getwork` RPC, which constructs a header for the miner directly. Since a
header only contains a single 4-byte nonce good for about 4 gigahashes,
many modern miners need to make dozens or hundreds of `getwork` requests
a second. Solo miners may still use `getwork`, but most pools today
discourage or disallow its use.
{% endautocrossref %}
#### getblocktemplate RPC
{% autocrossref %}
An improved method is the Bitcoin Core `getblocktemplate` RPC. This
provides the mining software with much more information:
1. The information necessary to construct a coinbase transaction
paying the pool or the solo miner's `bitcoind` wallet.
2. A complete dump of the transactions `bitcoind` or the mining pool
suggests including in the block, allowing the mining software to
inspect the transactions, optionally add additional transactions, and
optionally remove non-required transactions.
3. Other information necessary to construct a block header for the next
block: the block version, previous block hash, and bits (target).
4. The mining pool's current target threshold for accepting shares. (For
solo miners, this is the network target.)
Using the transactions received, the mining software adds a nonce to the
coinbase extra nonce field and then converts all the transactions into a
Merkle tree to derive a Merkle root it can use in a block header.
Whenever the extra nonce field needs to be changed, the mining software
rebuilds the necessary parts of the Merkle tree and updates the time and
Merkle root fields in the block header.
Like all `bitcoind` RPCs, `getblocktemplate` is sent over HTTP. To
ensure they get the most recent work, most miners use [HTTP longpoll][] to
leave a `getblocktemplate` request open at all times. This allows the
mining pool to push a new `getblocktemplate` to the miner as soon as any
miner on the peer-to-peer network publishes a new block or the pool
wants to send more transactions to the mining software.
{% endautocrossref %}
#### Stratum
{% autocrossref %}
A widely used alternative to `getblocktemplate` is the [Stratum mining
protocol][]. Stratum focuses on giving miners the minimal information they
need to construct block headers on their own:
1. The information necessary to construct a coinbase transaction
paying the pool.
2. The parts of the Merkle tree which need to be re-hashed to
create a new Merkle root when the coinbase transaction is
updated with a new extra nonce. The other parts of the Merkle
tree, if any, are not sent, effectively limiting the amount of data which needs
to be sent to (at most) about a kilobyte at current transaction
volume.
3. All of the other non-Merkle root information necessary to construct a
block header for the next block.
4. The mining pool's current target threshold for accepting shares.
Using the coinbase transaction received, the mining software adds a
nonce to the coinbase extra nonce field, hashes the coinbase
transaction, and adds the hash to the received parts of the Merkle tree.
The tree is hashed as necessary to create a Merkle root, which is added
to the block header information received. Whenever the extra nonce field
needs to be changed, the mining software updates and re-hashes the
coinbase transaction, rebuilds the Merkle root, and updates the header
Merkle root field.
Unlike `getblocktemplate`, miners using Stratum cannot inspect or add
transactions to the block they're currently mining. Also unlike
`getblocktemplate`, the Stratum protocol uses a two-way TCP socket which
stays open, so miners don't need to use longpoll to ensure they receive
immediate updates from mining pools when a new block is broadcast to the
peer-to-peer network.
<!-- SOMEDAY: describe p2pool -->
**Resources:** For more information, please see the [BFGMiner][] mining
software licensed under GPLv3 or the [Eloipool][] mining pool software
licensed under AGPLv3. A number of other mining and pool programs
exist, although many are forks of BFGMiner or Eloipool.
{% endautocrossref %}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,664 @@
## Transactions
{% autocrossref %}
<!-- reference tx (made by Satoshi in block 170):
bitcoind decoderawtransaction $( bitcoind getrawtransaction f4184fc596403b9d638783cf57adfe4c75c605f6356fbc91338530e9831e9e16 )
-->
<!-- SOMEDAY: we need more terms than just output/input to denote the
various ways the outputs/inputs are used, such as "prevout", "nextout",
"curout", "curin", "nextin". (Is there any use for "previn"?) Someday,
when I'm terribly bored, I should rewrite this whole transaction section
to use those terms and then get feedback to see if it actually helps. -harding -->
Transactions let users spend satoshis. Each transaction is constructed
out of several parts which enable both simple direct payments and complex
transactions. This section will describe each part and
demonstrate how to use them together to build complete transactions.
To keep things simple, this section pretends coinbase transactions do
not exist. Coinbase transactions can only be created by Bitcoin miners
and they're an exception to many of the rules listed below. Instead of
pointing out the coinbase exception to each rule, we invite you to read
about coinbase transactions in the block chain section of this guide.
![The Parts Of A Transaction](/img/dev/en-tx-overview.svg)
The figure above shows the core parts of a Bitcoin transaction. Each
transaction has at least one input and one output. Each [input][]{:#term-input}{:.term} spends the
satoshis paid to a previous output. Each [output][]{:#term-output}{:.term} then waits as an Unspent
Transaction Output (UTXO) until a later input spends it. When your
Bitcoin wallet tells you that you have a 10,000 satoshi balance, it really
means that you have 10,000 satoshis waiting in one or more UTXOs.
Each transaction is prefixed by a four-byte [transaction version number][]{:#term-transaction-version-number}{:.term} which tells
Bitcoin peers and miners which set of rules to use to validate it. This
lets developers create new rules for future transactions without
invalidating previous transactions.
The figures below help illustrate the other transaction features by
showing the workflow Alice uses to send Bob a transaction and which Bob
later uses to spend that transaction. Both Alice and Bob will use the
most common form of the standard Pay-To-Pubkey-Hash (P2PH) transaction
type. [P2PH][]{:#term-p2ph}{:.term} lets Alice spend satoshis to a typical Bitcoin address,
and then lets Bob further spend those satoshis using a simple
cryptographic key pair.
![Creating A P2PH Public Key Hash To Receive Payment](/img/dev/en-creating-p2ph-output.svg)
Bob must first generate a private/public [key pair][]{:#term-key-pair}{:.term} before Alice can create the
first transaction. Standard Bitcoin [private keys][private
key]{:#term-private-key}{:.term} are 256 bits of random
data. A copy of that data is deterministically transformed into a [public
key][]{:#term-public-key}{:.term}. Because the transformation can be reliably repeated later, the
public key does not need to be stored.
The public key is then cryptographically hashed. This pubkey hash can
also be reliably repeated later, so it also does not need to be stored.
The hash shortens and obfuscates the public key, making manual
transcription easier and providing security against
unanticipated problems which might allow reconstruction of private keys
from public key data at some later point.
<!-- Editors: from here on I will typically use the terms "pubkey hash"
and "full public key" to provide quick differentiation between the
different states of a public key and to help the text better match the
space-constrained diagrams where "public-key hash" wouldn't fit. -harding -->
Bob provides the [pubkey hash][]{:#term-pubkey-hash}{:.term} to Alice. Pubkey hashes are almost always
sent encoded as Bitcoin [addresses][]{:#term-address}{:.term}, which are base58-encoded strings
containing an address version number, the hash, and an error-detection
checksum to catch typos. The address can be transmitted
through any medium, including one-way mediums which prevent the spender
from communicating with the receiver, and it can be further encoded
into another format, such as a QR code containing a `bitcoin:`
URI.
Once Alice has the address and decodes it back into a standard hash, she
can create the first transaction. She creates a standard P2PH
transaction output containing instructions which allow anyone to spend that
output if they can prove they control the private key corresponding to
Bob's hashed public key. These instructions are called the output [script][]{:#term-script}{:.term}.
Alice broadcasts the transaction and it is added to the block chain.
The network categorizes it as an Unspent Transaction Output (UTXO), and Bob's
wallet software displays it as a spendable balance.
When, some time later, Bob decides to spend the UTXO, he must create an
input which references the transaction Alice created by its hash, called
a Transaction Identifier (txid), and the specific output she used by its
index number ([output index][]{:#term-output-index}{:.term}). He must then create a [scriptSig][]{:#term-scriptsig}{:.term}---a
collection of data parameters which satisfy the conditions Alice placed
in the previous output's script.
![Unlocking A P2PH Output For Spending](/img/dev/en-unlocking-p2ph-output.svg)
Bob does not need to communicate with Alice to do this; he must simply
prove to the Bitcoin peer-to-peer network that he can satisfy the
script's conditions. For a P2PH-style output, Bob's scriptSig will
contain the following two pieces of data:
1. His full (unhashed) public key, so the script can check that it
hashes to the same value as the pubkey hash provided by Alice.
2. A [signature][]{:#term-signature}{:.term} made by using the ECDSA cryptographic formula to combine
certain transaction data (described below) with Bob's private key.
This lets the script verify that Bob owns the private key which
created the public key.
Bob's signature doesn't just prove Bob controls his private key; it also
makes the rest of his transaction tamper-proof so Bob can safely
broadcast it over the peer-to-peer network.
![Some Things Signed When Spending An Output](/img/dev/en-signing-output-to-spend.svg)
As illustrated in the figure above, the data Bob signs includes the
txid and output index of the previous transaction, the previous
output's script, the script Bob creates which will let the next
recipient spend this transaction's output, and the amount of satoshis to
spend to the next recipient. In essence, the entire transaction is
signed except for any scriptSigs, which hold the full public keys and
signatures.
After putting his signature and public key in the scriptSig, Bob
broadcasts the transaction to Bitcoin miners through the peer-to-peer
network. Each peer and miner independently validates the transaction
before broadcasting it further or attempting to include it in a new block of
transactions.
{% endautocrossref %}
### P2PH Script Validation
{% autocrossref %}
The validation procedure requires evaluation of the script. In a P2PH
output, the script is:
{% endautocrossref %}
~~~
OP_DUP OP_HASH160 <PubkeyHash> OP_EQUALVERIFY OP_CHECKSIG
~~~
{% autocrossref %}
The spender's scriptSig is evaluated and prefixed to the beginning of the
script. In a P2PH transaction, the scriptSig contains a signature (sig)
and full public key (pubkey), creating the following concatenation:
{% endautocrossref %}
~~~
<Sig> <PubKey> OP_DUP OP_HASH160 <PubkeyHash> OP_EQUALVERIFY OP_CHECKSIG
~~~
{% autocrossref %}
The script language is a
[Forth-like](https://en.wikipedia.org/wiki/Forth_%28programming_language%29)
[stack][]{:#term-stack}{:.term}-based language deliberately designed to be stateless and not
Turing complete. Statelessness ensures that once a transaction is added
to the block chain, there is no condition which renders it permanently
unspendable. Turing-incompleteness (specifically, a lack of loops or
gotos) makes the script language less flexible and more predictable,
greatly simplifying the security model.
<!-- Editors: please do not substitute for the words push or pop in
sections about stacks. These are programming terms. Also "above",
"below", "top", and "bottom" are commonly used relative directions or
locations in stack descriptions. -harding -->
To test whether the transaction is valid, scriptSig and script arguments
are pushed to the stack one item at a time, starting with Bob's scriptSig
and continuing to the end of Alice's script. The figure below shows the
evaluation of a standard P2PH script; below the figure is a description
of the process.
![P2PH Stack Evaluation](/img/dev/en-p2ph-stack.svg)
* The signature (from Bob's scriptSig) is added (pushed) to an empty stack.
Because it's just data, nothing is done except adding it to the stack.
The public key (also from the scriptSig) is pushed on top of the signature.
* From Alice's script, the `OP_DUP` operation is pushed. `OP_DUP` replaces
itself with a copy of the data from one level below it---in this
case creating a copy of the public key Bob provided.
* The operation pushed next, `OP_HASH160`, replaces itself with a hash
of the data from one level below it---in this case, Bob's public key.
This creates a hash of Bob's public key.
* Alice's script then pushes the pubkey hash that Bob gave her for the
first transaction. At this point, there should be two copies of Bob's
pubkey hash at the top of the stack.
* Now it gets interesting: Alice's script adds `OP_EQUALVERIFY` to the
stack. `OP_EQUALVERIFY` expands to `OP_EQUAL` and `OP_VERIFY` (not shown).
`OP_EQUAL` (not shown) checks the two values below it; in this
case, it checks whether the pubkey hash generated from the full
public key Bob provided equals the pubkey hash Alice provided when
she created transaction #1. `OP_EQUAL` then replaces itself and
the two values it compared with the result of that comparison:
zero (*false*) or one (*true*).
`OP_VERIFY` (not shown) checks the value immediately below it. If
the value is *false* it immediately terminates stack evaluation and
the transaction validation fails. Otherwise it pops both itself and
the *true* value off the stack.
* Finally, Alice's script pushes `OP_CHECKSIG`, which checks the
signature Bob provided against the now-authenticated public key he
also provided. If the signature matches the public key and was
generated using all of the data required to be signed, `OP_CHECKSIG`
replaces itself with *true.*
If *true* is at the top of the stack after the script has been
evaluated, the transaction is valid (provided there are no other
problems with it).
{% endautocrossref %}
### P2SH Scripts
{% autocrossref %}
Output scripts are created by spenders who have little interest in the
long-term security or usefulness of the particular satoshis they're
currently spending. Receivers do care about the conditions imposed on
the satoshis by the output script and, if they want, they can ask
spenders to use a particular script. Unfortunately, custom scripts are
less convenient than short Bitcoin addresses and more difficult to
secure than P2PH pubkey hashes.
To solve these problems, pay-to-script-hash
([P2SH][]{:#term-p2sh}{:.term}) transactions were created in 2012 to let
a spender create an output script containing a [hash of a second
script][script hash]{:#term-script-hash}{:.term}, the
[redeemScript][]{:#term-redeemscript}{:.term}.
The basic P2SH workflow, illustrated below, looks almost identical to
the P2PH workflow. Bob creates a redeemScript with whatever script he
wants, hashes the redeemScript, and provides the redeemScript
hash to Alice. Alice creates a P2SH-style output containing
Bob's redeemScript hash.
![Creating A P2SH RedeemScript And Hash](/img/dev/en-creating-p2sh-output.svg)
When Bob wants to spend the output, he provides his signature along with
the full (serialized) redeemScript in the input scriptSig. The
peer-to-peer network ensures the full redeemScript hashes to the same
value as the script hash Alice put in her output; it then processes the
redeemScript exactly as it would if it were the primary script, letting
Bob spend the output if the redeemScript returns true.
![Unlocking A P2SH Output For Spending](/img/dev/en-unlocking-p2sh-output.svg)
The hash of the redeemScript has the same properties as a pubkey
hash---so it can be transformed into the standard Bitcoin address format
with only one small change to differentiate it from a standard address.
This makes collecting a P2SH-style address as simple as collecting a
P2PH-style address. The hash also obfuscates any public keys in the
redeemScript, so P2SH scripts are as secure as P2PH pubkey hashes.
{% endautocrossref %}
### Standard Transactions
{% autocrossref %}
Care must be taken to avoid non-standard output scripts. As of Bitcoin Core
0.9, the standard script types are:
**Pubkey Hash (P2PH)**
P2PH is the most common form of script used to send a transaction to one
or multiple Bitcoin addresses.
{% endautocrossref %}
~~~
script: OP_DUP OP_HASH160 <PubKeyHash> OP_EQUALVERIFY OP_CHECKSIG
scriptSig: <sig> <pubkey>
~~~
{% autocrossref %}
**Script Hash (P2SH)**
P2SH is used to send a transaction to a script hash. Each of the standard
scripts can be used inside a P2SH redeemScript, but in practice only the
multisig script makes sense until more transaction types are made standard.
{% endautocrossref %}
~~~
script: OP_HASH160 <redeemscripthash> OP_EQUAL
scriptSig: <sig> [sig] [sig...] <redeemscript>
~~~
{% autocrossref %}
**Multisig**
Although P2SH multisig is now generally used for multisig transactions, this base script
can be used to require multiple signatures before a UTXO can be spent.
In multisig scripts, called m-of-n, *m* is the *minimum* number of signatures
which must match a public key; *n* is the *number* of public keys being
provided. Both *m* and *n* should be op codes `OP_1` through `OP_16`,
corresponding to the number desired.
Because of an off-by-one error in the original Bitcoin implementation
which must be preserved for compatibility, `OP_CHECKMULTISIG`
consumes one more value from the stack than indicated by *m*, so the
list of signatures in the scriptSig must be prefaced with an extra value
(`OP_0`) which will be consumed but not used.
{% endautocrossref %}
~~~
script: <m> <pubkey> [pubkey] [pubkey...] <n> OP_CHECKMULTISIG
scriptSig: OP_0 <sig> [sig] [sig...]
~~~
{% autocrossref %}
Although its not a separate transaction type, this is a P2SH multisig with 2-of-3:
{% endautocrossref %}
~~~
script: OP_HASH160 <redeemscripthash> OP_EQUAL
redeemScript: <OP_2> <pubkey> <pubkey> <pubkey> <OP_3> OP_CHECKMULTISIG
scriptSig: OP_0 <sig> <sig> <redeemscript>
~~~
{% autocrossref %}
**Pubkey**
[Pubkey][]{:#term-pubkey}{:.term} scripts are a simplified form of the P2PH script; theyre used in all
coinbase transactions, but they arent as convenient
or secure as P2PH, so they generally
arent used elsewhere.
{% endautocrossref %}
~~~
script: <pubkey> OP_CHECKSIG
scriptSig: <sig>
~~~
{% autocrossref %}
**Null Data**
[Null data][]{:#term-null-data}{:.term} scripts let you add a small amount of arbitrary data to the block
chain in exchange for paying a transaction fee, but doing so is discouraged.
(Null data is a standard script type only because some people were adding data
to the block chain in more harmful ways.)
{% endautocrossref %}
~~~
script: OP_RETURN <data>
(Null data scripts cannot be spent, so there's no scriptSig)
~~~
#### Non-Standard Transactions
{% autocrossref %}
If you use anything besides a standard script in an output, peers
and miners using the default Bitcoin Core settings will neither
accept, broadcast, nor mine your transaction. When you try to broadcast
your transaction to a peer running the default settings, you will
receive an error.
Unfortunately, if you create a non-standard redeemScript, hash it, and use the hash
in a P2SH output, the network sees only the hash, so it will accept the
output as valid no matter what the redeemScript says. When you go to
spend that output, however, peers and miners using the default settings
will see the non-standard redeemScript and reject it. It will be
impossible to spend that output until you find a miner who disables the
default settings.
As of Bitcoin Core 0.9, standard transactions must also meet the following
conditions:
* The transaction must be finalized: either its locktime must be in the
past (or less than or equal to the current block height), or all of its sequence
numbers must be 0xffffffff.
* The transaction must be smaller than 100,000 bytes. That's around 200
times larger than a typical single-input, single-output P2PH
transaction.
* Each of the transaction's inputs must be smaller than 500 bytes.
That's large enough to allow 3-of-3 multisig transactions in P2SH.
Multisig transactions which require more than 3 public keys are
currently non-standard.
* The transaction's scriptSig must only push data to the script
evaluation stack. It cannot push new OP codes, with the exception of
OP codes which solely push data to the stack.
* If any of the transaction's outputs spend less than a minimal value
(currently 546 satoshis), the transaction must pay
a minimum transaction fee (currently 10,000 satoshis).
{% endautocrossref %}
### Signature Hash Types
{% autocrossref %}
`OP_CHECKSIG` extracts a non-stack argument from each signature it
evaluates, allowing the signer to decide which parts of the transaction
to sign. Since the signature protects those parts of the transaction
from modification, this lets signers selectively choose to let other
people modify their transactions.
The various options for what to sign are
called [signature hash][]{:#term-signature-hash}{:.term} types. There are three base SIGHASH types
currently available:
* [`SIGHASH_ALL`][sighash_all]{:#term-sighash-all}{:.term}, the default, signs all the inputs and outputs,
protecting everything except the scriptSigs against modification.
* [`SIGHASH_NONE`][sighash_none]{:#term-sighash-none}{:.term} signs all of the inputs but none of the outputs,
allowing anyone to change where the satoshis are going unless other
signatures using other signature hash flags protect the outputs.
* [`SIGHASH_SINGLE`][sighash_single]{:#term-sighash-single}{:.term} signs only this input and only one corresponding
output (the output with the same output index number as the input), ensuring
nobody can change your part of the transaction but allowing other
signers to change their part of the transaction. The corresponding
output must exist or the value "1" will be signed, breaking the security
scheme.
The base types can be modified with the [`SIGHASH_ANYONECANPAY`][shacp]{:#term-sighash-anyonecanpay}{:.term} (anyone can
pay) flag, creating three new combined types:
* [`SIGHASH_ALL|SIGHASH_ANYONECANPAY`][sha_shacp]{:#term-sighash-all-sighash-anyonecanpay}{:.term} signs all of the outputs but only
this one input, and it also allows anyone to add or remove other
inputs, so anyone can contribute additional satoshis but they cannot
change how many satoshis are sent nor where they go.
* [`SIGHASH_NONE|SIGHASH_ANYONECANPAY`][shn_shacp]{:#term-sighash-none-sighash-anyonecanpay}{:.term} signs only this one input and
allows anyone to add or remove other inputs or outputs, so anyone who
gets a copy of this input can spend it however they'd like.
* [`SIGHASH_SINGLE|SIGHASH_ANYONECANPAY`][shs_shacp]{:#term-sighash-single-sighash-anyonecanpay}{:.term} signs only this input and only
one corresponding output, but it also allows anyone to add or remove
other inputs.
Because each input is signed, a transaction with multiple inputs can
have multiple signature hash types signing different parts of the transaction. For
example, a single-input transaction signed with `NONE` could have its
output changed by the miner who adds it to the block chain. On the other
hand, if a two-input transaction has one input signed with `NONE` and
one input signed with `ALL`, the `ALL` signer can choose where to spend
the satoshis without consulting the `NONE` signer---but nobody else can
modify the transaction.
<!-- TODO: describe useful combinations maybe using a 3x3 grid;
do something similar for the multisig section with different hashtypes
between different sigs -->
<!-- TODO: add to the technical section details about what the different
hash types sign, including the procedure for inserting the subscript -->
{% endautocrossref %}
### Locktime And Sequence Number
{% autocrossref %}
One thing all signature hash types sign is the transaction's [locktime][]{:#term-locktime}{:.term}.
The locktime indicates the earliest time a transaction can be added to
the block chain.
Locktime allows signers to create time-locked transactions which will
only become valid in the future, giving the signers a chance to change
their minds.
If any of the signers change their mind, they can create a new
non-locktime transaction. The new transaction will use, as one of
its inputs, one of the same outputs which was used as an input to
the locktime transaction. This makes the locktime transaction
invalid if the new transaction is added to the block chain before
the time lock expires.
Care must be taken near the expiry time of a time lock. The peer-to-peer
network allows block time to be up to two hours ahead of
real time, so a locktime transaction can be added to the block chain up
to two hours before its time lock officially expires. Also, blocks are
not created at guaranteed intervals, so any attempt to cancel a valuable
transaction should be made a few hours before the time lock expires.
Previous versions of Bitcoin Core provided a feature which prevented
transaction signers from using the method described above to cancel a
time-locked transaction, but a necessary part of this feature was
disabled to prevent DOS attacks. A legacy of this system are four-byte
[sequence numbers][sequence number]{:#term-sequence-number}{:.term} in every input. Sequence numbers were meant to allow
multiple signers to agree to update a transaction; when they finished
updating the transaction, they could agree to set every input's
sequence number to the four-byte unsigned maximum (0xffffffff),
allowing the transaction to be added to a block even if its time lock
had not expired.
Even today, setting all sequence numbers to 0xffffffff (the default in
Bitcoin Core) can still disable the time lock, so if you want to use
locktime, at least one input must have a sequence number below the
maximum. Since sequence numbers are not used by the network for any
other purpose, setting any sequence number to zero is sufficient to
enable locktime.
Locktime itself is an unsigned 4-byte number which can be parsed two ways:
* If less than 500 million, locktime is parsed as a block height. The
transaction can be added to any block which has this height or higher.
* If greater than or equal to 500 million, locktime is parsed using the
Unix epoch time format (the number of seconds elapsed since
1970-01-01T00:00 UTC---currently over 1.395 billion). The transaction
can be added to any block whose block time is greater
than the locktime.
{% endautocrossref %}
### Transaction Fees And Change
{% autocrossref %}
Transactions typically pay transaction fees based on the total byte size
of the signed transaction. The transaction fee is given to the
Bitcoin miner, as explained in the [block chain section][block chain], and so it is
ultimately up to each miner to choose the minimum transaction fee they
will accept.
<!-- TODO: check: 50 KB or 50 KiB? Not that transactors care... -->
By default, miners reserve 50 KB of each block for [high-priority
transactions][]{:#term-high-priority-transactions}{:.term} which spend satoshis that haven't been spent for a long
time. The remaining space in each block is typically allocated to transactions
based on their fee per byte, with higher-paying transactions being added
in sequence until all of the available space is filled.
As of Bitcoin Core 0.9, transactions which do not count as high-priority transactions
need to pay a [minimum fee][]{:#term-minimum-fee}{:.term} of 10,000 satoshis to be
broadcast across the network. Any transaction paying the minimum fee
should be prepared to wait a long time before there's enough spare space
in a block to include it. Please see the [verifying payment section][section verifying payment]
for why this could be important.
Since each transaction spends Unspent Transaction Outputs (UTXOs) and
because a UTXO can only be spent once, the full value of the included
UTXOs must be spent or given to a miner as a transaction fee. Few
people will have UTXOs that exactly match the amount they want to pay,
so most transactions include a change output.
[Change outputs][change output]{:#term-change-output}{:.term} are regular outputs which spend the surplus satoshis
from the UTXOs back to the spender. They can reuse the same P2PH pubkey hash
or P2SH script hash as was used in the UTXO, but for the reasons
described in the [next subsection](#avoiding-key-reuse), it is highly recommended that change
outputs be sent to a new P2PH or P2SH address.
{% endautocrossref %}
### Avoiding Key Reuse
{% autocrossref %}
In a transaction, the spender and receiver each reveal to each other all
public keys or addresses used in the transaction. This allows either
person to use the public block chain to track past and future
transactions involving the other person's same public keys or addresses.
If the same public key is reused often, as happens when people use
Bitcoin addresses (hashed public keys) as static payment addresses,
other people can easily track the receiving and spending habits of that
person, including how many satoshis they control in known addresses.
It doesn't have to be that way. If each public key is used exactly
twice---once to receive a payment and once to spend that payment---the
user can gain a significant amount of financial privacy.
Even better, using new public keys or [unique
addresses][]{:#term-unique-address}{:.term} when accepting payments or creating
change outputs can be combined with other techniques discussed later,
such as CoinJoin or merge avoidance, to make it extremely difficult to
use the block chain by itself to reliably track how users receive and
spend their satoshis.
Avoiding key reuse in combination with P2PH or P2SH addresses also
prevents anyone from seeing the user's ECDSA public key until he spends
the satoshis sent to those addresses. This, combined with the block
chain, provides security against hypothetical future attacks which may
allow reconstruction of private keys from public keys in a matter of
hours, days, months, or years (but not any faster).
So, for both privacy and security, we encourage you to build your
applications to avoid public key reuse and, when possible, to discourage
users from reusing addresses. If your application needs to provide a
fixed URI to which payments should be sent, please see the
[`bitcoin:` URI section][bitcoin URI subsection] below.
{% endautocrossref %}
### Transaction Malleability
{% autocrossref %}
None of Bitcoin's signature hash types protect the scriptSig, leaving
the door open for a limited DOS attack called [transaction
malleability][]{:.term}{:#term-transaction-malleability}. The scriptSig
contains the signature, which can't sign itself, allowing attackers to
make non-functional modifications to a transaction without rendering it
invalid. For example, an attacker can add some data to the scriptSig
which will be dropped before the previous output script is processed.
Although the modifications are non-functional---so they do not change
what inputs the transaction uses nor what outputs it pays---they do
change the computed hash of the transaction. Since each transaction
links to previous transactions using hashes as a transaction
identifier (txid), a modified transaction will not have the txid its
creator expected.
This isn't a problem for most Bitcoin transactions which are designed to
be added to the block chain immediately. But it does become a problem
when the output from a transaction is spent before that transaction is
added to the block chain.
Bitcoin developers have been working to reduce transaction malleability
among standard transaction types, but a complete fix is still only in
the planning stages. At present, new transactions should not depend on
previous transactions which have not been added to the block chain yet,
especially if large amounts of satoshis are at stake.
Transaction malleability also affects payment tracking. Bitcoin Core's
RPC interface lets you track transactions by their txid---but if that
txid changes because the transaction was modified, it may appear that
the transaction has disappeared from the network.
Current best practices for transaction tracking dictate that a
transaction should be tracked by the transaction outputs (UTXOs) it
spends as inputs, as they cannot be changed without invalidating the
transaction.
<!-- TODO/harding: The paragraph above needs practical advice about how
to do that. I'll need to find some time to look at somebody's wallet
code. -harding -->
Best practices further dictate that if a transaction does seem to
disappear from the network and needs to be reissued, that it be reissued
in a way that invalidates the lost transaction. One method which will
always work is to ensure the reissued payment spends all of the same
outputs that the lost transaction used as inputs.
{% endautocrossref %}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,872 @@
#### ping
~~~
ping
~~~
{% autocrossref %}
Requests that a ping be sent to all other nodes, to measure ping time.
Results provided in `getpeerinfo` pingtime and pingwait fields as
decimal seconds. Ping command is handled in queue with all other
commands, so it measures processing backlog, not just network ping.
{% endautocrossref %}
**Example**
~~~
bitcoin-cli -testnet ping
~~~
(Success: no result printed.)
#### sendfrom
~~~
sendfrom <account> <address> <amount> [confirmations] [comment] [label]
~~~
{% autocrossref %}
Spend an amount from an account to a bitcoin address.
{% endautocrossref %}
**Argument #1: From Account**
{% autocrossref %}
*String, required:* the name of the account from which to spend the
funds. Use "" for the default account.
{% endautocrossref %}
**Argument #2: To Address**
{% autocrossref %}
*String, required:* the address to which the funds should be
spent. Use "" for the default account.
{% endautocrossref %}
**Argument #3: Amount To Spend**
{% autocrossref %}
*Number; required:* the amount to spend in decimal bitcoins.
{% endautocrossref %}
**Argument #4: Minimum Confirmations**
{% autocrossref %}
*Number; optional:* the minimum number of confirmations an incoming
transaction must have before it will be spent. Previously spent UTXOs
are not included regardless of the number of confirmations. Default is
1; use 0 to spend unconfirmed transactions.
{% endautocrossref %}
**Argument #5: A Comment**
{% autocrossref %}
*String; optional:* a comment to associate with this transaction.
{% endautocrossref %}
**Argument #6: A Label**
{% autocrossref %}
*String; optional:* the label (name) to give the recipient.
{% endautocrossref %}
**Result: TXID**
{% autocrossref %}
A txid for the transaction created.
{% endautocrossref %}
**Example**
{% autocrossref %}
Spend 0.1 bitcoins from the account "doc test" to the address indicated below
using only UTXOs with at least six confirmations, giving the
transaction the comment "Example spend" and labeling the spender
"Example.com":
{% endautocrossref %}
~~~
bitcoin-cli -testnet sendfrom "doc test" \
mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe \
0.1 \
6 \
"Example spend" \
"Example.com"
~~~
Result:
~~~
ca7cb6a5ffcc2f21036879493db4530c0ce9b5bff9648f9a3be46e2dfc8e0166
~~~
#### sendmany
~~~
sendmany <account> <addresses & amounts> [confirmations] [memo]
~~~
{% autocrossref %}
Create and broadcast a transaction which spends outputs to multiple addresses.
{% endautocrossref %}
**Argument #1: Account From Which The Satoshis Should Be Sent**
{% autocrossref %}
*String; required:* the wallet account from which the funds should be
withdrawn. Can be "" for the default account.
{% endautocrossref %}
**Argument #2: The Output Address/Amount Pairs**
{% autocrossref %}
*String; required:* a JSON object with addresses as keys and amounts as values.
{% endautocrossref %}
~~~
{
"<address>":<amount in decimal bitcoins>
,[...]
}
~~~
**Argument #3: The Minimum Number Of Confirmations For Inputs**
{% autocrossref %}
*Number; optional:* the minimum number of confirmations an previously-received
output must have before it will be spent. The default is 1
confirmation.
{% endautocrossref %}
**Argument #4: A Memo**
{% autocrossref %}
*String, optional:* a memo to be recorded with this transaction for
record-keeping purposes. The memo is not included in the transaction.
{% endautocrossref %}
**Result: A Transaction Identifier**
{% autocrossref %}
*String:* a transaction identifier (txid) for the transaction created
and broadcast to the peer-to-peer network.
{% endautocrossref %}
**Example**
{% autocrossref %}
From the account *test1*, send 0.1 bitcoins to the first address and 0.2
bitcoins to the second address, with a memo of "Example Transaction".
{% endautocrossref %}
~~~
> bitcoin-cli -testnet sendmany \
"test1" \
'''
{
"mjSk1Ny9spzU2fouzYgLqGUD8U41iR35QN": 0.1,
"mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe": 0.2
} ''' \
6 \
"Example Transaction"
~~~
Result:
~~~
ef7c0cbf6ba5af68d2ea239bba709b26ff7b0b669839a63bb01c2cb8e8de481e
~~~
#### sendrawtransaction
~~~
sendrawtransaction <hex> [true|false]
~~~
{% autocrossref %}
Broadcasts transaction in rawtransaction format to the peer-to-peer network.
See also: `createrawtransaction` and `signrawtransaction`
{% endautocrossref %}
**Argument #1: Raw Transaction**
{% autocrossref %}
*String; required:* a fully-signed transaction in rawtransaction format
(hex).
{% endautocrossref %}
**Argument #2: Whether To Allow High Fees**
{% autocrossref %}
*Boolean; optional:* whether or not to allow the transaction to have a
high transaction fee. Transaction fees are the difference between the
sum of the inputs and the sum of the outputs, so a raw transaction which
accidentally leaves off a change output, for example, can have a
transaction fee dozens or hundreds of times larger than the network
norm. If *true* is specified, that will be allowed. If *false* (the
default), the transaction will be rejected with an informative error
message.
{% endautocrossref %}
**Result: A TXID Or Error Message**
{% autocrossref %}
If successful, the transaction's txid (hash) will be returned. If
unsuccessful, an error message will be returned.
{% endautocrossref %}
**Examples**
{% autocrossref %}
Create and sign a transaction spending over 0.2 bitcoins as fees:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet signrawtransaction $(
bitcoin-cli -testnet createrawtransaction '''
[
{
"txid": "ef7c0cbf6ba5af68d2ea239bba709b26ff7b0b669839a63bb01c2cb8e8de481e",
"vout": 0
}
]''' '''
{
"mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe": 0.1
}'''
)
~~~
Result:
~~~
{
"hex" : "01000000011e48dee8b82c1cb03ba63998660b7bff269b70ba9\
b23ead268afa56bbf0c7cef000000006b4830450221009c711c\
e4df4cd8e22a10016ff6098e799f081e3a1706a9c0df14eeeb8\
6c31bb302206323d29ab4f3138371df7b7bb794bb7c6a5e7e40\
161e98b5c873f892d319d5230121027ce4f9db9f237fc75e420\
742320c7df3b4ca95c44b6bc715400930f24870b2b1ffffffff\
0180969800000000001976a9140dfc8bafc8419853b34d5e072\
ad37d1a5159f58488ac00000000",
"complete" : true
}
~~~
{% autocrossref %}
Now attempt to broadcast it:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet sendrawtransaction 01000000011e48dee8b82c\
1cb03ba63998660b7bff269b70ba9b23ead268afa56bbf0c7cef00000000\
6b4830450221009c711ce4df4cd8e22a10016ff6098e799f081e3a1706a9\
c0df14eeeb86c31bb302206323d29ab4f3138371df7b7bb794bb7c6a5e7e\
40161e98b5c873f892d319d5230121027ce4f9db9f237fc75e420742320c\
7df3b4ca95c44b6bc715400930f24870b2b1ffffffff0180969800000000\
001976a9140dfc8bafc8419853b34d5e072ad37d1a5159f58488ac00000000
~~~
Result:
~~~
error: {"code":-22,"message":"TX rejected"}
~~~
{% autocrossref %}
Allow high fees to force it to spend:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet sendrawtransaction 01000000[...]00000000 true
~~~
Result (success):
~~~
6d62d3f74be5ca614e32a2fb662deabe87ff95c7d90228cd8615da39cc824e34
~~~
#### sendtoaddress
~~~
sendtoaddress <address> <amount> <memo> <label>
~~~
{% autocrossref %}
Spend an amount to a given address. Encrypted wallets must be unlocked first.
{% endautocrossref %}
**Argument #1: Address**
{% autocrossref %}
*String; required:* A bitcoin address which will received payment.
{% endautocrossref %}
**Argument #2: Amount**
{% autocrossref %}
*Number; required:* the amount in decimal bitcoins.
{% endautocrossref %}
**Argument #3: Memo**
{% autocrossref %}
*String; optional:* the memo to give the transaction. This is not
broadcast to the peer-to-peer network; it is stored in your wallet only.
{% endautocrossref %}
**Argument #4: Label**
{% autocrossref %}
*String; optional:* the label to give the transaction. This is not
broadcast to the peer-to-peer network; it is stored in your wallet only.
{% endautocrossref %}
**Result: TXID**
{% autocrossref %}
If the spend is successful, the txid is returned.
{% endautocrossref %}
**Example**
{% autocrossref %}
Spend 0.1 bitcoins to the address below with the memo "sendtoadress
example" and the label "Nemo From Example.com":
{% endautocrossref %}
~~~
> bitcoin-cli -testnet sendtoaddress mmXgiR6KAhZCyQ8ndr2BCfEq1wNG2UnyG6 \
0.1 "sendtoaddress example" "Nemo From Example.com"
~~~
~~~
85a98fdf1529f7d5156483ad020a51b7f3340e47448cf932f470b72ff01a6821
~~~
#### setaccount
~~~
setaccount <address> <account>
~~~
{% autocrossref %}
Puts the given address in the given account.
{% endautocrossref %}
**Argument #1: A Bitcoin Address**
{% autocrossref %}
*String; required:* the address to put in the account.
{% endautocrossref %}
**Argument #2: An Account**
{% autocrossref %}
*String; required:* the account in which to put the address.
{% endautocrossref %}
**Result: None On Success**
{% autocrossref %}
No result generated on success.
{% endautocrossref %}
**Example**
{% autocrossref %}
Put the address indicated below in the "doc test" account.
{% endautocrossref %}
~~~
> bitcoin-cli -testnet setaccount \
mmXgiR6KAhZCyQ8ndr2BCfEq1wNG2UnyG6 "doc test"
~~~
(Success: no result displayed.)
#### setgenerate
~~~
setgenerate <true|false> [processors]
~~~
{% autocrossref %}
Enable or disable hashing to attempt to find the next block.
See also: `getgenerate`
{% endautocrossref %}
**Argument #1: Whether To Enable Or Disable Generation**
{% autocrossref %}
*Boolean; required:* to enable generation, *true*; to disable, *false*.
{% endautocrossref %}
**Argument #2: The Number Of Processors To Use**
{% autocrossref %}
*Number; optional:* the number of logical processors to use. Defaults
to 1; use -1 to use all available processors.
*Note:* in regtest mode, this argument will automatically create that
number of blocks. See example below.
{% endautocrossref %}
**Result: None On Success**
No result on success.
**Examples**
{% autocrossref %}
Enable generation using two logical processors (on this machine, two
cores of one physical processor):
{% endautocrossref %}
~~~
> bitcoin-cli -testnet setgenerate true 2
~~~
{% autocrossref %}
(Success: no result displayed. Process manager shows 200% CPU usage.)
Using regtest mode, generate 101 blocks (enough to be able to spend the
coinbase transaction of the first block generated):
{% endautocrossref %}
~~~
> bitcoin-cli -regtest setgenerate true 101
~~~
{% autocrossref %}
(Success: no result displayed. Wallet balance shows 50 bitcoins available.)
{% endautocrossref %}
#### settxfee
~~~
settxfee amount
~~~
{% autocrossref %}
Set the transaction fee per kilobyte.
{% endautocrossref %}
**Argument: Amount**
{% autocrossref %}
*Number; required:* the transaction fee in decimal bitcoins per kilobyte.
Will be rounded up to the nearest satoshi (0.00000001).
{% endautocrossref %}
**Result: True Or False**
{% autocrossref %}
*True* if successful.
{% endautocrossref %}
**Example**
{% autocrossref %}
Set the transaction fee per kilobyte to 100,000 satoshis (1 millibit).
{% endautocrossref %}
~~~
> bitcoin-cli -testnet settxfee 0.00100000
~~~
Result:
~~~
true
~~~
#### signmessage
~~~
signmessage <address> <message>
~~~
{% autocrossref %}
Sign a message with the private key of an address. Encrypted wallets
must be unlocked first.
{% endautocrossref %}
**Argument #1: Address**
{% autocrossref %}
*String; required:* the Bitcoin address corresponding to the private key
which should be used to sign the message.
{% endautocrossref %}
**Argument #2: Message**
{% autocrossref %}
*String; required:* The message to sign.
{% endautocrossref %}
**Result: Message Signature**
{% autocrossref %}
The signature of the message encoded in base64.
{% endautocrossref %}
**Example**
{% autocrossref %}
Sign a the message "Hello, World!" using the following address:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet signmessage mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe \
'Hello, World!'
~~~
Result:
~~~
IOGreqb/7UgD1ifcojESd32ZJgH5RGzUXitmbl6ZbdenSmitipWoLSi73TskmLY7zhcD662bTw3RHoYQl/dOAhE=
~~~
#### signrawtransaction
~~~
signrawtransaction <raw transaction hex> [previous transactions] [private keys] [sighashtype]
~~~
{% autocrossref %}
Sign inputs of a transaction in rawtransaction format using private keys
stored in the wallet or provided in the call.
{% endautocrossref %}
**Argument #1: The Transaction To Sign**
{% autocrossref %}
*String; required:* the transaction to sign in rawtransaction format
(hex).
{% endautocrossref %}
**Argument #2: P2SH Transaction Dependencies**
{% autocrossref %}
*String; optional:* A JSON array of JSON objects. Each object contains
details about an unknown-to-this-node P2SH transaction that this transaction
depends upon.
Each previous P2SH transaction must include its *txid* in hex, output
index number (*vout*), public key (*scriptPubKey*) in hex, and
*redeemScript* in hex.
{% endautocrossref %}
~~~
[
{
"txid":"<txid>",
"vout":<output index number>,
"scriptPubKey": "<scriptPubKey in hex>",
"redeemScript": "<redeemScript in hex>"
}
,[...]
]
~~~
**Argument #3: Private Keys For Signing**
{% autocrossref %}
*String; optional:* A JSON array of base58check-encoded private keys to use
for signing. If this argument is used, only the keys provided will be
used to sign even if the wallet has other matching keys. If this
argument is omitted, keys from the wallet will be used.
{% endautocrossref %}
~~~
[
"<private key in base58check hex>"
,[...]
]
~~~
**Argument #4: Sighash Type**
{% autocrossref %}
*String, optional:* The type of signature hash to use for all of the
signatures performed. (You must use separate calls to
`signrawtransaction` if you want to use different sighash types for
different signatures.)
The allowed values are *ALL*, *NONE*,
*SINGLE*, *ALL|ANYONECANPAY*, *NONE|ANYONECANPAY*,
and *SINGLE|ANYONECANPAY*.
{% endautocrossref %}
**Result: Signed Transaction**
{% autocrossref %}
*String:* a JSON object containing the transaction in *hex* with as many
signatures as could be applied and a *complete* key indicating whether
or not the the transaction is fully signed (0 indicates it is not
complete).
{% endautocrossref %}
~~~
{
"hex": "<signed raw transaction hex>",
"complete": <0|1>
}
~~~
**Example**
{% autocrossref %}
Sign the hex generated in the example section for the `rawtransaction`
RPC:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet signrawtransaction 010000000189957b01aed5\
96d3b361b576234eaeed3249246f14562d6bc6085166cd247d\
5a0000000000ffffffff0180969800000000001976a9140dfc\
8bafc8419853b34d5e072ad37d1a5159f58488ac00000000
~~~
Result:
~~~
{
"hex" : "010000000189957b01aed596d3b361b576234eaeed3249246f145\
62d6bc6085166cd247d5a000000006b483045022100c7a034fd7d\
990b8a2bfba45fde44cae40b5ffbe42c5cf7d8143bfe317bdef3f\
10220584e52f59b6a46d688322d65178efe83972a8517c9479630\
6d40083af5b807c901210321eeeb46fd878ce8e62d5e0f408a0ea\
b41d7c3a7872dc836ce360439536e423dffffffff018096980000\
0000001976a9140dfc8bafc8419853b34d5e072ad37d1a5159f58\
488ac00000000",
"complete" : true
}
~~~
#### stop
~~~
stop
~~~
Stop the Bitcoin Core server.
**Example**
~~~
bitcoin-cli -testnet stop
~~~
(Success: no result printed but `bitcoind` shutdown.)
#### submitblock
~~~
submitblock <new block> [extra parameters]
~~~
{% autocrossref %}
Attempts to broadcast a new block to network. Extra parameters are ignored
by Bitcoin Core but may be used by mining pools or other programs.
{% endautocrossref %}
**Argument #1: The New Block In Hex**
{% autocrossref %}
*String; required:* the hex-encoded block data to broadcast to the
peer-to-peer network.
{% endautocrossref %}
**Argument #2: Extra Parameters**
{% autocrossref %}
*String; optional:* A JSON object containing extra parameters for
mining pools and other software, such as a work identifier (workid).
The extra parameters will not be broadcast to the network.
{% endautocrossref %}
~~~
{
"<key>" : "<value>"
}
~~~
**Result: None**
No result printed if successful. An error message if failed.
**Example**
{% autocrossref %}
Submit the following block with the workid, "test".
{% endautocrossref %}
~~~
> bitcoin-cli -testnet submitblock 02000000df11c014a8d798395b505\
9c722ebdf3171a4217ead71bf6e0e99f4c7000000004a6f6a2\
db225c81e77773f6f0457bcb05865a94900ed11356d0b75228\
efb38c7785d6053ffff001d005d43700101000000010000000\
00000000000000000000000000000000000000000000000000\
0000000ffffffff0d03b477030164062f503253482ffffffff\
f0100f9029500000000232103adb7d8ef6b63de74313e0cd4e\
07670d09a169b13e4eda2d650f529332c47646dac00000000\
'{ "workid": "test" }'
~~~

View file

@ -0,0 +1,299 @@
#### validateaddress
~~~
validateaddress <address>
~~~
{% autocrossref %}
Return information about the given Bitcoin address.
{% endautocrossref %}
**Argument: An Address**
{% autocrossref %}
*String; required:* A Bitcoin address.
{% endautocrossref %}
**Result: Information About The Address**
{% autocrossref %}
A JSON object containing one or more values (the exact number depending
on the information). The result of *isvalid* is always returned to
indicated whether or not the address is valid. If it is valid, the
validated *address* is returned plus *ismine* to indicate whether or not
it belongs to this wallet and *account* to indicate which account it
belongs to. If it's a P2SH address, *isscript* will be true. If it's a
P2PH address, *pubkey* will contain the public key and *compressed* will
indicate whether or not the pubkey/address is compressed.
{% endautocrossref %}
~~~
{
"isvalid" : <true|false>,
"address" : "<address>",
"ismine" : <true|false>,
"isscript" : <true|false>,
"pubkey" : "<public key hex>",
"iscompressed" : <true|false>,
"account" : "<account>"
}
~~~
**Example**
{% autocrossref %}
Validate the following address from the wallet:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet validateaddress mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe
~~~
Result:
~~~
{
"isvalid" : true,
"address" : "mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe",
"ismine" : true,
"isscript" : false,
"pubkey" : "03bacb84c6464a58b3e0a53cc0ba4cb3b82848cd7bed25a7724b3cc75d76c9c1ba",
"iscompressed" : true,
"account" : "test label"
}
~~~
#### verifychain
~~~
verifychain [throughness] [blocks]
~~~
{% autocrossref %}
Verify the local blockchain database.
{% endautocrossref %}
**Argument #1: Throughness**
{% autocrossref %}
*Number; optional:* how thoroughly to check the database, from 0 to 4
with 4 being the most through. Defaults to 3. <!-- TODO: what does each
level do? -->
{% endautocrossref %}
**Argument #2: Number Of Blocks To Check**
{% autocrossref %}
*Number; optional:* check this number of the most recent blocks.
{% endautocrossref %}
**Result: Verified Or Not**
*True* if verified.
**Example**
{% autocrossref %}
Verify the most recent 10,000 blocks in the most through way:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet verifychain 4 10000
~~~
Result (took 25 seconds on a generic PC laptop):
~~~
true
~~~
#### verifymessage
~~~
verifymessage <address> <signature> <message>
~~~
{% autocrossref %}
Verify a signed message.
{% endautocrossref %}
**Argument #1: The Address**
{% autocrossref %}
*String; required:* the address corresponding to the private key used to
create the signature.
{% endautocrossref %}
**Argument #2: The Signature**
{% autocrossref %}
*String; required:* the signature provided in the same base64 format
generated by `signmessage`.
{% endautocrossref %}
**Argument #3: The Message**
{% autocrossref %}
*String; required:* the exact message which was signed.
{% endautocrossref %}
**Result: True Or False**
{% autocrossref %}
*True* if the message provided was signed by the private key corresponding to the
address provided.
{% endautocrossref %}
**Example**
{% autocrossref %}
Check the signature on the message created in the example for
`signmessage`:
{% endautocrossref %}
~~~
> bitcoin-cli -testnet verifymessage \
mgnucj8nYqdrPFh2JfZSB1NmUThUGnmsqe \
IOGreqb/7UgD1ifcojESd32ZJgH5RGzUXitmbl6ZbdenSmitipWoLSi73TskmLY7zhcD662bTw3RHoYQl/dOAhE= \
'Hello, World!'
~~~
Result:
~~~
true
~~~
#### walletlock
~~~
walletlock
~~~
{% autocrossref %}
Removes the wallet encryption key from memory, locking the wallet. After
calling this method, you will need to call `walletpassphrase` again before
being able to call any methods which require the wallet to be unlocked.
{% endautocrossref %}
**Return**
No return printed on success.
**Example**
~~~
> bitcoin-cli -testnet walletlock
~~~
(Success: nothing printed.)
#### walletpassphrase
walletpassphrase <passphrase> <seconds>
{% autocrossref %}
Stores the wallet decryption key in memory for the indicated number of
seconds. Issuing the `walletpassphrase` command while the wallet is
already unlocked will set a new unlock time that overrides the old one.
{% endautocrossref %}
**Argument #1: The Passphrase**
{% autocrossref %}
*String; required:* the passphrase to unlock the encrypted wallet.
{% endautocrossref %}
**Argument #2: The Number Of Seconds To Leave The Wallet Unlocked**
{% autocrossref %}
*Number; required:* The number of seconds after which the decryption key
will be automatically deleted from memory.
{% endautocrossref %}
**Result**
No result printed on success.
**Example**
{% autocrossref %}
Unlock the wallet for 10 minutes (the passphrase is "test"):
{% endautocrossref %}
~~~
> bitcoin-cli -testnet walletpassphrase test 600
~~~
(Success: no result printed.)
#### walletpassphrasechange
~~~
walletpassphrasechange <old passphrase> <new passphrase>
~~~
{% autocrossref %}
Changes the wallet passphrase from 'old passphrase' to 'new passphrase'.
{% endautocrossref %}
**Argument #1: The Old Passphrase**
*String; required:* the current passphrase.
**Argument #2: The New Passphrase**
*String; required:* the new passphrase.
**Result**
No result printed on success.
**Example**
Change the wallet passphrase from "test" to "example":
~~~
> bitcoin-cli -testnet walletpassphrasechange test example
~~~
(Success: no result printed.)

81
_plugins/autocrossref.rb Normal file
View file

@ -0,0 +1,81 @@
## autocrossref.rb automatically adds cross reference links in documentation
## texts using the list of words defined in _autocrossref.yaml.
## Example:
## {% autocrossref %}
## ...content...
## {% endautocrossref %}
## If you have a patten you usually want to match (such as "satoshi"
## (currency)) but which may appear a few times where you don't want it
## to match (such as "Satoshi" (name)), append a <!--noref--> HTML comment.
## E.g.: Bitcoin was invented by Satoshi<!--noref--> Nakamoto.
## An alternative match-prevention method, useful for strings inside ``
## (code) is to make it look to the parser like the string is inside of
## a do-not-parse [bracket] expression. E.g. [paymentrequest][] would
## otherwise match this:
## <!--[-->`src/qt/paymentrequest.proto`<!--]-->
module Jekyll
require 'yaml'
class AutoCrossRefBlock < Liquid::Block
def initialize(tag_name, text, tokens)
super
end
def render(context)
output = super
## Workaround for inconsistent relative directory
path = File.expand_path(File.dirname(__FILE__)) + "/.."
## Load terms from file
site = context.registers[:site].config
if !site.has_key?("crossref")
site['crossref'] = YAML.load_file(path + "/_autocrossref.yaml")
end
## Sort terms by reverse length, so longest matches get linked
## first (e.g. "block chain" before "block"). Otherwise short
## terms would get linked first and there'd be nothing for long
## terms to link to.
site['crossref'].sort_by { |k, v| -k.length }.each { |term|
term[1] = term[0] if term[1].nil? || term[1].empty?
term[0] = Regexp.escape(term[0])
## Replace literal space with \s to match across newlines. This
## can do weird things if you don't end sentences with a period,
## such as linking together "standard" and "transactions" in
## something like this:
### * RFC1234 is a standard
###
### Transactions are cool
term[0].gsub!('\ ', '\s+')
output.gsub!(/
(?<!\w) ## Don't match inside words
#{term[0]}('s)? ## Find our key
(?![^\[]*\]) ## No subst if key inside [brackets]
(?![^\{]*\}) ## No subst if key inside {braces}
(?![^\s]*<!--noref-->) ## No subst if <!--noref--> after key
(?![^\(]*(\.svg|\.png)) ## No subst if key inside an image name. This
## simple regex has the side effect that we can't
## use .svg or .png in non-image base text; if that
## becomes an issue, we can devise a more complex
## regex
(?!\w) ## Don't match inside words
/xmi, "[\\&][#{term[1]}]{:.auto-link}")
}
output.gsub!('<!--noref-->','') ## Remove all <!--noref--> comments
output
end
end
end
Liquid::Template.register_tag('autocrossref', Jekyll::AutoCrossRefBlock)

View file

@ -0,0 +1,39 @@
digraph {
size=6.25;
rankdir=BT
node [ shape = "box" ]
subgraph cluster_height {
h0 [ label = "Block 0" ]
h1 [ label = "Block 1" ]
h100 [ label = "Block 100" ]
h101 [ label = "Block 101" ]
h102 [ label = "Block 102" ]
h0 -> h1
h1 -> h100 [ style = dotted ];
h100 -> h101 -> h102
label = "Block Height"
labelloc = b;
}
subgraph cluster_depth {
edge [ dir = "back" ];
d0 [ label = "Depth 101" ]
d1 [ label = "Depth 100" ]
d100 [ label = "Depth 3" ]
d101 [ label = "Depth 2" ]
d102 [ label = "Depth 1" ]
d0 -> d1
d1 -> d100 [ style = dotted];
d100 -> d101 -> d102
label = "Block Depth"
labelloc = b;
}
label = "Block Height Compared\nTo Block Depth"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

View file

@ -0,0 +1,113 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: _anonymous_0 Pages: 1 -->
<svg width="242pt" height="431pt"
viewBox="0.00 0.00 242.00 431.00" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(1 1) rotate(0) translate(4 427)">
<title>_anonymous_0</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-427 239,-427 239,5 -4,5"/>
<text text-anchor="middle" x="117" y="-25.4" font-family="Sans" font-size="14.00">Block Height Compared</text>
<text text-anchor="middle" x="117" y="-8.4" font-family="Sans" font-size="14.00">To Block Depth</text>
<g id="graph2" class="cluster"><title>cluster_height</title>
<polygon fill="none" stroke="black" points="8,-50 8,-415 112,-415 112,-50 8,-50"/>
<text text-anchor="middle" x="60" y="-398.4" font-family="Sans" font-size="14.00">Block Height</text>
</g>
<g id="graph3" class="cluster"><title>cluster_depth</title>
<polygon fill="none" stroke="black" points="120,-50 120,-415 226,-415 226,-50 120,-50"/>
<text text-anchor="middle" x="173" y="-398.4" font-family="Sans" font-size="14.00">Block Depth</text>
</g>
<!-- h0 -->
<g id="node2" class="node"><title>h0</title>
<polygon fill="none" stroke="black" points="93,-94 27,-94 27,-58 93,-58 93,-94"/>
<text text-anchor="middle" x="60" y="-71.9" font-family="Sans" font-size="14.00">Block 0</text>
</g>
<!-- h1 -->
<g id="node3" class="node"><title>h1</title>
<polygon fill="none" stroke="black" points="93,-166 27,-166 27,-130 93,-130 93,-166"/>
<text text-anchor="middle" x="60" y="-143.9" font-family="Sans" font-size="14.00">Block 1</text>
</g>
<!-- h0&#45;&gt;h1 -->
<g id="edge3" class="edge"><title>h0&#45;&gt;h1</title>
<path fill="none" stroke="black" d="M60,-94.1686C60,-101.869 60,-111.026 60,-119.583"/>
<polygon fill="black" stroke="black" points="56.5001,-119.587 60,-129.587 63.5001,-119.587 56.5001,-119.587"/>
</g>
<!-- h100 -->
<g id="node4" class="node"><title>h100</title>
<polygon fill="none" stroke="black" points="102,-238 18,-238 18,-202 102,-202 102,-238"/>
<text text-anchor="middle" x="60" y="-215.9" font-family="Sans" font-size="14.00">Block 100</text>
</g>
<!-- h1&#45;&gt;h100 -->
<g id="edge5" class="edge"><title>h1&#45;&gt;h100</title>
<path fill="none" stroke="black" stroke-dasharray="1,5" d="M60,-166.169C60,-173.869 60,-183.026 60,-191.583"/>
<polygon fill="black" stroke="black" points="56.5001,-191.587 60,-201.587 63.5001,-191.587 56.5001,-191.587"/>
</g>
<!-- h101 -->
<g id="node5" class="node"><title>h101</title>
<polygon fill="none" stroke="black" points="102,-310 18,-310 18,-274 102,-274 102,-310"/>
<text text-anchor="middle" x="60" y="-287.9" font-family="Sans" font-size="14.00">Block 101</text>
</g>
<!-- h100&#45;&gt;h101 -->
<g id="edge7" class="edge"><title>h100&#45;&gt;h101</title>
<path fill="none" stroke="black" d="M60,-238.169C60,-245.869 60,-255.026 60,-263.583"/>
<polygon fill="black" stroke="black" points="56.5001,-263.587 60,-273.587 63.5001,-263.587 56.5001,-263.587"/>
</g>
<!-- h102 -->
<g id="node6" class="node"><title>h102</title>
<polygon fill="none" stroke="black" points="102,-382 18,-382 18,-346 102,-346 102,-382"/>
<text text-anchor="middle" x="60" y="-359.9" font-family="Sans" font-size="14.00">Block 102</text>
</g>
<!-- h101&#45;&gt;h102 -->
<g id="edge8" class="edge"><title>h101&#45;&gt;h102</title>
<path fill="none" stroke="black" d="M60,-310.169C60,-317.869 60,-327.026 60,-335.583"/>
<polygon fill="black" stroke="black" points="56.5001,-335.587 60,-345.587 63.5001,-335.587 56.5001,-335.587"/>
</g>
<!-- d0 -->
<g id="node11" class="node"><title>d0</title>
<polygon fill="none" stroke="black" points="218,-94 128,-94 128,-58 218,-58 218,-94"/>
<text text-anchor="middle" x="173" y="-71.9" font-family="Sans" font-size="14.00">Depth 101</text>
</g>
<!-- d1 -->
<g id="node12" class="node"><title>d1</title>
<polygon fill="none" stroke="black" points="218,-166 128,-166 128,-130 218,-130 218,-166"/>
<text text-anchor="middle" x="173" y="-143.9" font-family="Sans" font-size="14.00">Depth 100</text>
</g>
<!-- d0&#45;&gt;d1 -->
<g id="edge11" class="edge"><title>d0&#45;&gt;d1</title>
<path fill="none" stroke="black" d="M173,-104.427C173,-112.892 173,-121.941 173,-129.587"/>
<polygon fill="black" stroke="black" points="176.5,-104.169 173,-94.1686 169.5,-104.169 176.5,-104.169"/>
</g>
<!-- d100 -->
<g id="node13" class="node"><title>d100</title>
<polygon fill="none" stroke="black" points="209,-238 137,-238 137,-202 209,-202 209,-238"/>
<text text-anchor="middle" x="173" y="-215.9" font-family="Sans" font-size="14.00">Depth 3</text>
</g>
<!-- d1&#45;&gt;d100 -->
<g id="edge13" class="edge"><title>d1&#45;&gt;d100</title>
<path fill="none" stroke="black" stroke-dasharray="1,5" d="M173,-176.427C173,-184.892 173,-193.941 173,-201.587"/>
<polygon fill="black" stroke="black" points="176.5,-176.169 173,-166.169 169.5,-176.169 176.5,-176.169"/>
</g>
<!-- d101 -->
<g id="node14" class="node"><title>d101</title>
<polygon fill="none" stroke="black" points="209,-310 137,-310 137,-274 209,-274 209,-310"/>
<text text-anchor="middle" x="173" y="-287.9" font-family="Sans" font-size="14.00">Depth 2</text>
</g>
<!-- d100&#45;&gt;d101 -->
<g id="edge15" class="edge"><title>d100&#45;&gt;d101</title>
<path fill="none" stroke="black" d="M173,-248.427C173,-256.892 173,-265.941 173,-273.587"/>
<polygon fill="black" stroke="black" points="176.5,-248.169 173,-238.169 169.5,-248.169 176.5,-248.169"/>
</g>
<!-- d102 -->
<g id="node15" class="node"><title>d102</title>
<polygon fill="none" stroke="black" points="209,-382 137,-382 137,-346 209,-346 209,-382"/>
<text text-anchor="middle" x="173" y="-359.9" font-family="Sans" font-size="14.00">Depth 1</text>
</g>
<!-- d101&#45;&gt;d102 -->
<g id="edge16" class="edge"><title>d101&#45;&gt;d102</title>
<path fill="none" stroke="black" d="M173,-320.427C173,-328.892 173,-337.941 173,-345.587"/>
<polygon fill="black" stroke="black" points="176.5,-320.169 173,-310.169 169.5,-320.169 176.5,-320.169"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 6.1 KiB

View file

@ -0,0 +1,55 @@
digraph blockchain {
size=6.66;
//splines = "ortho";
rankdir=LR;
ranksep=0.1;
subgraph cluster_extended {
block00 [ label = block0 ];
block01 [ label = block1 ];
block02 [ label = block2 ];
block03 [ label = block3 ];
block04 [ label = block4 ];
block05 [ label = block5 ];
block06 [ label = block6 ];
block02x [ label = block2 ];
block03x [ label = block3 ];
block04x [ label = block4 ];
block05x [ label = block5 ];
block01 -> block02x;
block02x -> block03x;
block03x -> block04x;
block04x -> block05x;
block00 -> block01 [label = "Header Hash"];
block01 -> block02;
block02 -> block03;
block03 -> block04;
block04 -> block05
block05 -> block06;
label = "Rare Extended Forking";
}
subgraph cluster_normal {
block2x [ label = block2 ];
block5x [ label = block5 ];
block1 -> block2x;
block4 -> block5x;
block0 -> block1 [label = "Header Hash"];
block1 -> block2 [weight = 100];
block2 -> block3;
block3 -> block4;
block4 -> block5 [weight = 100];
block5 -> block6;
label = "Normal Occasional Forking";
}
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

View file

@ -0,0 +1,213 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="480pt" height="168pt"
viewBox="0.00 0.00 480.00 168.40" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.572792 0.572792) rotate(0) translate(4 290)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-290 835,-290 835,5 -4,5"/>
<g id="graph2" class="cluster"><title>cluster_extended</title>
<polygon fill="none" stroke="black" points="8,-8 8,-139 822,-139 822,-8 8,-8"/>
<text text-anchor="middle" x="415" y="-122.4" font-family="Sans" font-size="14.00">Rare Extended Forking</text>
</g>
<g id="graph3" class="cluster"><title>cluster_normal</title>
<polygon fill="none" stroke="black" points="8,-147 8,-278 822,-278 822,-147 8,-147"/>
<text text-anchor="middle" x="415" y="-261.4" font-family="Sans" font-size="14.00">Normal Occasional Forking</text>
</g>
<!-- block00 -->
<g id="node2" class="node"><title>block00</title>
<ellipse fill="none" stroke="black" cx="59" cy="-61" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="59" y="-56.9" font-family="Sans" font-size="14.00">block0</text>
</g>
<!-- block01 -->
<g id="node3" class="node"><title>block01</title>
<ellipse fill="none" stroke="black" cx="251" cy="-61" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="251" y="-56.9" font-family="Sans" font-size="14.00">block1</text>
</g>
<!-- block00&#45;&gt;block01 -->
<g id="edge11" class="edge"><title>block00&#45;&gt;block01</title>
<path fill="none" stroke="black" d="M101.611,-61C130.098,-61 167.781,-61 198.173,-61"/>
<polygon fill="black" stroke="black" points="198.177,-64.5001 208.177,-61 198.177,-57.5001 198.177,-64.5001"/>
<text text-anchor="middle" x="155" y="-65.4" font-family="Sans" font-size="14.00">Header Hash</text>
</g>
<!-- block02 -->
<g id="node4" class="node"><title>block02</title>
<ellipse fill="none" stroke="black" cx="355" cy="-34" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="355" y="-29.9" font-family="Sans" font-size="14.00">block2</text>
</g>
<!-- block01&#45;&gt;block02 -->
<g id="edge13" class="edge"><title>block01&#45;&gt;block02</title>
<path fill="none" stroke="black" d="M287.374,-51.5567C294.143,-49.7993 301.302,-47.9409 308.329,-46.1165"/>
<polygon fill="black" stroke="black" points="309.671,-49.3842 318.471,-43.4836 307.912,-42.6088 309.671,-49.3842"/>
</g>
<!-- block02x -->
<g id="node9" class="node"><title>block02x</title>
<ellipse fill="none" stroke="black" cx="355" cy="-88" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="355" y="-83.9" font-family="Sans" font-size="14.00">block2</text>
</g>
<!-- block01&#45;&gt;block02x -->
<g id="edge3" class="edge"><title>block01&#45;&gt;block02x</title>
<path fill="none" stroke="black" d="M287.374,-70.4433C294.143,-72.2007 301.302,-74.0591 308.329,-75.8835"/>
<polygon fill="black" stroke="black" points="307.912,-79.3912 318.471,-78.5164 309.671,-72.6158 307.912,-79.3912"/>
</g>
<!-- block03 -->
<g id="node5" class="node"><title>block03</title>
<ellipse fill="none" stroke="black" cx="459" cy="-34" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="459" y="-29.9" font-family="Sans" font-size="14.00">block3</text>
</g>
<!-- block02&#45;&gt;block03 -->
<g id="edge15" class="edge"><title>block02&#45;&gt;block03</title>
<path fill="none" stroke="black" d="M397.601,-34C400.397,-34 403.23,-34 406.068,-34"/>
<polygon fill="black" stroke="black" points="406.297,-37.5001 416.297,-34 406.297,-30.5001 406.297,-37.5001"/>
</g>
<!-- block04 -->
<g id="node6" class="node"><title>block04</title>
<ellipse fill="none" stroke="black" cx="563" cy="-34" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="563" y="-29.9" font-family="Sans" font-size="14.00">block4</text>
</g>
<!-- block03&#45;&gt;block04 -->
<g id="edge17" class="edge"><title>block03&#45;&gt;block04</title>
<path fill="none" stroke="black" d="M501.601,-34C504.397,-34 507.23,-34 510.068,-34"/>
<polygon fill="black" stroke="black" points="510.297,-37.5001 520.297,-34 510.297,-30.5001 510.297,-37.5001"/>
</g>
<!-- block05 -->
<g id="node7" class="node"><title>block05</title>
<ellipse fill="none" stroke="black" cx="667" cy="-34" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="667" y="-29.9" font-family="Sans" font-size="14.00">block5</text>
</g>
<!-- block04&#45;&gt;block05 -->
<g id="edge19" class="edge"><title>block04&#45;&gt;block05</title>
<path fill="none" stroke="black" d="M605.601,-34C608.397,-34 611.23,-34 614.068,-34"/>
<polygon fill="black" stroke="black" points="614.297,-37.5001 624.297,-34 614.297,-30.5001 614.297,-37.5001"/>
</g>
<!-- block06 -->
<g id="node8" class="node"><title>block06</title>
<ellipse fill="none" stroke="black" cx="771" cy="-34" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="771" y="-29.9" font-family="Sans" font-size="14.00">block6</text>
</g>
<!-- block05&#45;&gt;block06 -->
<g id="edge21" class="edge"><title>block05&#45;&gt;block06</title>
<path fill="none" stroke="black" d="M709.601,-34C712.397,-34 715.23,-34 718.068,-34"/>
<polygon fill="black" stroke="black" points="718.297,-37.5001 728.297,-34 718.297,-30.5001 718.297,-37.5001"/>
</g>
<!-- block03x -->
<g id="node10" class="node"><title>block03x</title>
<ellipse fill="none" stroke="black" cx="459" cy="-88" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="459" y="-83.9" font-family="Sans" font-size="14.00">block3</text>
</g>
<!-- block02x&#45;&gt;block03x -->
<g id="edge5" class="edge"><title>block02x&#45;&gt;block03x</title>
<path fill="none" stroke="black" d="M397.601,-88C400.397,-88 403.23,-88 406.068,-88"/>
<polygon fill="black" stroke="black" points="406.297,-91.5001 416.297,-88 406.297,-84.5001 406.297,-91.5001"/>
</g>
<!-- block04x -->
<g id="node11" class="node"><title>block04x</title>
<ellipse fill="none" stroke="black" cx="563" cy="-88" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="563" y="-83.9" font-family="Sans" font-size="14.00">block4</text>
</g>
<!-- block03x&#45;&gt;block04x -->
<g id="edge7" class="edge"><title>block03x&#45;&gt;block04x</title>
<path fill="none" stroke="black" d="M501.601,-88C504.397,-88 507.23,-88 510.068,-88"/>
<polygon fill="black" stroke="black" points="510.297,-91.5001 520.297,-88 510.297,-84.5001 510.297,-91.5001"/>
</g>
<!-- block05x -->
<g id="node12" class="node"><title>block05x</title>
<ellipse fill="none" stroke="black" cx="667" cy="-88" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="667" y="-83.9" font-family="Sans" font-size="14.00">block5</text>
</g>
<!-- block04x&#45;&gt;block05x -->
<g id="edge9" class="edge"><title>block04x&#45;&gt;block05x</title>
<path fill="none" stroke="black" d="M605.601,-88C608.397,-88 611.23,-88 614.068,-88"/>
<polygon fill="black" stroke="black" points="614.297,-91.5001 624.297,-88 614.297,-84.5001 614.297,-91.5001"/>
</g>
<!-- block2x -->
<g id="node24" class="node"><title>block2x</title>
<ellipse fill="none" stroke="black" cx="355" cy="-173" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="355" y="-168.9" font-family="Sans" font-size="14.00">block2</text>
</g>
<!-- block5x -->
<g id="node25" class="node"><title>block5x</title>
<ellipse fill="none" stroke="black" cx="667" cy="-173" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="667" y="-168.9" font-family="Sans" font-size="14.00">block5</text>
</g>
<!-- block1 -->
<g id="node26" class="node"><title>block1</title>
<ellipse fill="none" stroke="black" cx="251" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="251" y="-222.9" font-family="Sans" font-size="14.00">block1</text>
</g>
<!-- block1&#45;&gt;block2x -->
<g id="edge24" class="edge"><title>block1&#45;&gt;block2x</title>
<path fill="none" stroke="black" d="M278.053,-212.953C290.572,-206.453 305.618,-198.641 319.073,-191.655"/>
<polygon fill="black" stroke="black" points="320.82,-194.691 328.082,-186.977 317.594,-188.479 320.82,-194.691"/>
</g>
<!-- block2 -->
<g id="node33" class="node"><title>block2</title>
<ellipse fill="none" stroke="black" cx="355" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="355" y="-222.9" font-family="Sans" font-size="14.00">block2</text>
</g>
<!-- block1&#45;&gt;block2 -->
<g id="edge30" class="edge"><title>block1&#45;&gt;block2</title>
<path fill="none" stroke="black" d="M293.601,-227C296.397,-227 299.23,-227 302.068,-227"/>
<polygon fill="black" stroke="black" points="302.297,-230.5 312.297,-227 302.297,-223.5 302.297,-230.5"/>
</g>
<!-- block4 -->
<g id="node28" class="node"><title>block4</title>
<ellipse fill="none" stroke="black" cx="563" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="563" y="-222.9" font-family="Sans" font-size="14.00">block4</text>
</g>
<!-- block4&#45;&gt;block5x -->
<g id="edge26" class="edge"><title>block4&#45;&gt;block5x</title>
<path fill="none" stroke="black" d="M590.053,-212.953C602.572,-206.453 617.618,-198.641 631.073,-191.655"/>
<polygon fill="black" stroke="black" points="632.82,-194.691 640.082,-186.977 629.594,-188.479 632.82,-194.691"/>
</g>
<!-- block5 -->
<g id="node38" class="node"><title>block5</title>
<ellipse fill="none" stroke="black" cx="667" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="667" y="-222.9" font-family="Sans" font-size="14.00">block5</text>
</g>
<!-- block4&#45;&gt;block5 -->
<g id="edge36" class="edge"><title>block4&#45;&gt;block5</title>
<path fill="none" stroke="black" d="M605.601,-227C608.397,-227 611.23,-227 614.068,-227"/>
<polygon fill="black" stroke="black" points="614.297,-230.5 624.297,-227 614.297,-223.5 614.297,-230.5"/>
</g>
<!-- block0 -->
<g id="node30" class="node"><title>block0</title>
<ellipse fill="none" stroke="black" cx="59" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="59" y="-222.9" font-family="Sans" font-size="14.00">block0</text>
</g>
<!-- block0&#45;&gt;block1 -->
<g id="edge28" class="edge"><title>block0&#45;&gt;block1</title>
<path fill="none" stroke="black" d="M101.611,-227C130.098,-227 167.781,-227 198.173,-227"/>
<polygon fill="black" stroke="black" points="198.177,-230.5 208.177,-227 198.177,-223.5 198.177,-230.5"/>
<text text-anchor="middle" x="155" y="-231.4" font-family="Sans" font-size="14.00">Header Hash</text>
</g>
<!-- block3 -->
<g id="node35" class="node"><title>block3</title>
<ellipse fill="none" stroke="black" cx="459" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="459" y="-222.9" font-family="Sans" font-size="14.00">block3</text>
</g>
<!-- block2&#45;&gt;block3 -->
<g id="edge32" class="edge"><title>block2&#45;&gt;block3</title>
<path fill="none" stroke="black" d="M397.601,-227C400.397,-227 403.23,-227 406.068,-227"/>
<polygon fill="black" stroke="black" points="406.297,-230.5 416.297,-227 406.297,-223.5 406.297,-230.5"/>
</g>
<!-- block3&#45;&gt;block4 -->
<g id="edge34" class="edge"><title>block3&#45;&gt;block4</title>
<path fill="none" stroke="black" d="M501.601,-227C504.397,-227 507.23,-227 510.068,-227"/>
<polygon fill="black" stroke="black" points="510.297,-230.5 520.297,-227 510.297,-223.5 510.297,-230.5"/>
</g>
<!-- block6 -->
<g id="node40" class="node"><title>block6</title>
<ellipse fill="none" stroke="black" cx="771" cy="-227" rx="41.8891" ry="18"/>
<text text-anchor="middle" x="771" y="-222.9" font-family="Sans" font-size="14.00">block6</text>
</g>
<!-- block5&#45;&gt;block6 -->
<g id="edge38" class="edge"><title>block5&#45;&gt;block6</title>
<path fill="none" stroke="black" d="M709.601,-227C712.397,-227 715.23,-227 718.068,-227"/>
<polygon fill="black" stroke="black" points="718.297,-230.5 728.297,-227 718.297,-223.5 718.297,-230.5"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

View file

@ -0,0 +1,60 @@
digraph blockchain {
//splines = "ortho";
rankdir=LR;
size=6.66;
node [ shape = "box", penwidth = 1.75 ];
edge [ penwidth = 1.75 ];
penwidth = 1.75;
nodesep = 0.3;
_transactions0 [ label = "Block 1\nTransactions", width = 2 ];
subgraph cluster_block0header {
_blockHeader0 [ style = "invis", label = "", width = 0, height = 0 ];
hashBlock9 [label = "Hash Of Previous\nBlock Header", shape = box];
hashMerkleRoot0 [label = "Merkle Root"];
label = "Block 1\nHeader"
}
_transactions1 [ label = "Block 2\nTransactions", width = 2 ];
subgraph cluster_block1header {
_blockHeader1 [ style = "invis", label = "", width = 0, height = 0 ];
hashBlock0 [label = "Hash Of Previous\nBlock Header", shape = box];
hashMerkleRoot1 [label = "Merkle Root"];
label = "Block 2\nHeader"
}
_transactions2 [ label = "Block 3\nTransactions", width = 2 ];
_block2 [ style = "invis", label = "", width = 0, height = 0 ];
subgraph cluster_block2header {
_blockHeader2 [ style = "invis", label = "", width = 0, height = 0 ];
hashBlock1 [label = "Hash Of Previous\nBlock Header", shape = box];
hashMerkleRoot2 [label = "Merkle Root"];
label = "Block 3\nHeader"
}
invis0 [ style = "invis", label = "", width = 0, height = 0 ];
invis1 [ style = "invis", label = "", width = 0, height = 0 ];
invis0 -> hashBlock9 [ style = dotted ];
_blockHeader0 -> hashBlock0 [ minlen = 2 ];
//hashBlock0 -> hashBlock1 [ style = "invis" ];
_blockHeader1 -> hashBlock1 [ minlen = 2 ];
hashMerkleRoot0 -> hashMerkleRoot1 -> hashMerkleRoot2 [ style = invis, weight = 100, minlen = 2 ];
_transactions0 -> hashMerkleRoot0 [constraint = false, minlen = 1];
_transactions1 -> hashMerkleRoot1 [constraint = false, minlen = 1];
_transactions2 -> hashMerkleRoot2 [constraint = false, minlen = 1];
_transactions0 -> _transactions1 -> _transactions2 [ style = "invis", minlen = 2 ];
invis1 -> _transactions0 [ style = "invis", minlen = 1 ];
label = "\nSimplified Bitcoin Block Chain";
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.1 KiB

View file

@ -0,0 +1,121 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="480pt" height="220pt"
viewBox="0.00 0.00 480.00 220.44" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.752351 0.752351) rotate(0) translate(4 289)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-289 635,-289 635,5 -4,5"/>
<text text-anchor="middle" x="315" y="-8.4" font-family="Sans" font-size="14.00">Simplified Bitcoin Block Chain</text>
<g id="graph2" class="cluster"><title>cluster_block0header</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="34,-97 34,-277 186,-277 186,-97 34,-97"/>
<text text-anchor="middle" x="110" y="-260.4" font-family="Sans" font-size="14.00">Block 1</text>
<text text-anchor="middle" x="110" y="-243.4" font-family="Sans" font-size="14.00">Header</text>
</g>
<g id="graph3" class="cluster"><title>cluster_block1header</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="252,-97 252,-277 404,-277 404,-97 252,-97"/>
<text text-anchor="middle" x="328" y="-260.4" font-family="Sans" font-size="14.00">Block 2</text>
<text text-anchor="middle" x="328" y="-243.4" font-family="Sans" font-size="14.00">Header</text>
</g>
<g id="graph4" class="cluster"><title>cluster_block2header</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="470,-97 470,-277 622,-277 622,-97 470,-97"/>
<text text-anchor="middle" x="546" y="-260.4" font-family="Sans" font-size="14.00">Block 3</text>
<text text-anchor="middle" x="546" y="-243.4" font-family="Sans" font-size="14.00">Header</text>
</g>
<!-- _transactions0 -->
<g id="node1" class="node"><title>_transactions0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="182,-83 38,-83 38,-41 182,-41 182,-83"/>
<text text-anchor="middle" x="110" y="-66.4" font-family="Sans" font-size="14.00">Block 1</text>
<text text-anchor="middle" x="110" y="-49.4" font-family="Sans" font-size="14.00">Transactions</text>
</g>
<!-- hashMerkleRoot0 -->
<g id="node5" class="node"><title>hashMerkleRoot0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="159,-141 61,-141 61,-105 159,-105 159,-141"/>
<text text-anchor="middle" x="110" y="-118.9" font-family="Sans" font-size="14.00">Merkle Root</text>
</g>
<!-- _transactions0&#45;&gt;hashMerkleRoot0 -->
<g id="edge14" class="edge"><title>_transactions0&#45;&gt;hashMerkleRoot0</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M110,-83.4453C110,-87.1101 110,-90.7749 110,-94.4397"/>
<polygon fill="black" stroke="black" points="106.5,-94.7677 110,-104.768 113.5,-94.7678 106.5,-94.7677"/>
</g>
<!-- _transactions1 -->
<g id="node6" class="node"><title>_transactions1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="400,-83 256,-83 256,-41 400,-41 400,-83"/>
<text text-anchor="middle" x="328" y="-66.4" font-family="Sans" font-size="14.00">Block 2</text>
<text text-anchor="middle" x="328" y="-49.4" font-family="Sans" font-size="14.00">Transactions</text>
</g>
<!-- _transactions0&#45;&gt;_transactions1 -->
<!-- _blockHeader0 -->
<!-- hashBlock0 -->
<g id="node9" class="node"><title>hashBlock0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="395,-205 261,-205 261,-163 395,-163 395,-205"/>
<text text-anchor="middle" x="328" y="-188.4" font-family="Sans" font-size="14.00">Hash Of Previous</text>
<text text-anchor="middle" x="328" y="-171.4" font-family="Sans" font-size="14.00">Block Header</text>
</g>
<!-- _blockHeader0&#45;&gt;hashBlock0 -->
<g id="edge7" class="edge"><title>_blockHeader0&#45;&gt;hashBlock0</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M110.753,-226.914C116.577,-226.242 155.06,-221.716 186,-216 207.024,-212.116 229.66,-207.304 250.547,-202.602"/>
<polygon fill="black" stroke="black" points="251.35,-206.009 260.326,-200.38 249.799,-199.183 251.35,-206.009"/>
</g>
<!-- hashBlock9 -->
<g id="node4" class="node"><title>hashBlock9</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="177,-205 43,-205 43,-163 177,-163 177,-205"/>
<text text-anchor="middle" x="110" y="-188.4" font-family="Sans" font-size="14.00">Hash Of Previous</text>
<text text-anchor="middle" x="110" y="-171.4" font-family="Sans" font-size="14.00">Block Header</text>
</g>
<!-- hashMerkleRoot1 -->
<g id="node10" class="node"><title>hashMerkleRoot1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="377,-141 279,-141 279,-105 377,-105 377,-141"/>
<text text-anchor="middle" x="328" y="-118.9" font-family="Sans" font-size="14.00">Merkle Root</text>
</g>
<!-- hashMerkleRoot0&#45;&gt;hashMerkleRoot1 -->
<!-- _transactions1&#45;&gt;hashMerkleRoot1 -->
<g id="edge16" class="edge"><title>_transactions1&#45;&gt;hashMerkleRoot1</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M328,-83.4453C328,-87.1101 328,-90.7749 328,-94.4397"/>
<polygon fill="black" stroke="black" points="324.5,-94.7677 328,-104.768 331.5,-94.7678 324.5,-94.7677"/>
</g>
<!-- _transactions2 -->
<g id="node11" class="node"><title>_transactions2</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="618,-83 474,-83 474,-41 618,-41 618,-83"/>
<text text-anchor="middle" x="546" y="-66.4" font-family="Sans" font-size="14.00">Block 3</text>
<text text-anchor="middle" x="546" y="-49.4" font-family="Sans" font-size="14.00">Transactions</text>
</g>
<!-- _transactions1&#45;&gt;_transactions2 -->
<!-- _blockHeader1 -->
<!-- hashBlock1 -->
<g id="node15" class="node"><title>hashBlock1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="613,-205 479,-205 479,-163 613,-163 613,-205"/>
<text text-anchor="middle" x="546" y="-188.4" font-family="Sans" font-size="14.00">Hash Of Previous</text>
<text text-anchor="middle" x="546" y="-171.4" font-family="Sans" font-size="14.00">Block Header</text>
</g>
<!-- _blockHeader1&#45;&gt;hashBlock1 -->
<g id="edge9" class="edge"><title>_blockHeader1&#45;&gt;hashBlock1</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M328.753,-226.914C334.577,-226.242 373.06,-221.716 404,-216 425.024,-212.116 447.66,-207.304 468.547,-202.602"/>
<polygon fill="black" stroke="black" points="469.35,-206.009 478.326,-200.38 467.799,-199.183 469.35,-206.009"/>
</g>
<!-- hashMerkleRoot2 -->
<g id="node16" class="node"><title>hashMerkleRoot2</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="595,-141 497,-141 497,-105 595,-105 595,-141"/>
<text text-anchor="middle" x="546" y="-118.9" font-family="Sans" font-size="14.00">Merkle Root</text>
</g>
<!-- hashMerkleRoot1&#45;&gt;hashMerkleRoot2 -->
<!-- _transactions2&#45;&gt;hashMerkleRoot2 -->
<g id="edge18" class="edge"><title>_transactions2&#45;&gt;hashMerkleRoot2</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M546,-83.4453C546,-87.1101 546,-90.7749 546,-94.4397"/>
<polygon fill="black" stroke="black" points="542.5,-94.7677 546,-104.768 549.5,-94.7678 542.5,-94.7677"/>
</g>
<!-- _block2 -->
<!-- _blockHeader2 -->
<!-- invis0 -->
<!-- invis0&#45;&gt;hashBlock9 -->
<g id="edge5" class="edge"><title>invis0&#45;&gt;hashBlock9</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="1,5" d="M1.69605,-184C4.67071,-184 16.8595,-184 32.0519,-184"/>
<polygon fill="black" stroke="black" points="32.4026,-187.5 42.4025,-184 32.4025,-180.5 32.4026,-187.5"/>
</g>
<!-- invis1 -->
<!-- invis1&#45;&gt;_transactions0 -->
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 29 KiB

29
img/dev/en-cert-order.dot Normal file
View file

@ -0,0 +1,29 @@
digraph paymentchannel {
size=6.66;
//rankdir=LR;
//splines = true;
//nodesep = 0.4;
//edge [ minlen = 2 ];
node [ shape = box ];
subgraph cluster_signing {
btcorg [ label = "www.bitcoin.org" ]
rapidssl [ label = "RapidSSL CA" ]
geotrust [ label = "GeoTrust Global CA" ]
geotrust -> rapidssl -> btcorg
label = " Certificates In Signing Order \n "
}
subgraph cluster_loading {
one [ label = " x509.certificate.append(bitcoin_org-cert) " ]
two [ label = " x509.certificate.append(rapidssl_ca-cert) " ]
one -> two
label = "Certificates In Loading Order\n(Root CA Certificate Is Not Loaded)"
}
label = "(Certificates are loaded into X509Certificates() in reverse signing order)\n \nExample Certificate Loading Order For Payment Requests From Bitcoin.org"
}

BIN
img/dev/en-cert-order.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 9 KiB

66
img/dev/en-cert-order.svg Normal file
View file

@ -0,0 +1,66 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: paymentchannel Pages: 1 -->
<svg width="480pt" height="262pt"
viewBox="0.00 0.00 480.00 261.60" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.814941 0.814941) rotate(0) translate(4 317)">
<title>paymentchannel</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-317 586,-317 586,5 -4,5"/>
<text text-anchor="middle" x="290.5" y="-42.4" font-family="Sans" font-size="14.00">(Certificates are loaded into X509Certificates() in reverse signing order)</text>
<text text-anchor="middle" x="290.5" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="290.5" y="-8.4" font-family="Sans" font-size="14.00">Example Certificate Loading Order For Payment Requests From Bitcoin.org</text>
<g id="graph2" class="cluster"><title>cluster_signing</title>
<polygon fill="none" stroke="black" points="8,-67 8,-305 229,-305 229,-67 8,-67"/>
<text text-anchor="middle" x="118.5" y="-288.4" font-family="Sans" font-size="14.00"> Certificates In Signing Order </text>
<text text-anchor="middle" x="118.5" y="-271.4" font-family="Sans" font-size="14.00"> </text>
</g>
<g id="graph3" class="cluster"><title>cluster_loading</title>
<polygon fill="none" stroke="black" points="237,-139 237,-305 573,-305 573,-139 237,-139"/>
<text text-anchor="middle" x="405" y="-288.4" font-family="Sans" font-size="14.00">Certificates In Loading Order</text>
<text text-anchor="middle" x="405" y="-271.4" font-family="Sans" font-size="14.00">(Root CA Certificate Is Not Loaded)</text>
</g>
<!-- btcorg -->
<g id="node2" class="node"><title>btcorg</title>
<polygon fill="none" stroke="black" points="183,-111 53,-111 53,-75 183,-75 183,-111"/>
<text text-anchor="middle" x="118" y="-88.9" font-family="Sans" font-size="14.00">www.bitcoin.org</text>
</g>
<!-- rapidssl -->
<g id="node3" class="node"><title>rapidssl</title>
<polygon fill="none" stroke="black" points="170,-183 66,-183 66,-147 170,-147 170,-183"/>
<text text-anchor="middle" x="118" y="-160.9" font-family="Sans" font-size="14.00">RapidSSL CA</text>
</g>
<!-- rapidssl&#45;&gt;btcorg -->
<g id="edge4" class="edge"><title>rapidssl&#45;&gt;btcorg</title>
<path fill="none" stroke="black" d="M118,-146.831C118,-139.131 118,-129.974 118,-121.417"/>
<polygon fill="black" stroke="black" points="121.5,-121.413 118,-111.413 114.5,-121.413 121.5,-121.413"/>
</g>
<!-- geotrust -->
<g id="node4" class="node"><title>geotrust</title>
<polygon fill="none" stroke="black" points="194,-255 42,-255 42,-219 194,-219 194,-255"/>
<text text-anchor="middle" x="118" y="-232.9" font-family="Sans" font-size="14.00">GeoTrust Global CA</text>
</g>
<!-- geotrust&#45;&gt;rapidssl -->
<g id="edge3" class="edge"><title>geotrust&#45;&gt;rapidssl</title>
<path fill="none" stroke="black" d="M118,-218.831C118,-211.131 118,-201.974 118,-193.417"/>
<polygon fill="black" stroke="black" points="121.5,-193.413 118,-183.413 114.5,-193.413 121.5,-193.413"/>
</g>
<!-- one -->
<g id="node7" class="node"><title>one</title>
<polygon fill="none" stroke="black" points="565,-255 245,-255 245,-219 565,-219 565,-255"/>
<text text-anchor="middle" x="405" y="-232.9" font-family="Sans" font-size="14.00"> &#160;&#160;&#160;x509.certificate.append(bitcoin_org&#45;cert) </text>
</g>
<!-- two -->
<g id="node8" class="node"><title>two</title>
<polygon fill="none" stroke="black" points="564,-183 246,-183 246,-147 564,-147 564,-183"/>
<text text-anchor="middle" x="405" y="-160.9" font-family="Sans" font-size="14.00"> &#160;&#160;&#160;x509.certificate.append(rapidssl_ca&#45;cert) </text>
</g>
<!-- one&#45;&gt;two -->
<g id="edge7" class="edge"><title>one&#45;&gt;two</title>
<path fill="none" stroke="black" d="M405,-218.831C405,-211.131 405,-201.974 405,-193.417"/>
<polygon fill="black" stroke="black" points="408.5,-193.413 405,-183.413 401.5,-193.413 408.5,-193.413"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 4 KiB

99
img/dev/en-coinjoin.dot Normal file
View file

@ -0,0 +1,99 @@
digraph paymentchannel {
size=6.66;
rankdir=LR;
//splines = false;
nodesep = 0.1;
edge [ minlen = 1.33 ];
node [ shape = box ];
subgraph cluster_nemo {
label = "Nemo's UTXOs"
nemo_out1 [ label = "10 mBTC" ];
nemo_out2 [ label = "90 mBTC" ];
}
subgraph cluster_neminem {
label = "Neminem's UTXOs"
neminem_out1 [ label = "100 mBTC" ];
}
subgraph cluster_alice {
label = "AnonGirl's UTXOs"
alice_out1 [ label = "55 mBTC" ];
alice_out2 [ label = "25 mBTC" ];
alice_out3 [ label = "20 mBTC" ];
}
subgraph prevouts {
node [ style = invis, label="", width=0, height=0 ]
prevout3;
prevout4;
prevout5;
prevout0;
prevout1;
prevout2;
}
subgraph cluster_coinjoin {
label = "CoinJoin Transaction"
subgraph cluster_inputs {
label = "Inputs"
node [ label = "" ]
nemo_in1;
nemo_in2;
neminem_in1;
alice_in1;
alice_in2;
alice_in3;
}
subgraph cluster_outputs {
label = "Outputs"
node [ label = "100 mBTC" ];
out1;
out2;
out3;
}
}
utxo1 [ label = "Person 1" ];
utxo2 [ label = "Person 2" ];
utxo3 [ label = "Person 3" ];
// prevouts
prevout0 -> alice_out1 [ style = dashed, label = "From Bob" ];
prevout1 -> alice_out2 [ style = dashed, label = "From Charlie" ];
prevout2 -> alice_out3 [ style = dashed ];
prevout3 -> nemo_out1 [ style = dashed ];
prevout4 -> nemo_out2 [ style = dashed ];
prevout5 -> neminem_out1 [ style = dashed ];
alice_out1 -> alice_in1;
alice_out2 -> alice_in2;
alice_out3 -> alice_in3;
nemo_out1 -> nemo_in1;
nemo_out2 -> nemo_in2;
neminem_out1 -> neminem_in1;
out1 -> utxo1;
out2 -> utxo2;
out3 -> utxo3;
label = "Example CoinJoin Transaction\nOnly the participants know who gets which output."
}

BIN
img/dev/en-coinjoin.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

206
img/dev/en-coinjoin.svg Normal file
View file

@ -0,0 +1,206 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: paymentchannel Pages: 1 -->
<svg width="458pt" height="480pt"
viewBox="0.00 0.00 457.62 480.00" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.829016 0.829016) rotate(0) translate(4 575)">
<title>paymentchannel</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-575 549,-575 549,5 -4,5"/>
<text text-anchor="middle" x="272" y="-25.4" font-family="Sans" font-size="14.00">Example CoinJoin Transaction</text>
<text text-anchor="middle" x="272" y="-8.4" font-family="Sans" font-size="14.00">Only the participants know who gets which output.</text>
<g id="graph2" class="cluster"><title>cluster_nemo</title>
<polygon fill="none" stroke="black" points="130,-187 130,-307 248,-307 248,-187 130,-187"/>
<text text-anchor="middle" x="189" y="-290.4" font-family="Sans" font-size="14.00">Nemo&#39;s UTXOs</text>
</g>
<g id="graph3" class="cluster"><title>cluster_neminem</title>
<polygon fill="none" stroke="black" points="118,-486 118,-563 261,-563 261,-486 118,-486"/>
<text text-anchor="middle" x="189.5" y="-546.4" font-family="Sans" font-size="14.00">Neminem&#39;s UTXOs</text>
</g>
<g id="graph4" class="cluster"><title>cluster_alice</title>
<polygon fill="none" stroke="black" points="120,-315 120,-478 259,-478 259,-315 120,-315"/>
<text text-anchor="middle" x="189.5" y="-461.4" font-family="Sans" font-size="14.00">AnonGirl&#39;s UTXOs</text>
</g>
<g id="graph6" class="cluster"><title>cluster_coinjoin</title>
<polygon fill="none" stroke="black" points="281,-50 281,-554 438,-554 438,-50 281,-50"/>
<text text-anchor="middle" x="359.5" y="-537.4" font-family="Sans" font-size="14.00">CoinJoin Transaction</text>
</g>
<g id="graph7" class="cluster"><title>cluster_inputs</title>
<polygon fill="none" stroke="black" points="324,-229 324,-521 394,-521 394,-229 324,-229"/>
<text text-anchor="middle" x="359" y="-504.4" font-family="Sans" font-size="14.00">Inputs</text>
</g>
<g id="graph8" class="cluster"><title>cluster_outputs</title>
<polygon fill="none" stroke="black" points="306,-58 306,-221 412,-221 412,-58 306,-58"/>
<text text-anchor="middle" x="359" y="-204.4" font-family="Sans" font-size="14.00">Outputs</text>
</g>
<!-- nemo_out1 -->
<g id="node2" class="node"><title>nemo_out1</title>
<polygon fill="none" stroke="black" points="229,-274 149,-274 149,-238 229,-238 229,-274"/>
<text text-anchor="middle" x="189" y="-251.9" font-family="Sans" font-size="14.00">10 mBTC</text>
</g>
<!-- nemo_in1 -->
<g id="node19" class="node"><title>nemo_in1</title>
<polygon fill="none" stroke="black" points="386,-316 332,-316 332,-280 386,-280 386,-316"/>
</g>
<!-- nemo_out1&#45;&gt;nemo_in1 -->
<g id="edge27" class="edge"><title>nemo_out1&#45;&gt;nemo_in1</title>
<path fill="none" stroke="black" d="M229.288,-265.953C257.409,-272.901 294.659,-282.104 322.024,-288.865"/>
<polygon fill="black" stroke="black" points="321.441,-292.326 331.988,-291.326 323.12,-285.53 321.441,-292.326"/>
</g>
<!-- nemo_out2 -->
<g id="node3" class="node"><title>nemo_out2</title>
<polygon fill="none" stroke="black" points="229,-231 149,-231 149,-195 229,-195 229,-231"/>
<text text-anchor="middle" x="189" y="-208.9" font-family="Sans" font-size="14.00">90 mBTC</text>
</g>
<!-- nemo_in2 -->
<g id="node20" class="node"><title>nemo_in2</title>
<polygon fill="none" stroke="black" points="386,-273 332,-273 332,-237 386,-237 386,-273"/>
</g>
<!-- nemo_out2&#45;&gt;nemo_in2 -->
<g id="edge29" class="edge"><title>nemo_out2&#45;&gt;nemo_in2</title>
<path fill="none" stroke="black" d="M229.288,-222.953C257.409,-229.901 294.659,-239.104 322.024,-245.865"/>
<polygon fill="black" stroke="black" points="321.441,-249.326 331.988,-248.326 323.12,-242.53 321.441,-249.326"/>
</g>
<!-- neminem_out1 -->
<g id="node5" class="node"><title>neminem_out1</title>
<polygon fill="none" stroke="black" points="233,-530 145,-530 145,-494 233,-494 233,-530"/>
<text text-anchor="middle" x="189" y="-507.9" font-family="Sans" font-size="14.00">100 mBTC</text>
</g>
<!-- neminem_in1 -->
<g id="node21" class="node"><title>neminem_in1</title>
<polygon fill="none" stroke="black" points="386,-488 332,-488 332,-452 386,-452 386,-488"/>
</g>
<!-- neminem_out1&#45;&gt;neminem_in1 -->
<g id="edge31" class="edge"><title>neminem_out1&#45;&gt;neminem_in1</title>
<path fill="none" stroke="black" d="M233.665,-500.965C261.109,-494.185 295.855,-485.6 321.799,-479.191"/>
<polygon fill="black" stroke="black" points="322.759,-482.559 331.628,-476.763 321.08,-475.763 322.759,-482.559"/>
</g>
<!-- alice_out1 -->
<g id="node7" class="node"><title>alice_out1</title>
<polygon fill="none" stroke="black" points="229,-445 149,-445 149,-409 229,-409 229,-445"/>
<text text-anchor="middle" x="189" y="-422.9" font-family="Sans" font-size="14.00">55 mBTC</text>
</g>
<!-- alice_in1 -->
<g id="node22" class="node"><title>alice_in1</title>
<polygon fill="none" stroke="black" points="386,-445 332,-445 332,-409 386,-409 386,-445"/>
</g>
<!-- alice_out1&#45;&gt;alice_in1 -->
<g id="edge21" class="edge"><title>alice_out1&#45;&gt;alice_in1</title>
<path fill="none" stroke="black" d="M229.288,-427C257.285,-427 294.331,-427 321.662,-427"/>
<polygon fill="black" stroke="black" points="321.988,-430.5 331.988,-427 321.988,-423.5 321.988,-430.5"/>
</g>
<!-- alice_out2 -->
<g id="node8" class="node"><title>alice_out2</title>
<polygon fill="none" stroke="black" points="229,-402 149,-402 149,-366 229,-366 229,-402"/>
<text text-anchor="middle" x="189" y="-379.9" font-family="Sans" font-size="14.00">25 mBTC</text>
</g>
<!-- alice_in2 -->
<g id="node23" class="node"><title>alice_in2</title>
<polygon fill="none" stroke="black" points="386,-402 332,-402 332,-366 386,-366 386,-402"/>
</g>
<!-- alice_out2&#45;&gt;alice_in2 -->
<g id="edge23" class="edge"><title>alice_out2&#45;&gt;alice_in2</title>
<path fill="none" stroke="black" d="M229.288,-384C257.285,-384 294.331,-384 321.662,-384"/>
<polygon fill="black" stroke="black" points="321.988,-387.5 331.988,-384 321.988,-380.5 321.988,-387.5"/>
</g>
<!-- alice_out3 -->
<g id="node9" class="node"><title>alice_out3</title>
<polygon fill="none" stroke="black" points="229,-359 149,-359 149,-323 229,-323 229,-359"/>
<text text-anchor="middle" x="189" y="-336.9" font-family="Sans" font-size="14.00">20 mBTC</text>
</g>
<!-- alice_in3 -->
<g id="node24" class="node"><title>alice_in3</title>
<polygon fill="none" stroke="black" points="386,-359 332,-359 332,-323 386,-323 386,-359"/>
</g>
<!-- alice_out3&#45;&gt;alice_in3 -->
<g id="edge25" class="edge"><title>alice_out3&#45;&gt;alice_in3</title>
<path fill="none" stroke="black" d="M229.288,-341C257.285,-341 294.331,-341 321.662,-341"/>
<polygon fill="black" stroke="black" points="321.988,-344.5 331.988,-341 321.988,-337.5 321.988,-344.5"/>
</g>
<!-- prevout3 -->
<!-- prevout3&#45;&gt;nemo_out1 -->
<g id="edge15" class="edge"><title>prevout3&#45;&gt;nemo_out1</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-256C8.687,-256 85.331,-256 138.374,-256"/>
<polygon fill="black" stroke="black" points="138.64,-259.5 148.64,-256 138.64,-252.5 138.64,-259.5"/>
</g>
<!-- prevout4 -->
<!-- prevout4&#45;&gt;nemo_out2 -->
<g id="edge17" class="edge"><title>prevout4&#45;&gt;nemo_out2</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-213C8.687,-213 85.331,-213 138.374,-213"/>
<polygon fill="black" stroke="black" points="138.64,-216.5 148.64,-213 138.64,-209.5 138.64,-216.5"/>
</g>
<!-- prevout5 -->
<!-- prevout5&#45;&gt;neminem_out1 -->
<g id="edge19" class="edge"><title>prevout5&#45;&gt;neminem_out1</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-512C8.48509,-512 81.0563,-512 133.824,-512"/>
<polygon fill="black" stroke="black" points="134.089,-515.5 144.089,-512 134.089,-508.5 134.089,-515.5"/>
</g>
<!-- prevout0 -->
<!-- prevout0&#45;&gt;alice_out1 -->
<g id="edge9" class="edge"><title>prevout0&#45;&gt;alice_out1</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-427C8.687,-427 85.331,-427 138.374,-427"/>
<polygon fill="black" stroke="black" points="138.64,-430.5 148.64,-427 138.64,-423.5 138.64,-430.5"/>
<text text-anchor="middle" x="64" y="-431.4" font-family="Sans" font-size="14.00">From Bob</text>
</g>
<!-- prevout1 -->
<!-- prevout1&#45;&gt;alice_out2 -->
<g id="edge11" class="edge"><title>prevout1&#45;&gt;alice_out2</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-384C8.687,-384 85.331,-384 138.374,-384"/>
<polygon fill="black" stroke="black" points="138.64,-387.5 148.64,-384 138.64,-380.5 138.64,-387.5"/>
<text text-anchor="middle" x="64" y="-388.4" font-family="Sans" font-size="14.00">From Charlie</text>
</g>
<!-- prevout2 -->
<!-- prevout2&#45;&gt;alice_out3 -->
<g id="edge13" class="edge"><title>prevout2&#45;&gt;alice_out3</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M1.53931,-341C8.687,-341 85.331,-341 138.374,-341"/>
<polygon fill="black" stroke="black" points="138.64,-344.5 148.64,-341 138.64,-337.5 138.64,-344.5"/>
</g>
<!-- out1 -->
<g id="node26" class="node"><title>out1</title>
<polygon fill="none" stroke="black" points="403,-188 315,-188 315,-152 403,-152 403,-188"/>
<text text-anchor="middle" x="359" y="-165.9" font-family="Sans" font-size="14.00">100 mBTC</text>
</g>
<!-- utxo1 -->
<g id="node29" class="node"><title>utxo1</title>
<polygon fill="none" stroke="black" points="543,-188 467,-188 467,-152 543,-152 543,-188"/>
<text text-anchor="middle" x="505" y="-165.9" font-family="Sans" font-size="14.00">Person 1</text>
</g>
<!-- out1&#45;&gt;utxo1 -->
<g id="edge33" class="edge"><title>out1&#45;&gt;utxo1</title>
<path fill="none" stroke="black" d="M403.598,-170C420.126,-170 438.956,-170 455.865,-170"/>
<polygon fill="black" stroke="black" points="456.108,-173.5 466.108,-170 456.108,-166.5 456.108,-173.5"/>
</g>
<!-- out2 -->
<g id="node27" class="node"><title>out2</title>
<polygon fill="none" stroke="black" points="403,-145 315,-145 315,-109 403,-109 403,-145"/>
<text text-anchor="middle" x="359" y="-122.9" font-family="Sans" font-size="14.00">100 mBTC</text>
</g>
<!-- utxo2 -->
<g id="node30" class="node"><title>utxo2</title>
<polygon fill="none" stroke="black" points="543,-145 467,-145 467,-109 543,-109 543,-145"/>
<text text-anchor="middle" x="505" y="-122.9" font-family="Sans" font-size="14.00">Person 2</text>
</g>
<!-- out2&#45;&gt;utxo2 -->
<g id="edge35" class="edge"><title>out2&#45;&gt;utxo2</title>
<path fill="none" stroke="black" d="M403.598,-127C420.126,-127 438.956,-127 455.865,-127"/>
<polygon fill="black" stroke="black" points="456.108,-130.5 466.108,-127 456.108,-123.5 456.108,-130.5"/>
</g>
<!-- out3 -->
<g id="node28" class="node"><title>out3</title>
<polygon fill="none" stroke="black" points="403,-102 315,-102 315,-66 403,-66 403,-102"/>
<text text-anchor="middle" x="359" y="-79.9" font-family="Sans" font-size="14.00">100 mBTC</text>
</g>
<!-- utxo3 -->
<g id="node31" class="node"><title>utxo3</title>
<polygon fill="none" stroke="black" points="543,-102 467,-102 467,-66 543,-66 543,-102"/>
<text text-anchor="middle" x="505" y="-79.9" font-family="Sans" font-size="14.00">Person 3</text>
</g>
<!-- out3&#45;&gt;utxo3 -->
<g id="edge37" class="edge"><title>out3&#45;&gt;utxo3</title>
<path fill="none" stroke="black" d="M403.598,-84C420.126,-84 438.956,-84 455.865,-84"/>
<polygon fill="black" stroke="black" points="456.108,-87.5001 466.108,-84 456.108,-80.5001 456.108,-87.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

View file

@ -0,0 +1,41 @@
digraph blockchain {
size=6.25;
//splines = "false";
rankdir=LR;
//ranksep=0.1;
//splines=ortho;
node [ shape = box, penwidth = 1.75 ];
edge [ penwidth = 1.75 ];
penwidth = 1.75;
subgraph cluster_bob {
private_key [ label = "Private\nKey" ];
full_public_key [ label = "Full\nPublic Key" ];
pubkey_hash [ label = "Public Key\nHash" ];
label = "Bob's Computer"
}
subgraph cluster_alice {
spender_pubkey_hash [ label = "Copy Of\nPublic Key\nHash" ];
label = "Alice's Computer"
}
subgraph cluster_tx1 {
tx1_pubkey_hash [ label = "Copy Of\nPublic Key\nHash" ];
label = "TX 1"
}
private_key -> full_public_key -> pubkey_hash -> spender_pubkey_hash -> tx1_pubkey_hash;
label = "Creating A P2PH Public Key Hash To Receive Payment"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 4 KiB

View file

@ -0,0 +1,78 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="107pt"
viewBox="0.00 0.00 450.00 106.90" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.722311 0.722311) rotate(0) translate(4 144)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-144 620,-144 620,5 -4,5"/>
<text text-anchor="middle" x="307.5" y="-8.4" font-family="Sans" font-size="14.00">Creating A P2PH Public Key Hash To Receive Payment</text>
<g id="graph2" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-41 8,-124 334,-124 334,-41 8,-41"/>
<text text-anchor="middle" x="171" y="-107.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
</g>
<g id="graph3" class="cluster"><title>cluster_alice</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="354,-33 354,-132 485,-132 485,-33 354,-33"/>
<text text-anchor="middle" x="419.5" y="-115.4" font-family="Sans" font-size="14.00">Alice&#39;s Computer</text>
</g>
<g id="graph4" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="505,-33 505,-132 607,-132 607,-33 505,-33"/>
<text text-anchor="middle" x="556" y="-115.4" font-family="Sans" font-size="14.00">TX 1</text>
</g>
<!-- private_key -->
<g id="node2" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="82,-91 16,-91 16,-49 82,-49 82,-91"/>
<text text-anchor="middle" x="49" y="-74.4" font-family="Sans" font-size="14.00">Private</text>
<text text-anchor="middle" x="49" y="-57.4" font-family="Sans" font-size="14.00">Key</text>
</g>
<!-- full_public_key -->
<g id="node3" class="node"><title>full_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="204,-91 118,-91 118,-49 204,-49 204,-91"/>
<text text-anchor="middle" x="161" y="-74.4" font-family="Sans" font-size="14.00">Full</text>
<text text-anchor="middle" x="161" y="-57.4" font-family="Sans" font-size="14.00">Public Key</text>
</g>
<!-- private_key&#45;&gt;full_public_key -->
<g id="edge5" class="edge"><title>private_key&#45;&gt;full_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M82.3005,-70C90.272,-70 98.9822,-70 107.61,-70"/>
<polygon fill="black" stroke="black" points="107.65,-73.5001 117.65,-70 107.65,-66.5001 107.65,-73.5001"/>
</g>
<!-- pubkey_hash -->
<g id="node4" class="node"><title>pubkey_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="326,-91 240,-91 240,-49 326,-49 326,-91"/>
<text text-anchor="middle" x="283" y="-74.4" font-family="Sans" font-size="14.00">Public Key</text>
<text text-anchor="middle" x="283" y="-57.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- full_public_key&#45;&gt;pubkey_hash -->
<g id="edge6" class="edge"><title>full_public_key&#45;&gt;pubkey_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M204.013,-70C212.395,-70 221.275,-70 229.938,-70"/>
<polygon fill="black" stroke="black" points="229.965,-73.5001 239.965,-70 229.965,-66.5001 229.965,-73.5001"/>
</g>
<!-- spender_pubkey_hash -->
<g id="node6" class="node"><title>spender_pubkey_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="462,-99.5 376,-99.5 376,-40.5 462,-40.5 462,-99.5"/>
<text text-anchor="middle" x="419" y="-82.9" font-family="Sans" font-size="14.00">Copy Of</text>
<text text-anchor="middle" x="419" y="-65.9" font-family="Sans" font-size="14.00">Public Key</text>
<text text-anchor="middle" x="419" y="-48.9" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- pubkey_hash&#45;&gt;spender_pubkey_hash -->
<g id="edge7" class="edge"><title>pubkey_hash&#45;&gt;spender_pubkey_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M326.031,-70C338.558,-70 352.397,-70 365.486,-70"/>
<polygon fill="black" stroke="black" points="365.782,-73.5001 375.782,-70 365.782,-66.5001 365.782,-73.5001"/>
</g>
<!-- tx1_pubkey_hash -->
<g id="node8" class="node"><title>tx1_pubkey_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="599,-99.5 513,-99.5 513,-40.5 599,-40.5 599,-99.5"/>
<text text-anchor="middle" x="556" y="-82.9" font-family="Sans" font-size="14.00">Copy Of</text>
<text text-anchor="middle" x="556" y="-65.9" font-family="Sans" font-size="14.00">Public Key</text>
<text text-anchor="middle" x="556" y="-48.9" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- spender_pubkey_hash&#45;&gt;tx1_pubkey_hash -->
<g id="edge8" class="edge"><title>spender_pubkey_hash&#45;&gt;tx1_pubkey_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M462.348,-70C475.216,-70 489.46,-70 502.874,-70"/>
<polygon fill="black" stroke="black" points="502.934,-73.5001 512.934,-70 502.934,-66.5001 502.934,-73.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5 KiB

View file

@ -0,0 +1,42 @@
digraph blockchain {
size=6.25;
//splines = "false";
rankdir=LR;
ranksep=0.2;
//splines=ortho;
node [ shape = box, penwidth = 1.75 ];
edge [ penwidth = 1.75 ];
penwidth = 1.75;
subgraph cluster_bob {
private_key [ label = "Private\nKey" ];
full_public_key [ label = "Full\nPublic Key" ];
redeemScript [ label = "RedeemScript" ];
script_hash [ label = "Script\nHash" ];
label = "Bob's Computer"
}
subgraph cluster_alice {
spender_script_hash [ label = "Copy Of\nScript\nHash" ];
label = "Alice's Computer"
}
subgraph cluster_tx1 {
tx1_script_hash [ label = "Copy Of\nScript\nHash" ];
label = "TX 1"
}
private_key -> full_public_key -> redeemScript -> script_hash -> spender_script_hash -> tx1_script_hash;
label = "Creating A P2SH RedeemScript Hash To Receive Payment"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.4 KiB

View file

@ -0,0 +1,88 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="105pt"
viewBox="0.00 0.00 450.00 104.55" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.706436 0.706436) rotate(0) translate(4 144)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-144 634,-144 634,5 -4,5"/>
<text text-anchor="middle" x="314.5" y="-8.4" font-family="Sans" font-size="14.00">Creating A P2SH RedeemScript Hash To Receive Payment</text>
<g id="graph2" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-41 8,-124 386,-124 386,-41 8,-41"/>
<text text-anchor="middle" x="197" y="-107.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
</g>
<g id="graph3" class="cluster"><title>cluster_alice</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="394,-33 394,-132 525,-132 525,-33 394,-33"/>
<text text-anchor="middle" x="459.5" y="-115.4" font-family="Sans" font-size="14.00">Alice&#39;s Computer</text>
</g>
<g id="graph4" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="533,-33 533,-132 621,-132 621,-33 533,-33"/>
<text text-anchor="middle" x="577" y="-115.4" font-family="Sans" font-size="14.00">TX 1</text>
</g>
<!-- private_key -->
<g id="node2" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="82,-91 16,-91 16,-49 82,-49 82,-91"/>
<text text-anchor="middle" x="49" y="-74.4" font-family="Sans" font-size="14.00">Private</text>
<text text-anchor="middle" x="49" y="-57.4" font-family="Sans" font-size="14.00">Key</text>
</g>
<!-- full_public_key -->
<g id="node3" class="node"><title>full_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="182,-91 96,-91 96,-49 182,-49 182,-91"/>
<text text-anchor="middle" x="139" y="-74.4" font-family="Sans" font-size="14.00">Full</text>
<text text-anchor="middle" x="139" y="-57.4" font-family="Sans" font-size="14.00">Public Key</text>
</g>
<!-- private_key&#45;&gt;full_public_key -->
<g id="edge5" class="edge"><title>private_key&#45;&gt;full_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M82.0016,-70C83.2715,-70 84.5551,-70 85.848,-70"/>
<polygon fill="black" stroke="black" points="85.8679,-73.5001 95.8679,-70 85.8679,-66.5001 85.8679,-73.5001"/>
</g>
<!-- redeemScript -->
<g id="node4" class="node"><title>redeemScript</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="307,-88 197,-88 197,-52 307,-52 307,-88"/>
<text text-anchor="middle" x="252" y="-65.9" font-family="Sans" font-size="14.00">RedeemScript</text>
</g>
<!-- full_public_key&#45;&gt;redeemScript -->
<g id="edge6" class="edge"><title>full_public_key&#45;&gt;redeemScript</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M182.043,-70C183.341,-70 184.649,-70 185.964,-70"/>
<polygon fill="black" stroke="black" points="186.138,-73.5001 196.138,-70 186.137,-66.5001 186.138,-73.5001"/>
</g>
<!-- script_hash -->
<g id="node5" class="node"><title>script_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="378,-91 322,-91 322,-49 378,-49 378,-91"/>
<text text-anchor="middle" x="350" y="-74.4" font-family="Sans" font-size="14.00">Script</text>
<text text-anchor="middle" x="350" y="-57.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- redeemScript&#45;&gt;script_hash -->
<g id="edge7" class="edge"><title>redeemScript&#45;&gt;script_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M307.586,-70C308.947,-70 310.3,-70 311.643,-70"/>
<polygon fill="black" stroke="black" points="311.646,-73.5001 321.646,-70 311.646,-66.5001 311.646,-73.5001"/>
</g>
<!-- spender_script_hash -->
<g id="node7" class="node"><title>spender_script_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="494,-99.5 424,-99.5 424,-40.5 494,-40.5 494,-99.5"/>
<text text-anchor="middle" x="459" y="-82.9" font-family="Sans" font-size="14.00">Copy Of</text>
<text text-anchor="middle" x="459" y="-65.9" font-family="Sans" font-size="14.00">Script</text>
<text text-anchor="middle" x="459" y="-48.9" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- script_hash&#45;&gt;spender_script_hash -->
<g id="edge8" class="edge"><title>script_hash&#45;&gt;spender_script_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M378.07,-70C388.706,-70 401.113,-70 412.972,-70"/>
<polygon fill="black" stroke="black" points="413.194,-73.5001 423.194,-70 413.194,-66.5001 413.194,-73.5001"/>
</g>
<!-- tx1_script_hash -->
<g id="node9" class="node"><title>tx1_script_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="612,-99.5 542,-99.5 542,-40.5 612,-40.5 612,-99.5"/>
<text text-anchor="middle" x="577" y="-82.9" font-family="Sans" font-size="14.00">Copy Of</text>
<text text-anchor="middle" x="577" y="-65.9" font-family="Sans" font-size="14.00">Script</text>
<text text-anchor="middle" x="577" y="-48.9" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- spender_script_hash&#45;&gt;tx1_script_hash -->
<g id="edge9" class="edge"><title>spender_script_hash&#45;&gt;tx1_script_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M494.724,-70C506.161,-70 518.988,-70 531.05,-70"/>
<polygon fill="black" stroke="black" points="531.397,-73.5001 541.397,-70 531.397,-66.5001 531.397,-73.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5.6 KiB

View file

@ -0,0 +1,49 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.15;
splines = ortho;
ranksep = 0.7;
subgraph cluster_parent {
attacker_parent_private_key [ label = "Private", style = "invis" ];
attacker_parent_chain_code [ label = "Chain", style = "filled" ];
attacker_parent_public_key [ label = "Public", style = "invis" ];
label = "Parent"
}
subgraph cluster_child {
attacker_child_private_key [ label = "Private", style = "filled" ];
attacker_child_chain_code [ label = "Chain" ];
attacker_child_public_key [ label = "Public" ];
label = "Child"
}
subgraph cluster_grandchild {
attacker_grandchild_private_key [ label = "Private" ];
attacker_grandchild_chain_code [ label = "Chain" ];
attacker_grandchild_public_key [ label = "Public" ];
label = "Grandchild"
}
attacker_parent_public_key -> attacker_child_public_key [ style = "invis" ];
attacker_parent_chain_code -> attacker_child_chain_code;
attacker_parent_chain_code -> attacker_child_public_key [ style = "invis" ];
attacker_parent_private_key -> attacker_child_private_key [style = "invis" ];
attacker_child_private_key -> attacker_grandchild_private_key;
attacker_child_public_key -> attacker_grandchild_public_key;
attacker_child_chain_code -> attacker_grandchild_private_key;
attacker_child_chain_code -> attacker_grandchild_public_key;
attacker_child_chain_code -> attacker_grandchild_chain_code;
label = "Cross-Generational Key Compromise"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.6 KiB

View file

@ -0,0 +1,96 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="347pt" height="220pt"
viewBox="0.00 0.00 347.00 220.00" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(1 1) rotate(0) translate(4 216)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-216 344,-216 344,5 -4,5"/>
<text text-anchor="middle" x="169.5" y="-8.4" font-family="Sans" font-size="14.00">Cross&#45;Generational Key Compromise</text>
<g id="graph2" class="cluster"><title>cluster_parent</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-33 8,-204 90,-204 90,-33 8,-33"/>
<text text-anchor="middle" x="49" y="-187.4" font-family="Sans" font-size="14.00">Parent</text>
</g>
<g id="graph3" class="cluster"><title>cluster_child</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="124,-33 124,-204 206,-204 206,-33 124,-33"/>
<text text-anchor="middle" x="165" y="-187.4" font-family="Sans" font-size="14.00">Child</text>
</g>
<g id="graph4" class="cluster"><title>cluster_grandchild</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="240,-33 240,-204 331,-204 331,-33 240,-33"/>
<text text-anchor="middle" x="285.5" y="-187.4" font-family="Sans" font-size="14.00">Grandchild</text>
</g>
<!-- attacker_parent_private_key -->
<!-- attacker_child_private_key -->
<g id="node6" class="node"><title>attacker_child_private_key</title>
<polygon fill="lightgrey" stroke="black" stroke-width="1.75" points="198,-171 132,-171 132,-135 198,-135 198,-171"/>
<text text-anchor="middle" x="165" y="-148.9" font-family="Sans" font-size="14.00">Private</text>
</g>
<!-- attacker_parent_private_key&#45;&gt;attacker_child_private_key -->
<!-- attacker_parent_chain_code -->
<g id="node3" class="node"><title>attacker_parent_chain_code</title>
<polygon fill="lightgrey" stroke="black" stroke-width="1.75" points="77,-124 21,-124 21,-88 77,-88 77,-124"/>
<text text-anchor="middle" x="49" y="-101.9" font-family="Sans" font-size="14.00">Chain</text>
</g>
<!-- attacker_child_chain_code -->
<g id="node7" class="node"><title>attacker_child_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="193,-124 137,-124 137,-88 193,-88 193,-124"/>
<text text-anchor="middle" x="165" y="-101.9" font-family="Sans" font-size="14.00">Chain</text>
</g>
<!-- attacker_parent_chain_code&#45;&gt;attacker_child_chain_code -->
<g id="edge7" class="edge"><title>attacker_parent_chain_code&#45;&gt;attacker_child_chain_code</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M77.0804,-106C91.9313,-106 110.386,-106 126.548,-106"/>
<polygon fill="black" stroke="black" points="126.776,-109.5 136.776,-106 126.776,-102.5 126.776,-109.5"/>
</g>
<!-- attacker_child_public_key -->
<g id="node8" class="node"><title>attacker_child_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="193,-77 137,-77 137,-41 193,-41 193,-77"/>
<text text-anchor="middle" x="165" y="-54.9" font-family="Sans" font-size="14.00">Public</text>
</g>
<!-- attacker_parent_chain_code&#45;&gt;attacker_child_public_key -->
<!-- attacker_parent_public_key -->
<!-- attacker_parent_public_key&#45;&gt;attacker_child_public_key -->
<!-- attacker_grandchild_private_key -->
<g id="node10" class="node"><title>attacker_grandchild_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="318,-171 252,-171 252,-135 318,-135 318,-171"/>
<text text-anchor="middle" x="285" y="-148.9" font-family="Sans" font-size="14.00">Private</text>
</g>
<!-- attacker_child_private_key&#45;&gt;attacker_grandchild_private_key -->
<g id="edge13" class="edge"><title>attacker_child_private_key&#45;&gt;attacker_grandchild_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M198.108,-153C211.618,-153 227.42,-153 241.818,-153"/>
<polygon fill="black" stroke="black" points="242,-156.5 252,-153 242,-149.5 242,-156.5"/>
</g>
<!-- attacker_child_chain_code&#45;&gt;attacker_grandchild_private_key -->
<g id="edge17" class="edge"><title>attacker_child_chain_code&#45;&gt;attacker_grandchild_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M193.135,-117.019C207.844,-122.78 226.152,-129.951 242.544,-136.371"/>
<polygon fill="black" stroke="black" points="241.345,-139.661 251.933,-140.049 243.898,-133.143 241.345,-139.661"/>
</g>
<!-- attacker_grandchild_chain_code -->
<g id="node11" class="node"><title>attacker_grandchild_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="313,-124 257,-124 257,-88 313,-88 313,-124"/>
<text text-anchor="middle" x="285" y="-101.9" font-family="Sans" font-size="14.00">Chain</text>
</g>
<!-- attacker_child_chain_code&#45;&gt;attacker_grandchild_chain_code -->
<g id="edge21" class="edge"><title>attacker_child_chain_code&#45;&gt;attacker_grandchild_chain_code</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M193.135,-106C208.968,-106 228.972,-106 246.268,-106"/>
<polygon fill="black" stroke="black" points="246.626,-109.5 256.626,-106 246.626,-102.5 246.626,-109.5"/>
</g>
<!-- attacker_grandchild_public_key -->
<g id="node12" class="node"><title>attacker_grandchild_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="313,-77 257,-77 257,-41 313,-41 313,-77"/>
<text text-anchor="middle" x="285" y="-54.9" font-family="Sans" font-size="14.00">Public</text>
</g>
<!-- attacker_child_chain_code&#45;&gt;attacker_grandchild_public_key -->
<g id="edge19" class="edge"><title>attacker_child_chain_code&#45;&gt;attacker_grandchild_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M193.135,-94.9806C209.15,-88.7079 229.432,-80.764 246.863,-73.937"/>
<polygon fill="black" stroke="black" points="248.173,-77.1828 256.208,-70.2768 245.62,-70.6648 248.173,-77.1828"/>
</g>
<!-- attacker_child_public_key&#45;&gt;attacker_grandchild_public_key -->
<g id="edge15" class="edge"><title>attacker_child_public_key&#45;&gt;attacker_grandchild_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M193.743,-59C209.476,-59 229.188,-59 246.261,-59"/>
<polygon fill="black" stroke="black" points="246.492,-62.5001 256.492,-59 246.492,-55.5001 246.492,-62.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 6.4 KiB

View file

@ -0,0 +1,51 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.15;
splines = ortho;
ranksep = 0.3;
subgraph cluster_parent {
style = "invis";
parent_private_key [ label = "Parent Private Key" ];
parent_chain_code [ label = "Parent Chain Code" ];
parent_public_key [ label = "Parent Public Key" ];
}
child_private_key [ label = "Child Private Key" ];
child_chain_code [ label = "Child Chain Code" ];
child_public_key [ label = "Child Public Key" ];
i_norm [ label = "Index Number" ];
hmac [ label = "One-Way Hash", style = "diagonals" ];
rel1 [ label = "Mathematical\nRelationship", shape = "none" ]
rel2 [ label = "Derived\nMathematical\nRelationship", shape = "none" ]
rel1 -> parent_private_key [ weight = 0, dir = "back" ];
rel1 -> parent_chain_code [ style = "invis" ];
rel1 -> parent_public_key [ weight = 0 ];
child_private_key -> rel2 [ weight = 0 ];
child_chain_code -> rel2 [ weight = 1, style = "invis" ];
child_public_key -> rel2 [ weight = 0, dir = "back" ];
//rel1 -> rel2 [ weight = 0 ];
//parent_private_key -> parent_public_key [constraint = false, label = "Math Rel" ];
//child_private_key -> child_public_key [constraint = false, minlen = 2];
parent_private_key -> child_private_key;
parent_public_key -> child_public_key;
parent_chain_code -> hmac;
i_norm -> hmac;
hmac -> child_public_key;
hmac -> child_private_key;
hmac -> child_chain_code;
label = " \nNormal Hierarchical Deterministic (HD) Key Derivation (BIP32)"
}

BIN
img/dev/en-hd-overview.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

129
img/dev/en-hd-overview.svg Normal file
View file

@ -0,0 +1,129 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="156pt"
viewBox="0.00 0.00 450.00 155.87" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.628492 0.628492) rotate(0) translate(4 244)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-244 713,-244 713,5 -4,5"/>
<text text-anchor="middle" x="354" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="354" y="-8.4" font-family="Sans" font-size="14.00">Normal Hierarchical Deterministic (HD) Key Derivation (BIP32)</text>
<g id="graph2" class="cluster"><title>cluster_parent</title>
</g>
<!-- parent_private_key -->
<g id="node2" class="node"><title>parent_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="278,-224 132,-224 132,-188 278,-188 278,-224"/>
<text text-anchor="middle" x="205" y="-201.9" font-family="Sans" font-size="14.00">Parent Private Key</text>
</g>
<!-- child_private_key -->
<g id="node5" class="node"><title>child_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="576,-224 442,-224 442,-188 576,-188 576,-224"/>
<text text-anchor="middle" x="509" y="-201.9" font-family="Sans" font-size="14.00">Child Private Key</text>
</g>
<!-- parent_private_key&#45;&gt;child_private_key -->
<g id="edge15" class="edge"><title>parent_private_key&#45;&gt;child_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M278.202,-206C324.606,-206 384.552,-206 431.72,-206"/>
<polygon fill="black" stroke="black" points="431.886,-209.5 441.886,-206 431.886,-202.5 431.886,-209.5"/>
</g>
<!-- parent_chain_code -->
<g id="node3" class="node"><title>parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="278,-177 132,-177 132,-141 278,-141 278,-177"/>
<text text-anchor="middle" x="205" y="-154.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- hmac -->
<g id="node9" class="node"><title>hmac</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="419,-177 301,-177 301,-141 419,-141 419,-177"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="313,-177 301,-165 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="301,-153 313,-141 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="407,-141 419,-153 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="419,-165 407,-177 "/>
<text text-anchor="middle" x="360" y="-154.9" font-family="Sans" font-size="14.00">One&#45;Way Hash</text>
</g>
<!-- parent_chain_code&#45;&gt;hmac -->
<g id="edge19" class="edge"><title>parent_chain_code&#45;&gt;hmac</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M278.415,-159C282.322,-159 286.244,-159 290.139,-159"/>
<polygon fill="black" stroke="black" points="290.362,-162.5 300.362,-159 290.362,-155.5 290.362,-162.5"/>
</g>
<!-- parent_public_key -->
<g id="node4" class="node"><title>parent_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="273,-130 137,-130 137,-94 273,-94 273,-130"/>
<text text-anchor="middle" x="205" y="-107.9" font-family="Sans" font-size="14.00">Parent Public Key</text>
</g>
<!-- child_public_key -->
<g id="node7" class="node"><title>child_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="571,-130 447,-130 447,-94 571,-94 571,-130"/>
<text text-anchor="middle" x="509" y="-107.9" font-family="Sans" font-size="14.00">Child Public Key</text>
</g>
<!-- parent_public_key&#45;&gt;child_public_key -->
<g id="edge17" class="edge"><title>parent_public_key&#45;&gt;child_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M273.603,-112C321.996,-112 386.725,-112 436.057,-112"/>
<polygon fill="black" stroke="black" points="436.339,-115.5 446.339,-112 436.339,-108.5 436.339,-115.5"/>
</g>
<!-- rel2 -->
<g id="node11" class="node"><title>rel2</title>
<text text-anchor="middle" x="653" y="-171.9" font-family="Sans" font-size="14.00">Derived</text>
<text text-anchor="middle" x="653" y="-154.9" font-family="Sans" font-size="14.00">Mathematical</text>
<text text-anchor="middle" x="653" y="-137.9" font-family="Sans" font-size="14.00">Relationship</text>
</g>
<!-- child_private_key&#45;&gt;rel2 -->
<g id="edge9" class="edge"><title>child_private_key&#45;&gt;rel2</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M564.262,-187.963C572.044,-185.423 580.101,-182.793 588.044,-180.201"/>
<polygon fill="black" stroke="black" points="589.227,-183.497 597.648,-177.066 587.055,-176.842 589.227,-183.497"/>
</g>
<!-- child_chain_code -->
<g id="node6" class="node"><title>child_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="576,-177 442,-177 442,-141 576,-141 576,-177"/>
<text text-anchor="middle" x="509" y="-154.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- child_chain_code&#45;&gt;rel2 -->
<!-- child_public_key&#45;&gt;rel2 -->
<g id="edge13" class="edge"><title>child_public_key&#45;&gt;rel2</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M573.865,-133.171C581.806,-135.763 589.864,-138.393 597.648,-140.934"/>
<polygon fill="black" stroke="black" points="574.855,-129.813 564.262,-130.037 572.683,-136.467 574.855,-129.813"/>
</g>
<!-- i_norm -->
<g id="node8" class="node"><title>i_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="262,-78 148,-78 148,-42 262,-42 262,-78"/>
<text text-anchor="middle" x="205" y="-55.9" font-family="Sans" font-size="14.00">Index Number</text>
</g>
<!-- i_norm&#45;&gt;hmac -->
<g id="edge21" class="edge"><title>i_norm&#45;&gt;hmac</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M262.135,-76.929C275.539,-80.9004 286,-84 286,-84 286,-84 313.355,-111.725 334.802,-133.461"/>
<polygon fill="black" stroke="black" points="332.572,-136.184 342.087,-140.845 337.555,-131.268 332.572,-136.184"/>
</g>
<!-- hmac&#45;&gt;child_private_key -->
<g id="edge25" class="edge"><title>hmac&#45;&gt;child_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M417.181,-177.037C425.321,-179.605 433.753,-182.265 442.059,-184.884"/>
<polygon fill="black" stroke="black" points="441.136,-188.263 451.726,-187.934 443.242,-181.587 441.136,-188.263"/>
</g>
<!-- hmac&#45;&gt;child_chain_code -->
<g id="edge27" class="edge"><title>hmac&#45;&gt;child_chain_code</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M419.745,-159C423.73,-159 427.774,-159 431.828,-159"/>
<polygon fill="black" stroke="black" points="431.9,-162.5 441.9,-159 431.9,-155.5 431.9,-162.5"/>
</g>
<!-- hmac&#45;&gt;child_public_key -->
<g id="edge23" class="edge"><title>hmac&#45;&gt;child_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M417.181,-140.963C425.321,-138.395 433.753,-135.735 442.059,-133.116"/>
<polygon fill="black" stroke="black" points="443.242,-136.413 451.726,-130.066 441.136,-129.737 443.242,-136.413"/>
</g>
<!-- rel1 -->
<g id="node10" class="node"><title>rel1</title>
<text text-anchor="middle" x="55" y="-163.4" font-family="Sans" font-size="14.00">Mathematical</text>
<text text-anchor="middle" x="55" y="-146.4" font-family="Sans" font-size="14.00">Relationship</text>
</g>
<!-- rel1&#45;&gt;parent_private_key -->
<g id="edge3" class="edge"><title>rel1&#45;&gt;parent_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M119.618,-181.476C122.373,-182.434 124,-183 124,-183 124,-183 131.328,-185.081 141.576,-187.991"/>
<polygon fill="black" stroke="black" points="120.632,-178.123 110.037,-178.143 118.332,-184.734 120.632,-178.123"/>
</g>
<!-- rel1&#45;&gt;parent_chain_code -->
<!-- rel1&#45;&gt;parent_public_key -->
<g id="edge7" class="edge"><title>rel1&#45;&gt;parent_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M110.037,-139.857C118.235,-137.005 124,-135 124,-135 124,-135 127.007,-134.146 131.863,-132.767"/>
<polygon fill="black" stroke="black" points="132.912,-136.108 141.576,-130.009 131,-129.374 132.912,-136.108"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 8.2 KiB

View file

@ -0,0 +1,67 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.05;
splines = ortho;
ranksep = 1.0;
subgraph cluster_hard {
subgraph cluster_h_parent_extended_key {
h_parent_private_key [ label = "Parent Private Key" ];
h_parent_chain_code [ label = "Parent Chain Code" ];
}
subgraph cluster_child_extended_key_else {
child_private_key_hard [ label = "Child Private Key" ];
child_chain_code_hard [ label = "Child Chain Code" ];
}
hmac_hard [ style = "diagonals", label = "One-Way\nHash" ];
i_hard [ label = "Index ≥0x80000000" ];
h_parent_chain_code -> hmac_hard;
h_parent_private_key -> hmac_hard;
i_hard -> hmac_hard;
hmac_hard -> child_private_key_hard;
hmac_hard -> child_chain_code_hard;
h_parent_private_key -> child_private_key_hard;
label = "Hardened Private"
}
subgraph cluster_norm {
//style = "invis"
//label = "Creation Of Normal Child Extended Keys (Key + Chain Code)\nFrom Parent Extended Keys"
subgraph cluster_n_parent_extended_key {
n_parent_private_key [ label = "Parent Private Key" ];
n_parent_chain_code [ label = "Parent Chain Code" ];
}
subgraph cluster_child_extended_key_norm {
child_private_key_norm [ label = "Child Private Key" ];
child_chain_code_norm [ label = "Child Chain Code" ];
}
hmac_norm [ style = "diagonals", label = "One-Way\nHash" ];
i_norm [ label = "Index <0x80000000" ];
n_parent_chain_code -> hmac_norm;
i_norm -> hmac_norm;
hmac_norm -> child_private_key_norm;
hmac_norm -> child_chain_code_norm;
n_parent_private_key -> child_private_key_norm;
label = "Normal Private"
}
label = "Creation Of Child Extended Private Keys (Key, Chain Code)"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,159 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="326pt"
viewBox="0.00 0.00 450.00 325.62" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.792254 0.792254) rotate(0) translate(4 407)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-407 565,-407 565,5 -4,5"/>
<text text-anchor="middle" x="280" y="-8.4" font-family="Sans" font-size="14.00">Creation Of Child Extended Private Keys (Key, Chain Code)</text>
<g id="graph2" class="cluster"><title>cluster_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-33 8,-210 552,-210 552,-33 8,-33"/>
<text text-anchor="middle" x="280" y="-193.4" font-family="Sans" font-size="14.00">Hardened Private</text>
</g>
<g id="graph3" class="cluster"><title>cluster_h_parent_extended_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="16,-85 16,-177 178,-177 178,-85 16,-85"/>
</g>
<g id="graph4" class="cluster"><title>cluster_child_extended_key_else</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="394,-85 394,-177 544,-177 544,-85 394,-85"/>
</g>
<g id="graph5" class="cluster"><title>cluster_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-218 8,-395 552,-395 552,-218 8,-218"/>
<text text-anchor="middle" x="280" y="-378.4" font-family="Sans" font-size="14.00">Normal Private</text>
</g>
<g id="graph6" class="cluster"><title>cluster_n_parent_extended_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="16,-270 16,-362 178,-362 178,-270 16,-270"/>
</g>
<g id="graph7" class="cluster"><title>cluster_child_extended_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="394,-270 394,-362 544,-362 544,-270 394,-270"/>
</g>
<!-- h_parent_private_key -->
<g id="node3" class="node"><title>h_parent_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-169 24,-169 24,-133 170,-133 170,-169"/>
<text text-anchor="middle" x="97" y="-146.9" font-family="Sans" font-size="14.00">Parent Private Key</text>
</g>
<!-- child_private_key_hard -->
<g id="node6" class="node"><title>child_private_key_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="536,-169 402,-169 402,-133 536,-133 536,-169"/>
<text text-anchor="middle" x="469" y="-146.9" font-family="Sans" font-size="14.00">Child Private Key</text>
</g>
<!-- h_parent_private_key&#45;&gt;child_private_key_hard -->
<g id="edge15" class="edge"><title>h_parent_private_key&#45;&gt;child_private_key_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.051,-151C233.921,-151 326.389,-151 391.534,-151"/>
<polygon fill="black" stroke="black" points="391.746,-154.5 401.746,-151 391.746,-147.5 391.746,-154.5"/>
</g>
<!-- hmac_hard -->
<g id="node8" class="node"><title>hmac_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="330,-132 250,-132 250,-90 330,-90 330,-132"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="262,-132 250,-120 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="250,-102 262,-90 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="318,-90 330,-102 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="330,-120 318,-132 "/>
<text text-anchor="middle" x="290" y="-115.4" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="290" y="-98.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- h_parent_private_key&#45;&gt;hmac_hard -->
<g id="edge7" class="edge"><title>h_parent_private_key&#45;&gt;hmac_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.24,-135.821C193.425,-131.015 218.516,-125.815 239.712,-121.422"/>
<polygon fill="black" stroke="black" points="240.697,-124.793 249.779,-119.336 239.277,-117.938 240.697,-124.793"/>
</g>
<!-- h_parent_chain_code -->
<g id="node4" class="node"><title>h_parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-129 24,-129 24,-93 170,-93 170,-129"/>
<text text-anchor="middle" x="97" y="-106.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- h_parent_chain_code&#45;&gt;hmac_hard -->
<g id="edge5" class="edge"><title>h_parent_chain_code&#45;&gt;hmac_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.24,-111C193.425,-111 218.516,-111 239.712,-111"/>
<polygon fill="black" stroke="black" points="239.779,-114.5 249.779,-111 239.779,-107.5 239.779,-114.5"/>
</g>
<!-- child_chain_code_hard -->
<g id="node7" class="node"><title>child_chain_code_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="536,-129 402,-129 402,-93 536,-93 536,-129"/>
<text text-anchor="middle" x="469" y="-106.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- hmac_hard&#45;&gt;child_private_key_hard -->
<g id="edge11" class="edge"><title>hmac_hard&#45;&gt;child_private_key_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M330.171,-119.977C348.413,-124.053 370.63,-129.018 391.896,-133.77"/>
<polygon fill="black" stroke="black" points="391.386,-137.242 401.908,-136.007 392.912,-130.411 391.386,-137.242"/>
</g>
<!-- hmac_hard&#45;&gt;child_chain_code_hard -->
<g id="edge13" class="edge"><title>hmac_hard&#45;&gt;child_chain_code_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M330.171,-111C348.413,-111 370.63,-111 391.896,-111"/>
<polygon fill="black" stroke="black" points="391.908,-114.5 401.908,-111 391.908,-107.5 391.908,-114.5"/>
</g>
<!-- i_hard -->
<g id="node9" class="node"><title>i_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="177,-77 17,-77 17,-41 177,-41 177,-77"/>
<text text-anchor="middle" x="97" y="-54.9" font-family="Sans" font-size="14.00">Index ≥0x80000000</text>
</g>
<!-- i_hard&#45;&gt;hmac_hard -->
<g id="edge9" class="edge"><title>i_hard&#45;&gt;hmac_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M163.96,-77.0411C188.903,-83.7614 216.759,-91.2668 239.928,-97.5091"/>
<polygon fill="black" stroke="black" points="239.315,-100.969 249.881,-100.191 241.136,-94.2097 239.315,-100.969"/>
</g>
<!-- n_parent_private_key -->
<g id="node18" class="node"><title>n_parent_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-354 24,-354 24,-318 170,-318 170,-354"/>
<text text-anchor="middle" x="97" y="-331.9" font-family="Sans" font-size="14.00">Parent Private Key</text>
</g>
<!-- child_private_key_norm -->
<g id="node21" class="node"><title>child_private_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="536,-354 402,-354 402,-318 536,-318 536,-354"/>
<text text-anchor="middle" x="469" y="-331.9" font-family="Sans" font-size="14.00">Child Private Key</text>
</g>
<!-- n_parent_private_key&#45;&gt;child_private_key_norm -->
<g id="edge28" class="edge"><title>n_parent_private_key&#45;&gt;child_private_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.051,-336C233.921,-336 326.389,-336 391.534,-336"/>
<polygon fill="black" stroke="black" points="391.746,-339.5 401.746,-336 391.746,-332.5 391.746,-339.5"/>
</g>
<!-- n_parent_chain_code -->
<g id="node19" class="node"><title>n_parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-314 24,-314 24,-278 170,-278 170,-314"/>
<text text-anchor="middle" x="97" y="-291.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- hmac_norm -->
<g id="node23" class="node"><title>hmac_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="330,-317 250,-317 250,-275 330,-275 330,-317"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="262,-317 250,-305 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="250,-287 262,-275 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="318,-275 330,-287 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="330,-305 318,-317 "/>
<text text-anchor="middle" x="290" y="-300.4" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="290" y="-283.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- n_parent_chain_code&#45;&gt;hmac_norm -->
<g id="edge20" class="edge"><title>n_parent_chain_code&#45;&gt;hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.24,-296C193.425,-296 218.516,-296 239.712,-296"/>
<polygon fill="black" stroke="black" points="239.779,-299.5 249.779,-296 239.779,-292.5 239.779,-299.5"/>
</g>
<!-- child_chain_code_norm -->
<g id="node22" class="node"><title>child_chain_code_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="536,-314 402,-314 402,-278 536,-278 536,-314"/>
<text text-anchor="middle" x="469" y="-291.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- hmac_norm&#45;&gt;child_private_key_norm -->
<g id="edge24" class="edge"><title>hmac_norm&#45;&gt;child_private_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M330.171,-304.977C348.413,-309.053 370.63,-314.018 391.896,-318.77"/>
<polygon fill="black" stroke="black" points="391.386,-322.242 401.908,-321.007 392.912,-315.411 391.386,-322.242"/>
</g>
<!-- hmac_norm&#45;&gt;child_chain_code_norm -->
<g id="edge26" class="edge"><title>hmac_norm&#45;&gt;child_chain_code_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M330.171,-296C348.413,-296 370.63,-296 391.896,-296"/>
<polygon fill="black" stroke="black" points="391.908,-299.5 401.908,-296 391.908,-292.5 391.908,-299.5"/>
</g>
<!-- i_norm -->
<g id="node24" class="node"><title>i_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="177,-262 17,-262 17,-226 177,-226 177,-262"/>
<text text-anchor="middle" x="97" y="-239.9" font-family="Sans" font-size="14.00">Index &lt;0x80000000</text>
</g>
<!-- i_norm&#45;&gt;hmac_norm -->
<g id="edge22" class="edge"><title>i_norm&#45;&gt;hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M163.96,-262.041C188.903,-268.761 216.759,-276.267 239.928,-282.509"/>
<polygon fill="black" stroke="black" points="239.315,-285.969 249.881,-285.191 241.136,-279.21 239.315,-285.969"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,78 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.05;
splines = ortho;
ranksep = 0.30;
subgraph cluster_from_private {
//style = "invis"
//label = "Creation Of Normal Child Extended Keys (Key + Chain Code)\nFrom Parent Extended Keys"
subgraph cluster_fp_n_parent_extended_key {
fp_n_parent_private_key [ label = "Parent Private Key" ];
fp_n_parent_chain_code [ label = "Parent Chain Code" ];
}
subgraph cluster_fp_child_extended_key_norm {
fp_child_private_key_norm [ label = "Child Private Key" ];
fp_child_chain_code_norm [ label = "Child Chain Code" ];
}
subgraph cluster_fp_child_extended_key_pub {
fp_n_child_public_key_norm [ label = "Child Public Key" ];
fp_child_chain_code_norm1 [ label = "Child Chain Code" ];
}
fp_hmac_norm [ style = "diagonals", label = "One-Way\nHash" ];
fp_i_norm [ label = "i (Normal)" ];
fp_n_parent_chain_code -> fp_hmac_norm;
fp_i_norm -> fp_hmac_norm;
fp_hmac_norm -> fp_child_private_key_norm;
fp_hmac_norm -> fp_child_chain_code_norm;
fp_n_parent_private_key -> fp_child_private_key_norm;
fp_child_private_key_norm -> fp_n_child_public_key_norm;
fp_child_chain_code_norm -> fp_child_chain_code_norm1;
label = "From Parent Extended Private Key"
}
equiv [ label = "Equivalent For\nCorresponding\nExtended Keys\nAnd Same\nValue Of i", shape = "none" ];
equiv -> fp_n_child_public_key_norm [ constraint = false, style = "dashed", dir = "back" ];
child_public_key_hard -> equiv [ style = "dashed" ];
subgraph cluster_from_public {
subgraph cluster_h_parent_extended_key {
h_parent_public_key [ label = "Parent Public Key" ];
h_parent_chain_code [ label = "Parent Chain Code" ];
}
subgraph cluster_child_extended_key_else {
child_public_key_hard [ label = "Child Public Key" ];
child_chain_code_hard [ label = "Child Chain Code" ];
}
hmac_hard [ style = "diagonals", label = "One-Way\nHash" ];
i_hard [ label = "i (Normal)" ];
h_parent_chain_code -> hmac_hard;
i_hard -> hmac_hard;
hmac_hard -> child_public_key_hard;
hmac_hard -> child_chain_code_hard;
h_parent_public_key -> child_public_key_hard;
label = "From Parent Extended Public Key"
}
label = "Creation Of Equivalent Child Extended Public Keys From\nEither Private Or Public Parent Keys"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

View file

@ -0,0 +1,196 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="308pt"
viewBox="0.00 0.00 450.00 307.67" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.71885 0.71885) rotate(0) translate(4 424)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-424 623,-424 623,5 -4,5"/>
<text text-anchor="middle" x="309" y="-25.4" font-family="Sans" font-size="14.00">Creation Of Equivalent Child Extended Public Keys From</text>
<text text-anchor="middle" x="309" y="-8.4" font-family="Sans" font-size="14.00">Either Private Or Public Parent Keys</text>
<g id="graph2" class="cluster"><title>cluster_from_private</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-50 8,-227 610,-227 610,-50 8,-50"/>
<text text-anchor="middle" x="309" y="-210.4" font-family="Sans" font-size="14.00">From Parent Extended Private Key</text>
</g>
<g id="graph3" class="cluster"><title>cluster_fp_n_parent_extended_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="16,-102 16,-194 178,-194 178,-102 16,-102"/>
</g>
<g id="graph4" class="cluster"><title>cluster_fp_child_extended_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="286,-102 286,-194 436,-194 436,-102 286,-102"/>
</g>
<g id="graph5" class="cluster"><title>cluster_fp_child_extended_key_pub</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="452,-102 452,-194 602,-194 602,-102 452,-102"/>
</g>
<g id="graph6" class="cluster"><title>cluster_from_public</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-235 8,-412 444,-412 444,-235 8,-235"/>
<text text-anchor="middle" x="226" y="-395.4" font-family="Sans" font-size="14.00">From Parent Extended Public Key</text>
</g>
<g id="graph7" class="cluster"><title>cluster_h_parent_extended_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="16,-287 16,-379 178,-379 178,-287 16,-287"/>
</g>
<g id="graph8" class="cluster"><title>cluster_child_extended_key_else</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="286,-287 286,-379 436,-379 436,-287 286,-287"/>
</g>
<!-- fp_n_parent_private_key -->
<g id="node3" class="node"><title>fp_n_parent_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-186 24,-186 24,-150 170,-150 170,-186"/>
<text text-anchor="middle" x="97" y="-163.9" font-family="Sans" font-size="14.00">Parent Private Key</text>
</g>
<!-- fp_child_private_key_norm -->
<g id="node6" class="node"><title>fp_child_private_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="428,-186 294,-186 294,-150 428,-150 428,-186"/>
<text text-anchor="middle" x="361" y="-163.9" font-family="Sans" font-size="14.00">Child Private Key</text>
</g>
<!-- fp_n_parent_private_key&#45;&gt;fp_child_private_key_norm -->
<g id="edge14" class="edge"><title>fp_n_parent_private_key&#45;&gt;fp_child_private_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.188,-168C205.326,-168 247.454,-168 283.176,-168"/>
<polygon fill="black" stroke="black" points="283.555,-171.5 293.555,-168 283.555,-164.5 283.555,-171.5"/>
</g>
<!-- fp_n_parent_chain_code -->
<g id="node4" class="node"><title>fp_n_parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-146 24,-146 24,-110 170,-110 170,-146"/>
<text text-anchor="middle" x="97" y="-123.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- fp_hmac_norm -->
<g id="node11" class="node"><title>fp_hmac_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="272,-149 192,-149 192,-107 272,-107 272,-149"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="204,-149 192,-137 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="192,-119 204,-107 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="260,-107 272,-119 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="272,-137 260,-149 "/>
<text text-anchor="middle" x="232" y="-132.4" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="232" y="-115.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- fp_n_parent_chain_code&#45;&gt;fp_hmac_norm -->
<g id="edge6" class="edge"><title>fp_n_parent_chain_code&#45;&gt;fp_hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.032,-128C173.876,-128 177.696,-128 181.441,-128"/>
<polygon fill="black" stroke="black" points="181.758,-131.5 191.758,-128 181.758,-124.5 181.758,-131.5"/>
</g>
<!-- fp_n_child_public_key_norm -->
<g id="node9" class="node"><title>fp_n_child_public_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="589,-186 465,-186 465,-150 589,-150 589,-186"/>
<text text-anchor="middle" x="527" y="-163.9" font-family="Sans" font-size="14.00">Child Public Key</text>
</g>
<!-- fp_child_private_key_norm&#45;&gt;fp_n_child_public_key_norm -->
<g id="edge16" class="edge"><title>fp_child_private_key_norm&#45;&gt;fp_n_child_public_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M428.04,-168C436.642,-168 445.481,-168 454.17,-168"/>
<polygon fill="black" stroke="black" points="454.277,-171.5 464.277,-168 454.277,-164.5 454.277,-171.5"/>
</g>
<!-- fp_child_chain_code_norm -->
<g id="node7" class="node"><title>fp_child_chain_code_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="428,-146 294,-146 294,-110 428,-110 428,-146"/>
<text text-anchor="middle" x="361" y="-123.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- fp_child_chain_code_norm1 -->
<g id="node10" class="node"><title>fp_child_chain_code_norm1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="594,-146 460,-146 460,-110 594,-110 594,-146"/>
<text text-anchor="middle" x="527" y="-123.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- fp_child_chain_code_norm&#45;&gt;fp_child_chain_code_norm1 -->
<g id="edge18" class="edge"><title>fp_child_chain_code_norm&#45;&gt;fp_child_chain_code_norm1</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M428.04,-128C435.196,-128 442.516,-128 449.777,-128"/>
<polygon fill="black" stroke="black" points="449.98,-131.5 459.98,-128 449.98,-124.5 449.98,-131.5"/>
</g>
<!-- fp_hmac_norm&#45;&gt;fp_child_private_key_norm -->
<g id="edge10" class="edge"><title>fp_hmac_norm&#45;&gt;fp_child_private_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M272.094,-141.365C280.047,-144.016 286,-146 286,-146 286,-146 287.362,-146.4 289.719,-147.091"/>
<polygon fill="black" stroke="black" points="288.828,-150.477 299.408,-149.933 290.798,-143.76 288.828,-150.477"/>
</g>
<!-- fp_hmac_norm&#45;&gt;fp_child_chain_code_norm -->
<g id="edge12" class="edge"><title>fp_hmac_norm&#45;&gt;fp_child_chain_code_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M272.109,-128C275.911,-128 279.846,-128 283.848,-128"/>
<polygon fill="black" stroke="black" points="283.899,-131.5 293.899,-128 283.899,-124.5 283.899,-131.5"/>
</g>
<!-- fp_i_norm -->
<g id="node12" class="node"><title>fp_i_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="139,-94 55,-94 55,-58 139,-58 139,-94"/>
<text text-anchor="middle" x="97" y="-71.9" font-family="Sans" font-size="14.00">i (Normal)</text>
</g>
<!-- fp_i_norm&#45;&gt;fp_hmac_norm -->
<g id="edge8" class="edge"><title>fp_i_norm&#45;&gt;fp_hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M139.872,-89.232C159.301,-95.2287 178,-101 178,-101 178,-101 179.884,-101.942 182.947,-103.474"/>
<polygon fill="black" stroke="black" points="181.397,-106.611 191.906,-107.953 184.527,-100.35 181.397,-106.611"/>
</g>
<!-- equiv -->
<g id="node20" class="node"><title>equiv</title>
<text text-anchor="middle" x="527" y="-382.9" font-family="Sans" font-size="14.00">Equivalent For</text>
<text text-anchor="middle" x="527" y="-365.9" font-family="Sans" font-size="14.00">Corresponding</text>
<text text-anchor="middle" x="527" y="-348.9" font-family="Sans" font-size="14.00">Extended Keys</text>
<text text-anchor="middle" x="527" y="-331.9" font-family="Sans" font-size="14.00">And Same</text>
<text text-anchor="middle" x="527" y="-314.9" font-family="Sans" font-size="14.00">Value Of i</text>
</g>
<!-- equiv&#45;&gt;fp_n_child_public_key_norm -->
<g id="edge20" class="edge"><title>equiv&#45;&gt;fp_n_child_public_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M527,-296.86C527,-293.434 527,-291.333 527,-291.333 527,-291.333 527,-229.667 527,-229.667 527,-229.667 527,-204.359 527,-186.169"/>
<polygon fill="black" stroke="black" points="523.5,-296.894 527,-306.894 530.5,-296.894 523.5,-296.894"/>
</g>
<!-- child_public_key_hard -->
<g id="node22" class="node"><title>child_public_key_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="423,-371 299,-371 299,-335 423,-335 423,-371"/>
<text text-anchor="middle" x="361" y="-348.9" font-family="Sans" font-size="14.00">Child Public Key</text>
</g>
<!-- child_public_key_hard&#45;&gt;equiv -->
<g id="edge22" class="edge"><title>child_public_key_hard&#45;&gt;equiv</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M423.757,-353C434.864,-353 446.486,-353 457.759,-353"/>
<polygon fill="black" stroke="black" points="457.989,-356.5 467.989,-353 457.989,-349.5 457.989,-356.5"/>
</g>
<!-- h_parent_public_key -->
<g id="node26" class="node"><title>h_parent_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="165,-371 29,-371 29,-335 165,-335 165,-371"/>
<text text-anchor="middle" x="97" y="-348.9" font-family="Sans" font-size="14.00">Parent Public Key</text>
</g>
<!-- h_parent_public_key&#45;&gt;child_public_key_hard -->
<g id="edge35" class="edge"><title>h_parent_public_key&#45;&gt;child_public_key_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M165.674,-353C203.259,-353 249.822,-353 288.057,-353"/>
<polygon fill="black" stroke="black" points="288.096,-356.5 298.096,-353 288.096,-349.5 288.096,-356.5"/>
</g>
<!-- h_parent_chain_code -->
<g id="node27" class="node"><title>h_parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-331 24,-331 24,-295 170,-295 170,-331"/>
<text text-anchor="middle" x="97" y="-308.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- hmac_hard -->
<g id="node30" class="node"><title>hmac_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="272,-334 192,-334 192,-292 272,-292 272,-334"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="204,-334 192,-322 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="192,-304 204,-292 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="260,-292 272,-304 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="272,-322 260,-334 "/>
<text text-anchor="middle" x="232" y="-317.4" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="232" y="-300.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- h_parent_chain_code&#45;&gt;hmac_hard -->
<g id="edge27" class="edge"><title>h_parent_chain_code&#45;&gt;hmac_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.032,-313C173.876,-313 177.696,-313 181.441,-313"/>
<polygon fill="black" stroke="black" points="181.758,-316.5 191.758,-313 181.758,-309.5 181.758,-316.5"/>
</g>
<!-- child_chain_code_hard -->
<g id="node29" class="node"><title>child_chain_code_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="428,-331 294,-331 294,-295 428,-295 428,-331"/>
<text text-anchor="middle" x="361" y="-308.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- hmac_hard&#45;&gt;child_public_key_hard -->
<g id="edge31" class="edge"><title>hmac_hard&#45;&gt;child_public_key_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M272.094,-326.365C280.047,-329.016 286,-331 286,-331 286,-331 287.362,-331.4 289.719,-332.091"/>
<polygon fill="black" stroke="black" points="288.828,-335.477 299.408,-334.933 290.798,-328.76 288.828,-335.477"/>
</g>
<!-- hmac_hard&#45;&gt;child_chain_code_hard -->
<g id="edge33" class="edge"><title>hmac_hard&#45;&gt;child_chain_code_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M272.109,-313C275.911,-313 279.846,-313 283.848,-313"/>
<polygon fill="black" stroke="black" points="283.899,-316.5 293.899,-313 283.899,-309.5 283.899,-316.5"/>
</g>
<!-- i_hard -->
<g id="node31" class="node"><title>i_hard</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="139,-279 55,-279 55,-243 139,-243 139,-279"/>
<text text-anchor="middle" x="97" y="-256.9" font-family="Sans" font-size="14.00">i (Normal)</text>
</g>
<!-- i_hard&#45;&gt;hmac_hard -->
<g id="edge29" class="edge"><title>i_hard&#45;&gt;hmac_hard</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M139.872,-274.232C159.301,-280.229 178,-286 178,-286 178,-286 179.884,-286.942 182.947,-288.474"/>
<polygon fill="black" stroke="black" points="181.397,-291.611 191.906,-292.953 184.527,-285.35 181.397,-291.611"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 13 KiB

View file

@ -0,0 +1,39 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.05;
splines = ortho;
ranksep = 1.0;
subgraph cluster_norm {
//style = "invis"
//label = "Creation Of Normal Child Extended Keys (Key + Chain Code)\nFrom Parent Extended Keys"
subgraph cluster_n_public_extended_key {
n_parent_public_key [ label = "Parent Public Key" ];
n_parent_chain_code [ label = "Parent Chain Code" ];
}
subgraph cluster_child_extended_key_norm {
child_public_key_norm [ label = "Child Public Key" ];
child_chain_code_norm [ label = "Child Chain Code" ];
}
hmac_norm [ style = "diagonals", label = "One-Way\nHash" ];
i_norm [ label = "i (Normal)" ];
n_parent_chain_code -> hmac_norm;
i_norm -> hmac_norm;
hmac_norm -> child_public_key_norm;
hmac_norm -> child_chain_code_norm;
n_parent_public_key -> child_public_key_norm;
label = "Normal Public"
}
label = "Creation Of Child Extended Public Keys (Key, Chain Code)\n(Hardened Child Public Keys Cannot Be Created From A Parent Public Key)"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 7 KiB

View file

@ -0,0 +1,85 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="195pt"
viewBox="0.00 0.00 450.00 195.27" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.803571 0.803571) rotate(0) translate(4 239)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-239 557,-239 557,5 -4,5"/>
<text text-anchor="middle" x="276" y="-25.4" font-family="Sans" font-size="14.00">Creation Of Child Extended Public Keys (Key, Chain Code)</text>
<text text-anchor="middle" x="276" y="-8.4" font-family="Sans" font-size="14.00">(Hardened Child Public Keys Cannot Be Created From A Parent Public Key)</text>
<g id="graph2" class="cluster"><title>cluster_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-50 8,-227 544,-227 544,-50 8,-50"/>
<text text-anchor="middle" x="276" y="-210.4" font-family="Sans" font-size="14.00">Normal Public</text>
</g>
<g id="graph3" class="cluster"><title>cluster_n_public_extended_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="16,-102 16,-194 178,-194 178,-102 16,-102"/>
</g>
<g id="graph4" class="cluster"><title>cluster_child_extended_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="386,-102 386,-194 536,-194 536,-102 386,-102"/>
</g>
<!-- n_parent_public_key -->
<g id="node3" class="node"><title>n_parent_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="165,-186 29,-186 29,-150 165,-150 165,-186"/>
<text text-anchor="middle" x="97" y="-163.9" font-family="Sans" font-size="14.00">Parent Public Key</text>
</g>
<!-- child_public_key_norm -->
<g id="node6" class="node"><title>child_public_key_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="523,-186 399,-186 399,-150 523,-150 523,-186"/>
<text text-anchor="middle" x="461" y="-163.9" font-family="Sans" font-size="14.00">Child Public Key</text>
</g>
<!-- n_parent_public_key&#45;&gt;child_public_key_norm -->
<g id="edge13" class="edge"><title>n_parent_public_key&#45;&gt;child_public_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M165.894,-168C229.477,-168 323.575,-168 388.332,-168"/>
<polygon fill="black" stroke="black" points="388.464,-171.5 398.464,-168 388.464,-164.5 388.464,-171.5"/>
</g>
<!-- n_parent_chain_code -->
<g id="node4" class="node"><title>n_parent_chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="170,-146 24,-146 24,-110 170,-110 170,-146"/>
<text text-anchor="middle" x="97" y="-123.9" font-family="Sans" font-size="14.00">Parent Chain Code</text>
</g>
<!-- hmac_norm -->
<g id="node8" class="node"><title>hmac_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="322,-149 242,-149 242,-107 322,-107 322,-149"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="254,-149 242,-137 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="242,-119 254,-107 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="310,-107 322,-119 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="322,-137 310,-149 "/>
<text text-anchor="middle" x="282" y="-132.4" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="282" y="-115.4" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- n_parent_chain_code&#45;&gt;hmac_norm -->
<g id="edge5" class="edge"><title>n_parent_chain_code&#45;&gt;hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M170.117,-128C190.739,-128 212.708,-128 231.668,-128"/>
<polygon fill="black" stroke="black" points="231.865,-131.5 241.865,-128 231.865,-124.5 231.865,-131.5"/>
</g>
<!-- child_chain_code_norm -->
<g id="node7" class="node"><title>child_chain_code_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="528,-146 394,-146 394,-110 528,-110 528,-146"/>
<text text-anchor="middle" x="461" y="-123.9" font-family="Sans" font-size="14.00">Child Chain Code</text>
</g>
<!-- hmac_norm&#45;&gt;child_public_key_norm -->
<g id="edge9" class="edge"><title>hmac_norm&#45;&gt;child_public_key_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M322.171,-136.977C341.745,-141.351 365.897,-146.748 388.538,-151.807"/>
<polygon fill="black" stroke="black" points="387.948,-155.262 398.471,-154.027 389.475,-148.43 387.948,-155.262"/>
</g>
<!-- hmac_norm&#45;&gt;child_chain_code_norm -->
<g id="edge11" class="edge"><title>hmac_norm&#45;&gt;child_chain_code_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M322.171,-128C340.413,-128 362.63,-128 383.896,-128"/>
<polygon fill="black" stroke="black" points="383.908,-131.5 393.908,-128 383.908,-124.5 383.908,-131.5"/>
</g>
<!-- i_norm -->
<g id="node9" class="node"><title>i_norm</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="139,-94 55,-94 55,-58 139,-58 139,-94"/>
<text text-anchor="middle" x="97" y="-71.9" font-family="Sans" font-size="14.00">i (Normal)</text>
</g>
<!-- i_norm&#45;&gt;hmac_norm -->
<g id="edge7" class="edge"><title>i_norm&#45;&gt;hmac_norm</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M139.908,-88.0605C167.407,-95.79 203.208,-105.853 231.993,-113.944"/>
<polygon fill="black" stroke="black" points="231.284,-117.38 241.858,-116.717 233.178,-110.641 231.284,-117.38"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5.5 KiB

View file

@ -0,0 +1,42 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75 ];
nodesep=0.2;
ranksep=0.2;
splines = ortho;
entropy [ label = "128, 256,\nOr 512 Bits\nOf Entropy\n(The Seed)" ];
hmac [ label = "512-Bit\nOne-Way\nHash", style = "diagonals" ];
entropy -> hmac;
hmac -> private_key [label = "256 Bits" ];
hmac -> chain_code [label = "256 Bits" ];
subgraph cluster_y {
style = "invis"
public_key [ label = "Master\nPublic Key" ];
private_key [ label = "Master\nPrivate Key" ];
chain_code [ label = "Master\nChain Code" ];
}
style = "invis"
subgraph cluster_x {
extended_private_key [ label = "Master\nExtended\nPrivate Key" ];
extended_public_key [ label = "Master\nExtended\nPublic Key" ];
}
private_key -> public_key [ style = "dashed", constraint = 1 ];
chain_code -> extended_private_key;
chain_code -> extended_public_key;
private_key -> extended_private_key;
public_key -> extended_public_key;
label = "Creation Of The Master Keys"
}

BIN
img/dev/en-hd-root-keys.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.7 KiB

111
img/dev/en-hd-root-keys.svg Normal file
View file

@ -0,0 +1,111 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="148pt"
viewBox="0.00 0.00 450.00 147.86" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.714286 0.714286) rotate(0) translate(4 203)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-203 627,-203 627,5 -4,5"/>
<text text-anchor="middle" x="311" y="-8.4" font-family="Sans" font-size="14.00">Creation Of The Master Keys</text>
<g id="graph2" class="cluster"><title>cluster_y</title>
</g>
<g id="graph3" class="cluster"><title>cluster_x</title>
</g>
<!-- entropy -->
<g id="node1" class="node"><title>entropy</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="96,-174 3.55271e-14,-174 0,-98 96,-98 96,-174"/>
<text text-anchor="middle" x="48" y="-157.4" font-family="Sans" font-size="14.00">128, 256,</text>
<text text-anchor="middle" x="48" y="-140.4" font-family="Sans" font-size="14.00">Or 512 Bits</text>
<text text-anchor="middle" x="48" y="-123.4" font-family="Sans" font-size="14.00">Of Entropy</text>
<text text-anchor="middle" x="48" y="-106.4" font-family="Sans" font-size="14.00">(The Seed)</text>
</g>
<!-- hmac -->
<g id="node2" class="node"><title>hmac</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="194,-165.5 114,-165.5 114,-106.5 194,-106.5 194,-165.5"/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="126,-165.5 114,-153.5 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="114,-118.5 126,-106.5 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="182,-106.5 194,-118.5 "/>
<polyline fill="none" stroke="black" stroke-width="1.75" points="194,-153.5 182,-165.5 "/>
<text text-anchor="middle" x="154" y="-148.9" font-family="Sans" font-size="14.00">512&#45;Bit</text>
<text text-anchor="middle" x="154" y="-131.9" font-family="Sans" font-size="14.00">One&#45;Way</text>
<text text-anchor="middle" x="154" y="-114.9" font-family="Sans" font-size="14.00">Hash</text>
</g>
<!-- entropy&#45;&gt;hmac -->
<g id="edge2" class="edge"><title>entropy&#45;&gt;hmac</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M96.0377,-136C98.5335,-136 101.044,-136 103.547,-136"/>
<polygon fill="black" stroke="black" points="103.737,-139.5 113.737,-136 103.737,-132.5 103.737,-139.5"/>
</g>
<!-- private_key -->
<g id="node5" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="371,-183 277,-183 277,-141 371,-141 371,-183"/>
<text text-anchor="middle" x="324" y="-166.4" font-family="Sans" font-size="14.00">Master</text>
<text text-anchor="middle" x="324" y="-149.4" font-family="Sans" font-size="14.00">Private Key</text>
</g>
<!-- hmac&#45;&gt;private_key -->
<g id="edge4" class="edge"><title>hmac&#45;&gt;private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M194.288,-142.162C215.852,-145.46 242.783,-149.579 266.509,-153.207"/>
<polygon fill="black" stroke="black" points="266.042,-156.677 276.457,-154.729 267.101,-149.757 266.042,-156.677"/>
<text text-anchor="middle" x="231" y="-156.4" font-family="Sans" font-size="14.00">256 Bits</text>
</g>
<!-- chain_code -->
<g id="node7" class="node"><title>chain_code</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="371,-127 277,-127 277,-85 371,-85 371,-127"/>
<text text-anchor="middle" x="324" y="-110.4" font-family="Sans" font-size="14.00">Master</text>
<text text-anchor="middle" x="324" y="-93.4" font-family="Sans" font-size="14.00">Chain Code</text>
</g>
<!-- hmac&#45;&gt;chain_code -->
<g id="edge6" class="edge"><title>hmac&#45;&gt;chain_code</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M194.074,-125.147C198.81,-123.864 202,-123 202,-123 202,-123 234.754,-118.436 266.319,-114.038"/>
<polygon fill="black" stroke="black" points="267.061,-117.468 276.482,-112.621 266.095,-110.535 267.061,-117.468"/>
<text text-anchor="middle" x="231" y="-127.4" font-family="Sans" font-size="14.00">256 Bits</text>
</g>
<!-- public_key -->
<g id="node9" class="node"><title>public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="476,-183 390,-183 390,-141 476,-141 476,-183"/>
<text text-anchor="middle" x="433" y="-166.4" font-family="Sans" font-size="14.00">Master</text>
<text text-anchor="middle" x="433" y="-149.4" font-family="Sans" font-size="14.00">Public Key</text>
</g>
<!-- private_key&#45;&gt;public_key -->
<g id="edge10" class="edge"><title>private_key&#45;&gt;public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M371.809,-162C374.412,-162 377.035,-162 379.655,-162"/>
<polygon fill="black" stroke="black" points="379.69,-165.5 389.69,-162 379.69,-158.5 379.69,-165.5"/>
</g>
<!-- extended_private_key -->
<g id="node11" class="node"><title>extended_private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="605,-99.5 511,-99.5 511,-40.5 605,-40.5 605,-99.5"/>
<text text-anchor="middle" x="558" y="-82.9" font-family="Sans" font-size="14.00">Master</text>
<text text-anchor="middle" x="558" y="-65.9" font-family="Sans" font-size="14.00">Extended</text>
<text text-anchor="middle" x="558" y="-48.9" font-family="Sans" font-size="14.00">Private Key</text>
</g>
<!-- private_key&#45;&gt;extended_private_key -->
<g id="edge16" class="edge"><title>private_key&#45;&gt;extended_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M371.615,-141.8C382.023,-137.384 390,-134 390,-134 390,-134 452.085,-110.348 500.771,-91.8015"/>
<polygon fill="black" stroke="black" points="502.208,-94.9994 510.307,-88.1686 499.716,-88.4579 502.208,-94.9994"/>
</g>
<!-- chain_code&#45;&gt;extended_private_key -->
<g id="edge12" class="edge"><title>chain_code&#45;&gt;extended_private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M366.157,-84.9214C374.113,-80.9433 380,-78 380,-78 380,-78 492,-71 492,-71 492,-71 495.274,-70.9504 500.363,-70.8733"/>
<polygon fill="black" stroke="black" points="500.439,-74.3726 510.385,-70.7214 500.333,-67.3734 500.439,-74.3726"/>
</g>
<!-- extended_public_key -->
<g id="node12" class="node"><title>extended_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="601,-171.5 515,-171.5 515,-112.5 601,-112.5 601,-171.5"/>
<text text-anchor="middle" x="558" y="-154.9" font-family="Sans" font-size="14.00">Master</text>
<text text-anchor="middle" x="558" y="-137.9" font-family="Sans" font-size="14.00">Extended</text>
<text text-anchor="middle" x="558" y="-120.9" font-family="Sans" font-size="14.00">Public Key</text>
</g>
<!-- chain_code&#45;&gt;extended_public_key -->
<g id="edge14" class="edge"><title>chain_code&#45;&gt;extended_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M371.635,-113.329C410.235,-119.267 464.599,-127.631 504.654,-133.793"/>
<polygon fill="black" stroke="black" points="504.353,-137.288 514.769,-135.349 505.417,-130.369 504.353,-137.288"/>
</g>
<!-- public_key&#45;&gt;extended_public_key -->
<g id="edge18" class="edge"><title>public_key&#45;&gt;extended_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M476.018,-155.117C485.348,-153.624 495.321,-152.029 504.984,-150.482"/>
<polygon fill="black" stroke="black" points="505.581,-153.932 514.903,-148.896 504.475,-147.019 505.581,-153.932"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 7.5 KiB

66
img/dev/en-hd-tree.dot Normal file
View file

@ -0,0 +1,66 @@
digraph extended {
size=6.25;
rankdir=LR;
penwidth=1.75;
node [ penwidth = 1.75, shape = "box" ];
edge [ penwidth = 1.75, style = "dashed" ];
nodesep=0.15;
splines = ortho;
ranksep = 0.70;
subgraph cluster_0p {
m0p [ label = "m/0'" ];
M0p [ label = "M/0'" ];
m0p -> M0p [ constraint = false ];
label = "Hardened"
}
// DEPTH 1
subgraph cluster_0p_0 {
m0p_0 [ label = "m/0'/0" ];
M0p_0 [ label = "M/0'/0" ];
m0p_0 -> M0p_0 [ constraint = false ];
label = "Normal"
}
subgraph cluster_0p_1p {
m0p_1p [ label = "m/0'/1'" ];
M0p_1p [ label = "M/0'/1'" ];
m0p_1p -> M0p_1p [ constraint = false ];
label = "Hardened";
}
subgraph cluster_0p_0_0 {
m0p_0_0 [ label = "m/0'/0/0" ];
M0p_0_0 [ label = "M/0'/0/0" ];
m0p_0_0 -> M0p_0_0 [ constraint = false ];
label = "Normal"
}
subgraph cluster_0p_1p_0 {
m0p_1p_0 [ label = "m/0'/1'/0" ];
M0p_1p_0 [ label = "M/0'/1'/0" ];
m0p_1p_0 -> M0p_1p_0 [ constraint = false ];
label = "Normal"
}
m0p -> m0p_0;
m0p -> m0p_1p;
m0p_0 -> m0p_0_0;
M0p_0 -> M0p_0_0 [ label = "Normal extended\npublic keys\ncan derive child\npublic keys" ];
m0p_1p -> m0p_1p_0 [ label = "Only derivation from\nextended private keys\nis possible for\nhardened keys" ];
label = "Hierarchical Deterministic Key Derivation"
}

BIN
img/dev/en-hd-tree.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

142
img/dev/en-hd-tree.svg Normal file
View file

@ -0,0 +1,142 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: extended Pages: 1 -->
<svg width="450pt" height="300pt"
viewBox="0.00 0.00 450.00 299.70" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.889328 0.889328) rotate(0) translate(4 333)">
<title>extended</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-333 503,-333 503,5 -4,5"/>
<text text-anchor="middle" x="249" y="-8.4" font-family="Sans" font-size="14.00">Hierarchical Deterministic Key Derivation</text>
<g id="graph2" class="cluster"><title>cluster_0p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-72 8,-207 91,-207 91,-72 8,-72"/>
<text text-anchor="middle" x="49.5" y="-190.4" font-family="Sans" font-size="14.00">Hardened</text>
</g>
<g id="graph3" class="cluster"><title>cluster_0p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="130,-176 130,-311 206,-311 206,-176 130,-176"/>
<text text-anchor="middle" x="168" y="-294.4" font-family="Sans" font-size="14.00">Normal</text>
</g>
<g id="graph4" class="cluster"><title>cluster_0p_1p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="127,-33 127,-168 210,-168 210,-33 127,-33"/>
<text text-anchor="middle" x="168.5" y="-151.4" font-family="Sans" font-size="14.00">Hardened</text>
</g>
<g id="graph5" class="cluster"><title>cluster_0p_0_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="399,-186 399,-321 489,-321 489,-186 399,-186"/>
<text text-anchor="middle" x="444" y="-304.4" font-family="Sans" font-size="14.00">Normal</text>
</g>
<g id="graph6" class="cluster"><title>cluster_0p_1p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="398,-33 398,-168 490,-168 490,-33 398,-33"/>
<text text-anchor="middle" x="444" y="-151.4" font-family="Sans" font-size="14.00">Normal</text>
</g>
<!-- m0p -->
<g id="node2" class="node"><title>m0p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="76,-174 22,-174 22,-138 76,-138 76,-174"/>
<text text-anchor="middle" x="49" y="-151.9" font-family="Sans" font-size="14.00">m/0&#39;</text>
</g>
<!-- M0p -->
<g id="node3" class="node"><title>M0p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="76,-116 22,-116 22,-80 76,-80 76,-116"/>
<text text-anchor="middle" x="49" y="-93.9" font-family="Sans" font-size="14.00">M/0&#39;</text>
</g>
<!-- m0p&#45;&gt;M0p -->
<g id="edge3" class="edge"><title>m0p&#45;&gt;M0p</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M49,-137.935C49,-137.139 49,-136.667 49,-136.667 49,-136.667 49,-131.527 49,-126.373"/>
<polygon fill="black" stroke="black" points="52.5001,-126.065 49,-116.065 45.5001,-126.065 52.5001,-126.065"/>
</g>
<!-- m0p_0 -->
<g id="node6" class="node"><title>m0p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="197,-278 139,-278 139,-242 197,-242 197,-278"/>
<text text-anchor="middle" x="168" y="-255.9" font-family="Sans" font-size="14.00">m/0&#39;/0</text>
</g>
<!-- m0p&#45;&gt;m0p_0 -->
<g id="edge17" class="edge"><title>m0p&#45;&gt;m0p_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M69.4936,-174.129C92.6036,-194.572 127,-225 127,-225 127,-225 132.188,-229.429 138.873,-235.135"/>
<polygon fill="black" stroke="black" points="136.661,-237.849 146.539,-241.68 141.206,-232.525 136.661,-237.849"/>
</g>
<!-- m0p_1p -->
<g id="node10" class="node"><title>m0p_1p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="199,-135 137,-135 137,-99 199,-99 199,-135"/>
<text text-anchor="middle" x="168" y="-112.9" font-family="Sans" font-size="14.00">m/0&#39;/1&#39;</text>
</g>
<!-- m0p&#45;&gt;m0p_1p -->
<g id="edge19" class="edge"><title>m0p&#45;&gt;m0p_1p</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M76.0029,-147.15C91.1364,-142.191 110.316,-135.905 127.242,-130.358"/>
<polygon fill="black" stroke="black" points="128.487,-133.633 136.899,-127.193 126.307,-126.981 128.487,-133.633"/>
</g>
<!-- M0p_0 -->
<g id="node7" class="node"><title>M0p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="197,-220 139,-220 139,-184 197,-184 197,-220"/>
<text text-anchor="middle" x="168" y="-197.9" font-family="Sans" font-size="14.00">M/0&#39;/0</text>
</g>
<!-- m0p_0&#45;&gt;M0p_0 -->
<g id="edge6" class="edge"><title>m0p_0&#45;&gt;M0p_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M168,-241.935C168,-241.139 168,-240.667 168,-240.667 168,-240.667 168,-235.527 168,-230.373"/>
<polygon fill="black" stroke="black" points="171.5,-230.065 168,-220.065 164.5,-230.065 171.5,-230.065"/>
</g>
<!-- m0p_0_0 -->
<g id="node14" class="node"><title>m0p_0_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="480,-288 408,-288 408,-252 480,-252 480,-288"/>
<text text-anchor="middle" x="444" y="-265.9" font-family="Sans" font-size="14.00">m/0&#39;/0/0</text>
</g>
<!-- m0p_0&#45;&gt;m0p_0_0 -->
<g id="edge21" class="edge"><title>m0p_0&#45;&gt;m0p_0_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M197.846,-265.059C212.48,-267.539 227,-270 227,-270 227,-270 333.132,-270 396.95,-270"/>
<polygon fill="black" stroke="black" points="397.189,-273.5 407.189,-270 397.189,-266.5 397.189,-273.5"/>
</g>
<!-- M0p_0_0 -->
<g id="node15" class="node"><title>M0p_0_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="480,-230 408,-230 408,-194 480,-194 480,-230"/>
<text text-anchor="middle" x="444" y="-207.9" font-family="Sans" font-size="14.00">M/0&#39;/0/0</text>
</g>
<!-- M0p_0&#45;&gt;M0p_0_0 -->
<g id="edge23" class="edge"><title>M0p_0&#45;&gt;M0p_0_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M197.846,-200.988C212.48,-200.492 227,-200 227,-200 227,-200 381,-200 381,-200 381,-200 388.151,-201.362 397.635,-203.169"/>
<polygon fill="black" stroke="black" points="397.239,-206.656 407.718,-205.089 398.549,-199.78 397.239,-206.656"/>
<text text-anchor="middle" x="304" y="-255.4" font-family="Sans" font-size="14.00">Normal extended</text>
<text text-anchor="middle" x="304" y="-238.4" font-family="Sans" font-size="14.00">public keys</text>
<text text-anchor="middle" x="304" y="-221.4" font-family="Sans" font-size="14.00">can derive child</text>
<text text-anchor="middle" x="304" y="-204.4" font-family="Sans" font-size="14.00">public keys</text>
</g>
<!-- M0p_1p -->
<g id="node11" class="node"><title>M0p_1p</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="199,-77 137,-77 137,-41 199,-41 199,-77"/>
<text text-anchor="middle" x="168" y="-54.9" font-family="Sans" font-size="14.00">M/0&#39;/1&#39;</text>
</g>
<!-- m0p_1p&#45;&gt;M0p_1p -->
<g id="edge9" class="edge"><title>m0p_1p&#45;&gt;M0p_1p</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M168,-98.9352C168,-98.1387 168,-97.6667 168,-97.6667 168,-97.6667 168,-92.5265 168,-87.3731"/>
<polygon fill="black" stroke="black" points="171.5,-87.0648 168,-77.0648 164.5,-87.0649 171.5,-87.0648"/>
</g>
<!-- m0p_1p_0 -->
<g id="node18" class="node"><title>m0p_1p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="482,-135 406,-135 406,-99 482,-99 482,-135"/>
<text text-anchor="middle" x="444" y="-112.9" font-family="Sans" font-size="14.00">m/0&#39;/1&#39;/0</text>
</g>
<!-- m0p_1p&#45;&gt;m0p_1p_0 -->
<g id="edge25" class="edge"><title>m0p_1p&#45;&gt;m0p_1p_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M199.124,-117C247.035,-117 339.231,-117 395.814,-117"/>
<polygon fill="black" stroke="black" points="395.946,-120.5 405.946,-117 395.946,-113.5 395.946,-120.5"/>
<text text-anchor="middle" x="304" y="-172.4" font-family="Sans" font-size="14.00">Only derivation from</text>
<text text-anchor="middle" x="304" y="-155.4" font-family="Sans" font-size="14.00">extended private keys</text>
<text text-anchor="middle" x="304" y="-138.4" font-family="Sans" font-size="14.00">is possible for</text>
<text text-anchor="middle" x="304" y="-121.4" font-family="Sans" font-size="14.00">hardened keys</text>
</g>
<!-- m0p_0_0&#45;&gt;M0p_0_0 -->
<g id="edge12" class="edge"><title>m0p_0_0&#45;&gt;M0p_0_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M444,-251.935C444,-251.139 444,-250.667 444,-250.667 444,-250.667 444,-245.527 444,-240.373"/>
<polygon fill="black" stroke="black" points="447.5,-240.065 444,-230.065 440.5,-240.065 447.5,-240.065"/>
</g>
<!-- M0p_1p_0 -->
<g id="node19" class="node"><title>M0p_1p_0</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="481,-77 407,-77 407,-41 481,-41 481,-77"/>
<text text-anchor="middle" x="444" y="-54.9" font-family="Sans" font-size="14.00">M/0&#39;/1&#39;/0</text>
</g>
<!-- m0p_1p_0&#45;&gt;M0p_1p_0 -->
<g id="edge15" class="edge"><title>m0p_1p_0&#45;&gt;M0p_1p_0</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M444,-98.9352C444,-98.1387 444,-97.6667 444,-97.6667 444,-97.6667 444,-92.5265 444,-87.3731"/>
<polygon fill="black" stroke="black" points="447.5,-87.0648 444,-77.0648 440.5,-87.0649 447.5,-87.0648"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 9.3 KiB

View file

@ -0,0 +1,54 @@
digraph paymentchannel {
size=6.66;
rankdir=LR;
//splines = false;
nodesep = 0.1;
edge [ fontname="Sans", minlen = 4 ];
node [ fontname="Sans", style = invis, shape = box ];
graph [ fontname="Sans" ]
subgraph cluster_alice {
label = "Alice's Computer\n(Server)"
rank = same;
//atx2v1;
atx2v1s;
atx1v2 [ label = "Bond\n(2-of-2\nmultisig)", style = unfilled, bgcolor = grey ];
//atx2v2;
atx2v3 [ label = " \n \n "];
atx2v4;
atx2v5 [ label = "Refund v45\nBob: 66\n Alice: 44\n(No Lock)", style = unfilled, bgcolor = grey ];
}
subgraph cluster_bob {
label = "Bob's Computer\n(Client)"
rank = same;
btx2v1 [ label = "Refund v1\nBob: 100\nAlice: 0\n(Locktime)", style = unfilled, bgcolor = grey ];
//btx2v1s;
btx1v2 [label = " \n \n \n "];
btx2v2s;
btx2v3;
btx2v4 [ label = " \n \n \n "];
btx2v5;
}
btx2v1 -> atx2v1s [ label = "B: Please sign refund version 1,\nwhich is a full refund of the bond\nthat can't be spent for 24 hours" ];
atx2v1s -> btx1v2 [ style = dashed, label = "A: Signed; please send me the bond to\nprove you funded the account" ];
btx1v2 -> atx1v2 [ label = "B: Here's the bond; please start working" ];
atx1v2 -> btx2v2s [ style = dashed, label = "A: Some work done; please sign refund v2\nreducing your refund by 1 mBTC" ];
btx2v2s -> atx2v3 [ label = "B: Signed; refund now pays Bob: 99; Alice: 1" ];
atx2v3 -> btx2v3 [ style = dashed, label = "A: More work done; please sign v3\nreducing your refund by another 1 mBTC" ];
btx2v3 -> atx2v4 [ label = "B: Signed; refund now pays Bob: 98; Alice: 2" ];
atx2v4 -> btx2v4 [ style = dashed, label = "A: [...]" ];
btx2v4 -> atx2v5 [ label = "B: [...]" ];
atx2v5 -> btx2v5 [ style = dashed, label = "A: I'm done for the day. I'm\ngoing to broadcast refund v45" ];
label = " \n \nAlice broadcasts the bond to the Bitcoin network immediately.\nShe broadcasts the final version of the refund when she finishes work\nor before the locktime. If she fails to broadcast before refund v1's time lock\nexpires, Bob can broadcast refund v1 to get a full refund.\n \nBitcoin Micropayment Channels (As Implemented In Bitcoinj)"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 20 KiB

View file

@ -0,0 +1,128 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: paymentchannel Pages: 1 -->
<svg width="480pt" height="394pt"
viewBox="0.00 0.00 480.00 393.63" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.659341 0.659341) rotate(0) translate(4 593)">
<title>paymentchannel</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-593 725,-593 725,5 -4,5"/>
<text text-anchor="middle" x="360" y="-127.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="360" y="-110.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="360" y="-93.4" font-family="Sans" font-size="14.00">Alice broadcasts the bond to the Bitcoin network immediately.</text>
<text text-anchor="middle" x="360" y="-76.4" font-family="Sans" font-size="14.00">She broadcasts the final version of the refund when she finishes work</text>
<text text-anchor="middle" x="360" y="-59.4" font-family="Sans" font-size="14.00">or before the locktime. &#160;If she fails to broadcast before refund v1&#39;s time lock</text>
<text text-anchor="middle" x="360" y="-42.4" font-family="Sans" font-size="14.00">expires, Bob can broadcast refund v1 to get a full refund.</text>
<text text-anchor="middle" x="360" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="360" y="-8.4" font-family="Sans" font-size="14.00">Bitcoin Micropayment Channels (As Implemented In Bitcoinj)</text>
<g id="graph2" class="cluster"><title>cluster_alice</title>
<polygon fill="none" stroke="black" points="8,-161 8,-511 139,-511 139,-161 8,-161"/>
<text text-anchor="middle" x="73.5" y="-494.4" font-family="Sans" font-size="14.00">Alice&#39;s Computer</text>
<text text-anchor="middle" x="73.5" y="-477.4" font-family="Sans" font-size="14.00">(Server)</text>
</g>
<g id="graph3" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" points="587,-152 587,-581 712,-581 712,-152 587,-152"/>
<text text-anchor="middle" x="649.5" y="-564.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
<text text-anchor="middle" x="649.5" y="-547.4" font-family="Sans" font-size="14.00">(Client)</text>
</g>
<!-- atx2v1s -->
<!-- btx1v2 -->
<!-- atx2v1s&#45;&gt;btx1v2 -->
<g id="edge6" class="edge"><title>atx2v1s&#45;&gt;btx1v2</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M109.156,-451.842C127.301,-455.543 149.689,-459 170,-459 170,-459 170,-459 556,-459 568.056,-459 592.44,-445.948 613.216,-433.316"/>
<polygon fill="black" stroke="black" points="615.193,-436.208 621.852,-427.968 611.508,-430.257 615.193,-436.208"/>
<text text-anchor="middle" x="363" y="-480.4" font-family="Sans" font-size="14.00">A: Signed; please send me the bond to</text>
<text text-anchor="middle" x="363" y="-463.4" font-family="Sans" font-size="14.00">prove you funded the account</text>
</g>
<!-- atx1v2 -->
<g id="node3" class="node"><title>atx1v2</title>
<polygon fill="none" stroke="black" points="111,-418.5 35,-418.5 35,-359.5 111,-359.5 111,-418.5"/>
<text text-anchor="middle" x="73" y="-401.9" font-family="Sans" font-size="14.00">Bond</text>
<text text-anchor="middle" x="73" y="-384.9" font-family="Sans" font-size="14.00">(2&#45;of&#45;2</text>
<text text-anchor="middle" x="73" y="-367.9" font-family="Sans" font-size="14.00">multisig)</text>
</g>
<!-- btx2v2s -->
<!-- atx1v2&#45;&gt;btx2v2s -->
<g id="edge10" class="edge"><title>atx1v2&#45;&gt;btx2v2s</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M111.163,-383.817C129.001,-381.816 150.55,-380 170,-380 170,-380 170,-380 556,-380 556,-380 579.688,-371.595 603.153,-363.268"/>
<polygon fill="black" stroke="black" points="604.524,-366.496 612.777,-359.853 602.183,-359.899 604.524,-366.496"/>
<text text-anchor="middle" x="363" y="-401.4" font-family="Sans" font-size="14.00">A: Some work done; please sign refund v2</text>
<text text-anchor="middle" x="363" y="-384.4" font-family="Sans" font-size="14.00">reducing your refund by 1 mBTC</text>
</g>
<!-- atx2v3 -->
<!-- btx2v3 -->
<!-- atx2v3&#45;&gt;btx2v3 -->
<g id="edge14" class="edge"><title>atx2v3&#45;&gt;btx2v3</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M100.189,-313.979C119.413,-307.781 145.943,-301 170,-301 170,-301 170,-301 556,-301 572.432,-301 590.488,-301.474 606.284,-302.045"/>
<polygon fill="black" stroke="black" points="606.171,-305.543 616.298,-302.43 606.44,-298.548 606.171,-305.543"/>
<text text-anchor="middle" x="363" y="-322.4" font-family="Sans" font-size="14.00">A: More work done; please sign v3</text>
<text text-anchor="middle" x="363" y="-305.4" font-family="Sans" font-size="14.00">reducing your refund by another 1 mBTC</text>
</g>
<!-- atx2v4 -->
<!-- btx2v4 -->
<!-- atx2v4&#45;&gt;btx2v4 -->
<g id="edge18" class="edge"><title>atx2v4&#45;&gt;btx2v4</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M105.567,-259.071C132.409,-250.145 166.608,-239 170,-239 170,-239 170,-239 556,-239 574.322,-239 594.67,-239.393 611.65,-239.83"/>
<polygon fill="black" stroke="black" points="611.647,-243.331 621.738,-240.105 611.838,-236.334 611.647,-243.331"/>
<text text-anchor="middle" x="363" y="-243.4" font-family="Sans" font-size="14.00">A: [...]</text>
</g>
<!-- atx2v5 -->
<g id="node6" class="node"><title>atx2v5</title>
<polygon fill="none" stroke="black" points="120,-245 26,-245 26,-169 120,-169 120,-245"/>
<text text-anchor="middle" x="73" y="-228.4" font-family="Sans" font-size="14.00">Refund v45</text>
<text text-anchor="middle" x="73" y="-211.4" font-family="Sans" font-size="14.00">Bob: 66</text>
<text text-anchor="middle" x="73" y="-194.4" font-family="Sans" font-size="14.00"> Alice: 44</text>
<text text-anchor="middle" x="73" y="-177.4" font-family="Sans" font-size="14.00">(No Lock)</text>
</g>
<!-- btx2v5 -->
<!-- atx2v5&#45;&gt;btx2v5 -->
<g id="edge22" class="edge"><title>atx2v5&#45;&gt;btx2v5</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M120.721,-173.594C135.792,-165.939 152.971,-160 170,-160 170,-160 170,-160 556,-160 572.593,-160 590.553,-162.796 606.225,-166.184"/>
<polygon fill="black" stroke="black" points="605.626,-169.638 616.156,-168.473 607.198,-162.817 605.626,-169.638"/>
<text text-anchor="middle" x="363" y="-181.4" font-family="Sans" font-size="14.00">A: I&#39;m done for the day. &#160;I&#39;m</text>
<text text-anchor="middle" x="363" y="-164.4" font-family="Sans" font-size="14.00">going to broadcast refund v45</text>
</g>
<!-- btx2v1 -->
<g id="node8" class="node"><title>btx2v1</title>
<polygon fill="none" stroke="black" points="693,-531 605,-531 605,-455 693,-455 693,-531"/>
<text text-anchor="middle" x="649" y="-514.4" font-family="Sans" font-size="14.00">Refund v1</text>
<text text-anchor="middle" x="649" y="-497.4" font-family="Sans" font-size="14.00">Bob: 100</text>
<text text-anchor="middle" x="649" y="-480.4" font-family="Sans" font-size="14.00">Alice: 0</text>
<text text-anchor="middle" x="649" y="-463.4" font-family="Sans" font-size="14.00">(Locktime)</text>
</g>
<!-- btx2v1&#45;&gt;atx2v1s -->
<g id="edge4" class="edge"><title>btx2v1&#45;&gt;atx2v1s</title>
<path fill="none" stroke="black" d="M604.266,-502.493C589.026,-504.99 571.838,-507 556,-507 170,-507 170,-507 170,-507 140.695,-507 113.418,-486.397 95.3012,-468.57"/>
<polygon fill="black" stroke="black" points="97.5945,-465.908 88.1186,-461.169 92.5709,-470.783 97.5945,-465.908"/>
<text text-anchor="middle" x="363" y="-545.4" font-family="Sans" font-size="14.00">B: Please sign refund version 1,</text>
<text text-anchor="middle" x="363" y="-528.4" font-family="Sans" font-size="14.00">which is a full refund of the bond</text>
<text text-anchor="middle" x="363" y="-511.4" font-family="Sans" font-size="14.00">that can&#39;t be spent for 24 hours</text>
</g>
<!-- btx1v2&#45;&gt;atx1v2 -->
<g id="edge8" class="edge"><title>btx1v2&#45;&gt;atx1v2</title>
<path fill="none" stroke="black" d="M621.597,-418.157C603.215,-422.92 578.366,-428 556,-428 170,-428 170,-428 170,-428 159.783,-428 139.794,-420.458 120.603,-412.007"/>
<polygon fill="black" stroke="black" points="121.847,-408.729 111.292,-407.815 118.973,-415.112 121.847,-408.729"/>
<text text-anchor="middle" x="363" y="-432.4" font-family="Sans" font-size="14.00">B: Here&#39;s the bond; please start working</text>
</g>
<!-- btx2v2s&#45;&gt;atx2v3 -->
<g id="edge12" class="edge"><title>btx2v2s&#45;&gt;atx2v3</title>
<path fill="none" stroke="black" d="M612.788,-348.14C595.585,-348.589 574.733,-349 556,-349 170,-349 170,-349 170,-349 149.604,-349 127.537,-343.753 109.612,-338.066"/>
<polygon fill="black" stroke="black" points="110.71,-334.743 100.116,-334.893 108.491,-341.382 110.71,-334.743"/>
<text text-anchor="middle" x="363" y="-353.4" font-family="Sans" font-size="14.00">B: Signed; refund now pays Bob: 99; Alice: 1</text>
</g>
<!-- btx2v3&#45;&gt;atx2v4 -->
<g id="edge16" class="edge"><title>btx2v3&#45;&gt;atx2v4</title>
<path fill="none" stroke="black" d="M616.438,-292.641C606.928,-289.271 596.531,-285.535 587,-282 573.148,-276.863 570.774,-270 556,-270 170,-270 170,-270 170,-270 152.289,-270 132.758,-270 115.893,-270"/>
<polygon fill="black" stroke="black" points="115.776,-266.5 105.776,-270 115.776,-273.5 115.776,-266.5"/>
<text text-anchor="middle" x="363" y="-274.4" font-family="Sans" font-size="14.00">B: Signed; refund now pays Bob: 98; Alice: 2</text>
</g>
<!-- btx2v4&#45;&gt;atx2v5 -->
<g id="edge20" class="edge"><title>btx2v4&#45;&gt;atx2v5</title>
<path fill="none" stroke="black" d="M621.812,-225.852C603.726,-217.177 579.128,-208 556,-208 170,-208 170,-208 170,-208 157.376,-208 143.828,-207.914 130.979,-207.793"/>
<polygon fill="black" stroke="black" points="130.892,-204.292 120.856,-207.689 130.82,-211.292 130.892,-204.292"/>
<text text-anchor="middle" x="363" y="-212.4" font-family="Sans" font-size="14.00">B: [...]</text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 9.9 KiB

145
img/dev/en-p2ph-stack.dot Normal file
View file

@ -0,0 +1,145 @@
digraph blockchain {
size=6.66;
splines = "false";
//rankdir=LR;
//ranksep=0.1;
//splines=ortho;
node [ shape = box ];
edge [ style = invis, minlen = 1 ];
//fixedsize
nodesep = 0.05;
//concentrate = true;
subgraph cluster_alice {
bgcolor = grey;
alice_opchecksig [ label = "CHECKSIG" ];
alice_opequalverify [ label = "OP_EQUALVERIFY" ];
alice_pubkeyhash [ label = "Pk Hash", shape = "" ];
alice_ophash [ label = "OP_HASH160" ];
alice_opdup [ label = "OP_DUP" ];
alice_pubkey [style = invis, label="PubKey", shape = "" ];
alice_sig [style = invis, label="Sig", shape = "" ];
label = "Instructions And Data Provided By Alice In Transaction #1's Output Script"
/* label = "Data Provided By Spender 1 To Spend Output" */
}
subgraph cluster_bob {
bgcolor = grey;
bob_opchecksig [ label = "CHECKSIG", style = invis ];
bob_opequalverify [ label = "OP_EQUALVERIFY", style = invis ];
bob_pubkeyhash [ label = "Pk Hash", style = invis, shape = "" ];
bob_ophash [ label = "OP_HASH160", style = invis ];
bob_opdup [ label = "OP_DUP", style = invis ];
bob_pubkey [style = unfilled, label="PubKey", shape = "" ];
bob_sig [style = unfilled, label="Sig", shape = "" ];
label = "Data Provided By Bob In Transaction #2's Input ScriptSig"
}
alice_sig -> bob_sig;
alice_pubkey -> bob_pubkey;
alice_opdup -> bob_opdup;
alice_ophash -> bob_ophash;
alice_pubkeyhash -> bob_pubkeyhash;
alice_opequalverify -> bob_opequalverify;
alice_opchecksig -> bob_opchecksig;
subgraph invis {
node [ style = invis, label="", width=0, height=0 ];
invis0_0;
invis0_1;
invis0_2;
invis0_3;
invis1_0;
invis1_1;
invis1_2;
invis2_0;
invis2_1;
invis3_0;
invis4_0;
invis5_0;
invis5_1;
invis6_0;
invis6_1;
invis6_2;
invis6_3;
invis6_4;
invis6_5;
invis6_6;
}
stack7_opchecksig [style = filled, label="OP_CHECKSIG" ];
stack7_pubkey [style = filled, label="PubKey", shape = "" ];
stack7_sig [style = filled, label="Sig", shape = "" ];
stack6_opequalverify [style = filled, label="OP_EQUALVERIFY" ];
stack6_pubkeyhash [style = filled, label="Pk Hash", shape = "" ];
stack6_ophash [style = filled, label="Pk Hash" ];
stack6_pubkey [style = unfilled, label="PubKey", shape = "" ];
stack6_sig [style = unfilled, label="Sig", shape = "" ];
stack5_pubkeyhash [style = unfilled, label="Pk Hash", shape = "" ];
stack5_ophash [style = unfilled, label="Pk Hash" ];
stack5_pubkey [style = unfilled, label="PubKey", shape = "" ];
stack5_sig [style = unfilled, label="Sig", shape = "" ];
stack4_ophash [style = filled, label="OP_HASH160" ];
stack4_opdup [style = filled, label="PubKey" ];
stack4_pubkey [style = unfilled, label="PubKey", shape = "" ];
stack4_sig [style = unfilled, label="Sig", shape = "" ];
stack3_opdup [style = filled, label="OP_DUP" ];
stack3_pubkey [style = filled, label="PubKey", shape = "" ];
stack3_sig [style = unfilled, label="Sig", shape = "" ];
stack2_pubkey [style = unfilled, label="PubKey", shape = "" ];
stack2_sig [style = unfilled, label="Sig", shape = "" ];
stack1_sig [style = unfilled, label="Sig", shape = "" ];
bob_sig -> invis0_0 -> invis0_1 -> invis0_2 -> invis0_3 -> stack1_sig;
bob_sig -> invis0_1 [ style = "dotted" ];
bob_pubkey -> invis1_0 -> invis1_1 -> invis1_2 -> stack2_pubkey;
bob_pubkey -> stack2_pubkey; stack2_pubkey -> stack2_sig;
bob_opdup -> invis2_0 -> invis2_1 -> stack3_opdup;
alice_opdup -> invis2_1 [ constraint = false, style = "dotted" ]; stack3_opdup -> stack3_pubkey -> stack3_sig;
bob_ophash -> invis3_0 -> stack4_ophash;
bob_ophash -> stack4_ophash; stack4_ophash -> stack4_opdup -> stack4_pubkey -> stack4_sig;
bob_pubkeyhash -> invis4_0 -> stack5_pubkeyhash;
bob_pubkeyhash -> stack5_pubkeyhash; stack5_pubkeyhash -> stack5_ophash -> stack5_pubkey -> stack5_sig;
bob_opequalverify -> stack6_opequalverify; stack6_opequalverify -> stack6_pubkeyhash -> stack6_ophash -> stack6_pubkey -> stack6_sig
bob_opchecksig -> invis5_0 -> invis5_1 -> stack7_opchecksig;
bob_opchecksig -> stack7_opchecksig; stack7_opchecksig -> stack7_pubkey -> stack7_sig
invis6_0 -> invis6_1 -> invis6_2 -> invis6_3 -> invis6_4 -> invis6_5 -> TRUE;
stack7_opchecksig -> TRUE [ style = "", minlen = 2 ];
stack3_opdup -> stack4_opdup [ constraint = false, style = "" ];
stack3_pubkey -> stack3_opdup [ style = "" ];
stack4_ophash -> stack5_ophash [ constraint = false, style = "" ];
stack4_opdup -> stack4_ophash [ style = "" ];
stack6_pubkeyhash -> stack6_opequalverify [ style = "" ];
stack6_ophash -> stack6_pubkeyhash [ style = "" ];
stack7_pubkey -> stack7_opchecksig [ style = "" ];
stack7_sig -> stack7_pubkey [ style = "" ];
label = "Evaluation Stack Over Time During Succesful P2PH Script Validation"
}

BIN
img/dev/en-p2ph-stack.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 20 KiB

306
img/dev/en-p2ph-stack.svg Normal file
View file

@ -0,0 +1,306 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="480pt" height="351pt"
viewBox="0.00 0.00 480.00 350.53" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.631579 0.631579) rotate(0) translate(4 551)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-551 757,-551 757,5 -4,5"/>
<text text-anchor="middle" x="376" y="-8.4" font-family="Sans" font-size="14.00">Evaluation Stack Over Time During Succesful P2PH Script Validation</text>
<g id="graph2" class="cluster"><title>cluster_alice</title>
<polygon fill="grey" stroke="black" points="8,-462 8,-539 710,-539 710,-462 8,-462"/>
<text text-anchor="middle" x="359" y="-522.4" font-family="Sans" font-size="14.00">Instructions And Data Provided By Alice In Transaction #1&#39;s Output Script</text>
</g>
<g id="graph3" class="cluster"><title>cluster_bob</title>
<polygon fill="grey" stroke="black" points="8,-377 8,-454 710,-454 710,-377 8,-377"/>
<text text-anchor="middle" x="359" y="-437.4" font-family="Sans" font-size="14.00">Data Provided By Bob In Transaction #2&#39;s Input ScriptSig</text>
</g>
<!-- alice_opchecksig -->
<g id="node2" class="node"><title>alice_opchecksig</title>
<polygon fill="none" stroke="black" points="702,-506 614,-506 614,-470 702,-470 702,-506"/>
<text text-anchor="middle" x="658" y="-483.9" font-family="Sans" font-size="14.00">CHECKSIG</text>
</g>
<!-- bob_opchecksig -->
<!-- alice_opchecksig&#45;&gt;bob_opchecksig -->
<!-- alice_opequalverify -->
<g id="node3" class="node"><title>alice_opequalverify</title>
<polygon fill="none" stroke="black" points="610,-506 468,-506 468,-470 610,-470 610,-506"/>
<text text-anchor="middle" x="539" y="-483.9" font-family="Sans" font-size="14.00">OP_EQUALVERIFY</text>
</g>
<!-- bob_opequalverify -->
<!-- alice_opequalverify&#45;&gt;bob_opequalverify -->
<!-- alice_pubkeyhash -->
<g id="node4" class="node"><title>alice_pubkeyhash</title>
<ellipse fill="none" stroke="black" cx="414" cy="-488" rx="50.2242" ry="18"/>
<text text-anchor="middle" x="414" y="-483.9" font-family="Sans" font-size="14.00">Pk Hash</text>
</g>
<!-- bob_pubkeyhash -->
<!-- alice_pubkeyhash&#45;&gt;bob_pubkeyhash -->
<!-- alice_ophash -->
<g id="node5" class="node"><title>alice_ophash</title>
<polygon fill="none" stroke="black" points="360,-506 250,-506 250,-470 360,-470 360,-506"/>
<text text-anchor="middle" x="305" y="-483.9" font-family="Sans" font-size="14.00">OP_HASH160</text>
</g>
<!-- bob_ophash -->
<!-- alice_ophash&#45;&gt;bob_ophash -->
<!-- alice_opdup -->
<g id="node6" class="node"><title>alice_opdup</title>
<polygon fill="none" stroke="black" points="246,-506 172,-506 172,-470 246,-470 246,-506"/>
<text text-anchor="middle" x="209" y="-483.9" font-family="Sans" font-size="14.00">OP_DUP</text>
</g>
<!-- bob_opdup -->
<!-- alice_opdup&#45;&gt;bob_opdup -->
<!-- invis2_1 -->
<!-- alice_opdup&#45;&gt;invis2_1 -->
<g id="edge40" class="edge"><title>alice_opdup&#45;&gt;invis2_1</title>
<path fill="none" stroke="black" stroke-dasharray="1,5" d="M209.16,-469.647C209.559,-423.956 210.588,-306.178 210.905,-269.84"/>
<polygon fill="black" stroke="black" points="214.406,-269.73 210.994,-259.7 207.407,-269.669 214.406,-269.73"/>
</g>
<!-- alice_pubkey -->
<!-- bob_pubkey -->
<g id="node15" class="node"><title>bob_pubkey</title>
<ellipse fill="none" stroke="black" cx="121" cy="-403" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="121" y="-398.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- alice_pubkey&#45;&gt;bob_pubkey -->
<!-- alice_sig -->
<!-- bob_sig -->
<g id="node16" class="node"><title>bob_sig</title>
<ellipse fill="none" stroke="black" cx="43" cy="-403" rx="27" ry="18"/>
<text text-anchor="middle" x="43" y="-398.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- alice_sig&#45;&gt;bob_sig -->
<!-- invis5_0 -->
<!-- bob_opchecksig&#45;&gt;invis5_0 -->
<!-- stack7_opchecksig -->
<g id="node45" class="node"><title>stack7_opchecksig</title>
<polygon fill="lightgrey" stroke="black" points="723,-205 607,-205 607,-169 723,-169 723,-205"/>
<text text-anchor="middle" x="665" y="-182.9" font-family="Sans" font-size="14.00">OP_CHECKSIG</text>
</g>
<!-- bob_opchecksig&#45;&gt;stack7_opchecksig -->
<!-- stack6_opequalverify -->
<g id="node48" class="node"><title>stack6_opequalverify</title>
<polygon fill="lightgrey" stroke="black" points="610,-349 468,-349 468,-313 610,-313 610,-349"/>
<text text-anchor="middle" x="539" y="-326.9" font-family="Sans" font-size="14.00">OP_EQUALVERIFY</text>
</g>
<!-- bob_opequalverify&#45;&gt;stack6_opequalverify -->
<!-- invis4_0 -->
<!-- bob_pubkeyhash&#45;&gt;invis4_0 -->
<!-- stack5_pubkeyhash -->
<g id="node53" class="node"><title>stack5_pubkeyhash</title>
<ellipse fill="none" stroke="black" cx="420" cy="-259" rx="50.2242" ry="18"/>
<text text-anchor="middle" x="420" y="-254.9" font-family="Sans" font-size="14.00">Pk Hash</text>
</g>
<!-- bob_pubkeyhash&#45;&gt;stack5_pubkeyhash -->
<!-- invis3_0 -->
<!-- bob_ophash&#45;&gt;invis3_0 -->
<!-- stack4_ophash -->
<g id="node57" class="node"><title>stack4_ophash</title>
<polygon fill="lightgrey" stroke="black" points="365,-277 255,-277 255,-241 365,-241 365,-277"/>
<text text-anchor="middle" x="310" y="-254.9" font-family="Sans" font-size="14.00">OP_HASH160</text>
</g>
<!-- bob_ophash&#45;&gt;stack4_ophash -->
<!-- invis2_0 -->
<!-- bob_opdup&#45;&gt;invis2_0 -->
<!-- invis1_0 -->
<!-- bob_pubkey&#45;&gt;invis1_0 -->
<!-- stack2_pubkey -->
<g id="node64" class="node"><title>stack2_pubkey</title>
<ellipse fill="none" stroke="black" cx="114" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="114" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- bob_pubkey&#45;&gt;stack2_pubkey -->
<!-- invis0_0 -->
<!-- bob_sig&#45;&gt;invis0_0 -->
<!-- invis0_1 -->
<!-- bob_sig&#45;&gt;invis0_1 -->
<g id="edge25" class="edge"><title>bob_sig&#45;&gt;invis0_1</title>
<path fill="none" stroke="black" stroke-dasharray="1,5" d="M43.1267,-384.762C43.338,-354.322 43.7563,-294.095 43.9259,-269.668"/>
<polygon fill="black" stroke="black" points="47.4265,-269.584 43.9961,-259.56 40.4267,-269.535 47.4265,-269.584"/>
</g>
<!-- invis0_0&#45;&gt;invis0_1 -->
<!-- invis0_2 -->
<!-- invis0_1&#45;&gt;invis0_2 -->
<!-- invis0_3 -->
<!-- invis0_2&#45;&gt;invis0_3 -->
<!-- stack1_sig -->
<g id="node66" class="node"><title>stack1_sig</title>
<ellipse fill="none" stroke="black" cx="44" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="44" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- invis0_3&#45;&gt;stack1_sig -->
<!-- invis1_1 -->
<!-- invis1_0&#45;&gt;invis1_1 -->
<!-- invis1_2 -->
<!-- invis1_1&#45;&gt;invis1_2 -->
<!-- invis1_2&#45;&gt;stack2_pubkey -->
<!-- invis2_0&#45;&gt;invis2_1 -->
<!-- stack3_opdup -->
<g id="node61" class="node"><title>stack3_opdup</title>
<polygon fill="lightgrey" stroke="black" points="249,-205 175,-205 175,-169 249,-169 249,-205"/>
<text text-anchor="middle" x="212" y="-182.9" font-family="Sans" font-size="14.00">OP_DUP</text>
</g>
<!-- invis2_1&#45;&gt;stack3_opdup -->
<!-- invis3_0&#45;&gt;stack4_ophash -->
<!-- invis4_0&#45;&gt;stack5_pubkeyhash -->
<!-- invis5_1 -->
<!-- invis5_0&#45;&gt;invis5_1 -->
<!-- invis5_1&#45;&gt;stack7_opchecksig -->
<!-- invis6_0 -->
<!-- invis6_1 -->
<!-- invis6_0&#45;&gt;invis6_1 -->
<!-- invis6_2 -->
<!-- invis6_1&#45;&gt;invis6_2 -->
<!-- invis6_3 -->
<!-- invis6_2&#45;&gt;invis6_3 -->
<!-- invis6_4 -->
<!-- invis6_3&#45;&gt;invis6_4 -->
<!-- invis6_5 -->
<!-- invis6_4&#45;&gt;invis6_5 -->
<!-- TRUE -->
<g id="node87" class="node"><title>TRUE</title>
<polygon fill="none" stroke="black" points="752,-61 698,-61 698,-25 752,-25 752,-61"/>
<text text-anchor="middle" x="725" y="-38.9" font-family="Sans" font-size="14.00">TRUE</text>
</g>
<!-- invis6_5&#45;&gt;TRUE -->
<!-- invis6_6 -->
<!-- stack7_pubkey -->
<g id="node46" class="node"><title>stack7_pubkey</title>
<ellipse fill="lightgrey" stroke="black" cx="665" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="665" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack7_opchecksig&#45;&gt;stack7_pubkey -->
<!-- stack7_opchecksig&#45;&gt;TRUE -->
<g id="edge86" class="edge"><title>stack7_opchecksig&#45;&gt;TRUE</title>
<path fill="none" stroke="black" d="M672.599,-168.762C682.923,-143.985 701.47,-99.4714 713.503,-70.5939"/>
<polygon fill="black" stroke="black" points="716.847,-71.6666 717.463,-61.0896 710.386,-68.9742 716.847,-71.6666"/>
</g>
<!-- stack7_pubkey&#45;&gt;stack7_opchecksig -->
<g id="edge100" class="edge"><title>stack7_pubkey&#45;&gt;stack7_opchecksig</title>
<path fill="none" stroke="black" d="M666.328,-133.413C666.49,-141.059 666.538,-150.108 666.47,-158.573"/>
<polygon fill="black" stroke="black" points="662.967,-158.782 666.323,-168.831 669.966,-158.883 662.967,-158.782"/>
</g>
<!-- stack7_sig -->
<g id="node47" class="node"><title>stack7_sig</title>
<ellipse fill="lightgrey" stroke="black" cx="665" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="665" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack7_pubkey&#45;&gt;stack7_sig -->
<!-- stack7_sig&#45;&gt;stack7_pubkey -->
<g id="edge102" class="edge"><title>stack7_sig&#45;&gt;stack7_pubkey</title>
<path fill="none" stroke="black" d="M666.328,-61.4133C666.49,-69.0593 666.538,-78.1084 666.47,-86.5726"/>
<polygon fill="black" stroke="black" points="662.967,-86.7821 666.323,-96.8314 669.966,-86.8827 662.967,-86.7821"/>
</g>
<!-- stack6_pubkeyhash -->
<g id="node49" class="node"><title>stack6_pubkeyhash</title>
<ellipse fill="lightgrey" stroke="black" cx="539" cy="-259" rx="50.2242" ry="18"/>
<text text-anchor="middle" x="539" y="-254.9" font-family="Sans" font-size="14.00">Pk Hash</text>
</g>
<!-- stack6_opequalverify&#45;&gt;stack6_pubkeyhash -->
<!-- stack6_pubkeyhash&#45;&gt;stack6_opequalverify -->
<g id="edge96" class="edge"><title>stack6_pubkeyhash&#45;&gt;stack6_opequalverify</title>
<path fill="none" stroke="black" d="M540.328,-277.413C540.49,-285.059 540.538,-294.108 540.47,-302.573"/>
<polygon fill="black" stroke="black" points="536.967,-302.782 540.323,-312.831 543.966,-302.883 536.967,-302.782"/>
</g>
<!-- stack6_ophash -->
<g id="node50" class="node"><title>stack6_ophash</title>
<polygon fill="lightgrey" stroke="black" points="575,-205 503,-205 503,-169 575,-169 575,-205"/>
<text text-anchor="middle" x="539" y="-182.9" font-family="Sans" font-size="14.00">Pk Hash</text>
</g>
<!-- stack6_pubkeyhash&#45;&gt;stack6_ophash -->
<!-- stack6_ophash&#45;&gt;stack6_pubkeyhash -->
<g id="edge98" class="edge"><title>stack6_ophash&#45;&gt;stack6_pubkeyhash</title>
<path fill="none" stroke="black" d="M540.328,-205.413C540.49,-213.059 540.538,-222.108 540.47,-230.573"/>
<polygon fill="black" stroke="black" points="536.967,-230.782 540.323,-240.831 543.966,-230.883 536.967,-230.782"/>
</g>
<!-- stack6_pubkey -->
<g id="node51" class="node"><title>stack6_pubkey</title>
<ellipse fill="none" stroke="black" cx="539" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="539" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack6_ophash&#45;&gt;stack6_pubkey -->
<!-- stack6_sig -->
<g id="node52" class="node"><title>stack6_sig</title>
<ellipse fill="none" stroke="black" cx="539" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="539" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack6_pubkey&#45;&gt;stack6_sig -->
<!-- stack5_ophash -->
<g id="node54" class="node"><title>stack5_ophash</title>
<polygon fill="none" stroke="black" points="456,-205 384,-205 384,-169 456,-169 456,-205"/>
<text text-anchor="middle" x="420" y="-182.9" font-family="Sans" font-size="14.00">Pk Hash</text>
</g>
<!-- stack5_pubkeyhash&#45;&gt;stack5_ophash -->
<!-- stack5_pubkey -->
<g id="node55" class="node"><title>stack5_pubkey</title>
<ellipse fill="none" stroke="black" cx="420" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="420" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack5_ophash&#45;&gt;stack5_pubkey -->
<!-- stack5_sig -->
<g id="node56" class="node"><title>stack5_sig</title>
<ellipse fill="none" stroke="black" cx="420" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="420" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack5_pubkey&#45;&gt;stack5_sig -->
<!-- stack4_ophash&#45;&gt;stack5_ophash -->
<g id="edge92" class="edge"><title>stack4_ophash&#45;&gt;stack5_ophash</title>
<path fill="none" stroke="black" d="M337.758,-240.831C351.697,-231.707 368.76,-220.539 383.723,-210.745"/>
<polygon fill="black" stroke="black" points="385.801,-213.568 392.251,-205.163 381.967,-207.711 385.801,-213.568"/>
</g>
<!-- stack4_opdup -->
<g id="node58" class="node"><title>stack4_opdup</title>
<polygon fill="lightgrey" stroke="black" points="344,-205 276,-205 276,-169 344,-169 344,-205"/>
<text text-anchor="middle" x="310" y="-182.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack4_ophash&#45;&gt;stack4_opdup -->
<!-- stack4_opdup&#45;&gt;stack4_ophash -->
<g id="edge94" class="edge"><title>stack4_opdup&#45;&gt;stack4_ophash</title>
<path fill="none" stroke="black" d="M311.328,-205.413C311.49,-213.059 311.538,-222.108 311.47,-230.573"/>
<polygon fill="black" stroke="black" points="307.967,-230.782 311.323,-240.831 314.966,-230.883 307.967,-230.782"/>
</g>
<!-- stack4_pubkey -->
<g id="node59" class="node"><title>stack4_pubkey</title>
<ellipse fill="none" stroke="black" cx="310" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="310" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack4_opdup&#45;&gt;stack4_pubkey -->
<!-- stack4_sig -->
<g id="node60" class="node"><title>stack4_sig</title>
<ellipse fill="none" stroke="black" cx="310" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="310" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack4_pubkey&#45;&gt;stack4_sig -->
<!-- stack3_opdup&#45;&gt;stack4_opdup -->
<g id="edge88" class="edge"><title>stack3_opdup&#45;&gt;stack4_opdup</title>
<path fill="none" stroke="black" d="M249.133,-187C254.542,-187 259.951,-187 265.36,-187"/>
<polygon fill="black" stroke="black" points="265.762,-190.5 275.762,-187 265.762,-183.5 265.762,-190.5"/>
</g>
<!-- stack3_pubkey -->
<g id="node62" class="node"><title>stack3_pubkey</title>
<ellipse fill="lightgrey" stroke="black" cx="212" cy="-115" rx="46.7546" ry="18"/>
<text text-anchor="middle" x="212" y="-110.9" font-family="Sans" font-size="14.00">PubKey</text>
</g>
<!-- stack3_opdup&#45;&gt;stack3_pubkey -->
<!-- stack3_pubkey&#45;&gt;stack3_opdup -->
<g id="edge90" class="edge"><title>stack3_pubkey&#45;&gt;stack3_opdup</title>
<path fill="none" stroke="black" d="M213.328,-133.413C213.49,-141.059 213.538,-150.108 213.47,-158.573"/>
<polygon fill="black" stroke="black" points="209.967,-158.782 213.323,-168.831 216.966,-158.883 209.967,-158.782"/>
</g>
<!-- stack3_sig -->
<g id="node63" class="node"><title>stack3_sig</title>
<ellipse fill="none" stroke="black" cx="212" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="212" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack3_pubkey&#45;&gt;stack3_sig -->
<!-- stack2_sig -->
<g id="node65" class="node"><title>stack2_sig</title>
<ellipse fill="none" stroke="black" cx="114" cy="-43" rx="27" ry="18"/>
<text text-anchor="middle" x="114" y="-38.9" font-family="Sans" font-size="14.00">Sig</text>
</g>
<!-- stack2_pubkey&#45;&gt;stack2_sig -->
</g>
</svg>

After

Width:  |  Height:  |  Size: 16 KiB

View file

@ -0,0 +1,29 @@
graph unique {
size="6.66";
rankdir=LR;
//ratio=fill;
splines=ortho;
overlap = false;
edge [ dir = forward, penwidth=1.75 ];
node [ shape = box, penwidth=1.75 ];
submit_order [ style = invis, width=0, height=0, label = "", ];
calc_total [ label = "Price\nOrder\nIn\nBTC" ]
request_payment [ label = "Request\nPayment" ]
verify_payment [ label = "Verify\nPayment\n& Fulfill\nOrder" ]
issue_refund [ label = "Issue\nRefund\n(Sometimes)" ]
pay_expenses [ label = "Disburse\nIncome\n(Optional)" ]
rebill_recurring [ label = "Rebill\nRecurring\n(Optional)" ]
submit_order -- calc_total [ label = "New\nOrder", minlen = 1 ]
calc_total -- request_payment -- verify_payment [ weight = 100 ]
verify_payment -- issue_refund -- pay_expenses -- rebill_recurring [ style = dashed, weight = 100 ]
rebill_recurring -- calc_total [ style = dashed ]
label = " \nPayment Processing With Bitcoin (From A Receiver's Perspective)"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 6 KiB

View file

@ -0,0 +1,96 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: unique Pages: 1 -->
<svg width="480pt" height="97pt"
viewBox="0.00 0.00 480.00 96.75" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.628272 0.628272) rotate(0) translate(4 150)">
<title>unique</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-150 761,-150 761,5 -4,5"/>
<text text-anchor="middle" x="378" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="378" y="-8.4" font-family="Sans" font-size="14.00">Payment Processing With Bitcoin (From A Receiver&#39;s Perspective)</text>
<!-- submit_order -->
<!-- calc_total -->
<g id="node2" class="node"><title>calc_total</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="134,-146 78,-146 78,-70 134,-70 134,-146"/>
<text text-anchor="middle" x="106" y="-129.4" font-family="Sans" font-size="14.00">Price</text>
<text text-anchor="middle" x="106" y="-112.4" font-family="Sans" font-size="14.00">Order</text>
<text text-anchor="middle" x="106" y="-95.4" font-family="Sans" font-size="14.00">In</text>
<text text-anchor="middle" x="106" y="-78.4" font-family="Sans" font-size="14.00">BTC</text>
</g>
<!-- submit_order&#45;&#45;calc_total -->
<g id="edge2" class="edge"><title>submit_order&#45;&#45;calc_total</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M1.67051,-108C6.76584,-108 39.9259,-108 67.5146,-108"/>
<polygon fill="black" stroke="black" points="67.7454,-111.5 77.7454,-108 67.7454,-104.5 67.7454,-111.5"/>
<text text-anchor="middle" x="40" y="-129.4" font-family="Sans" font-size="14.00">New</text>
<text text-anchor="middle" x="40" y="-112.4" font-family="Sans" font-size="14.00">Order</text>
</g>
<!-- request_payment -->
<g id="node3" class="node"><title>request_payment</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="249,-129 173,-129 173,-87 249,-87 249,-129"/>
<text text-anchor="middle" x="211" y="-112.4" font-family="Sans" font-size="14.00">Request</text>
<text text-anchor="middle" x="211" y="-95.4" font-family="Sans" font-size="14.00">Payment</text>
</g>
<!-- calc_total&#45;&#45;request_payment -->
<g id="edge4" class="edge"><title>calc_total&#45;&#45;request_payment</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M134.138,-108C142.703,-108 152.38,-108 161.907,-108"/>
<polygon fill="black" stroke="black" points="162.126,-111.5 172.126,-108 162.126,-104.5 162.126,-111.5"/>
</g>
<!-- verify_payment -->
<g id="node4" class="node"><title>verify_payment</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="365,-146 289,-146 289,-70 365,-70 365,-146"/>
<text text-anchor="middle" x="327" y="-129.4" font-family="Sans" font-size="14.00">Verify</text>
<text text-anchor="middle" x="327" y="-112.4" font-family="Sans" font-size="14.00">Payment</text>
<text text-anchor="middle" x="327" y="-95.4" font-family="Sans" font-size="14.00">&amp; Fulfill</text>
<text text-anchor="middle" x="327" y="-78.4" font-family="Sans" font-size="14.00">Order</text>
</g>
<!-- request_payment&#45;&#45;verify_payment -->
<g id="edge5" class="edge"><title>request_payment&#45;&#45;verify_payment</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M249.626,-108C258.726,-108 268.544,-108 278.031,-108"/>
<polygon fill="black" stroke="black" points="278.147,-111.5 288.147,-108 278.147,-104.5 278.147,-111.5"/>
</g>
<!-- issue_refund -->
<g id="node5" class="node"><title>issue_refund</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="507,-137.5 405,-137.5 405,-78.5 507,-78.5 507,-137.5"/>
<text text-anchor="middle" x="456" y="-120.9" font-family="Sans" font-size="14.00">Issue</text>
<text text-anchor="middle" x="456" y="-103.9" font-family="Sans" font-size="14.00">Refund</text>
<text text-anchor="middle" x="456" y="-86.9" font-family="Sans" font-size="14.00">(Sometimes)</text>
</g>
<!-- verify_payment&#45;&#45;issue_refund -->
<g id="edge7" class="edge"><title>verify_payment&#45;&#45;issue_refund</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M365.704,-108C374.738,-108 384.579,-108 394.334,-108"/>
<polygon fill="black" stroke="black" points="394.431,-111.5 404.431,-108 394.431,-104.5 394.431,-111.5"/>
</g>
<!-- pay_expenses -->
<g id="node6" class="node"><title>pay_expenses</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="632,-137.5 546,-137.5 546,-78.5 632,-78.5 632,-137.5"/>
<text text-anchor="middle" x="589" y="-120.9" font-family="Sans" font-size="14.00">Disburse</text>
<text text-anchor="middle" x="589" y="-103.9" font-family="Sans" font-size="14.00">Income</text>
<text text-anchor="middle" x="589" y="-86.9" font-family="Sans" font-size="14.00">(Optional)</text>
</g>
<!-- issue_refund&#45;&#45;pay_expenses -->
<g id="edge8" class="edge"><title>issue_refund&#45;&#45;pay_expenses</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M507.802,-108C516.917,-108 526.42,-108 535.578,-108"/>
<polygon fill="black" stroke="black" points="535.733,-111.5 545.733,-108 535.733,-104.5 535.733,-111.5"/>
</g>
<!-- rebill_recurring -->
<g id="node7" class="node"><title>rebill_recurring</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="756,-137.5 670,-137.5 670,-78.5 756,-78.5 756,-137.5"/>
<text text-anchor="middle" x="713" y="-120.9" font-family="Sans" font-size="14.00">Rebill</text>
<text text-anchor="middle" x="713" y="-103.9" font-family="Sans" font-size="14.00">Recurring</text>
<text text-anchor="middle" x="713" y="-86.9" font-family="Sans" font-size="14.00">(Optional)</text>
</g>
<!-- pay_expenses&#45;&#45;rebill_recurring -->
<g id="edge9" class="edge"><title>pay_expenses&#45;&#45;rebill_recurring</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M632.021,-108C640.864,-108 650.278,-108 659.44,-108"/>
<polygon fill="black" stroke="black" points="659.635,-111.5 669.635,-108 659.635,-104.5 659.635,-111.5"/>
</g>
<!-- rebill_recurring&#45;&#45;calc_total -->
<g id="edge11" class="edge"><title>rebill_recurring&#45;&#45;calc_total</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M669.979,-85.1016C634.165,-66.0393 589,-42 589,-42 211,-42 211,-42 211,-42 211,-42 173.093,-65.827 142.832,-84.8483"/>
<polygon fill="black" stroke="black" points="140.742,-82.0282 134.138,-90.3132 144.467,-87.9547 140.742,-82.0282"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 6.5 KiB

View file

@ -0,0 +1,56 @@
digraph paymentchannel {
size=6.66;
rankdir=LR;
splines = true;
nodesep = 0.4;
//edge [ minlen = 2 ];
node [ style = invis, shape = box ];
subgraph cluster_client {
c0;
c2 [ style = "", label = "Pay 10 mBTC\nTo example.com\n(VERIFIED)\nExp. In 10 Min.\nMemo: [...]" ];
c3 [ label = " \n \n \n \n \n \n " ];
label = "Spender"
}
subgraph cluster_wallet {
w0;
w1;
w2 [ style = "", label = <<FONT FACE="Courier-Bold">Payment</FONT><BR/> <BR/>TX1<BR/>[TX...]<BR/>Memo<BR/>Refund<BR/>address(es)> ];
w3;
label = "Spender's\nWallet"
}
subgraph cluster_merchant {
subgraph cluster_payment_request {
label = <<FONT FACE="Courier-Bold">Payment<BR/>Request</FONT>>
m1 [ style = "", label = <<FONT FACE="Courier-Bold">Payment<BR/>Details</FONT><BR/> <BR/><FONT FACE="Courier-Bold">Outputs</FONT><BR/>Exp. Time<BR/>Memo<BR/>Pay URL<BR/>Ref #>];
sig [ style = "", label = "X.509 Sig" ];
}
m3 [ style = "", label = "TX1\n[TX...]\nMemo" ];
label = "Receiver"
}
uri [ style = "", label = "Pay Now\nLink/QR Code" ]
uri -> c0 [constraint = false, label = "bitcoin:\n ?r=http://example.com/pay/123\n \n \n \n"];
c0 -> w0 [ label = "I clicked a\nbitcoin: URI", weight = 100 ];
w0 -> m1 [ label = "Send the\ninvoice from\n[...]/pay/123", weight = 100 ];
m1 -> w1 [ label = "Here's the invoice" ];
w1 -> c2 [ label = "Do you agree to\nthe invoice terms?" ];
p2p [ style = "invis", label="", width=0, height=0 ];
c2 -> w2 [ label = "Yes.\nPay the invoice" ];
w2 -> m3 [ label = "TX(es) attached\nwith refund\naddresses and\na memo" ];
m3 -> p2p [ label = "", style = dashed ]
m3 -> w3 [ label = <<FONT FACE="Courier-Bold">PaymentACK</FONT><BR/>Thanks!<BR/>payment accepted<BR/>for processing> ];
w3 -> c3 [ label = "Payment accepted;\nyou can go do\nsomething else" ];
label = "\nThe Bitcoin Payment Protocol As Described In BIP70"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

View file

@ -0,0 +1,164 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: paymentchannel Pages: 1 -->
<svg width="480pt" height="362pt"
viewBox="0.00 0.00 480.00 362.34" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.668524 0.668524) rotate(0) translate(4 538)">
<title>paymentchannel</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-538 715,-538 715,5 -4,5"/>
<text text-anchor="middle" x="355" y="-8.4" font-family="Sans" font-size="14.00">The Bitcoin Payment Protocol As Described In BIP70</text>
<g id="graph2" class="cluster"><title>cluster_client</title>
<polygon fill="none" stroke="black" points="8,-58 8,-411 152,-411 152,-58 8,-58"/>
<text text-anchor="middle" x="80" y="-394.4" font-family="Sans" font-size="14.00">Spender</text>
</g>
<g id="graph3" class="cluster"><title>cluster_wallet</title>
<polygon fill="none" stroke="black" points="304,-49 304,-428 416,-428 416,-49 304,-49"/>
<text text-anchor="middle" x="360" y="-411.4" font-family="Sans" font-size="14.00">Spender&#39;s</text>
<text text-anchor="middle" x="360" y="-394.4" font-family="Sans" font-size="14.00">Wallet</text>
</g>
<g id="graph4" class="cluster"><title>cluster_merchant</title>
<polygon fill="none" stroke="black" points="562,-129 562,-514 680,-514 680,-129 562,-129"/>
<text text-anchor="middle" x="621" y="-497.4" font-family="Sans" font-size="14.00">Receiver</text>
</g>
<g id="graph5" class="cluster"><title>cluster_payment_request</title>
<polygon fill="none" stroke="black" points="570,-216 570,-481 672,-481 672,-216 570,-216"/>
<text text-anchor="start" x="592" y="-466.733" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Payment</text>
<text text-anchor="start" x="592" y="-449.933" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Request</text>
</g>
<!-- c0 -->
<!-- w0 -->
<!-- c0&#45;&gt;w0 -->
<g id="edge8" class="edge"><title>c0&#45;&gt;w0</title>
<path fill="none" stroke="black" d="M107.102,-360C157.491,-360 265.657,-360 322.827,-360"/>
<polygon fill="black" stroke="black" points="322.883,-363.5 332.883,-360 322.883,-356.5 322.883,-363.5"/>
<text text-anchor="middle" x="228" y="-381.4" font-family="Sans" font-size="14.00">I clicked a</text>
<text text-anchor="middle" x="228" y="-364.4" font-family="Sans" font-size="14.00">bitcoin: URI</text>
</g>
<!-- c2 -->
<g id="node3" class="node"><title>c2</title>
<polygon fill="none" stroke="black" points="143,-313.5 17,-313.5 17,-220.5 143,-220.5 143,-313.5"/>
<text text-anchor="middle" x="80" y="-296.9" font-family="Sans" font-size="14.00">Pay 10 mBTC</text>
<text text-anchor="middle" x="80" y="-279.9" font-family="Sans" font-size="14.00">To example.com</text>
<text text-anchor="middle" x="80" y="-262.9" font-family="Sans" font-size="14.00">(VERIFIED)</text>
<text text-anchor="middle" x="80" y="-245.9" font-family="Sans" font-size="14.00">Exp. In 10 Min.</text>
<text text-anchor="middle" x="80" y="-228.9" font-family="Sans" font-size="14.00">Memo: [...]</text>
</g>
<!-- w2 -->
<g id="node8" class="node"><title>w2</title>
<polygon fill="none" stroke="black" points="408,-248 312,-248 312,-122 408,-122 408,-248"/>
<text text-anchor="start" x="331" y="-233.733" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Payment</text>
<text text-anchor="start" x="357.5" y="-216.933" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="start" x="345.5" y="-200.133" font-family="Sans" font-size="14.00">TX1</text>
<text text-anchor="start" x="338" y="-183.333" font-family="Sans" font-size="14.00">[TX...]</text>
<text text-anchor="start" x="339" y="-166.533" font-family="Sans" font-size="14.00">Memo</text>
<text text-anchor="start" x="335.5" y="-149.733" font-family="Sans" font-size="14.00">Refund</text>
<text text-anchor="start" x="320.5" y="-132.933" font-family="Sans" font-size="14.00">address(es)</text>
</g>
<!-- c2&#45;&gt;w2 -->
<g id="edge16" class="edge"><title>c2&#45;&gt;w2</title>
<path fill="none" stroke="black" d="M143.737,-241.24C149.873,-239.028 156.033,-236.91 162,-235 208.538,-220.107 262.354,-206.758 302.124,-197.607"/>
<polygon fill="black" stroke="black" points="302.948,-201.009 311.919,-195.373 301.391,-194.185 302.948,-201.009"/>
<text text-anchor="middle" x="228" y="-256.4" font-family="Sans" font-size="14.00">Yes.</text>
<text text-anchor="middle" x="228" y="-239.4" font-family="Sans" font-size="14.00">Pay the invoice</text>
</g>
<!-- c3 -->
<!-- m1 -->
<g id="node12" class="node"><title>m1</title>
<polygon fill="none" stroke="black" points="664,-431.5 578,-431.5 578,-288.5 664,-288.5 664,-431.5"/>
<text text-anchor="start" x="592" y="-417.233" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Payment</text>
<text text-anchor="start" x="592" y="-400.433" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Details</text>
<text text-anchor="start" x="618.5" y="-383.633" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="start" x="592" y="-366.833" font-family="Courier,monospace" font-weight="bold" font-size="14.00">Outputs</text>
<text text-anchor="start" x="586.5" y="-350.033" font-family="Sans" font-size="14.00">Exp. Time</text>
<text text-anchor="start" x="600" y="-333.233" font-family="Sans" font-size="14.00">Memo</text>
<text text-anchor="start" x="592" y="-316.433" font-family="Sans" font-size="14.00">Pay URL</text>
<text text-anchor="start" x="601.5" y="-299.633" font-family="Sans" font-size="14.00">Ref #</text>
</g>
<!-- w0&#45;&gt;m1 -->
<g id="edge10" class="edge"><title>w0&#45;&gt;m1</title>
<path fill="none" stroke="black" d="M387.438,-360C429.981,-360 512.644,-360 567.338,-360"/>
<polygon fill="black" stroke="black" points="567.546,-363.5 577.546,-360 567.546,-356.5 567.546,-363.5"/>
<text text-anchor="middle" x="490" y="-398.4" font-family="Sans" font-size="14.00">Send the</text>
<text text-anchor="middle" x="490" y="-381.4" font-family="Sans" font-size="14.00">invoice from</text>
<text text-anchor="middle" x="490" y="-364.4" font-family="Sans" font-size="14.00">[...]/pay/123</text>
</g>
<!-- w1 -->
<!-- w1&#45;&gt;c2 -->
<g id="edge14" class="edge"><title>w1&#45;&gt;c2</title>
<path fill="none" stroke="black" d="M332.709,-292.271C291.606,-288.161 212.37,-280.237 153.532,-274.353"/>
<polygon fill="black" stroke="black" points="153.835,-270.866 143.536,-273.354 153.138,-277.831 153.835,-270.866"/>
<text text-anchor="middle" x="228" y="-310.4" font-family="Sans" font-size="14.00">Do you agree to</text>
<text text-anchor="middle" x="228" y="-293.4" font-family="Sans" font-size="14.00">the invoice terms?</text>
</g>
<!-- m3 -->
<g id="node14" class="node"><title>m3</title>
<polygon fill="none" stroke="black" points="651,-195.5 591,-195.5 591,-136.5 651,-136.5 651,-195.5"/>
<text text-anchor="middle" x="621" y="-178.9" font-family="Sans" font-size="14.00">TX1</text>
<text text-anchor="middle" x="621" y="-161.9" font-family="Sans" font-size="14.00">[TX...]</text>
<text text-anchor="middle" x="621" y="-144.9" font-family="Sans" font-size="14.00">Memo</text>
</g>
<!-- w2&#45;&gt;m3 -->
<g id="edge18" class="edge"><title>w2&#45;&gt;m3</title>
<path fill="none" stroke="black" d="M408.176,-181.493C457.747,-177.884 534.104,-172.326 580.616,-168.94"/>
<polygon fill="black" stroke="black" points="580.913,-172.428 590.632,-168.211 580.404,-165.446 580.913,-172.428"/>
<text text-anchor="middle" x="490" y="-235.4" font-family="Sans" font-size="14.00">TX(es) attached</text>
<text text-anchor="middle" x="490" y="-218.4" font-family="Sans" font-size="14.00">with refund</text>
<text text-anchor="middle" x="490" y="-201.4" font-family="Sans" font-size="14.00">addresses and</text>
<text text-anchor="middle" x="490" y="-184.4" font-family="Sans" font-size="14.00">a memo</text>
</g>
<!-- w3 -->
<!-- w3&#45;&gt;c3 -->
<g id="edge24" class="edge"><title>w3&#45;&gt;c3</title>
<path fill="none" stroke="black" d="M332.717,-79.6384C294.478,-86.2128 222.805,-98.8028 162,-111 147.281,-113.953 131.132,-117.443 117.086,-120.561"/>
<polygon fill="black" stroke="black" points="116.277,-117.155 107.281,-122.752 117.804,-123.987 116.277,-117.155"/>
<text text-anchor="middle" x="228" y="-149.4" font-family="Sans" font-size="14.00">Payment accepted;</text>
<text text-anchor="middle" x="228" y="-132.4" font-family="Sans" font-size="14.00">you can go do</text>
<text text-anchor="middle" x="228" y="-115.4" font-family="Sans" font-size="14.00">something else</text>
</g>
<!-- m1&#45;&gt;w1 -->
<g id="edge12" class="edge"><title>m1&#45;&gt;w1</title>
<path fill="none" stroke="black" d="M577.669,-343.512C569.849,-340.814 561.727,-338.19 554,-336 500.186,-320.751 436.533,-308.343 397.209,-301.312"/>
<polygon fill="black" stroke="black" points="397.73,-297.85 387.273,-299.558 396.513,-304.743 397.73,-297.85"/>
<text text-anchor="middle" x="490" y="-340.4" font-family="Sans" font-size="14.00">Here&#39;s the invoice</text>
</g>
<!-- sig -->
<g id="node13" class="node"><title>sig</title>
<polygon fill="none" stroke="black" points="663,-260 579,-260 579,-224 663,-224 663,-260"/>
<text text-anchor="middle" x="621" y="-237.9" font-family="Sans" font-size="14.00">X.509 Sig</text>
</g>
<!-- m3&#45;&gt;w3 -->
<g id="edge22" class="edge"><title>m3&#45;&gt;w3</title>
<path fill="none" stroke="black" d="M600.465,-136.81C588.622,-122.336 572.435,-106.053 554,-97 503.9,-72.3953 437.986,-70.3411 397.33,-72.0072"/>
<polygon fill="black" stroke="black" points="397.124,-68.513 387.314,-72.5144 397.478,-75.5041 397.124,-68.513"/>
<text text-anchor="start" x="448.5" y="-154.733" font-family="Courier,monospace" font-weight="bold" font-size="14.00">PaymentACK</text>
<text text-anchor="start" x="461.5" y="-137.933" font-family="Sans" font-size="14.00">Thanks!</text>
<text text-anchor="start" x="426.5" y="-121.133" font-family="Sans" font-size="14.00">payment accepted</text>
<text text-anchor="start" x="442" y="-104.333" font-family="Sans" font-size="14.00">for processing</text>
</g>
<!-- p2p -->
<!-- m3&#45;&gt;p2p -->
<g id="edge20" class="edge"><title>m3&#45;&gt;p2p</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M651.285,-166C667.505,-166 686.488,-166 698.127,-166"/>
<polygon fill="black" stroke="black" points="698.182,-169.5 708.182,-166 698.182,-162.5 698.182,-169.5"/>
</g>
<!-- uri -->
<g id="node15" class="node"><title>uri</title>
<polygon fill="none" stroke="black" points="135,-534 25,-534 25,-492 135,-492 135,-534"/>
<text text-anchor="middle" x="80" y="-517.4" font-family="Sans" font-size="14.00">Pay Now</text>
<text text-anchor="middle" x="80" y="-500.4" font-family="Sans" font-size="14.00">Link/QR Code</text>
</g>
<!-- uri&#45;&gt;c0 -->
<g id="edge6" class="edge"><title>uri&#45;&gt;c0</title>
<path fill="none" stroke="black" d="M80,-388.443C80,-418.379 80,-464.815 80,-491.726"/>
<polygon fill="black" stroke="black" points="83.5,-388.228 80,-378.228 76.5,-388.228 83.5,-388.228"/>
<text text-anchor="middle" x="194.5" y="-464.9" font-family="Sans" font-size="14.00">bitcoin:</text>
<text text-anchor="middle" x="194.5" y="-447.9" font-family="Sans" font-size="14.00"> &#160;?r=http://example.com/pay/123</text>
<text text-anchor="middle" x="194.5" y="-430.9" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="194.5" y="-413.9" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="194.5" y="-396.9" font-family="Sans" font-size="14.00"> </text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 11 KiB

View file

@ -0,0 +1,25 @@
digraph {
size=6.25;
rankdir=LR
node [ shape = "box" ]
splines = ortho;
//ranksep = 10;
nodesep = 0.5;
p2pnetwork [ label = "P2P\nNetwork" ]
asic0 [ label = "ASIC" ];
software [ label = "Mining\nSoftware" ]
pool0 [ label = "Mining\nPool" ];
pool0 -> software [ label = "Prototype\nBlock→" ];
p2pnetwork -> pool0 [ label = "TXes→" ];
pool0 -> p2pnetwork [ label = "←Blocks" ];
software -> asic0 [ label = "Block\nHeaders &\nTargets→" ];
asic0 -> software [ label = "←Headers\nBelow\nTarget" ];
software -> pool0 [ constraint = false, label = "←Shares" ];
label = "Pool-Based Bitcoin Mining Workflow"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.4 KiB

View file

@ -0,0 +1,78 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: _anonymous_0 Pages: 1 -->
<svg width="450pt" height="110pt"
viewBox="0.00 0.00 450.00 110.20" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.765306 0.765306) rotate(0) translate(4 140)">
<title>_anonymous_0</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-140 585,-140 585,5 -4,5"/>
<text text-anchor="middle" x="290" y="-8.4" font-family="Sans" font-size="14.00">Pool&#45;Based Bitcoin Mining Workflow</text>
<!-- p2pnetwork -->
<g id="node1" class="node"><title>p2pnetwork</title>
<polygon fill="none" stroke="black" points="77,-100 1,-100 1,-58 77,-58 77,-100"/>
<text text-anchor="middle" x="39" y="-83.4" font-family="Sans" font-size="14.00">P2P</text>
<text text-anchor="middle" x="39" y="-66.4" font-family="Sans" font-size="14.00">Network</text>
</g>
<!-- pool0 -->
<g id="node4" class="node"><title>pool0</title>
<polygon fill="none" stroke="black" points="232,-100 170,-100 170,-58 232,-58 232,-100"/>
<text text-anchor="middle" x="201" y="-83.4" font-family="Sans" font-size="14.00">Mining</text>
<text text-anchor="middle" x="201" y="-66.4" font-family="Sans" font-size="14.00">Pool</text>
</g>
<!-- p2pnetwork&#45;&gt;pool0 -->
<g id="edge4" class="edge"><title>p2pnetwork&#45;&gt;pool0</title>
<path fill="none" stroke="black" d="M77.803,-79C102.457,-79 134.346,-79 159.503,-79"/>
<polygon fill="black" stroke="black" points="159.831,-82.5001 169.831,-79 159.831,-75.5001 159.831,-82.5001"/>
<text text-anchor="middle" x="124" y="-83.4" font-family="Sans" font-size="14.00">TXes→</text>
</g>
<!-- asic0 -->
<g id="node2" class="node"><title>asic0</title>
<polygon fill="none" stroke="black" points="580,-97 526,-97 526,-61 580,-61 580,-97"/>
<text text-anchor="middle" x="553" y="-74.9" font-family="Sans" font-size="14.00">ASIC</text>
</g>
<!-- software -->
<g id="node3" class="node"><title>software</title>
<polygon fill="none" stroke="black" points="418,-100 338,-100 338,-58 418,-58 418,-100"/>
<text text-anchor="middle" x="378" y="-83.4" font-family="Sans" font-size="14.00">Mining</text>
<text text-anchor="middle" x="378" y="-66.4" font-family="Sans" font-size="14.00">Software</text>
</g>
<!-- asic0&#45;&gt;software -->
<g id="edge10" class="edge"><title>asic0&#45;&gt;software</title>
<path fill="none" stroke="black" d="M537.765,-60.7181C524.71,-45.0522 508,-25 508,-25 508,-25 436,-25 436,-25 436,-25 422.132,-37.9116 407.958,-51.1078"/>
<polygon fill="black" stroke="black" points="405.524,-48.5917 400.59,-57.9676 410.294,-53.715 405.524,-48.5917"/>
<text text-anchor="middle" x="472" y="-63.4" font-family="Sans" font-size="14.00">←Headers</text>
<text text-anchor="middle" x="472" y="-46.4" font-family="Sans" font-size="14.00">Below</text>
<text text-anchor="middle" x="472" y="-29.4" font-family="Sans" font-size="14.00">Target</text>
</g>
<!-- software&#45;&gt;asic0 -->
<g id="edge8" class="edge"><title>software&#45;&gt;asic0</title>
<path fill="none" stroke="black" d="M418.283,-83.1672C428.18,-84.191 436,-85 436,-85 436,-85 508,-85 508,-85 508,-85 511.085,-84.5886 515.64,-83.9813"/>
<polygon fill="black" stroke="black" points="516.336,-87.4197 525.785,-82.6286 515.41,-80.4811 516.336,-87.4197"/>
<text text-anchor="middle" x="472" y="-123.4" font-family="Sans" font-size="14.00">Block</text>
<text text-anchor="middle" x="472" y="-106.4" font-family="Sans" font-size="14.00">Headers &amp;</text>
<text text-anchor="middle" x="472" y="-89.4" font-family="Sans" font-size="14.00">Targets→</text>
</g>
<!-- software&#45;&gt;pool0 -->
<g id="edge12" class="edge"><title>software&#45;&gt;pool0</title>
<path fill="none" stroke="black" d="M337.717,-60.9421C327.82,-56.5055 320,-53 320,-53 320,-53 250,-53 250,-53 250,-53 246.279,-54.9745 240.888,-57.8352"/>
<polygon fill="black" stroke="black" points="239.225,-54.7549 232.032,-62.5338 242.506,-60.9383 239.225,-54.7549"/>
<text text-anchor="middle" x="285" y="-57.4" font-family="Sans" font-size="14.00">←Shares</text>
</g>
<!-- pool0&#45;&gt;p2pnetwork -->
<g id="edge6" class="edge"><title>pool0&#45;&gt;p2pnetwork</title>
<path fill="none" stroke="black" d="M169.968,-62.5338C160.243,-57.3739 152,-53 152,-53 152,-53 96,-53 96,-53 96,-53 92.3058,-54.6851 86.7984,-57.1972"/>
<polygon fill="black" stroke="black" points="85.2967,-54.0352 77.6511,-61.3697 88.2018,-60.4039 85.2967,-54.0352"/>
<text text-anchor="middle" x="124" y="-57.4" font-family="Sans" font-size="14.00">←Blocks</text>
</g>
<!-- pool0&#45;&gt;software -->
<g id="edge2" class="edge"><title>pool0&#45;&gt;software</title>
<path fill="none" stroke="black" d="M232.237,-79C258.629,-79 296.93,-79 327.648,-79"/>
<polygon fill="black" stroke="black" points="327.746,-82.5001 337.746,-79 327.746,-75.5001 327.746,-82.5001"/>
<text text-anchor="middle" x="285" y="-100.4" font-family="Sans" font-size="14.00">Prototype</text>
<text text-anchor="middle" x="285" y="-83.4" font-family="Sans" font-size="14.00">Block→</text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5.1 KiB

BIN
img/dev/en-qr-code.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.4 KiB

225
img/dev/en-qr-code.svg Normal file
View file

@ -0,0 +1,225 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="507.98975"
height="180.34579"
id="svg2"
version="1.1"
inkscape:version="0.48.3.1 r9886"
sodipodi:docname="qr-code.svg">
<defs
id="defs4" />
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="1"
inkscape:pageshadow="2"
inkscape:zoom="0.98994949"
inkscape:cx="299.12153"
inkscape:cy="67.832358"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="false"
inkscape:window-width="1278"
inkscape:window-height="762"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="0"
fit-margin-top="1"
fit-margin-right="1"
fit-margin-bottom="1"
fit-margin-left="1"
units="mm" />
<metadata
id="metadata7">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(-181.68411,-447.73083)">
<rect
style="fill:#ffffff;fill-opacity:1;stroke:none"
id="rect3324"
width="519.21838"
height="186.87822"
x="-4.0406103"
y="-2.491816"
transform="translate(181.68411,447.73083)" />
<text
xml:space="preserve"
style="font-size:12px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans;-inkscape-font-specification:Sans"
x="237.82751"
y="622.03723"
id="text3050"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan3052"
x="237.82751"
y="622.03723">bitcoin:mjSk1Ny9spzU2fouzYgLqGUD8U41iR35QN?amount=.1</tspan></text>
<text
xml:space="preserve"
style="font-size:12px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans;-inkscape-font-specification:Sans"
x="230.32329"
y="496.75681"
id="text3113"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan3115"
x="230.32329"
y="496.75681">Low</tspan></text>
<text
xml:space="preserve"
style="font-size:12px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans;-inkscape-font-specification:Sans"
x="333.35886"
y="484.63495"
id="text3117"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan3119"
x="333.35886"
y="484.63495">Medium</tspan></text>
<text
xml:space="preserve"
style="font-size:12px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans;-inkscape-font-specification:Sans"
x="456.59744"
y="471.50299"
id="text3121"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan3123"
x="456.59744"
y="471.50299">Quartile</tspan></text>
<text
xml:space="preserve"
style="font-size:12px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Sans;-inkscape-font-specification:Sans"
x="603.06958"
y="460.39133"
id="text3125"
sodipodi:linespacing="125%"><tspan
sodipodi:role="line"
id="tspan3127"
x="603.06958"
y="460.39133">High</tspan></text>
<image
y="499.90402"
x="185.22742"
id="image3047"
xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAG8AAABvCAIAAABtpwk3AAAAA3NCSVQICAjb4U/gAAACqklEQVR4
nO2cQW4EIQwEM1H+/+XNjQuSZZtas1pVHROGTFpuBozheb1ePwLxe/sFvgrVJFFNEtUkUU0S1SRR
TRLVJFFNEtUkUU2Sv0yj53lO/kaQCgh6Xk/tbYJflfopkUloGJskqkmScvqilL7bnfU+X5de7PC/
CDA2SVSTpOb0Rc90lGfX43vjYKAI+um9xo6xSaKaJE2n9wgcGjQudXh309DYJFFNklGnZz6ve5t9
JlD6TE9639gkUU2SptN79tmtmvnJ+14MHwSMTRLVJKk5/TB93aM3PpTW8hTGJolqkjxXFraHxuyt
AgYwNklUk4TfTz9MsGcW7EHj0m4dvogwNklUk+Q0I3forKDDHpm5QS/FZ+XMNKpJgmXkMs7K9BM8
HowPmcalkcf99PuoJslp5Uxgn8MamMzjvUlCqbbH2fs1VJOEr4alTFfy2uGcn9rjMzZJVJOklnsf
qGLFf7W/Ye9cjOv0aVST5HSXrZeWL/Vc2onrlc+5Tv9EVJMk5fSMEXqVKpSLg8YDBl8YmySqScKf
ZdvbvK9wfXJi7+x9GtUkOd1lo06m7E8teqfadwZKeY1NEtUkqc3eqftbFodrB2qSQNXQGpskqkky
USO3sxr3PvcDG3C9JbyxSaKaJBM1cpnHS86iLrLYOzzM0RmbJKpJMnqWrVeGerh2KE3se/0sjE0S
1SS5fDdsb/rdMy+ePNwxNklUk2T0btje+bJe2m1noKrW2CRRTZLRu2GpjH1pDOltwFkNex/VJBm9
MXKx+6j0Ke8NJlQ1YICxSaKaJHecfngrO1X3ftjhjrFJopoko3fDBmSOt1PFcpm/3uvH2CRRTZLL
d8MGzsI/05mezb1/EKpJcudu2G/F2CRRTRLVJFFNEtUkUU0S1SRRTRLVJFFNEtUk+QcaXTfA4mJ7
PwAAAABJRU5ErkJggg==
"
height="111"
width="111" />
<image
y="487.90402"
x="291.19513"
id="image3191"
xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAHsAAAB7CAIAAADbpWgoAAAAA3NCSVQICAjb4U/gAAADQklEQVR4
nO2dS47jMAwFx4O5/5UzO28EEPy5nEZXLbstS3lgXiiJsq/P5/NHQP6+PYBfh4rTqDiNitOoOI2K
06g4jYrTqDiNitOoOM2/zEXXdU36KC3d3H3drYLeg2vOTs87B733yHxSY5xGxWlSrnLT84dhF6d1
BH/JDCNjQc99UmOcRsVpaq5yk8kfhnfOmEmmeZC0lMZz0vukxjiNitM0XWVIaVKzZS+ZFAXAGKdR
cZp3XCX4pq8bTsmLAIxxGhWnabpK71c+mJ6UbKFkSsNlmfV8xhinUXGamqus/8r3pjnDyVFpYOsY
4zQqTnO9W7GfyRZKzTNuUMpV1jHGaVScJuUqwbevtChaqioJmvcKTjKtAMMxxmlUnKbmKic9Mwko
Gdewvi645hzP0O5ujHEaFaeZ5irBxSeZr2Gvr+Gdn7PEE2OcRsVpUqu1pblDb3pS+sqXyCz23mRs
YZgyGeM0Kk7T3ANaX2AJ6G0ED+cypYGVMMZpVJymtge0vob53GLv+gyolLAFGOM0Kk4zdZWtH/dX
/Ooc2Nb56ABjnEbFaab1Kr2f8q0Z0PBY9Hpzc5VvRMVpas9X2XoEQc8oenX1vUnWc4UrxjiNitPs
z4CG+7brxSRB85MtdwowxmlUnGYtVymdPr7pPdOgd8Pn6v1KGOM0Kk5Tq1dZXw8pJTYnpUlWQGna
NayoMcZpVJym+dzanj+czYO/nPfZMophGjNMWoxxGhWnWTuz/Mrp45PhwcNhia/rKt+IitNMTxee
PHfEeHg8cIvhPpExTqPiNM11leGaSTAD2tqPXt9myjTPYIzTqDjN2pnl4c7IsNStV7U7HHOm9xNj
nEbFadBnwa2nDcHFJ89NqZwBfTUqToO+u7BX3FIqU8nQq43ZSnWMcRoVp0HfXfjcskymi5utc4I9
jHEaFadB312YWaRdr7bNsJWMZTDGaVScBn3LWGkPqHcYsHcCsWdl7iz/DFScBnUVoMKttENd2uDe
OsVsjNOoOA367sLgPsMTPcMHKWQMp7SQG2CM06g4DfruwszWz/rDDUrjOf+V2cDSVb4aFad5+d2F
vxBjnEbFaVScRsVpVJxGxWlUnEbFaVScRsVpVJzmP8M8ChN/iw3mAAAAAElFTkSuQmCC
"
height="123"
width="123" />
<image
y="475.90402"
x="409.16284"
id="image3256"
xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAIcAAACHCAIAAACzhd1dAAAAA3NCSVQICAjb4U/gAAAEAklEQVR4
nO2dwY7jMAxDt4v9/1+evfnigSBSSocdvHdsnDgtIcKWZff19fX1B8L4+9MvAN+AKomgSiKokgiq
JIIqiaBKIqiSCKokgiqJoEoi/zqNXq/XpI871XYeeC7dXRSXijadtF7n6xTPWf81boiVRFAlkZaD
HaS0/x3phXFJLtexl+Kuoi+J4a9RQKwkgiqJaA526IyLiksdc5NczqMY+A2fM3wgsZIIqiRiOphH
x4sKN5Cmk55JhkCsJIIqibzVwW6GE0OpTdHYy6c9B7GSCKokYjqYF+CFUXhWVrTp9F60kTpdtzti
JRFUSURzsK28k2dl0l1bn3S+zjrESiKokkjLwdbHGNKk777rxstodaysuOs5iJVEUCWRl1cSIDnG
0F4679Ppq7OUKc1PpWI26XcmVhJBlUS0itbhbEtqLNmLVxnbWcGU+tqCWEkEVRJZW4uUVgwlvBS6
N0PsPMcbVkl3ESuJoEoi2izym/uXJmtemw7Dvta3F+FgnwqqJLK2L/Kd2xiHfQ3T9d5OKAliJRFU
SWQ6i/RyU4f13L5X0dq51Oliq2aMWEkEVRIxZ5FvqMg6PFfQVXyvG2lW63njgVhJBFUS2c+DHYa5
9K1ireFZOhJbfREriaBKImZNflEwXzQepr63yiFuvGN/7tcoYBb58aBKImY92EHK/HgDpOfK7LcM
8H7ggUz+7wFVEmnNIr0ByXrB53p9xdAbO228BB2xkgiqJKI52GG9IGH93AnPbJ+rg70vFRAriaBK
ImunTHtLdVLNw9aeJqm6Y2vTN3mwjwdVEpmeMj2M2WH5VtGms6fJ25HtrahKECuJoEoi0xMOhyWp
604ovaHnn8UnW4dUECuJoEoia//0IeWvvCp9yS2Hqa2OO63X0x6IlURQJZG1Mdh6vf2QzqjsuWXT
A9UUvwdUSWRaTdFpIy1lrnvacLjorXJ2+iogVhJBlUQerKaQWN9w5H0vqS8J8mAfD6okYlZTbM0Q
i0no3aZgK+sl8dzck1hJBFUS2V+L7NQzFCVenU6l9+ncLvnncHGzA7GSCKokMj2bQuvssWy/l+zy
EmLeAyWIlURQJZG1M1oL7hFXp/Hde+eStEfb2/IzrLAlD/apoEoia7uKbqQaeOl2ycreubGxU8nf
gVhJBFUSWatoPQw3E3Vi31tDLNp0nuxl6rwJJrGSCKoksvZvaxLDvdXe1KxjL1v706UB5A2xkgiq
JPJWBxvm5D3D8ZZNC95QyU+sJIIqiUyrKSS8lceiU28MJhWhrS8fdCBWEkGVRMxz8j2GZ+lISbNh
2qrzPsVzbqSfjlhJBFUSeWs9GDQhVhJBlURQJRFUSQRVEkGVRFAlEVRJBFUSQZVEUCWR/0GKvmDV
ZtCGAAAAAElFTkSuQmCC
"
height="135"
width="135" />
<image
y="463.90402"
x="539.13055"
id="image3321"
xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAJMAAACTCAIAAAAFh7xCAAAAA3NCSVQICAjb4U/gAAAEmElEQVR4
nO2dwbLbMAhFm877/19ONx1tmKFwwU5vfM7WtqTkDgQBcl7v9/sXGPL70wsAEZRzBeVcQTlXUM4V
lHMF5VxBOVdQzhWUcwXlXPmp3PR6vSZznNRoHCdeSvKorWVURq6sJ16qsPWNJWBzrqCcKyVveVj3
GPGe5KnEAbac7bknPp7MXvG68dJ1PhabcwXlXOl5y0PFp1UuVfxDEu8lC6u4qVasq33kZK7W4xFs
zhWUc0X0lhqV6K4S77V22a08QMtJJnPdADbnCsq5cqu3rLCVMGxFicMt+Ud6VrE5V1DOFdFbbvmH
lm9c37YnacZK1NoKKdc9KjbnCsq50vOWw1JvQquC06ryfGTkw3XfGDbnCsq58vrILnLLh7Qq4K06
i5bAJG8J/wblXJnmLYd9Nev1kcqAraVql+I9yTK0VC025wrKuTLtTh9GZVrkVnEv62WaSkE/oXVz
BWzOFZRzpeQtNUsflqfjONp6tDLNek5yfSOPzbmCcq6U8pZbJxa1zezw5oPm869LaQ6zENicKyjn
Sq/Ko4WLCcOTMluzV9j67NrPSgSbcwXlXNl/q8bwWI02qTbFcK7I0P2yE38EKOfKWmzZYugb198m
tJUQGDZwEls+ApRzRXwH0fB84kF745BGxcdedyZ9y0kesDlXUM6V/diydUnrb0y47uTOMHxdB5tz
BeVcEc/yDKvA8Z5hF+KwSSlZYWXSyuPsxOEvKOeKeE684p20iEvLHGoN8MOu+8o4lZE1sDlXUM4V
sd/ysF4Wqcyu3dzKDAw31+sJigg25wrKuSLmLQ/rbZZbKcQt76S5zfVCfASbcwXlXJn2W2qBn7ar
rbiX4SHNBK2rfMu1RrA5V1DOlek7iFpZwSS32Uppak+1Lh2SNGyFliekg+gRoJwr03ent8orW41D
W/nPZM2tS8kyWvFwC2zOFZRz5Y7YcqtnW+vPGeZaW65MG5nu9GeBcq6svQ040vJgrdSoRpJUTKLf
9XL5Yfi5sDlXUM6V6cnHrZ3vdU6psh5tm6w1XlY6VKnyfDMo58r0f3m0TF1rnMOw2akyznpmVesZ
wFt+MyjnithB1Eozap6ntU2OCxueqYxzXVd/11aIzbmCcq7c+p+Pw9PlrW17MrLmnSqz31lawuZc
QTlXeicfh5vQeE8yV4WtXa22jK1jUPEevOU3g3Ku9P7F7HBDUea6kQ+VjXxyc7y0FVtWwOZcQTlX
xNjyuo7xG2pDw/B1y93FKYgtHwHKufL/5i1vcErD2bV+qlb+MwGbcwXlXJm+sa3CMFxsLUPLiGpe
LhlH25tzlucRoJwrYnd6haGPrbzY57qS0HU/ENo50Ag25wrKuSKefNTitOTxpE9S8yrDe7RI8s4g
HJtzBeVcmZ4Tb6EdDEweb8WEWkVJa4jSlkFs+QhQzpVbveXwmPlWmUbzTq1j3TdU0rE5V1DOlen7
LYePD3vID1rANjyeM5w9Ps5O/BGgnCvifz4Oae2pW4evK9nOyuMJWq/+1u/CAZtzBeVcubXfEhbB
5lxBOVdQzhWUcwXlXEE5V1DOFZRzBeVcQTlXUM6VP7Dln2u1jDhDAAAAAElFTkSuQmCC
"
height="147"
width="147" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 11 KiB

View file

@ -0,0 +1,87 @@
digraph blockchain {
size="6.25";
//splines = "false";
rankdir=TB;
ranksep=-0.1;
//splines=ortho;
overlap = true;
nodesep = 0.1;
node [ shape = box, penwidth = 1.75 ];
edge [ penwidth = 1.75, minlen = 2 ];
penwidth = 1.75;
subgraph cluster_tx1 {
tx1_txid [ label = "TXID" ];
tx1_vout [ label = "Output Index Number" ];
tx1_script [ label = "Script" ];
label = "Transaction 1 (TX 1)"
}
subgraph cluster_sig {
node [ style = "invis", label = "", height=0 ];
sig_tx1_txid [ width = 0.7 ];
sig_tx1_vout [ width = 2.3 ];
sig_tx1_script [ width = 1.6 ];
//nil_pubkey [ width = 1.3 ];
sig_tx2t_script [ width = 0.75 ];
sig_tx2t_amount [ width = 0.95 ];
signature [ width = 1.25 ];
label = "Signed Data"
}
subgraph cluster_tx2 {
tx2_tx1_txid [ label = "TXID" ];
tx2_tx1_vout [ label = "Output Index Number" ];
tx2_script [ label = "Script" ];
public_key [ label = "Full Public Key" ];
tx2_amount [ label = "Amount" ];
tx2_signature [ label = "Signature" ];
label = "Transaction 2"
}
subgraph cluster_bob {
private_key [ label = "Private Key" ];
label = "Bob's Computer"
subgraph cluster_tx2t {
tx2t_script [ label = "Script" ];
tx2t_amount [ label = "Amount" ];
label = "TX2 Template"
}
}
{
edge [ arrowhead = "dot" ];
tx1_script -> sig_tx1_script;
tx1_txid -> sig_tx1_txid;
tx1_vout -> sig_tx1_vout;
tx2t_script -> sig_tx2t_script;
tx2t_amount -> sig_tx2t_amount;
private_key -> signature [ style = "dotted" ];
}
sig_tx1_txid -> tx2_tx1_txid;
sig_tx1_vout -> tx2_tx1_vout;
sig_tx2t_script -> tx2_script;
sig_tx2t_amount -> tx2_amount;
signature -> tx2_signature;
label = "Some Of The Data Signed By Default"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.8 KiB

View file

@ -0,0 +1,155 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="230pt"
viewBox="0.00 0.00 450.00 230.35" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.713154 0.713154) rotate(0) translate(4 319)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-319 628,-319 628,5 -4,5"/>
<text text-anchor="middle" x="311.5" y="-8.4" font-family="Sans" font-size="14.00">Some Of The Data Signed By Default</text>
<g id="graph2" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="9,-197 9,-274 317,-274 317,-197 9,-197"/>
<text text-anchor="middle" x="163" y="-257.4" font-family="Sans" font-size="14.00">Transaction 1 (TX 1)</text>
</g>
<g id="graph3" class="cluster"><title>cluster_sig</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="11,-128 11,-171 604,-171 604,-128 11,-128"/>
<text text-anchor="middle" x="307.5" y="-154.4" font-family="Sans" font-size="14.00">Signed Data</text>
</g>
<g id="graph4" class="cluster"><title>cluster_tx2</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-33 8,-110 605,-110 605,-33 8,-33"/>
<text text-anchor="middle" x="306.5" y="-93.4" font-family="Sans" font-size="14.00">Transaction 2</text>
</g>
<g id="graph5" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="348,-189 348,-307 615,-307 615,-189 348,-189"/>
<text text-anchor="middle" x="481.5" y="-290.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
</g>
<g id="graph6" class="cluster"><title>cluster_tx2t</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="458,-197 458,-274 607,-274 607,-197 458,-197"/>
<text text-anchor="middle" x="532.5" y="-257.4" font-family="Sans" font-size="14.00">TX2 Template</text>
</g>
<!-- tx1_txid -->
<g id="node2" class="node"><title>tx1_txid</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="71,-241 17,-241 17,-205 71,-205 71,-241"/>
<text text-anchor="middle" x="44" y="-218.9" font-family="Sans" font-size="14.00">TXID</text>
</g>
<!-- sig_tx1_txid -->
<!-- tx1_txid&#45;&gt;sig_tx1_txid -->
<g id="edge10" class="edge"><title>tx1_txid&#45;&gt;sig_tx1_txid</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M44,-204.762C44,-186.762 44,-159.981 44,-146.092"/>
<ellipse fill="black" stroke="black" cx="44" cy="-141.75" rx="4" ry="4"/>
</g>
<!-- tx1_vout -->
<g id="node3" class="node"><title>tx1_vout</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="246,-241 78,-241 78,-205 246,-205 246,-241"/>
<text text-anchor="middle" x="162" y="-218.9" font-family="Sans" font-size="14.00">Output Index Number</text>
</g>
<!-- sig_tx1_vout -->
<!-- tx1_vout&#45;&gt;sig_tx1_vout -->
<g id="edge12" class="edge"><title>tx1_vout&#45;&gt;sig_tx1_vout</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M161.364,-204.762C160.736,-186.762 159.802,-159.981 159.317,-146.092"/>
<ellipse fill="black" stroke="black" cx="159.166" cy="-141.748" rx="4" ry="4"/>
</g>
<!-- tx1_script -->
<g id="node4" class="node"><title>tx1_script</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="309,-241 253,-241 253,-205 309,-205 309,-241"/>
<text text-anchor="middle" x="281" y="-218.9" font-family="Sans" font-size="14.00">Script</text>
</g>
<!-- sig_tx1_script -->
<!-- tx1_script&#45;&gt;sig_tx1_script -->
<g id="edge8" class="edge"><title>tx1_script&#45;&gt;sig_tx1_script</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M286.302,-204.762C291.587,-186.58 299.477,-159.439 303.478,-145.675"/>
<ellipse fill="black" stroke="black" cx="304.665" cy="-141.591" rx="4.00001" ry="4.00001"/>
</g>
<!-- tx2_tx1_txid -->
<g id="node13" class="node"><title>tx2_tx1_txid</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="70,-77 16,-77 16,-41 70,-41 70,-77"/>
<text text-anchor="middle" x="43" y="-54.9" font-family="Sans" font-size="14.00">TXID</text>
</g>
<!-- sig_tx1_txid&#45;&gt;tx2_tx1_txid -->
<g id="edge20" class="edge"><title>sig_tx1_txid&#45;&gt;tx2_tx1_txid</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M43.9888,-136.124C43.9269,-131.3 43.6214,-107.47 43.3661,-87.5593"/>
<polygon fill="black" stroke="black" points="46.8631,-87.2911 43.2351,-77.3368 39.8637,-87.3809 46.8631,-87.2911"/>
</g>
<!-- tx2_tx1_vout -->
<g id="node14" class="node"><title>tx2_tx1_vout</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="245,-77 77,-77 77,-41 245,-41 245,-77"/>
<text text-anchor="middle" x="161" y="-54.9" font-family="Sans" font-size="14.00">Output Index Number</text>
</g>
<!-- sig_tx1_vout&#45;&gt;tx2_tx1_vout -->
<g id="edge22" class="edge"><title>sig_tx1_vout&#45;&gt;tx2_tx1_vout</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M159.022,-136.124C159.146,-131.3 159.757,-107.47 160.268,-87.5593"/>
<polygon fill="black" stroke="black" points="163.772,-87.4233 160.53,-77.3368 156.775,-87.2438 163.772,-87.4233"/>
</g>
<!-- sig_tx2t_script -->
<!-- tx2_script -->
<g id="node15" class="node"><title>tx2_script</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="520,-77 464,-77 464,-41 520,-41 520,-77"/>
<text text-anchor="middle" x="492" y="-54.9" font-family="Sans" font-size="14.00">Script</text>
</g>
<!-- sig_tx2t_script&#45;&gt;tx2_script -->
<g id="edge24" class="edge"><title>sig_tx2t_script&#45;&gt;tx2_script</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M493.978,-136.124C493.854,-131.3 493.243,-107.47 492.732,-87.5593"/>
<polygon fill="black" stroke="black" points="496.225,-87.2438 492.47,-77.3368 489.228,-87.4233 496.225,-87.2438"/>
</g>
<!-- sig_tx2t_amount -->
<!-- tx2_amount -->
<g id="node17" class="node"><title>tx2_amount</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="597,-77 527,-77 527,-41 597,-41 597,-77"/>
<text text-anchor="middle" x="562" y="-54.9" font-family="Sans" font-size="14.00">Amount</text>
</g>
<!-- sig_tx2t_amount&#45;&gt;tx2_amount -->
<g id="edge26" class="edge"><title>sig_tx2t_amount&#45;&gt;tx2_amount</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M562,-136.124C562,-131.3 562,-107.47 562,-87.5593"/>
<polygon fill="black" stroke="black" points="565.5,-87.3368 562,-77.3368 558.5,-87.3369 565.5,-87.3368"/>
</g>
<!-- signature -->
<!-- tx2_signature -->
<g id="node18" class="node"><title>tx2_signature</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="457,-77 373,-77 373,-41 457,-41 457,-77"/>
<text text-anchor="middle" x="415" y="-54.9" font-family="Sans" font-size="14.00">Signature</text>
</g>
<!-- signature&#45;&gt;tx2_signature -->
<g id="edge28" class="edge"><title>signature&#45;&gt;tx2_signature</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M415,-136.124C415,-131.3 415,-107.47 415,-87.5593"/>
<polygon fill="black" stroke="black" points="418.5,-87.3368 415,-77.3368 411.5,-87.3369 418.5,-87.3368"/>
</g>
<!-- public_key -->
<g id="node16" class="node"><title>public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="366,-77 252,-77 252,-41 366,-41 366,-77"/>
<text text-anchor="middle" x="309" y="-54.9" font-family="Sans" font-size="14.00">Full Public Key</text>
</g>
<!-- private_key -->
<g id="node20" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="450,-241 356,-241 356,-205 450,-205 450,-241"/>
<text text-anchor="middle" x="403" y="-218.9" font-family="Sans" font-size="14.00">Private Key</text>
</g>
<!-- private_key&#45;&gt;signature -->
<g id="edge18" class="edge"><title>private_key&#45;&gt;signature</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="1,5" d="M405.545,-204.762C408.082,-186.58 411.869,-159.439 413.79,-145.675"/>
<ellipse fill="black" stroke="black" cx="414.343" cy="-141.712" rx="4.00001" ry="4.00001"/>
</g>
<!-- tx2t_script -->
<g id="node22" class="node"><title>tx2t_script</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="522,-241 466,-241 466,-205 522,-205 522,-241"/>
<text text-anchor="middle" x="494" y="-218.9" font-family="Sans" font-size="14.00">Script</text>
</g>
<!-- tx2t_script&#45;&gt;sig_tx2t_script -->
<g id="edge14" class="edge"><title>tx2t_script&#45;&gt;sig_tx2t_script</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M494,-204.762C494,-186.762 494,-159.981 494,-146.092"/>
<ellipse fill="black" stroke="black" cx="494" cy="-141.75" rx="4" ry="4"/>
</g>
<!-- tx2t_amount -->
<g id="node23" class="node"><title>tx2t_amount</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="599,-241 529,-241 529,-205 599,-205 599,-241"/>
<text text-anchor="middle" x="564" y="-218.9" font-family="Sans" font-size="14.00">Amount</text>
</g>
<!-- tx2t_amount&#45;&gt;sig_tx2t_amount -->
<g id="edge16" class="edge"><title>tx2t_amount&#45;&gt;sig_tx2t_amount</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M563.576,-204.762C563.157,-186.762 562.534,-159.981 562.211,-146.092"/>
<ellipse fill="black" stroke="black" cx="562.11" cy="-141.749" rx="4" ry="4"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 9.3 KiB

View file

@ -0,0 +1,25 @@
digraph {
size=6.25;
rankdir=LR
node [ shape = "box" ]
splines = ortho;
//ranksep = 10;
nodesep = 0.5;
p2pnetwork [ label = "P2P\nNetwork" ]
asic0 [ label = "ASIC" ];
software [ label = "Mining\nSoftware" ]
pool0 [ label = "bitcoind" ];
pool0 -> software [ label = "Block\nTemplate→" ];
p2pnetwork -> pool0 [ label = "TXes→" ];
pool0 -> p2pnetwork [ label = "←Blocks" ];
software -> asic0 [ label = "Block\nHeaders &\nTargets→" ];
asic0 -> software [ label = "←Headers\nBelow\nTarget" ];
software -> pool0 [ constraint = false, label = "←Blocks" ];
label = "Solo Bitcoin Mining Workflow"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.1 KiB

View file

@ -0,0 +1,77 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: _anonymous_0 Pages: 1 -->
<svg width="450pt" height="107pt"
viewBox="0.00 0.00 450.00 107.28" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.745033 0.745033) rotate(0) translate(4 140)">
<title>_anonymous_0</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-140 601,-140 601,5 -4,5"/>
<text text-anchor="middle" x="298" y="-8.4" font-family="Sans" font-size="14.00">Solo Bitcoin Mining Workflow</text>
<!-- p2pnetwork -->
<g id="node1" class="node"><title>p2pnetwork</title>
<polygon fill="none" stroke="black" points="77,-100 1,-100 1,-58 77,-58 77,-100"/>
<text text-anchor="middle" x="39" y="-83.4" font-family="Sans" font-size="14.00">P2P</text>
<text text-anchor="middle" x="39" y="-66.4" font-family="Sans" font-size="14.00">Network</text>
</g>
<!-- pool0 -->
<g id="node4" class="node"><title>pool0</title>
<polygon fill="none" stroke="black" points="241,-97 171,-97 171,-61 241,-61 241,-97"/>
<text text-anchor="middle" x="206" y="-74.9" font-family="Sans" font-size="14.00">bitcoind</text>
</g>
<!-- p2pnetwork&#45;&gt;pool0 -->
<g id="edge4" class="edge"><title>p2pnetwork&#45;&gt;pool0</title>
<path fill="none" stroke="black" d="M77.7329,-79C102.292,-79 134.187,-79 160.027,-79"/>
<polygon fill="black" stroke="black" points="160.328,-82.5001 170.328,-79 160.328,-75.5001 160.328,-82.5001"/>
<text text-anchor="middle" x="124" y="-83.4" font-family="Sans" font-size="14.00">TXes→</text>
</g>
<!-- asic0 -->
<g id="node2" class="node"><title>asic0</title>
<polygon fill="none" stroke="black" points="596,-97 542,-97 542,-61 596,-61 596,-97"/>
<text text-anchor="middle" x="569" y="-74.9" font-family="Sans" font-size="14.00">ASIC</text>
</g>
<!-- software -->
<g id="node3" class="node"><title>software</title>
<polygon fill="none" stroke="black" points="434,-100 354,-100 354,-58 434,-58 434,-100"/>
<text text-anchor="middle" x="394" y="-83.4" font-family="Sans" font-size="14.00">Mining</text>
<text text-anchor="middle" x="394" y="-66.4" font-family="Sans" font-size="14.00">Software</text>
</g>
<!-- asic0&#45;&gt;software -->
<g id="edge10" class="edge"><title>asic0&#45;&gt;software</title>
<path fill="none" stroke="black" d="M553.765,-60.7181C540.71,-45.0522 524,-25 524,-25 524,-25 452,-25 452,-25 452,-25 438.132,-37.9116 423.958,-51.1078"/>
<polygon fill="black" stroke="black" points="421.524,-48.5917 416.59,-57.9676 426.294,-53.715 421.524,-48.5917"/>
<text text-anchor="middle" x="488" y="-63.4" font-family="Sans" font-size="14.00">←Headers</text>
<text text-anchor="middle" x="488" y="-46.4" font-family="Sans" font-size="14.00">Below</text>
<text text-anchor="middle" x="488" y="-29.4" font-family="Sans" font-size="14.00">Target</text>
</g>
<!-- software&#45;&gt;asic0 -->
<g id="edge8" class="edge"><title>software&#45;&gt;asic0</title>
<path fill="none" stroke="black" d="M434.283,-83.1672C444.18,-84.191 452,-85 452,-85 452,-85 524,-85 524,-85 524,-85 527.085,-84.5886 531.64,-83.9813"/>
<polygon fill="black" stroke="black" points="532.336,-87.4197 541.785,-82.6286 531.41,-80.4811 532.336,-87.4197"/>
<text text-anchor="middle" x="488" y="-123.4" font-family="Sans" font-size="14.00">Block</text>
<text text-anchor="middle" x="488" y="-106.4" font-family="Sans" font-size="14.00">Headers &amp;</text>
<text text-anchor="middle" x="488" y="-89.4" font-family="Sans" font-size="14.00">Targets→</text>
</g>
<!-- software&#45;&gt;pool0 -->
<g id="edge12" class="edge"><title>software&#45;&gt;pool0</title>
<path fill="none" stroke="black" d="M353.717,-60.9421C343.82,-56.5055 336,-53 336,-53 336,-53 260,-53 260,-53 260,-53 256.28,-54.7909 250.794,-57.4326"/>
<polygon fill="black" stroke="black" points="249.21,-54.3107 241.718,-61.8024 252.246,-60.6177 249.21,-54.3107"/>
<text text-anchor="middle" x="298" y="-57.4" font-family="Sans" font-size="14.00">←Blocks</text>
</g>
<!-- pool0&#45;&gt;p2pnetwork -->
<g id="edge6" class="edge"><title>pool0&#45;&gt;p2pnetwork</title>
<path fill="none" stroke="black" d="M170.282,-61.8024C160.24,-56.9673 152,-53 152,-53 152,-53 96,-53 96,-53 96,-53 92.3058,-54.6851 86.7984,-57.1972"/>
<polygon fill="black" stroke="black" points="85.2967,-54.0352 77.6511,-61.3697 88.2018,-60.4039 85.2967,-54.0352"/>
<text text-anchor="middle" x="124" y="-57.4" font-family="Sans" font-size="14.00">←Blocks</text>
</g>
<!-- pool0&#45;&gt;software -->
<g id="edge2" class="edge"><title>pool0&#45;&gt;software</title>
<path fill="none" stroke="black" d="M241.804,-79C270.644,-79 311.532,-79 343.667,-79"/>
<polygon fill="black" stroke="black" points="343.767,-82.5001 353.767,-79 343.767,-75.5001 343.767,-82.5001"/>
<text text-anchor="middle" x="298" y="-100.4" font-family="Sans" font-size="14.00">Block</text>
<text text-anchor="middle" x="298" y="-83.4" font-family="Sans" font-size="14.00">Template→</text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 5 KiB

View file

@ -0,0 +1,86 @@
digraph blockchain {
//splines = "ortho";
rankdir=LR;
ranksep=0.1;
size=6.25;
node [ shape = box ]
subgraph cluster_tx0 {
label = "Transaction 0\n(TX 0)"
tx0_input0 [ label = "input0" ]
tx0_output0 [ label = "output0" ]
tx0_output1 [ label = "output1" ]
}
subgraph cluster_tx1 {
label = "TX 1"
tx1_input0 [ label = "input0" ]
tx1_output0 [ label = "output0" ]
}
subgraph cluster_tx2 {
label = "TX 2"
tx2_input0 [ label = "input0" ]
tx2_output0 [ label = "output0" ]
tx2_output1 [ label = "output1" ]
}
subgraph cluster_tx3 {
label = "TX 3"
tx3_input0 [ label = "input0" ]
tx3_output0 [ label = "output0" ]
}
subgraph cluster_tx4 {
label = "TX 4"
tx4_input0 [ label = "input0" ]
tx4_output0 [ label = "output0" ]
}
subgraph cluster_tx5 {
label = "TX 5"
tx5_input0 [ label = "input0" ]
tx5_output0 [ label = "output0" ]
}
subgraph cluster_tx6 {
label = "TX 6"
tx6_input0 [ label = "input0" ]
tx6_input1 [ label = "input1" ]
tx6_output0 [ label = "output0" ]
}
txold [ style = "invis", label = "", width = 0, height = 0 ];
utxo0 [ style = "invis", label = "", width = 0, height = 0 ];
//spacer0 [ style = "invis", label = "", width = 0, height = 0 ];
//tx3_output0 -> spacer0 -> utxo0 [ style = invis ];
//tx6_input0 -> utxo0 [style = invis];
utxo1 [ style = "invis", label = "", width = 0, height = 0 ];
txold -> tx0_input0 [ label = "100,000\n(100k)\nsatoshis", style = dotted ]
tx0_output0 -> tx1_input0 [ label = "40k" ]
tx0_output1 -> tx2_input0 [ label = "50k" ]
tx1_output0 -> tx3_input0 [ label = "30k" ]
tx2_output0 -> tx4_input0 [ label = "20k" ]
tx2_output1 -> tx5_input0 [ label = "20k"]
tx4_output0 -> tx6_input0 [ label = "10k" ]
tx5_output0 -> tx6_input1 [ label = "10k" ]
tx3_output0 -> utxo0 [ style=dashed, labelfloat = true, minlen = 2, label = "20k Unspent TX\nOutput (UTXO)" ]
tx6_output0 -> utxo1 [ style=dashed, label = "10k\nUTXO" ]
label = "Triple-Entry Bookkeeping (Transaction-To-Transaction Payments) As Used By Bitcoin"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,195 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="353pt"
viewBox="0.00 0.00 450.00 353.37" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.690184 0.690184) rotate(0) translate(4 508)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-508 649,-508 649,5 -4,5"/>
<text text-anchor="middle" x="322" y="-8.4" font-family="Sans" font-size="14.00">Triple&#45;Entry Bookkeeping (Transaction&#45;To&#45;Transaction Payments) As Used By Bitcoin</text>
<g id="graph2" class="cluster"><title>cluster_tx0</title>
<polygon fill="none" stroke="black" points="78,-290 78,-492 188,-492 188,-290 78,-290"/>
<text text-anchor="middle" x="133" y="-475.4" font-family="Sans" font-size="14.00">Transaction 0</text>
<text text-anchor="middle" x="133" y="-458.4" font-family="Sans" font-size="14.00">(TX 0)</text>
</g>
<g id="graph3" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" points="232,-365 232,-496 320,-496 320,-365 232,-365"/>
<text text-anchor="middle" x="276" y="-479.4" font-family="Sans" font-size="14.00">TX 1</text>
</g>
<g id="graph4" class="cluster"><title>cluster_tx2</title>
<polygon fill="none" stroke="black" points="232,-172 232,-357 320,-357 320,-172 232,-172"/>
<text text-anchor="middle" x="276" y="-340.4" font-family="Sans" font-size="14.00">TX 2</text>
</g>
<g id="graph5" class="cluster"><title>cluster_tx3</title>
<polygon fill="none" stroke="black" points="364,-311 364,-442 452,-442 452,-311 364,-311"/>
<text text-anchor="middle" x="408" y="-425.4" font-family="Sans" font-size="14.00">TX 3</text>
</g>
<g id="graph6" class="cluster"><title>cluster_tx4</title>
<polygon fill="none" stroke="black" points="364,-172 364,-303 452,-303 452,-172 364,-172"/>
<text text-anchor="middle" x="408" y="-286.4" font-family="Sans" font-size="14.00">TX 4</text>
</g>
<g id="graph7" class="cluster"><title>cluster_tx5</title>
<polygon fill="none" stroke="black" points="364,-33 364,-164 452,-164 452,-33 364,-33"/>
<text text-anchor="middle" x="408" y="-147.4" font-family="Sans" font-size="14.00">TX 5</text>
</g>
<g id="graph8" class="cluster"><title>cluster_tx6</title>
<polygon fill="none" stroke="black" points="496,-41 496,-226 584,-226 584,-41 496,-41"/>
<text text-anchor="middle" x="540" y="-209.4" font-family="Sans" font-size="14.00">TX 6</text>
</g>
<!-- tx0_input0 -->
<g id="node2" class="node"><title>tx0_input0</title>
<polygon fill="none" stroke="black" points="164,-442 102,-442 102,-406 164,-406 164,-442"/>
<text text-anchor="middle" x="133" y="-419.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx0_output0 -->
<g id="node3" class="node"><title>tx0_output0</title>
<polygon fill="none" stroke="black" points="169,-388 97,-388 97,-352 169,-352 169,-388"/>
<text text-anchor="middle" x="133" y="-365.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- tx1_input0 -->
<g id="node6" class="node"><title>tx1_input0</title>
<polygon fill="none" stroke="black" points="307,-463 245,-463 245,-427 307,-427 307,-463"/>
<text text-anchor="middle" x="276" y="-440.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx0_output0&#45;&gt;tx1_input0 -->
<g id="edge11" class="edge"><title>tx0_output0&#45;&gt;tx1_input0</title>
<path fill="none" stroke="black" d="M169.205,-387.498C175.495,-390.616 181.955,-393.869 188,-397 203.741,-405.152 220.887,-414.416 235.828,-422.616"/>
<polygon fill="black" stroke="black" points="234.367,-425.807 244.814,-427.565 237.744,-419.675 234.367,-425.807"/>
<text text-anchor="middle" x="210" y="-419.4" font-family="Sans" font-size="14.00">40k</text>
</g>
<!-- tx0_output1 -->
<g id="node4" class="node"><title>tx0_output1</title>
<polygon fill="none" stroke="black" points="169,-334 97,-334 97,-298 169,-298 169,-334"/>
<text text-anchor="middle" x="133" y="-311.9" font-family="Sans" font-size="14.00">output1</text>
</g>
<!-- tx2_input0 -->
<g id="node9" class="node"><title>tx2_input0</title>
<polygon fill="none" stroke="black" points="307,-324 245,-324 245,-288 307,-288 307,-324"/>
<text text-anchor="middle" x="276" y="-301.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx0_output1&#45;&gt;tx2_input0 -->
<g id="edge13" class="edge"><title>tx0_output1&#45;&gt;tx2_input0</title>
<path fill="none" stroke="black" d="M169.085,-313.477C189.045,-312.081 213.932,-310.34 234.671,-308.89"/>
<polygon fill="black" stroke="black" points="235.052,-312.372 244.784,-308.183 234.564,-305.389 235.052,-312.372"/>
<text text-anchor="middle" x="210" y="-315.4" font-family="Sans" font-size="14.00">50k</text>
</g>
<!-- tx1_output0 -->
<g id="node7" class="node"><title>tx1_output0</title>
<polygon fill="none" stroke="black" points="312,-409 240,-409 240,-373 312,-373 312,-409"/>
<text text-anchor="middle" x="276" y="-386.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- tx3_input0 -->
<g id="node13" class="node"><title>tx3_input0</title>
<polygon fill="none" stroke="black" points="439,-409 377,-409 377,-373 439,-373 439,-409"/>
<text text-anchor="middle" x="408" y="-386.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx1_output0&#45;&gt;tx3_input0 -->
<g id="edge15" class="edge"><title>tx1_output0&#45;&gt;tx3_input0</title>
<path fill="none" stroke="black" d="M312.07,-391C328.884,-391 348.988,-391 366.437,-391"/>
<polygon fill="black" stroke="black" points="366.906,-394.5 376.906,-391 366.906,-387.5 366.906,-394.5"/>
<text text-anchor="middle" x="342" y="-395.4" font-family="Sans" font-size="14.00">30k</text>
</g>
<!-- tx2_output0 -->
<g id="node10" class="node"><title>tx2_output0</title>
<polygon fill="none" stroke="black" points="312,-270 240,-270 240,-234 312,-234 312,-270"/>
<text text-anchor="middle" x="276" y="-247.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- tx4_input0 -->
<g id="node16" class="node"><title>tx4_input0</title>
<polygon fill="none" stroke="black" points="439,-270 377,-270 377,-234 439,-234 439,-270"/>
<text text-anchor="middle" x="408" y="-247.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx2_output0&#45;&gt;tx4_input0 -->
<g id="edge17" class="edge"><title>tx2_output0&#45;&gt;tx4_input0</title>
<path fill="none" stroke="black" d="M312.07,-252C328.884,-252 348.988,-252 366.437,-252"/>
<polygon fill="black" stroke="black" points="366.906,-255.5 376.906,-252 366.906,-248.5 366.906,-255.5"/>
<text text-anchor="middle" x="342" y="-256.4" font-family="Sans" font-size="14.00">20k</text>
</g>
<!-- tx2_output1 -->
<g id="node11" class="node"><title>tx2_output1</title>
<polygon fill="none" stroke="black" points="312,-216 240,-216 240,-180 312,-180 312,-216"/>
<text text-anchor="middle" x="276" y="-193.9" font-family="Sans" font-size="14.00">output1</text>
</g>
<!-- tx5_input0 -->
<g id="node19" class="node"><title>tx5_input0</title>
<polygon fill="none" stroke="black" points="439,-131 377,-131 377,-95 439,-95 439,-131"/>
<text text-anchor="middle" x="408" y="-108.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx2_output1&#45;&gt;tx5_input0 -->
<g id="edge19" class="edge"><title>tx2_output1&#45;&gt;tx5_input0</title>
<path fill="none" stroke="black" d="M303.994,-179.974C323.682,-167.296 350.215,-150.21 371.554,-136.469"/>
<polygon fill="black" stroke="black" points="373.534,-139.357 380.047,-131 369.744,-133.472 373.534,-139.357"/>
<text text-anchor="middle" x="342" y="-168.4" font-family="Sans" font-size="14.00">20k</text>
</g>
<!-- tx3_output0 -->
<g id="node14" class="node"><title>tx3_output0</title>
<polygon fill="none" stroke="black" points="444,-355 372,-355 372,-319 444,-319 444,-355"/>
<text text-anchor="middle" x="408" y="-332.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- utxo0 -->
<!-- tx3_output0&#45;&gt;utxo0 -->
<g id="edge25" class="edge"><title>tx3_output0&#45;&gt;utxo0</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M444.204,-337C498.689,-337 598.917,-337 632.049,-337"/>
<polygon fill="black" stroke="black" points="632.145,-340.5 642.145,-337 632.145,-333.5 632.145,-340.5"/>
<text text-anchor="middle" x="540" y="-358.4" font-family="Sans" font-size="14.00">20k Unspent TX</text>
<text text-anchor="middle" x="540" y="-341.4" font-family="Sans" font-size="14.00">Output (UTXO)</text>
</g>
<!-- tx4_output0 -->
<g id="node17" class="node"><title>tx4_output0</title>
<polygon fill="none" stroke="black" points="444,-216 372,-216 372,-180 444,-180 444,-216"/>
<text text-anchor="middle" x="408" y="-193.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- tx6_input0 -->
<g id="node22" class="node"><title>tx6_input0</title>
<polygon fill="none" stroke="black" points="571,-193 509,-193 509,-157 571,-157 571,-193"/>
<text text-anchor="middle" x="540" y="-170.9" font-family="Sans" font-size="14.00">input0</text>
</g>
<!-- tx4_output0&#45;&gt;tx6_input0 -->
<g id="edge21" class="edge"><title>tx4_output0&#45;&gt;tx6_input0</title>
<path fill="none" stroke="black" d="M444.163,-186.661C449.439,-185.273 454.833,-183.995 460,-183 472.421,-180.608 486.074,-178.907 498.529,-177.707"/>
<polygon fill="black" stroke="black" points="499.003,-181.179 508.657,-176.814 498.388,-174.206 499.003,-181.179"/>
<text text-anchor="middle" x="474" y="-187.4" font-family="Sans" font-size="14.00">10k</text>
</g>
<!-- tx5_output0 -->
<g id="node20" class="node"><title>tx5_output0</title>
<polygon fill="none" stroke="black" points="444,-77 372,-77 372,-41 444,-41 444,-77"/>
<text text-anchor="middle" x="408" y="-54.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- tx6_input1 -->
<g id="node23" class="node"><title>tx6_input1</title>
<polygon fill="none" stroke="black" points="571,-139 509,-139 509,-103 571,-103 571,-139"/>
<text text-anchor="middle" x="540" y="-116.9" font-family="Sans" font-size="14.00">input1</text>
</g>
<!-- tx5_output0&#45;&gt;tx6_input1 -->
<g id="edge23" class="edge"><title>tx5_output0&#45;&gt;tx6_input1</title>
<path fill="none" stroke="black" d="M444.07,-75.9418C461.202,-83.9887 481.747,-93.6389 499.422,-101.941"/>
<polygon fill="black" stroke="black" points="498.367,-105.312 508.906,-106.395 501.343,-98.9758 498.367,-105.312"/>
<text text-anchor="middle" x="474" y="-100.4" font-family="Sans" font-size="14.00">10k</text>
</g>
<!-- tx6_output0 -->
<g id="node24" class="node"><title>tx6_output0</title>
<polygon fill="none" stroke="black" points="576,-85 504,-85 504,-49 576,-49 576,-85"/>
<text text-anchor="middle" x="540" y="-62.9" font-family="Sans" font-size="14.00">output0</text>
</g>
<!-- utxo1 -->
<!-- tx6_output0&#45;&gt;utxo1 -->
<g id="edge27" class="edge"><title>tx6_output0&#45;&gt;utxo1</title>
<path fill="none" stroke="black" stroke-dasharray="5,2" d="M576.024,-67C595.705,-67 618.71,-67 631.993,-67"/>
<polygon fill="black" stroke="black" points="632.339,-70.5001 642.339,-67 632.339,-63.5001 632.339,-70.5001"/>
<text text-anchor="middle" x="613" y="-88.4" font-family="Sans" font-size="14.00">10k</text>
<text text-anchor="middle" x="613" y="-71.4" font-family="Sans" font-size="14.00">UTXO</text>
</g>
<!-- txold -->
<!-- txold&#45;&gt;tx0_input0 -->
<g id="edge9" class="edge"><title>txold&#45;&gt;tx0_input0</title>
<path fill="none" stroke="black" stroke-dasharray="1,5" d="M1.84293,-424C8.67759,-424 55.6789,-424 91.4816,-424"/>
<polygon fill="black" stroke="black" points="91.7074,-427.5 101.707,-424 91.7074,-420.5 91.7074,-427.5"/>
<text text-anchor="middle" x="40" y="-462.4" font-family="Sans" font-size="14.00">100,000</text>
<text text-anchor="middle" x="40" y="-445.4" font-family="Sans" font-size="14.00">(100k)</text>
<text text-anchor="middle" x="40" y="-428.4" font-family="Sans" font-size="14.00">satoshis</text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 12 KiB

View file

@ -0,0 +1,84 @@
digraph blockchain {
size=6.25;
splines = "false";
rankdir=LR;
ranksep=0.1;
//splines=ortho;
node [ penwidth=1.75, fontname="Sans", shape = box ];
edge [ penwidth=1.75, fontname="Sans" ];
graph [ penwidth=1.75, fontname="Sans" ];
//edge [ style = invis, minlen = 1 ];
//fixedsize
nodesep = 0.25;
//concentrate = true;
tophelp0 [style = invis, label="", width=0, height=0 ];
prevout [style = invis, label="", width=0, height=0 ];
nextout [style = invis, label="", width=0, height=0 ];
subgraph cluster_tx {
version;
subgraph cluster_input {
sequence;
vout [label="output index"];
txid;
input [style = invis, label="", width=0, height=0 ];
subgraph cluster_scriptsig {
label = "scriptSig"
subgraph cluster_signature {
hashtype;
signature [style = invis, label="", width=0, height=0 ];
label = "signature"
}
scriptsig [style = invis, label="", width=0, height=0 ];
}
label = "Input"
}
left0 [style = invis ];
left1 [style = invis ];
left2 [style = invis ];
middle1 [style = invis, label="", width=0, height=0 ];
middle2 [style = invis, label="", width=0, height=0 ];
middle3 [style = invis, label="", width=0, height=1.05 ];
middle4 [style = invis, label="", width=0, height=0 ];
middle5 [style = invis, label="", width=0, height=0 ];
middle6 [style = invis, label="", width=0, height=0 ];
middle7 [style = invis, label="", width=0, height=0 ];
middle0 [style = invis, label="", width=0, height=0 ];
subgraph cluster_output {
output [style = invis, label="", width=0, height=0 ];
amount;
script;
label = "Output"
}
locktime;
label = "A Basic Transaction With One Input & One Output"
}
prevout -> input [ style = "dashed", label = "Each input\nspends\nsatoshis\nfrom a\nprevious\noutput\n(prevout)" ];
output -> nextout [style="dashed", label = "Each output\nwaits as an\nUnspent\nTx Output\n(UTXO)\nuntil a\nlater input\nspends it"];
tophelp0 -> version [ style = invis ];
txid -> middle1 [ dir = none, label = "Select a previous tx with an\noutput to spend" ];
vout -> middle2 [ dir = none, label = "Select an output from previous tx" ];
sequence -> middle3 [ dir = none, label = "Allow override of locktime" ];
scriptsig -> middle4 [ dir = none, label = "Satisfy prevout script conditions" ];
signature -> middle5 [ dir = none, label = "Protect tx against modification\nby unauthorized parties" ];
hashtype -> middle6 [ dir = none, label = "Authorize others to modify tx;\nselect what they can modify" ];
version -> middle7 [ dir = none, label = "Indicate what rules this tx follows" ];
left2 -> locktime [ dir = none, label = "Prevent tx from being added to the\nblock chain before a particular time" ];
left0 -> amount [ dir = none, label = "Set amount to spend & pay in fees" ];
left1 -> script [ dir = none, label = "Describe conditions necessary\nto spend this output" ];
label = "(Metadata not shown: number of inputs/outputs, length in bytes of each script/scriptSig)\n \nThe Parts Of A Transaction"
}

BIN
img/dev/en-tx-overview.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

175
img/dev/en-tx-overview.svg Normal file
View file

@ -0,0 +1,175 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="444pt"
viewBox="0.00 0.00 450.00 444.16" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.648415 0.648415) rotate(0) translate(4 681)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-681 691,-681 691,5 -4,5"/>
<text text-anchor="middle" x="343" y="-42.4" font-family="Sans" font-size="14.00">(Metadata not shown: number of inputs/outputs, length in bytes of each script/scriptSig)</text>
<text text-anchor="middle" x="343" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="343" y="-8.4" font-family="Sans" font-size="14.00">The Parts Of A Transaction</text>
<g id="graph2" class="cluster"><title>cluster_tx</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="92,-67 92,-669 582,-669 582,-67 92,-67"/>
<text text-anchor="middle" x="337" y="-652.4" font-family="Sans" font-size="14.00">A Basic Transaction With One Input &amp; One Output</text>
</g>
<g id="graph3" class="cluster"><title>cluster_input</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="100,-247 100,-592 228,-592 228,-247 100,-247"/>
<text text-anchor="middle" x="164" y="-575.4" font-family="Sans" font-size="14.00">Input</text>
</g>
<g id="graph4" class="cluster"><title>cluster_scriptsig</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="108,-263 108,-407 220,-407 220,-263 108,-263"/>
<text text-anchor="middle" x="164" y="-390.4" font-family="Sans" font-size="14.00">scriptSig</text>
</g>
<g id="graph5" class="cluster"><title>cluster_signature</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="116,-271 116,-366 212,-366 212,-271 116,-271"/>
<text text-anchor="middle" x="164" y="-349.4" font-family="Sans" font-size="14.00">signature</text>
</g>
<g id="graph6" class="cluster"><title>cluster_output</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="488,-138 488,-287 574,-287 574,-138 488,-138"/>
<text text-anchor="middle" x="531" y="-270.4" font-family="Sans" font-size="14.00">Output</text>
</g>
<!-- tophelp0 -->
<!-- version -->
<g id="node5" class="node"><title>version</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="197,-636 131,-636 131,-600 197,-600 197,-636"/>
<text text-anchor="middle" x="164" y="-613.9" font-family="Sans" font-size="14.00">version</text>
</g>
<!-- tophelp0&#45;&gt;version -->
<!-- prevout -->
<!-- input -->
<!-- prevout&#45;&gt;input -->
<g id="edge7" class="edge"><title>prevout&#45;&gt;input</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M1.72672,-255C11.5697,-255 118.636,-255 153.264,-255"/>
<polygon fill="black" stroke="black" points="153.328,-258.5 163.328,-255 153.328,-251.5 153.328,-258.5"/>
<text text-anchor="middle" x="47" y="-361.4" font-family="Sans" font-size="14.00">Each input</text>
<text text-anchor="middle" x="47" y="-344.4" font-family="Sans" font-size="14.00">spends</text>
<text text-anchor="middle" x="47" y="-327.4" font-family="Sans" font-size="14.00">satoshis</text>
<text text-anchor="middle" x="47" y="-310.4" font-family="Sans" font-size="14.00">from a</text>
<text text-anchor="middle" x="47" y="-293.4" font-family="Sans" font-size="14.00">previous</text>
<text text-anchor="middle" x="47" y="-276.4" font-family="Sans" font-size="14.00">output</text>
<text text-anchor="middle" x="47" y="-259.4" font-family="Sans" font-size="14.00">(prevout)</text>
</g>
<!-- nextout -->
<!-- middle7 -->
<!-- version&#45;&gt;middle7 -->
<g id="edge25" class="edge"><title>version&#45;&gt;middle7</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M197.542,-618C285.309,-618 515.97,-618 530.301,-618"/>
<text text-anchor="middle" x="358" y="-622.4" font-family="Sans" font-size="14.00">Indicate what rules this tx follows</text>
</g>
<!-- sequence -->
<g id="node7" class="node"><title>sequence</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="204,-451 124,-451 124,-415 204,-415 204,-451"/>
<text text-anchor="middle" x="164" y="-428.9" font-family="Sans" font-size="14.00">sequence</text>
</g>
<!-- middle3 -->
<!-- sequence&#45;&gt;middle3 -->
<g id="edge17" class="edge"><title>sequence&#45;&gt;middle3</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M204.678,-433C297.245,-433 516.709,-433 530.335,-433"/>
<text text-anchor="middle" x="358" y="-437.4" font-family="Sans" font-size="14.00">Allow override of locktime</text>
</g>
<!-- vout -->
<g id="node8" class="node"><title>vout</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="216,-505 112,-505 112,-469 216,-469 216,-505"/>
<text text-anchor="middle" x="164" y="-482.9" font-family="Sans" font-size="14.00">output index</text>
</g>
<!-- middle2 -->
<!-- vout&#45;&gt;middle2 -->
<g id="edge15" class="edge"><title>vout&#45;&gt;middle2</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M216.582,-487.287C314.89,-487.822 517.8,-488.928 530.386,-488.997"/>
<text text-anchor="middle" x="358" y="-493.4" font-family="Sans" font-size="14.00">Select an output from previous tx</text>
</g>
<!-- txid -->
<g id="node9" class="node"><title>txid</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="191,-559 137,-559 137,-523 191,-523 191,-559"/>
<text text-anchor="middle" x="164" y="-536.9" font-family="Sans" font-size="14.00">txid</text>
</g>
<!-- middle1 -->
<!-- txid&#45;&gt;middle1 -->
<g id="edge13" class="edge"><title>txid&#45;&gt;middle1</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M191.285,-541C273.68,-541 515.249,-541 530.267,-541"/>
<text text-anchor="middle" x="358" y="-562.4" font-family="Sans" font-size="14.00">Select a previous tx with an</text>
<text text-anchor="middle" x="358" y="-545.4" font-family="Sans" font-size="14.00">output to spend</text>
</g>
<!-- hashtype -->
<g id="node13" class="node"><title>hashtype</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="204,-315 124,-315 124,-279 204,-279 204,-315"/>
<text text-anchor="middle" x="164" y="-292.9" font-family="Sans" font-size="14.00">hashtype</text>
</g>
<!-- middle6 -->
<!-- hashtype&#45;&gt;middle6 -->
<g id="edge23" class="edge"><title>hashtype&#45;&gt;middle6</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M204.325,-296.78C296.683,-296.277 516.674,-295.078 530.333,-295.004"/>
<text text-anchor="middle" x="358" y="-316.4" font-family="Sans" font-size="14.00">Authorize others to modify tx;</text>
<text text-anchor="middle" x="358" y="-299.4" font-family="Sans" font-size="14.00">select what they can modify</text>
</g>
<!-- signature -->
<!-- middle5 -->
<!-- signature&#45;&gt;middle5 -->
<g id="edge21" class="edge"><title>signature&#45;&gt;middle5</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M164.595,-333C180.617,-333 514.777,-333 530.432,-333"/>
<text text-anchor="middle" x="358" y="-354.4" font-family="Sans" font-size="14.00">Protect tx against modification</text>
<text text-anchor="middle" x="358" y="-337.4" font-family="Sans" font-size="14.00">by unauthorized parties</text>
</g>
<!-- scriptsig -->
<!-- middle4 -->
<!-- scriptsig&#45;&gt;middle4 -->
<g id="edge19" class="edge"><title>scriptsig&#45;&gt;middle4</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M164.595,-374.005C180.617,-374.136 514.777,-376.867 530.432,-376.995"/>
<text text-anchor="middle" x="358" y="-381.4" font-family="Sans" font-size="14.00">Satisfy prevout script conditions</text>
</g>
<!-- left0 -->
<!-- amount -->
<g id="node29" class="node"><title>amount</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="566,-236 496,-236 496,-200 566,-200 566,-236"/>
<text text-anchor="middle" x="531" y="-213.9" font-family="Sans" font-size="14.00">amount</text>
</g>
<!-- left0&#45;&gt;amount -->
<g id="edge29" class="edge"><title>left0&#45;&gt;amount</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M191.285,-218.926C256.819,-218.747 423.047,-218.294 495.891,-218.096"/>
<text text-anchor="middle" x="358" y="-223.4" font-family="Sans" font-size="14.00">Set amount to spend &amp; pay in fees</text>
</g>
<!-- left1 -->
<!-- script -->
<g id="node30" class="node"><title>script</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="558,-182 504,-182 504,-146 558,-146 558,-182"/>
<text text-anchor="middle" x="531" y="-159.9" font-family="Sans" font-size="14.00">script</text>
</g>
<!-- left1&#45;&gt;script -->
<g id="edge31" class="edge"><title>left1&#45;&gt;script</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M191.285,-164.926C259.228,-164.741 435.402,-164.26 503.536,-164.075"/>
<text text-anchor="middle" x="358" y="-186.4" font-family="Sans" font-size="14.00">Describe conditions necessary</text>
<text text-anchor="middle" x="358" y="-169.4" font-family="Sans" font-size="14.00">to spend this output</text>
</g>
<!-- left2 -->
<!-- locktime -->
<g id="node31" class="node"><title>locktime</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="568,-125 494,-125 494,-89 568,-89 568,-125"/>
<text text-anchor="middle" x="531" y="-102.9" font-family="Sans" font-size="14.00">locktime</text>
</g>
<!-- left2&#45;&gt;locktime -->
<g id="edge27" class="edge"><title>left2&#45;&gt;locktime</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M191.285,-110.703C256.238,-109.995 420.105,-108.209 493.931,-107.404"/>
<text text-anchor="middle" x="358" y="-132.4" font-family="Sans" font-size="14.00">Prevent tx from being added to the</text>
<text text-anchor="middle" x="358" y="-115.4" font-family="Sans" font-size="14.00">block chain before a particular time</text>
</g>
<!-- middle0 -->
<!-- output -->
<!-- output&#45;&gt;nextout -->
<g id="edge9" class="edge"><title>output&#45;&gt;nextout</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M531.687,-254C540.903,-254 640.334,-254 673.96,-254"/>
<polygon fill="black" stroke="black" points="674.365,-257.5 684.365,-254 674.365,-250.5 674.365,-257.5"/>
<text text-anchor="middle" x="633" y="-377.4" font-family="Sans" font-size="14.00">Each output</text>
<text text-anchor="middle" x="633" y="-360.4" font-family="Sans" font-size="14.00">waits as an</text>
<text text-anchor="middle" x="633" y="-343.4" font-family="Sans" font-size="14.00">Unspent</text>
<text text-anchor="middle" x="633" y="-326.4" font-family="Sans" font-size="14.00">Tx Output</text>
<text text-anchor="middle" x="633" y="-309.4" font-family="Sans" font-size="14.00">(UTXO)</text>
<text text-anchor="middle" x="633" y="-292.4" font-family="Sans" font-size="14.00">until a</text>
<text text-anchor="middle" x="633" y="-275.4" font-family="Sans" font-size="14.00">later input</text>
<text text-anchor="middle" x="633" y="-258.4" font-family="Sans" font-size="14.00">spends it</text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 11 KiB

View file

@ -0,0 +1,47 @@
digraph blockchain {
size="6.25";
//splines = "false";
rankdir=LR;
//ranksep=0.1;
//splines=ortho;
overlap = false;
nodesep = 0.1;
node [ shape = box, penwidth = 1.75 ];
edge [ penwidth = 1.75, minlen = 2 ];
penwidth = 1.75;
subgraph cluster_tx2 {
scriptSig [ label = "ScriptSig", shape = "none" ];
tx2_signature [ label = "Signature" ];
tx2_full_public_key [ label = "Full Public Key" ];
script [ label = " \nScript", shape = "none" ];
tx2_pubkey_hash [ label = "Public Key Hash" ];
}
subgraph cluster_tx1 {
tx1_pubkey_hash [ label = "Public Key Hash" ];
label = "TX 1 Output"
}
subgraph cluster_bob {
private_key [ label = "Private Key" ];
full_public_key [ label = "Full Public Key" ];
label = "Bob's Computer"
}
tx1_pubkey_hash -> tx2_pubkey_hash;
{
edge [ arrowhead = "none", arrowtail = "normal", dir=both ]
tx2_full_public_key -> full_public_key;
tx2_signature -> private_key [ style = "dashed" ];
}
label = " \nSpending A P2PH Output"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.4 KiB

View file

@ -0,0 +1,80 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="240pt"
viewBox="0.00 0.00 450.00 239.57" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.809353 0.809353) rotate(0) translate(4 292)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-292 553,-292 553,5 -4,5"/>
<text text-anchor="middle" x="274" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="274" y="-8.4" font-family="Sans" font-size="14.00">Spending A P2PH Output</text>
<g id="graph2" class="cluster"><title>cluster_tx2</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="208,-50 208,-280 350,-280 350,-50 208,-50"/>
</g>
<g id="graph3" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-50 8,-127 150,-127 150,-50 8,-50"/>
<text text-anchor="middle" x="79" y="-110.4" font-family="Sans" font-size="14.00">TX 1 Output</text>
</g>
<g id="graph4" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="408,-142 408,-262 540,-262 540,-142 408,-142"/>
<text text-anchor="middle" x="474" y="-245.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
</g>
<!-- scriptSig -->
<g id="node2" class="node"><title>scriptSig</title>
<text text-anchor="middle" x="279" y="-249.9" font-family="Sans" font-size="14.00">ScriptSig</text>
</g>
<!-- tx2_signature -->
<g id="node3" class="node"><title>tx2_signature</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="321,-229 237,-229 237,-193 321,-193 321,-229"/>
<text text-anchor="middle" x="279" y="-206.9" font-family="Sans" font-size="14.00">Signature</text>
</g>
<!-- private_key -->
<g id="node10" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="521,-229 427,-229 427,-193 521,-193 521,-229"/>
<text text-anchor="middle" x="474" y="-206.9" font-family="Sans" font-size="14.00">Private Key</text>
</g>
<!-- tx2_signature&#45;&gt;private_key -->
<g id="edge10" class="edge"><title>tx2_signature&#45;&gt;private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M331.438,-211C360.968,-211 397.568,-211 426.29,-211"/>
<polygon fill="black" stroke="black" points="331.312,-207.5 321.312,-211 331.312,-214.5 331.312,-207.5"/>
</g>
<!-- tx2_full_public_key -->
<g id="node4" class="node"><title>tx2_full_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="336,-186 222,-186 222,-150 336,-150 336,-186"/>
<text text-anchor="middle" x="279" y="-163.9" font-family="Sans" font-size="14.00">Full Public Key</text>
</g>
<!-- full_public_key -->
<g id="node11" class="node"><title>full_public_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="531,-186 417,-186 417,-150 531,-150 531,-186"/>
<text text-anchor="middle" x="474" y="-163.9" font-family="Sans" font-size="14.00">Full Public Key</text>
</g>
<!-- tx2_full_public_key&#45;&gt;full_public_key -->
<g id="edge8" class="edge"><title>tx2_full_public_key&#45;&gt;full_public_key</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M346.944,-168C369.611,-168 394.632,-168 416.433,-168"/>
<polygon fill="black" stroke="black" points="346.715,-164.5 336.715,-168 346.715,-171.5 346.715,-164.5"/>
</g>
<!-- script -->
<g id="node5" class="node"><title>script</title>
<text text-anchor="middle" x="279" y="-126.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="279" y="-109.4" font-family="Sans" font-size="14.00">Script</text>
</g>
<!-- tx2_pubkey_hash -->
<g id="node6" class="node"><title>tx2_pubkey_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="341,-94 217,-94 217,-58 341,-58 341,-94"/>
<text text-anchor="middle" x="279" y="-71.9" font-family="Sans" font-size="14.00">Public Key Hash</text>
</g>
<!-- tx1_pubkey_hash -->
<g id="node8" class="node"><title>tx1_pubkey_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="141,-94 17,-94 17,-58 141,-58 141,-94"/>
<text text-anchor="middle" x="79" y="-71.9" font-family="Sans" font-size="14.00">Public Key Hash</text>
</g>
<!-- tx1_pubkey_hash&#45;&gt;tx2_pubkey_hash -->
<g id="edge5" class="edge"><title>tx1_pubkey_hash&#45;&gt;tx2_pubkey_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M141.733,-76C162.21,-76 185.12,-76 206.268,-76"/>
<polygon fill="black" stroke="black" points="206.49,-79.5001 216.49,-76 206.49,-72.5001 206.49,-79.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.7 KiB

View file

@ -0,0 +1,47 @@
digraph blockchain {
size="6.25";
//splines = "false";
rankdir=LR;
//ranksep=0.1;
//splines=ortho;
overlap = false;
nodesep = 0.1;
node [ shape = box, penwidth = 1.75 ];
edge [ penwidth = 1.75, minlen = 2 ];
penwidth = 1.75;
subgraph cluster_tx2 {
scriptSig [ label = "ScriptSig", shape = "none" ];
tx2_signature [ label = "Signature" ];
tx2_redeemScript [ label = "Full RedeemScript" ];
script [ label = " \nScript", shape = "none" ];
tx2_redeemScript_hash [ label = "RedeemScript Hash" ];
}
subgraph cluster_tx1 {
tx1_redeemScript_hash [ label = "RedeemScript Hash" ];
label = "TX 1 Output"
}
subgraph cluster_bob {
private_key [ label = "Private Key" ];
redeemScript [ label = "Full RedeemScript" ];
label = "Bob's Computer"
}
tx1_redeemScript_hash -> tx2_redeemScript_hash;
{
edge [ dir=back ]
tx2_redeemScript -> redeemScript;
tx2_signature -> private_key [ style = "dashed" ];
}
label = " \nSpending A P2SH Output"
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.9 KiB

View file

@ -0,0 +1,80 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<!-- Generated by graphviz version 2.26.3 (20100126.1600)
-->
<!-- Title: blockchain Pages: 1 -->
<svg width="450pt" height="212pt"
viewBox="0.00 0.00 450.00 212.10" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="graph1" class="graph" transform="scale(0.716561 0.716561) rotate(0) translate(4 292)">
<title>blockchain</title>
<polygon fill="white" stroke="white" points="-4,5 -4,-292 625,-292 625,5 -4,5"/>
<text text-anchor="middle" x="310" y="-25.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="310" y="-8.4" font-family="Sans" font-size="14.00">Spending A P2SH Output</text>
<g id="graph2" class="cluster"><title>cluster_tx2</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="232,-50 232,-280 398,-280 398,-50 232,-50"/>
</g>
<g id="graph3" class="cluster"><title>cluster_tx1</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="8,-50 8,-127 174,-127 174,-50 8,-50"/>
<text text-anchor="middle" x="91" y="-110.4" font-family="Sans" font-size="14.00">TX 1 Output</text>
</g>
<g id="graph4" class="cluster"><title>cluster_bob</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="456,-142 456,-262 612,-262 612,-142 456,-142"/>
<text text-anchor="middle" x="534" y="-245.4" font-family="Sans" font-size="14.00">Bob&#39;s Computer</text>
</g>
<!-- scriptSig -->
<g id="node2" class="node"><title>scriptSig</title>
<text text-anchor="middle" x="315" y="-249.9" font-family="Sans" font-size="14.00">ScriptSig</text>
</g>
<!-- tx2_signature -->
<g id="node3" class="node"><title>tx2_signature</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="357,-229 273,-229 273,-193 357,-193 357,-229"/>
<text text-anchor="middle" x="315" y="-206.9" font-family="Sans" font-size="14.00">Signature</text>
</g>
<!-- private_key -->
<g id="node10" class="node"><title>private_key</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="581,-229 487,-229 487,-193 581,-193 581,-229"/>
<text text-anchor="middle" x="534" y="-206.9" font-family="Sans" font-size="14.00">Private Key</text>
</g>
<!-- tx2_signature&#45;&gt;private_key -->
<g id="edge10" class="edge"><title>tx2_signature&#45;&gt;private_key</title>
<path fill="none" stroke="black" stroke-width="1.75" stroke-dasharray="5,2" d="M367.556,-211C403.645,-211 451.169,-211 486.193,-211"/>
<polygon fill="black" stroke="black" points="367.225,-207.5 357.225,-211 367.225,-214.5 367.225,-207.5"/>
</g>
<!-- tx2_redeemScript -->
<g id="node4" class="node"><title>tx2_redeemScript</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="385,-186 245,-186 245,-150 385,-150 385,-186"/>
<text text-anchor="middle" x="315" y="-163.9" font-family="Sans" font-size="14.00">Full RedeemScript</text>
</g>
<!-- redeemScript -->
<g id="node11" class="node"><title>redeemScript</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="604,-186 464,-186 464,-150 604,-150 604,-186"/>
<text text-anchor="middle" x="534" y="-163.9" font-family="Sans" font-size="14.00">Full RedeemScript</text>
</g>
<!-- tx2_redeemScript&#45;&gt;redeemScript -->
<g id="edge8" class="edge"><title>tx2_redeemScript&#45;&gt;redeemScript</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M395.37,-168C417.814,-168 442.019,-168 463.825,-168"/>
<polygon fill="black" stroke="black" points="395.197,-164.5 385.197,-168 395.197,-171.5 395.197,-164.5"/>
</g>
<!-- script -->
<g id="node5" class="node"><title>script</title>
<text text-anchor="middle" x="315" y="-126.4" font-family="Sans" font-size="14.00"> </text>
<text text-anchor="middle" x="315" y="-109.4" font-family="Sans" font-size="14.00">Script</text>
</g>
<!-- tx2_redeemScript_hash -->
<g id="node6" class="node"><title>tx2_redeemScript_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="390,-94 240,-94 240,-58 390,-58 390,-94"/>
<text text-anchor="middle" x="315" y="-71.9" font-family="Sans" font-size="14.00">RedeemScript Hash</text>
</g>
<!-- tx1_redeemScript_hash -->
<g id="node8" class="node"><title>tx1_redeemScript_hash</title>
<polygon fill="none" stroke="black" stroke-width="1.75" points="166,-94 16,-94 16,-58 166,-58 166,-94"/>
<text text-anchor="middle" x="91" y="-71.9" font-family="Sans" font-size="14.00">RedeemScript Hash</text>
</g>
<!-- tx1_redeemScript_hash&#45;&gt;tx2_redeemScript_hash -->
<g id="edge5" class="edge"><title>tx1_redeemScript_hash&#45;&gt;tx2_redeemScript_hash</title>
<path fill="none" stroke="black" stroke-width="1.75" d="M166.212,-76C186.637,-76 208.898,-76 229.831,-76"/>
<polygon fill="black" stroke="black" points="229.987,-79.5001 239.987,-76 229.987,-72.5001 229.987,-79.5001"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.8 KiB