Go to file
Dave Collins df1898cead
blockchain: Reverse utxo set semantics.
This modifies the way the unspent transaction output set is handled to
reverse its current semantics so that it is optimized for the typical
case, provides simpler handling, and resolves various issues with the
previous approach.  In addition, it updates the transaction, address,
and existsaddress indexes to no longer remove entries from blocks that
have been disapproved as, in all cases, the data still exists in the
blockchain and thus should be queryable via the indexes even though
there is special handling applied which treats them as if they did not
exist in certain regards.

Prior to this change, transactions in the regular tree were not applied
to the utxo set until the next block was processed and did not vote
against them.  However, that approach has several undesirable
consequences such as temporarily "invisible" utxos that are actually
spendable, disapproved transactions missing from indexes even though
they are still in the blockchain, and poor performance characteristics.

In a certain sense, the previous approach could be viewed as the
transactions not being valid until they were approved, however, that is
not really true because it was (and still is) perfectly acceptable to
spend utxos created by transactions in the regular tree of the same
block so long as they come before the transactions that spend them.
Further, utxos from a transaction in the regular tree of a block can be
spent in the next block so long as that block does not disapprove them,
which further illustrates that the utxos are actually valid unless they
are disapproved.

Consequently, this modifies that behavior to instead make the utxo set
always track the most recent block and remove the regular transactions
in the parent when a block votes against them.  This approach is
significantly more efficient for the normal case where the previous
block is not disapproved by its successor.

Also, the terminology is changed in several places to refer to
disapproved blocks and transaction trees as opposed to invalid, because
invalid implies the tree/block is malformed or does not follow the
consensus rules.  On the contrary, when a block votes against its
parent, it is only voting against regular transaction tree of the
parent.  Both the block and transaction tree are still valid in that
case, only the regular transaction tree is treated as if it never
existed in terms of effects on the utxo set and duplicate transaction
semantics.

High level overview of changes:
- Modify the utxo viewpoint to reverse semantics as previously described
  - Remove all code related to stake viewpoints
  - Change all block connection code in the viewpoint to first undo all
    transactions in the regular tree of the parent block if the current
    one disapproves it then connect all of the stake txns followed by
    the regular transactions in the block
    - NOTE: The order here is important since stake transactions are not
      allowed to spend outputs from the regular transactions in the same
      block as the next block might disapprove them
  - Change all block disconnection code in the viewpoint to first undo
    all the transactions in the regular and stake trees of the block
    being disconnected, and then resurrect the regular transactions in
    the parent block if the block being disconnected disapproved of it
  - Introduce a new type named viewFilteredSet for handling sets
    filtered by transactions that already exist in a view
  - Introduce a function on the viewpoint for specifically fetching the
    inputs to the regular transactions
  - Update mempool block connection and disconnection code to match the
    new semantics
  - Update all tests to handle the new semantics
- Modify the best state number of transactions to include all
  transactions in all blocks regardless of disapproval because they
  still had to be processed and still exist in the blockchain
- Remove include recent block parameter from mempool.FetchTransaction
  since the utxoset now always includes the latest block
  - This also has the side effect of correcting some unexpected results
    such as coinbases in the most recent block being incorrectly
    reported as having zero confirmations
- Modify mempool utxo fetch logic to use a cached disapproved view, when
  needed, rather than recreating the view for every new transaction
  added to it
- Update spend journal to include all transactions in the block instead
  of only stake transactions from the current block and regular
  transactions from the parent block
- Modify tx and address indexes to store the block index of each tx
  along with its location within the files and update the query
  functions to return the information as well
- Change the tx, address, and existsaddress indexes to index all
  transactions regardless of their disapproval
  - This also corrects several issues such as the inability to query and
    retrieve transactions that exist in a disapproved block
- Update all RPC commands that return verbose transaction information
  to set that newly available block index information properly
- Rename IsRegTxTreeKnownDisapproved in the mining.TxSource interface to
  IsRegTxTreeKnownDisapproved
  - NOTE: This will require a major bump to the mining module before
    the next release
