基于以太坊dpos实现

GitHub地址 https://github.com/TTCECO/gttc
基于以太坊go-ethereum的DPOS实现

一 构建以太坊

1 git clone https://github.com/TTCECO/gttc.git
  • 目录结构为~/github.com/TTCECO/gttc
2 在根目录make gttc(make all)

二.构建有多个节点的以太坊链

Before read this instruction, please make sure the gttc, bootnode 
and puppeth already compiled and installed correctly in your server.

1 在目录 gttc/build/bin下创建节点目录

$ mkdir node1 node2

2 生成超级节点账号

$ gttc --datadir node1/ account new
$ gttc --datadir node2/ account new
  • 输入密码后会显示生成的地址node1_address和node2_address

3 把账号信息写入文件来启动节点

$ echo 'node1_address' >> account.txt
$ echo 'node2_address' >> account.txt
$ echo 'password1' >> node1/password.txt
$ echo 'password2' >> node2/password.txt

4 通过puppeth来构建创世配置文件

$ puppeth

+-----------------------------------------------------------+
| Welcome to puppeth, your private network manager          |
|                                                           |
| This tool lets you create a new Ethereum network down to  |
| the genesis block, bootnodes, miners and ethstats servers |
| without the hassle that it would normally entail.         |
|                                                           |
| Puppeth uses SSH to dial in to remote servers, and builds |
| its network components out of Docker containers using the |
| docker-compose toolset.                                   |
+-----------------------------------------------------------+

Please specify a network name to administer (no spaces or hyphens, please)
> devnet

Sweet, you can set this via --network=devnet next time!

INFO [06-04|12:33:34] Administering Ethereum network           name=devnet
WARN [06-04|12:33:34] No previous configurations found         path=/Users/tataufo/.puppeth/devnet

What would you like to do? (default = stats)
 1. Show network stats
 2. Configure new genesis
 3. Track new remote server
 4. Deploy network components
> 2

Which consensus engine to use? (default = alien)
 1. Ethash - proof-of-work
 2. Clique - proof-of-authority
 3. Alien  - delegated-proof-of-stake
> 3

How many seconds should blocks take? (default = 3)
> 4

How many blocks create for one epoch? (default = 30000)
> 30

What is the max number of signers? (default = 21)
> 3

What is the minimize balance for valid voter ? (default = 10000TTC)
> 100

How many minutes delay to create first block ? (default = 5 minutes)
> 5

Which accounts are vote by themselves to seal the block?(least one, those accounts will be auto pre-funded)
(The follow two address can be found in account.txt)
> 0xfa846876ef5ed3826e483303f42d987a66af8e15 
> 0x62739566c666df9a057d7e7c92898511d4e64c07
> 0x

Which accounts should be pre-funded? (advisable at least one)
> 0x

Specify your chain/network ID if you want an explicit one (default = random)
>
INFO [06-04|12:35:27] Configured new genesis block

What would you like to do? (default = stats)
 1. Show network stats
 2. Manage existing genesis
 3. Track new remote server
 4. Deploy network components
> 2

 1. Modify existing fork rules
 2. Export genesis configuration
 3. Remove genesis configuration
> 2

Which file to save the genesis into? (default = devnet.json)
> genesis.json
INFO [06-04|12:35:45] Exported existing genesis block

What would you like to do? (default = stats)
 1. Show network stats
 2. Manage existing genesis
 3. Track new remote server
 4. Deploy network components
> ^C

5 初始化节点数据

$ gttc --datadir node1/ init genesis.json
$ gttc --datadir node2/ init genesis.json

if old data in node folder, please remove them before initialize.

6 生成bootnode

$ bootnode -genkey boot.key

bootnode简化了Ethereum客户端实现,它只参与网络节点发现协议,但不运行任何高级应用程序协议。它可以用作轻量级的引导节点,以帮助在私有网络中找到对等点。
总而言之,就是一个用于节点发现或者说节点引导的轻量节点,方便联盟链的搭建~

7 运行bootnode

$ bootnode -nodekey boot.key -verbosity 9 -addr 127.0.0.1:30310

上面命令运行完,会打印类似下面的log

 enode://20940eac58b9e615706ea3c357c409aecbb44998d1388db49a8df61e727f92029019708b2ad69467f94eef9a49b5d4ffb2cc1e71bb06addeb134fe8bdbc62153@127.0.0.1:30310

encode后面的这么一长串东西,就是这个节点的ID信息,下面启动geth节点的时候要指定连接这个bootnode~

