-
Notifications
You must be signed in to change notification settings - Fork 210
/
util.go
137 lines (116 loc) · 2.49 KB
/
util.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
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
package tortoise
import (
"fmt"
"github.com/spacemeshos/go-spacemesh/common/types"
"github.com/spacemeshos/go-spacemesh/common/util"
"github.com/spacemeshos/go-spacemesh/log"
)
const (
verifyingTortoise = "verifying"
fullTortoise = "full"
)
const (
support sign = 1
against sign = -1
abstain sign = 0
)
type sign int8
func (a sign) String() string {
switch a {
case 1:
return "support"
case -1:
return "against"
case 0:
return "abstain"
default:
panic("sign should be 0/-1/1")
}
}
type votes map[types.BlockID]sign
type tortoiseBallot struct {
id, base types.BallotID
votes votes
abstain map[types.LayerID]struct{}
weight util.Weight
}
func persistContextualValidity(logger log.Log,
updater blockValidityUpdater,
from, to types.LayerID,
blocks map[types.LayerID][]types.BlockID,
opinion votes,
) error {
var err error
iterateLayers(from.Add(1), to, func(lid types.LayerID) bool {
for _, bid := range blocks[lid] {
sign := opinion[bid]
if sign == abstain {
logger.With().Panic("bug: layer should not be verified if there is an undecided block", lid, bid)
}
err = updater.UpdateBlockValidity(bid, lid, sign == support)
if err != nil {
err = fmt.Errorf("saving validity for %s: %w", bid, err)
return false
}
}
return true
})
return err
}
func iterateLayers(from, to types.LayerID, callback func(types.LayerID) bool) {
for lid := from; !lid.After(to); lid = lid.Add(1) {
if !callback(lid) {
return
}
}
}
type voteReason string
func (v voteReason) String() string {
return string(v)
}
const (
reasonHareOutput voteReason = "hare"
reasonValidity voteReason = "validity"
reasonLocalThreshold voteReason = "local_threshold"
reasonCoinflip voteReason = "coinflip"
)
// lsb is a mode, second bit is rerun
// examples (lsb is on the right, prefix with 6 bits is droppped)
// 10 - rerun in verifying
// 00 - live tortoise in verifying
// 11 - rerun in full
// 01 - live tortoise in full.
type mode [2]bool
func (m mode) String() string {
humanize := "verifying"
if m.isFull() {
humanize = "full"
}
if m.isRerun() {
return "rerun_" + humanize
}
return humanize
}
func (m mode) toggleRerun() mode {
m[1] = !m[1]
return m
}
func (m mode) isRerun() bool {
return m[1]
}
func (m mode) toggleMode() mode {
m[0] = !m[0]
return m
}
func (m mode) isVerifying() bool {
return !m[0]
}
func (m mode) isFull() bool {
return m[0]
}
func maxLayer(i, j types.LayerID) types.LayerID {
if i.After(j) {
return i
}
return j
}