Source file baking.ml
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
open Alpha_context
open Misc
type error +=
|
Insufficient_endorsing_power of {
endorsing_power : int;
consensus_threshold : int;
}
let () =
register_error_kind
`Permanent
~id:"baking.insufficient_endorsing_power"
~title:"Insufficient endorsing power"
~description:
"The endorsing power is insufficient to satisfy the consensus threshold."
~pp:(fun ppf (endorsing_power, consensus_threshold) ->
Format.fprintf
ppf
"The endorsing power (%d) is insufficient to satisfy the consensus \
threshold (%d)."
endorsing_power
consensus_threshold)
Data_encoding.(
obj2 (req "endorsing_power" int31) (req "consensus_threshold" int31))
(function
| Insufficient_endorsing_power {endorsing_power; consensus_threshold} ->
Some (endorsing_power, consensus_threshold)
| _ -> None)
(fun (endorsing_power, consensus_threshold) ->
Insufficient_endorsing_power {endorsing_power; consensus_threshold})
let bonus_baking_reward ctxt ~endorsing_power =
let consensus_threshold = Constants.consensus_threshold ctxt in
let baking_reward_bonus_per_slot =
Constants.baking_reward_bonus_per_slot ctxt
in
let = endorsing_power - consensus_threshold in
error_when
Compare.Int.(extra_endorsing_power < 0)
(Insufficient_endorsing_power {endorsing_power; consensus_threshold})
>>? fun () ->
Tez.(baking_reward_bonus_per_slot *? Int64.of_int extra_endorsing_power)
let baking_rights c level =
let rec f c round =
Stake_distribution.baking_rights_owner c level ~round
>>=? fun (c, _slot, (delegate, _)) ->
return (LCons (delegate, fun () -> f c (Round.succ round)))
in
f c Round.zero
let endorsing_rights (ctxt : t) level =
let consensus_committee_size = Constants.consensus_committee_size ctxt in
Slot.slot_range ~min:0 ~count:consensus_committee_size >>?= fun slots ->
List.fold_left_es
(fun (ctxt, acc) slot ->
Stake_distribution.slot_owner ctxt level slot >>=? fun (ctxt, (_, pkh)) ->
return (ctxt, (slot, pkh) :: acc))
(ctxt, [])
slots
>>=? fun (ctxt, right_owners) ->
let rights =
List.fold_left
(fun acc (slot, pkh) ->
let slots =
match Signature.Public_key_hash.Map.find pkh acc with
| None -> [slot]
| Some slots -> slot :: slots
in
Signature.Public_key_hash.Map.add pkh slots acc)
Signature.Public_key_hash.Map.empty
right_owners
in
return (ctxt, rights)
let endorsing_rights_by_first_slot ctxt level =
Slot.slot_range ~min:0 ~count:(Constants.consensus_committee_size ctxt)
>>?= fun slots ->
List.fold_left_es
(fun (ctxt, (delegates_map, slots_map)) slot ->
Stake_distribution.slot_owner ctxt level slot
>|=? fun (ctxt, (pk, pkh)) ->
let (initial_slot, delegates_map) =
match Signature.Public_key_hash.Map.find pkh delegates_map with
| None ->
(slot, Signature.Public_key_hash.Map.add pkh slot delegates_map)
| Some initial_slot -> (initial_slot, delegates_map)
in
let slots_map =
Slot.Map.update
initial_slot
(function
| None -> Some (pk, pkh, 1)
| Some (pk, pkh, count) -> Some (pk, pkh, count + 1))
slots_map
in
(ctxt, (delegates_map, slots_map)))
(ctxt, (Signature.Public_key_hash.Map.empty, Slot.Map.empty))
slots
>>=? fun (ctxt, (_, slots_map)) -> return (ctxt, slots_map)