8 运行节点1和节点2

  • 下面命令中 unlock后面的地址为之前写入account.txt文件中的地址,以挖矿的形式启动
  • enode地址为上面第7步生成的encode。 (也可以不用第七步生成的encode节点地址作为下面的启动参数,后续直接将节点进行关联即可(第九步))
  • networkid 为genesis.json中的 ChinaId
$ gttc --datadir node1/ --syncmode 'full' --port 30311 --rpc --rpcaddr 'localhost' --rpcport 8501 --rpcapi 'personal,db,eth,net,web3,txpool,miner,alien,admin' --bootnodes 'enode://20940eac58b9e615706ea3c357c409aecbb44998d1388db49a8df61e727f92029019708b2ad69467f94eef9a49b5d4ffb2cc1e71bb06addeb134fe8bdbc62153@127.0.0.1:30310' --networkid 1014 --gasprice '1' -unlock 'fa846876ef5ed3826e483303f42d987a66af8e15' --password node1/password.txt --mine
后台启动方式:
nohup ./gwsc --datadir node1/ --syncmode 'full' --port 30311 --rpc --rpcaddr '127.0.0.1' --rpcport 8501 --rpcapi 'personal,db,eth,net,web3,txpool,miner,alien,admin' --networkid 1001 --gasprice '1' -unlock '6672c4a5d01751e92f86e5d0393feceb1513481b' --password node1/password.txt --mine >/dev/null 2>log & 
$ gttc --datadir node2/ --syncmode 'full' --port 30312 --rpc --rpcaddr 'localhost' --rpcport 8502 --rpcapi 'personal,db,eth,net,web3,txpool,miner,alien,admin' --bootnodes 'enode://20940eac58b9e615706ea3c357c409aecbb44998d1388db49a8df61e727f92029019708b2ad69467f94eef9a49b5d4ffb2cc1e71bb06addeb134fe8bdbc62153@127.0.0.1:30310' --networkid 1014 --gasprice '1' -unlock '62739566c666df9a057d7e7c92898511d4e64c07' --password node2/password.txt --mine
不用第七步生成的encode节点地址作为下面的启动参数
gttc --datadir node1/ --syncmode 'full' --port 30311 --rpc --rpcaddr 'localhost' --rpcport 8501 --rpcapi 'personal,db,eth,net,web3,txpool,miner,alien,admin' --networkid 1001 --gasprice '1' -unlock 'e363576de44cc5ca22fd96b49daa0724a3d4f6e4' --password node1/password.txt --mine

9 节点互联
1 进入geth JavaScript控制台

 ./gttc attach rpc:http://127.0.0.1:8501
 ./gttc attach rpc:http://127.0.0.1:8502

2 查看节点是否互联

admin.peers
[]

返回数据为[] 说明节点之间没有互相发现。
3 设置节点互联

admin.nodeInfo

记录下enode

"enode://7f2f1a5818b4bb7e756036ab08834386534807bbf5c5a305ddcbefa1ff9ea99028feb00cb78322ac39340501d5b7c6147e169aadbb028daf20f8d73dbdfea98e@[::]:30311"
"enode://6ab4f74058b9c1e43d2d0c6f55f538ea7f2f366dd9f8f560024f14603333f017d3404b9c9711538289fa76504fecf33cf0e36cce7b0414604f673abe93012413@[::]:30312"

4 进入node1 geth控制台

#添加节点2的监视器
admin.addPeer("enode://7f2f1a5818b4bb7e756036ab08834386534807bbf5c5a305ddcbefa1ff9ea99028feb00cb78322ac39340501d5b7c6147e169aadbb028daf20f8d73dbdfea98e@[::]:30311")

addPeer的时候注意如果节点不是在同一台服务器上,需要把@后面[::]换成当前节点所在机器的ip地址。

  • 进入node2 geth控制台 添加节点1的监视器

三 进行投票

投票操作也属于一笔交易,是从投票人给候选者进行投票。投票人的金额必须大于投票最小金额,否则投票无效。参数为:genesis.json中的minVoterBalance

  • ufo : prefix of custom data
  • 1 : custom info version
  • event : category of info (event, oplog …)
  • vote : vote event

The sample vote in console is like this

personal.sendTransaction({from:"t07544bf9c90d175da395b8d08fcaf34da0a3e0688",to:"t0aafeaaf6111762fea733ff7b4c8b59ac69316385",value:0,data:web3.toHex("ufo:1:event:vote")})

从A地址向B地址转移数量为0的代币,代表A投*票给B地址,而票数的计算则是A地址当前拥有货币的数量。

