OSDN Git Service

Merge pull request #1777 from Bytom/txpool
authorPaladz <yzhu101@uottawa.ca>
Wed, 14 Aug 2019 08:55:35 +0000 (16:55 +0800)
committerGitHub <noreply@github.com>
Wed, 14 Aug 2019 08:55:35 +0000 (16:55 +0800)
restore Tx back to Tx pool when chain is reorganized

protocol/orphan_manage.go
protocol/orphan_manage_test.go

index 1e3eac4..fad633a 100644 (file)
@@ -24,7 +24,7 @@ type OrphanBlock struct {
 
 func NewOrphanBlock(block *types.Block, expiration time.Time) *OrphanBlock {
        return &OrphanBlock{
-               Block: block,
+               Block:      block,
                expiration: expiration,
        }
 }
@@ -70,8 +70,8 @@ func (o *OrphanManage) Add(block *types.Block) {
        }
 
        if len(o.orphan) >= numOrphanBlockLimit {
+               o.deleteLRU()
                log.WithFields(log.Fields{"module": logModule, "hash": blockHash.String(), "height": block.Height}).Info("the number of orphan blocks exceeds the limit")
-               return
        }
 
        o.orphan[blockHash] = &OrphanBlock{block, time.Now().Add(orphanBlockTTL)}
@@ -137,13 +137,27 @@ func (o *OrphanManage) delete(hash *bc.Hash) {
        }
 
        for i, preOrphan := range prevOrphans {
-               if preOrphan == hash {
+               if *preOrphan == *hash {
                        o.prevOrphans[block.Block.PreviousBlockHash] = append(prevOrphans[:i], prevOrphans[i+1:]...)
                        return
                }
        }
 }
 
+func (o *OrphanManage) deleteLRU() {
+       var deleteBlock *OrphanBlock
+       for _, orphan := range o.orphan {
+               if deleteBlock == nil || orphan.expiration.Before(deleteBlock.expiration) {
+                       deleteBlock = orphan
+               }
+       }
+
+       if deleteBlock != nil {
+               blockHash := deleteBlock.Block.Hash()
+               o.delete(&blockHash)
+       }
+}
+
 func (o *OrphanManage) orphanExpireWorker() {
        ticker := time.NewTicker(orphanExpireWorkInterval)
        for now := range ticker.C {
index 8159f4d..6e74265 100644 (file)
@@ -10,15 +10,15 @@ import (
 )
 
 var testBlocks = []*types.Block{
-       &types.Block{BlockHeader: types.BlockHeader{
+       {BlockHeader: types.BlockHeader{
                PreviousBlockHash: bc.Hash{V0: 1},
                Nonce:             0,
        }},
-       &types.Block{BlockHeader: types.BlockHeader{
+       {BlockHeader: types.BlockHeader{
                PreviousBlockHash: bc.Hash{V0: 1},
                Nonce:             1,
        }},
-       &types.Block{BlockHeader: types.BlockHeader{
+       {BlockHeader: types.BlockHeader{
                PreviousBlockHash: bc.Hash{V0: 2},
                Nonce:             3,
        }},
@@ -32,6 +32,65 @@ func init() {
        }
 }
 
+func TestDeleteLRU(t *testing.T) {
+       now := time.Now()
+       cases := []struct {
+               before *OrphanManage
+               after  *OrphanManage
+       }{
+               {
+                       before: &OrphanManage{
+                               orphan: map[bc.Hash]*OrphanBlock{
+                                       blockHashes[0]: {testBlocks[0], now},
+                               },
+                               prevOrphans: map[bc.Hash][]*bc.Hash{
+                                       {V0: 1}: {&blockHashes[0]},
+                               },
+                       },
+                       after: &OrphanManage{
+                               orphan:      map[bc.Hash]*OrphanBlock{},
+                               prevOrphans: map[bc.Hash][]*bc.Hash{},
+                       },
+               },
+               {
+                       before: &OrphanManage{
+                               orphan:      map[bc.Hash]*OrphanBlock{},
+                               prevOrphans: map[bc.Hash][]*bc.Hash{},
+                       },
+                       after: &OrphanManage{
+                               orphan:      map[bc.Hash]*OrphanBlock{},
+                               prevOrphans: map[bc.Hash][]*bc.Hash{},
+                       },
+               },
+               {
+                       before: &OrphanManage{
+                               orphan: map[bc.Hash]*OrphanBlock{
+                                       blockHashes[0]: {testBlocks[0], now.Add(2)},
+                                       blockHashes[1]: {testBlocks[1], now.Add(1)},
+                               },
+                               prevOrphans: map[bc.Hash][]*bc.Hash{
+                                       {V0: 1}: {&blockHashes[0], &blockHashes[1]},
+                               },
+                       },
+                       after: &OrphanManage{
+                               orphan: map[bc.Hash]*OrphanBlock{
+                                       blockHashes[0]: {testBlocks[0], now.Add(2)},
+                               },
+                               prevOrphans: map[bc.Hash][]*bc.Hash{
+                                       {V0: 1}: {&blockHashes[0]},
+                               },
+                       },
+               },
+       }
+
+       for i, c := range cases {
+               c.before.deleteLRU()
+               if !testutil.DeepEqual(c.before, c.after) {
+                       t.Errorf("case %d: got %v want %v", i, c.before, c.after)
+               }
+       }
+}
+
 func TestOrphanManageAdd(t *testing.T) {
        cases := []struct {
                before    *OrphanManage
@@ -45,10 +104,10 @@ func TestOrphanManageAdd(t *testing.T) {
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        addOrphan: testBlocks[0],
@@ -56,18 +115,18 @@ func TestOrphanManageAdd(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        addOrphan: testBlocks[0],
@@ -75,19 +134,19 @@ func TestOrphanManageAdd(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
-                                       blockHashes[1]: &OrphanBlock{testBlocks[1], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
+                                       blockHashes[1]: {testBlocks[1], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0], &blockHashes[1]},
+                                       {V0: 1}: {&blockHashes[0], &blockHashes[1]},
                                },
                        },
                        addOrphan: testBlocks[1],
@@ -95,20 +154,20 @@ func TestOrphanManageAdd(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
-                                       blockHashes[2]: &OrphanBlock{testBlocks[2], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
+                                       blockHashes[2]: {testBlocks[2], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
-                                       bc.Hash{V0: 2}: []*bc.Hash{&blockHashes[2]},
+                                       {V0: 1}: {&blockHashes[0]},
+                                       {V0: 2}: {&blockHashes[2]},
                                },
                        },
                        addOrphan: testBlocks[2],
@@ -135,18 +194,18 @@ func TestOrphanManageDelete(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        remove: &blockHashes[1],
@@ -154,10 +213,10 @@ func TestOrphanManageDelete(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
@@ -169,19 +228,19 @@ func TestOrphanManageDelete(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
-                                       blockHashes[1]: &OrphanBlock{testBlocks[1], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
+                                       blockHashes[1]: {testBlocks[1], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0], &blockHashes[1]},
+                                       {V0: 1}: {&blockHashes[0], &blockHashes[1]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{testBlocks[0], time.Time{}},
+                                       blockHashes[0]: {testBlocks[0], time.Time{}},
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        remove: &blockHashes[1],
@@ -204,13 +263,13 @@ func TestOrphanManageExpire(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{
+                                       blockHashes[0]: {
                                                testBlocks[0],
                                                time.Unix(1633479700, 0),
                                        },
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
@@ -221,24 +280,24 @@ func TestOrphanManageExpire(t *testing.T) {
                {
                        before: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{
+                                       blockHashes[0]: {
                                                testBlocks[0],
                                                time.Unix(1633479702, 0),
                                        },
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                        after: &OrphanManage{
                                orphan: map[bc.Hash]*OrphanBlock{
-                                       blockHashes[0]: &OrphanBlock{
+                                       blockHashes[0]: {
                                                testBlocks[0],
                                                time.Unix(1633479702, 0),
                                        },
                                },
                                prevOrphans: map[bc.Hash][]*bc.Hash{
-                                       bc.Hash{V0: 1}: []*bc.Hash{&blockHashes[0]},
+                                       {V0: 1}: {&blockHashes[0]},
                                },
                        },
                },
@@ -253,24 +312,24 @@ func TestOrphanManageExpire(t *testing.T) {
 }
 
 func TestOrphanManageNumLimit(t *testing.T) {
-       cases := []struct{
-               addOrphanBlockNum int
+       cases := []struct {
+               addOrphanBlockNum    int
                expectOrphanBlockNum int
        }{
                {
-                       addOrphanBlockNum: 10,
+                       addOrphanBlockNum:    10,
                        expectOrphanBlockNum: 10,
                },
                {
-                       addOrphanBlockNum: numOrphanBlockLimit,
+                       addOrphanBlockNum:    numOrphanBlockLimit,
                        expectOrphanBlockNum: numOrphanBlockLimit,
                },
                {
-                       addOrphanBlockNum: numOrphanBlockLimit + 1,
+                       addOrphanBlockNum:    numOrphanBlockLimit + 1,
                        expectOrphanBlockNum: numOrphanBlockLimit,
                },
                {
-                       addOrphanBlockNum: numOrphanBlockLimit + 10,
+                       addOrphanBlockNum:    numOrphanBlockLimit + 10,
                        expectOrphanBlockNum: numOrphanBlockLimit,
                },
        }
@@ -283,7 +342,7 @@ func TestOrphanManageNumLimit(t *testing.T) {
                for num := 0; num < c.addOrphanBlockNum; num++ {
                        orphanManage.Add(&types.Block{BlockHeader: types.BlockHeader{Height: uint64(num)}})
                }
-               if (len(orphanManage.orphan) != c.expectOrphanBlockNum) {
+               if len(orphanManage.orphan) != c.expectOrphanBlockNum {
                        t.Errorf("case %d: got %d want %d", i, len(orphanManage.orphan), c.expectOrphanBlockNum)
                }
        }