Cryptocurrency Code In C++

Cryptocurrency code in c++

Naivecoin - a cryptocurrency implementation in less than 1500 lines of code

Motivation

Cryptocurrencies and smart-contracts on top of a blockchain aren't the most trivial concepts to understand, things like wallets, addresses, block proof-of-work, transactions and their signatures, make more sense when they are in a broad context.

Cryptocurrency code in c++

Inspired by naivechain, this project is an attempt to provide as concise and simple an implementation of a cryptocurrency as possible.

What is cryptocurrency

From Wikipedia : A cryptocurrency (or crypto currency) is a digital asset designed to work as a medium of exchange using cryptography to secure the transactions and to control the creation of additional units of the currency.

Key concepts of Naivecoin

  • Components
    • HTTP Server
    • Node
    • Blockchain
    • Operator
    • Miner
  • HTTP API interface to control everything
  • Synchronization of blockchain and transactions
  • Simple proof-of-work (The difficulty increases every 5 blocks)
  • Addresses creation using a deterministic approach EdDSA
  • Data is persisted to a folder

Naivechain uses websocket for p2p communication, but it was dropped to simplify the understanding of message exchange.

It is relying only on REST communication.

Components communication

Not all components in this implementation follow the complete list of requirements for a secure and scalable cryptocurrency.

First look at the Bitcoin source code

Inside the source-code, you can find comments with that describes what parts could be improved (and how) and what techniques were used to solve that specific challenge.

HTTP Server

Provides an API to manage the blockchain, wallets, addresses, transaction creation, mining request and peer connectivity.

It's the starting point to interact with the naivecoin, and every node provides a swagger API to make this interaction easier.

Available endpoints:

Blockchain
MethodURLDescription
GET/blockchain/blocksGet all blocks
GET/blockchain/blocks/{index}Get block by index
GET/blockchain/blocks/{hash}Get block by hash
GET/blockchain/blocks/latestGet the latest block
PUT/blockchain/blocks/latestUpdate the latest block
GET/blockchain/blocks/transactions/{transactionId}Get a transaction from some block
GET/blockchain/transactionsGet unconfirmed transactions
POST/blockchain/transactionsCreate a transaction
GET/blockchain/transactions/unspentGet unspent transactions
Operator
MethodURLDescription
GET/operator/walletsGet all wallets
POST/operator/walletsCreate a wallet from a password
GET/operator/wallets/{walletId}Get wallet by id
GET/operator/wallets/{walletId}/addressesGet all addresses of a wallet
POST/operator/wallets/{walletId}/transactionsCreate a new transaction
POST/operator/wallets/{walletId}/addressesCreate a new address
GET/operator/{addressId}/balanceGet the balance of a given address
Node
MethodURLDescription
GET/node/peersGet all peers connected to node
POST/node/peersConnects a new peer to node
GET/node/transactions/{transactionId}/confirmationsGet how many confirmations a block has
Miner
MethodURLDescription
POST/miner/mineMine a new block

From the Swagger UI is possible to access a simple UI to visualize the blockchain and the unconfirmed transactions.

Blockchain

The blockchain holds two pieces of information, the block list (a linked list), and the transaction list (a hash map).

It's responsible for:

  • Verification of arriving blocks;
  • Verification of arriving transactions;
  • Synchronization of the transaction list;
  • Synchronization of the block list;

The blockchain is a linked list where the hash of the next block is calculated based on the hash of the previous block plus the data inside the block itself:

A block is added to the block list if:

  1. The block is the last one (previous index + 1);
  2. The previous block is correct (previous hash == block.previousHash);
  3. The hash is correct (calculated block hash == block.hash);
  4. The difficulty level of the proof-of-work challenge is correct (difficulty at blockchain index n < block difficulty);
  5. All transactions inside the block are valid;
  6. The sum of output transactions are equal the sum of input transactions + 50 coins representing the reward for the block miner;
  7. Check if there is a double spending in that block
  8. There is only 1 fee transaction and 1 reward transaction.

A transaction inside a block is valid if:

  1. The transaction hash is correct (calculated transaction hash == transaction.hash);
  2. The signature of all input transactions are correct (transaction data is signed by the public key of the address);
  3. The sum of input transactions are greater than output transactions, it needs to leave some room for the transaction fee;
  4. The transaction isn't already in the blockchain
  5. All input transactions are unspent in the blockchain.

You can read this post from naivechain for more details about how the blockchain works.

Transactions is a list of unconfirmed transactions.

Nothing special about it.

Cryptocurrency code in c++

In this implementation, the list of transactions contains only the unconfirmed transactions. As soon as a transaction is confirmed, the blockchain removes it from this list.

A transaction is added to the transaction list if:

  1. It's not already in the transaction list;
  2. The transaction hash is correct (calculated transaction hash == transaction.hash);
  3. The signature of all input transactions are correct (transaction data is signed by the public key of the address);
  4. The sum of input transactions are greater than output transactions, it needs to leave some room for the transaction fee;
  5. The transaction isn't already in the blockchain
  6. All input transactions are unspent in the blockchain;
Block structure

A block represents a group of transactions and contains information that links it to the previous block.

{ // Block"index":0, // (first block: 0)"previousHash":"0", // (hash of previous block, first block is 0) (64 bytes)"timestamp":1465154705, // number of seconds since January 1, 1970"nonce":0, // nonce used to identify the proof-of-work step."transactions": [ // list of transactions inside the block { // transaction 0"id":"63ec3ac02f...8d5ebc6dba", // random id (64 bytes)"hash":"563b8aa350...3eecfbd26b", // hash taken from the contents of the transaction: sha256 (id + data) (64 bytes)"type":"regular", // transaction type (regular, fee, reward)

Cryptocurrency code in c++