6 dbm "github.com/tendermint/tmlibs/db"
8 "github.com/bytom/protocol"
9 "github.com/bytom/protocol/bc/types"
12 func declChain(name string, baseChain *protocol.Chain, baseHeight uint64, height uint64) (*protocol.Chain, error) {
13 chainDB := dbm.NewDB(name, "leveldb", name)
14 chain, _, _, err := MockChain(chainDB)
20 if err := AppendBlocks(chain, height); err != nil {
26 for i := uint64(1); i <= baseHeight; i++ {
27 block, err := baseChain.GetBlockByHeight(i)
31 if err := SolveAndUpdate(chain, block); err != nil {
36 err = AppendBlocks(chain, height-baseHeight)
40 func ancestorOf(c1 *protocol.Chain, c2 *protocol.Chain) (*types.Block, error) {
41 start := c1.BestBlockHeight()
42 if c2.BestBlockHeight() < c1.BestBlockHeight() {
43 start = c2.BestBlockHeight()
46 for i := start; i >= 0; i-- {
47 b1, err := c1.GetBlockByHeight(i)
51 b2, err := c2.GetBlockByHeight(i)
55 if b1.Hash() == b2.Hash() {
59 return nil, fmt.Errorf("can't find ancestor")
62 func merge(c1 *protocol.Chain, c2 *protocol.Chain) error {
64 if c1.BestBlockHeight() == c2.BestBlockHeight() && *c1.BestBlockHash() == *c2.BestBlockHash() {
68 ancestor, err := ancestorOf(c1, c2)
73 processBlocks := func(dest *protocol.Chain, src *protocol.Chain, height uint64) error {
74 for h := src.BestBlockHeight(); h > height; h-- {
75 block, err := src.GetBlockByHeight(h)
79 _, err = dest.ProcessBlock(block)
87 if err := processBlocks(c1, c2, ancestor.Height); err != nil {
90 return processBlocks(c2, c1, ancestor.Height)