- Rename several utxoView instances to view for consistency
- Rename several variables that dealt with disapproved trees from
  names that contained Invalid to ones that contain Disapproved

NOTE: This does not yet have database migration code and thus will
require a full chain download.  It will exit with error in the case you
attempt to run it against an existing v4 database.  The new database it
creates will be v5, so attempting to run an older version will reject
the new database to prevent corruption.

The database migration will be added in a separate commit.
2018-11-09 17:23:46 -06:00
.github docs: Add github pull request template. 2018-10-01 11:32:16 -05:00
addrmgr build: Tidy module sums (go mod tidy). 2018-08-16 20:03:27 -05:00
blockchain blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
certgen multi: Make changes suggested by Go 1.11 gofmt -s. 2018-08-23 12:52:07 -05:00
chaincfg chaincfg: Unexport internal errors. 2018-10-10 17:56:16 -05:00
cmd limits: Make limits package internal. 2018-09-06 15:19:25 -05:00
connmgr build: Tidy module sums (go mod tidy). 2018-08-16 20:03:27 -05:00
database multi: Remove unused code. 2018-10-31 21:50:09 -04:00
dcrec multi: Address some golint complaints. 2018-10-10 19:50:06 -05:00
dcrjson multi: Return total chain work in RPC results. 2018-10-16 11:30:58 -05:00
dcrutil multi: Use regression test network in unit tests. 2018-10-09 19:40:10 -05:00
docs multi: Return total chain work in RPC results. 2018-10-16 11:30:58 -05:00
gcs build: Tidy module sums (go mod tidy). 2018-08-16 20:03:27 -05:00
hdkeychain multi: Remove unused code. 2018-10-31 21:50:09 -04:00
internal limits: Make limits package internal. 2018-09-06 15:19:25 -05:00
mempool blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
mining blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
peer dcrjson: Add listtickets command. 2018-10-11 16:21:34 -05:00
release Add example service files. 2017-03-23 02:07:08 -05:00
rpcclient multi: Cleanup the unsupported dcrwallet commands. 2018-10-11 14:15:22 -05:00
rpctest multi: Address some golint complaints. 2018-10-10 19:50:06 -05:00
sampleconfig sampleconfig: Fix proxy typo. 2018-11-07 01:33:24 -06:00
txscript multi: Remove unused code. 2018-10-31 21:50:09 -04:00
wire multi: Resurrect regression network. 2018-10-09 18:52:13 -05:00
.dockerignore docker: Add dockerfiles for running dcrd nodes. 2018-07-07 05:33:53 -05:00
.gitignore main: add address encoding magic constants test 2018-09-26 16:09:11 -05:00
.travis.yml multi: Make use of new internal version package. 2018-09-04 17:34:31 -05:00
blocklogger.go multi: Replace btclog with slog. 2018-05-23 14:22:10 -05:00
blockmanager.go blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
cert_test.go main: move cert tests to a separated file 2018-10-18 20:06:53 +02:00
CHANGES multi: Properly capitalize Decred. 2018-03-01 17:41:35 -06:00
config_test.go multi: Cleanup recent alt DNS names additions. 2018-10-11 14:16:51 -05:00
config.go multi: Cleanup recent alt DNS names additions. 2018-10-11 14:16:51 -05:00
cpuminer.go multi: Move update blk time to blk templ generator. 2018-09-13 23:32:58 -05:00
dcrd.go limits: Make limits package internal. 2018-09-06 15:19:25 -05:00
doc.go multi: Cleanup recent alt DNS names additions. 2018-10-11 14:16:51 -05:00
Dockerfile docker: Update to go 1.11. 2018-09-20 13:25:35 -05:00
Dockerfile.alpine docker: Update to go 1.11. 2018-09-20 13:25:35 -05:00
go.mod multi: Use regression test network in unit tests. 2018-10-09 19:40:10 -05:00
go.sum build: Tidy module sums (go mod tidy). 2018-08-16 20:03:27 -05:00
ipc.go travis: add ineffassign linter 2017-12-01 09:14:04 -05:00
LICENSE multi: Add initial committed filter (CF) support 2018-03-30 13:52:12 -04:00
log.go multi: Replace btclog with slog. 2018-05-23 14:22:10 -05:00
mining_test.go mining_test: add edge conditions from btcd. 2017-08-31 00:28:36 -05:00
mining.go blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
miningerror.go blockchain: Rework to use new db interface. 2016-08-18 15:42:18 -04:00
networkparams_test.go multi: Resurrect regression network. 2018-10-09 18:52:13 -05:00
params.go multi: Resurrect regression network. 2018-10-09 18:52:13 -05:00
README.md multi: Remove unused code. 2018-10-31 21:50:09 -04:00
rpcserver_test.go main: move cert tests to a separated file 2018-10-18 20:06:53 +02:00
rpcserver.go blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
rpcserverhelp_test.go blockchain: Rework to use new db interface. 2016-08-18 15:42:18 -04:00
rpcserverhelp.go multi: Return total chain work in RPC results. 2018-10-16 11:30:58 -05:00
rpcwebsocket.go rpc: Use upstream gorilla/websocket. 2018-05-23 19:35:36 -05:00
run_tests.sh build: Support MacOS sed for obtaining module list. 2018-10-08 12:32:17 -05:00
server.go blockchain: Reverse utxo set semantics. 2018-11-09 17:23:46 -06:00
service_windows.go multi: Make use of new internal version package. 2018-09-04 17:34:31 -05:00
signal.go dcrd: Simplify shutdown signal handling logic sync. 2016-11-18 12:06:55 -06:00
signalsigterm.go Add pipes for parent process IPC. (#311) 2016-08-31 10:45:16 -04:00
upnp.go multi: Error descriptions are in lower case. 2017-09-08 18:03:59 +02:00

dcrd

Build Status ISC License GoDoc Go Report Card

Decred Overview

Decred is a blockchain-based cryptocurrency with a strong focus on community input, open governance, and sustainable funding for development. It utilizes a hybrid proof-of-work and proof-of-stake mining system to ensure that a small group cannot dominate the flow of transactions or make changes to Decred without the input of the community. A unit of the currency is called a decred (DCR).

https://decred.org

Latest Downloads

https://decred.org/downloads

What is dcrd?

dcrd is a full node implementation of Decred written in Go (golang).

It acts as a fully-validating chain daemon for the Decred cryptocurrency. dcrd maintains the entire past transactional ledger of Decred and allows relaying of transactions to other Decred nodes around the world.

This software is currently under active development. It is extremely stable and has been in production use since February 2016.

The software was originally forked from btcd, which is a bitcoin full node implementation that is still under active development. To gain the benefit of btcd's ongoing upgrades, including improved peer and connection handling, database optimization, and other blockchain related technology improvements, dcrd is continuously synced with the btcd codebase.

What is a full node?

The term 'full node' is short for 'fully-validating node' and refers to software that fully validates all transactions and blocks, as opposed to trusting a 3rd party. In addition to validating transactions and blocks, nearly all full nodes also participate in relaying transactions and blocks to other full nodes around the world, thus forming the peer-to-peer network that is the backbone of the Decred cryptocurrency.

The full node distinction is important, since full nodes are not the only type of software participating in the Decred peer network. For instance, there are 'lightweight nodes' which rely on full nodes to serve the transactions, blocks, and cryptographic proofs they require to function, as well as relay their transactions to the rest of the global network.

Why run dcrd?

As described in the previous section, the Decred cryptocurrency relies on having a peer-to-peer network of nodes that fully validate all transactions and blocks and then relay them to other full nodes.

Running a full node with dcrd contributes to the overall security of the network, increases the available paths for transactions and blocks to relay, and helps ensure there are an adequate number of nodes available to serve lightweight clients, such as Simplified Payment Verification (SPV) wallets.

Without enough full nodes, the network could be unable to expediently serve users of lightweight clients which could force them to have to rely on centralized services that significantly reduce privacy and are vulnerable to censorship.

In terms of individual benefits, since dcrd fully validates every block and transaction, it provides the highest security and privacy possible when used in conjunction with a wallet that also supports directly connecting to it in full validation mode, such as dcrwallet (CLI) and Decrediton (GUI).

  • 10 GB disk space (as of September 2018, increases over time)
  • 1GB memory (RAM)
  • ~150MB/day download, ~1.5GB/day upload
    • Plus one-time initial download of the entire block chain
  • Windows 7/8.x/10 (server preferred), macOS, Linux
  • High uptime

Getting Started

So, you've decided to help the network by running a full node. Great! Running dcrd is simple. All you need to do is install dcrd on a machine that is connected to the internet and meets the minimum recommended specifications, and launch it.

Also, make sure your firewall is configured to allow inbound connections to port 9108.

Installing and updating

Binaries (Windows/Linux/macOS)

Binary releases are provided for common operating systems and architectures:

https://decred.org/downloads

Build from source (all platforms)

Building or updating from source requires the following build dependencies:

To build and install from a checked-out repo, run go install . ./cmd/... in the repo's root directory. Some notes:

  • Set the GO111MODULE=on environment variable if using Go 1.11 and building from within GOPATH.

  • Replace go with vgo when using Go 1.10.

  • The dcrd executable will be installed to $GOPATH/bin. GOPATH defaults to $HOME/go (or %USERPROFILE%\go on Windows) if unset.

Example of obtaining and building from source on Windows 10 with Go 1.11:

PS> git clone https://github.com/decred/dcrd $env:USERPROFILE\src\dcrd
PS> cd $env:USERPROFILE\src\dcrd
PS> go install . .\cmd\...
PS> & "$(go env GOPATH)\bin\dcrd" -V

Example of obtaining and building from source on Linux with Go 1.10:

$ git clone https://github.com/decred/dcrd ~/src/dcrd
$ cd ~/src/dcrd
$ vgo install . ./cmd/...
$ $(vgo env GOPATH)/bin/dcrd -V

Docker

Running dcrd

You can run a decred node from inside a docker container. To build the image yourself, use the following command:

docker build -t decred/dcrd .

Or you can create an alpine based image (requires Docker 17.05 or higher):

docker build -t decred/dcrd:alpine -f Dockerfile.alpine .

You can then run the image using:

docker run decred/dcrd

You may wish to use an external volume to customise your config and persist the data in an external volume:

docker run --rm -v /home/user/dcrdata:/root/.dcrd/data decred/dcrd

For a minimal image, you can use the decred/dcrd:alpine tag. This is typically a more secure option while also being a much smaller image.

You can run dcrctl from inside the image. For example, run an image (mounting your data from externally) with:

docker run --rm -ti --name=dcrd-1 -v /home/user/.dcrd:/root/.dcrd \
  decred/dcrd:alpine

And then run dcrctl commands against it. For example:

docker exec -ti dcrd-1 dcrctl getbestblock

Running Tests

All tests and linters may be run in a docker (or podman) container using the script run_tests.sh by specifying either docker or podman as the first parameter. This script defaults to using the current latest supported version of Go, but it also respects the GOVERSION environment variable set to the major version of Go to allow testing on a previous version of Go. Generally, Decred only supports the current and previous major versions of Go.

./run_tests.sh docker

To run the tests locally without docker on the latest supported version of Go:

./run_tests.sh

To run the tests locally without docker on Go 1.10:

GOVERSION=1.10 ./run_tests.sh

Contact

If you have any further questions you can find us at:

https://decred.org/community

Issue Tracker

The integrated github issue tracker is used for this project.

Documentation

The documentation for dcrd is a work-in-progress. It is located in the docs folder.

License

dcrd is licensed under the copyfree ISC License.