四 生成新的超级节点地址进行挖矿(方式跟node1和node2类似)

1 创建超级节点账户

./gttc --datadir super_node/ account new
  • 输入密码后会显示生成的地址暂且把地址记为:super_node_address

2 把密码写入super_node文件下

$ echo 'password' >> super_node/password.txt

3 初始化超级节点

$ gttc --datadir super_node/ init genesis.json

4 Run bootnode

$ bootnode -nodekey boot.key -verbosity 9 -addr 127.0.0.1:30310
  • boot.key使用之前运行node1生成的就可以了

5 运行超级节点进行挖矿(同理也可以不用第4步生成的encode地址参数)

$ gttc --datadir super_node/ --syncmode 'full' --port 30313 --rpc --rpcaddr 'localhost' --rpcport 8503 --rpcapi 'personal,db,eth,net,web3,txpool,miner,net' --bootnodes 'enode://20940eac58b9e615706ea3c357c409aecbb44998d1388db49a8df61e727f92029019708b2ad69467f94eef9a49b5d4ffb2cc1e71bb06addeb134fe8bdbc62153@127.0.0.1:30310' --networkid 1014 --gasprice '1' -unlock '62739566c666df9a057d7e7c92898511d4e64c07' --password super_node/password.txt --mine

6 节点互联

  • 进入node1的geth控制台 添加super_node的监视器(addPeer) 。node2 同理
  • 进入super_node的geth控制台 添加node1和node2的监视器。进行节点之间互联。
  • 超级节点地址需要有人投票并且成为有效见证人后才能挖矿。
    用户投票是有最小投票金额限制的,否则无效。
    参数为:genesis.json中的minVoterBalance

