forked from irinazheltisheva/powergate
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathchainsync.go
More file actions
73 lines (64 loc) · 1.92 KB
/
chainsync.go
File metadata and controls
73 lines (64 loc) · 1.92 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
package chainsync
import (
"context"
"fmt"
"github.com/filecoin-project/lotus/chain/store"
"github.com/filecoin-project/lotus/chain/types"
)
// API provides an abstraction to a Filecoin full-node
type API interface {
ChainGetPath(context.Context, types.TipSetKey, types.TipSetKey) ([]*store.HeadChange, error)
ChainGetGenesis(context.Context) (*types.TipSet, error)
}
// ChainSync provides methods to resolve chain syncing situations
type ChainSync struct {
api API
}
// New returns a new ChainSync
func New(api API) *ChainSync {
return &ChainSync{
api: api,
}
}
// Precedes returns true if from and to don't live in different chain forks, and
// from is at a lower epoch than to.
func (cs *ChainSync) Precedes(ctx context.Context, from, to types.TipSetKey) (bool, error) {
fpath, err := cs.api.ChainGetPath(ctx, from, to)
if err != nil {
return false, fmt.Errorf("getting path from %v to %v: %s", from.Cids(), to.Cids(), err)
}
if len(fpath) == 0 {
return true, nil
}
norevert := fpath[0].Type == store.HCApply
return norevert, nil
}
// ResolveBase returns the base TipSetKey that both left and right TipSetKey share,
// plus a Revert/Apply set of operations to get from last to new.
func ResolveBase(ctx context.Context, api API, left *types.TipSetKey, right types.TipSetKey) (*types.TipSetKey, []*types.TipSet, error) {
var path []*types.TipSet
if left == nil {
genesis, err := api.ChainGetGenesis(ctx)
if err != nil {
return nil, nil, fmt.Errorf("getting genesis tipset: %s", err)
}
path = append(path, genesis)
gtsk := types.NewTipSetKey(genesis.Cids()...)
left = >sk
}
fpath, err := api.ChainGetPath(ctx, *left, right)
if err != nil {
return nil, nil, err
}
var base *types.TipSetKey
for _, ts := range fpath {
if ts.Type == store.HCApply {
if base == nil {
b := types.NewTipSetKey(ts.Val.Blocks()[0].Parents...)
base = &b
}
path = append(path, ts.Val)
}
}
return base, path, nil
}