-
Notifications
You must be signed in to change notification settings - Fork 1.3k
/
checkpoint.go
57 lines (45 loc) · 1.46 KB
/
checkpoint.go
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
package chain
import (
"context"
"golang.org/x/xerrors"
"github.com/filecoin-project/lotus/chain/types"
)
func (syncer *Syncer) SyncCheckpoint(ctx context.Context, tsk types.TipSetKey) error {
if tsk == types.EmptyTSK {
return xerrors.Errorf("called with empty tsk")
}
ts, err := syncer.ChainStore().LoadTipSet(ctx, tsk)
if err != nil {
tss, err := syncer.Exchange.GetBlocks(ctx, tsk, 1)
if err != nil {
return xerrors.Errorf("failed to fetch tipset: %w", err)
} else if len(tss) != 1 {
return xerrors.Errorf("expected 1 tipset, got %d", len(tss))
}
ts = tss[0]
}
if err := syncer.switchChain(ctx, ts); err != nil {
return xerrors.Errorf("failed to switch chain when syncing checkpoint: %w", err)
}
if err := syncer.ChainStore().SetCheckpoint(ctx, ts); err != nil {
return xerrors.Errorf("failed to set the chain checkpoint: %w", err)
}
return nil
}
func (syncer *Syncer) switchChain(ctx context.Context, ts *types.TipSet) error {
hts := syncer.ChainStore().GetHeaviestTipSet()
if hts.Equals(ts) {
return nil
}
if anc, err := syncer.store.IsAncestorOf(ctx, ts, hts); err == nil && anc {
return nil
}
// Otherwise, sync the chain and set the head.
if err := syncer.collectChain(ctx, ts, hts, true); err != nil {
return xerrors.Errorf("failed to collect chain for checkpoint: %w", err)
}
if err := syncer.ChainStore().SetHead(ctx, ts); err != nil {
return xerrors.Errorf("failed to set the chain head: %w", err)
}
return nil
}