参数:

 alien.getSnapshotAtNumber(48)
  {
    confirmedNumber: 44,
    confirms: {
      41: ["t08feba63259ef7e79da13246dc20ff79fe446a478", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t07c352585cd7549bfbc0a7e88bf820fa574174598"],
      42: ["t07c352585cd7549bfbc0a7e88bf820fa574174598", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t08feba63259ef7e79da13246dc20ff79fe446a478"],
      43: ["t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t07c352585cd7549bfbc0a7e88bf820fa574174598", "t08feba63259ef7e79da13246dc20ff79fe446a478"],
      44: ["t07c352585cd7549bfbc0a7e88bf820fa574174598", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t08feba63259ef7e79da13246dc20ff79fe446a478"],
      45: ["t08feba63259ef7e79da13246dc20ff79fe446a478", "t07c352585cd7549bfbc0a7e88bf820fa574174598", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1"],
      46: ["t08feba63259ef7e79da13246dc20ff79fe446a478", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t07c352585cd7549bfbc0a7e88bf820fa574174598"]
    },
    hash: "t027009a5d7480cb2802e45b9d0ef2547ce7ad5e720d9281b0d628f314998a6416",
    headerTime: 1533341653,
    historyHash: ["t0fb741ff569db0a9277111285d157a0412c4dc6e30509834e7e87ce84755db336", "t0855589fcf6fb8157b29df69cba0393737a1c15a7427666f5e84b34c8a5680523", "t07b37e235e0686c8defaa0068b0508fe55921bd5e27bf0f1ee3e6909184dc74f4", "t0664bb4e6889acfd8bd4c277ba109cd9fbaf1366ce8472761b050451c01cf1a04", "t0d3d64b715e8568be7d86a82dbfd9a801013132d4229d96963f3869b584426f7a", "t068a1241b27c209ab584155a670a0473f29ae302eb2fe47d1a75b1eea45898ab2", "t04c8e6e969c950810c2acf128866f2aa416dc56b1ef2987281de4812622ebb44f", "t03c7047ba4574bf1e49c9e068d82e1b2c3f59e958658d897f4836db23f6ffcc3c", "t0c05b07cb1c00be507742bd9de8702a42d8cf77f43c566f52196f5b0bc47d084c", "t0d1f96774a2feb4c21add4aeb14ac0d92d5357b1cdc53cead0ed9df459ce308ac", "t0c95bd9b4fd9f9d4ca5a38d2433f6f9d6f48027098316d8b9d95fa1436639338d", "t0300addbe720652487d69c62b37d7281298200b2c7c68170a24dad8503c73940e", "t06ede482139d9a8f5a7bc385b16c5d3c59ad11715091ad1609aa451f605fcc633", "t027009a5d7480cb2802e45b9d0ef2547ce7ad5e720d9281b0d628f314998a6416"],
    loopStartTime: 1533341639,
    number: 48,
    period: 4,
    punished: {
      t07c352585cd7549bfbc0a7e88bf820fa574174598: 880,
      t08feba63259ef7e79da13246dc20ff79fe446a478: 950,
      t0cc9c08721c7d8a792e238e80f6c20cb066e919a1: 1370
    },
    signers: ["t07c352585cd7549bfbc0a7e88bf820fa574174598", "t08feba63259ef7e79da13246dc20ff79fe446a478", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t07c352585cd7549bfbc0a7e88bf820fa574174598", "t08feba63259ef7e79da13246dc20ff79fe446a478", "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1", "t07c352585cd7549bfbc0a7e88bf820fa574174598"],
    tally: {
      t07c352585cd7549bfbc0a7e88bf820fa574174598: 9.046256971665328e+74,
      t08feba63259ef7e79da13246dc20ff79fe446a478: 9.046256971665328e+74,
      t0cc9c08721c7d8a792e238e80f6c20cb066e919a1: 9.046256971665328e+74
    },
    voters: {
      t07c352585cd7549bfbc0a7e88bf820fa574174598: 0,
      t08feba63259ef7e79da13246dc20ff79fe446a478: 0,
      t0cc9c08721c7d8a792e238e80f6c20cb066e919a1: 0
    },
    votes: {
      t07c352585cd7549bfbc0a7e88bf820fa574174598: {
        Candidate: "t07c352585cd7549bfbc0a7e88bf820fa574174598",
        Stake: 9.046256971665328e+74,
        Voter: "t07c352585cd7549bfbc0a7e88bf820fa574174598"
      },
      t08feba63259ef7e79da13246dc20ff79fe446a478: {
        Candidate: "t08feba63259ef7e79da13246dc20ff79fe446a478",
        Stake: 9.046256971665328e+74,
        Voter: "t08feba63259ef7e79da13246dc20ff79fe446a478"
      },
      t0cc9c08721c7d8a792e238e80f6c20cb066e919a1: {
        Candidate: "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1",
        Stake: 9.046256971665328e+74,
        Voter: "t0cc9c08721c7d8a792e238e80f6c20cb066e919a1"
      }
    }
  }

  • signers : Signers queue in current loop (每一轮的超级节点队列)
  • loopStartTime: Start Time of the current loop, used to calculate the right miner(signer) by time(每一轮的开始时间)
  • 重新选取超级节点时间:当出块数=节点数*轮数时,会重重选一次超级节点。
    轮数参数:consensus/alien/alien.go文件中的defauleLoopCntRecalculateSigners = 10(默认为10轮)
  • period: 4 每4秒出一个块

> 投票规则: 假如超级节点为3个。则每出30个块(10轮)signers中的节点会重新选取3个超级节点。每出三个块(一轮12秒),loopStartTime会变一次,同时signers的顺序也会变一次。但是不换出块节点,只有当出了30个块则更换节点

> 超级节点挖矿的收益
go-ethereum consensus/alien/alien.go中方法accumulateRewards

主要代码如下:
	secondsPerYear     = 365 * 24 * 3600
	//config.Alien.Period:为多少秒出一次块
	blockNumPerYear := secondsPerYear / config.Alien.Period
	initSignerBlockReward := new(big.Int).Div(totalBlockReward, big.NewInt(int64(2*blockNumPerYear)))
	yearCount := header.Number.Uint64() / blockNumPerYear
	//根据块数计算当前年数  再进行右位移运算  得到当前挖出一块的总收益
	blockReward := new(big.Int).Rsh(initSignerBlockReward, uint(yearCount))

	minerReward := new(big.Int).Set(blockReward)
	minerReward.Mul(minerReward, new(big.Int).SetUint64(snap.MinerReward))
	//minerReward为挖矿人的收益。
	minerReward.Div(minerReward, big.NewInt(1000)) // cause the reward is calculate by cnt per thousand
	//votersReward 投票人获得的返佣收益(投票人平分)
	votersReward := blockReward.Sub(blockReward, minerReward)

blockReward = minerReward + votersReward。

  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以太坊是一个平台,它上面提供各种模块让用户来搭建应用,如果将搭建应用比作造房子,那么以太坊就提供了墙面、屋顶、地板等模块,用户只需像搭积木一样把房子搭起来,因此在以太坊上建立应用的成本和速度都大大改善。具体来说,以太坊通过一套图灵完备的脚本语言(Ethereum Virtual Machinecode,简称EVM语言)来建立应用,它类似于汇编语言。我们知道,直接用汇编语言编程是非常痛苦的,但以太坊里的编程并不需要直接使用EVM语言,而是类似C语言、Python、Lisp等高级语言,再通过编译器转成EVM语言。上面所说的平台之上的应用,其实就是合约,这是以太坊的核心。合约是一个活在以太坊系统里的自动代理人,他有一个自己的以太币地址,当用户向合约的地址里发送一笔交易后,该合约就被激活,然后根据交易中的额外信息,合约会运行自身的代码,最后返回一个结果,这个结果可能是从合约的地址发出另外一笔交易。需要指出的是,以太坊中的交易,不单只是发送以太币而已,它还可以嵌入相当多的额外信息。如果一笔交易是发送给合约的,那么这些信息就非常重要,因为合约将根据这些信息来完成自身的业务逻辑。合约所能提供的业务,几乎是无穷无尽的,它的边界就是你的想象力,因为图灵完备的语言提供了完整的自由度,让用户搭建各种应用。白皮书举了几个例子,如储蓄账户、用户自定义的子货币等。 2013年年末,以太坊创始人Vitalik Buterin发布了以太坊初版白皮书,启动了项目。2014年7月24日起,以太坊进行了为期42天的以太币预售。2016年初,以太坊的技术得到市场认可,价格开始暴涨,吸引了大量开发者以外的人进入以太坊的世界。中国三大比特币交易所之二的火币网及OKCoin币行都于2017年5月31日正式上线以太坊。 [1] 自从进入2016年以来,那些密切关注数字货币产业的人都急切地观察着第二代加密货币平台以太坊的发展动向。作为一种比较新的利用比特币技术的开发项目,以太坊致力于实施全球去中心化且无所有权的的数字技术计算机来执行点对点合约。简单来说就是,以太坊是一个你无法关闭的世界计算机。加密架构与图灵完整性的创新型结合可以促进大量的新产业的出现。反过来,传统行业的创新压力越来越大,甚至面临淘汰的风险。比特币网络事实上是一套分布式的数据库,而以太坊则更进一步,她可以看作是一台分布式的计算机:区块链是计算机的ROM,合约是程序,而以太坊的矿工们则负责计算,担任CPU的角色。这台计算机不是、也不可能是免费使用的,不然任何人都可以往里面存储各种垃圾信息和执行各种鸡毛蒜皮的计算,使用它至少需要支付计算费和存储费,当然还有其它一些费用。最为知名的是2017年初以摩根大通、芝加哥交易所集团、纽约梅隆银行、汤森路透、微软、英特尔、埃森哲等20多家全球top金融机构和科技公司成立的企业以太坊联盟。而以太坊催生的加密货币以太币近期又成了继比特币之后受追捧的资产。  智能合约的潜在应用很多。彭博社商业周刊称它是“所有人共享但无法篡改的软件”。更高级的软件有可能用以太坊创建网络商店。区块链程序以太坊可以用来创建去中心化的程序、自治组织和智能合约,据纽约时报的报导,在2016年5月已经有数十个可用的程序。预期的应用目标涵盖金融、物联网、农田到餐桌(farm-to-table)、智能电网、体育,菠菜等。去中心化自治组织有潜力让许多原本无法运行或成本过高的营运模型成为可能。较知名的应用有:去中心化创业投资:The DAO用以太币资金创立,目标是为商企业和非营利机构创建新的去中心化营业模式、The Rudimental让独立艺术家在区块链上进行群众募资。社会经济平台:Backfeed。去中心化预测市场:Augur。物联网:Ethcore(一间以太坊公司)研发的客户端、Chronicled(一间区块链公司)发表了以太坊区块链的实物资产验证平台;芯片公司、物理IP创建者和生产者可以用植入的蓝牙或近场通信进行验证。Slock.It开发的智能锁可以在付费后自动打开,让用户在付费后可以帮电动车充电、或是打开租屋的房门。虚拟宝物交易平台:FreeMyVunk。版权授权:Ujo Music平台让创作人用智能合约发布音乐,消费者可以直接付费给创作人。伊莫珍·希普用此平台发布了一首单曲。智能电网:TransActive Grid让用户可以和邻居买卖能源。去中心化期权市场:Etheropt。钉住汇率的代币:DigixDAO提供与黄金挂钩的代币,在2016年四月正式营运。Decentralized Capital提供和各种货币挂钩的代币。移动支付:Everex让外劳汇款回家乡。客户端软件以太坊的两个主要的客户端软件是Geth和Parity。企业软件企业软件公司也正测试用以太坊作为各种用途。已知有兴趣的公司包括微软、IBM、摩根大通。德勤和ConsenSys在2016年

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值