diff --git a/src/proto_alpha/lib_delegate/baking_actions.ml b/src/proto_alpha/lib_delegate/baking_actions.ml index 59346da12915e615d3f68fc2b648582cad4997e9..b6464b02fc13c4671ac53645c227a06f1fb29cc7 100644 --- a/src/proto_alpha/lib_delegate/baking_actions.ml +++ b/src/proto_alpha/lib_delegate/baking_actions.ml @@ -919,6 +919,10 @@ let prepare_waiting_for_quorum state = level_watched = latest_proposal.shell.level; round_watched = latest_proposal.round; payload_hash_watched = latest_proposal.payload_hash; + branch_watched = + (if state.global_state.constants.parametric.aggregate_attestation then + Some latest_proposal.grandparent + else None); } in (consensus_threshold, get_slot_voting_power, candidate) diff --git a/src/proto_alpha/lib_delegate/baking_lib.ml b/src/proto_alpha/lib_delegate/baking_lib.ml index 8c241ee2186d73e9a9d77e5431bf3ef763e28618..af3021f99cbb14a054da176568af17c22fe4e6d1 100644 --- a/src/proto_alpha/lib_delegate/baking_lib.ml +++ b/src/proto_alpha/lib_delegate/baking_lib.ml @@ -413,6 +413,12 @@ let propose (cctxt : Protocol_client_context.full) ?minimal_fees level_watched = latest_proposal.shell.level; round_watched = latest_proposal.round; payload_hash_watched = latest_proposal.payload_hash; + branch_watched = + (if + state.global_state.constants.parametric + .aggregate_attestation + then Some latest_proposal.grandparent + else None); } in let* state = diff --git a/src/proto_alpha/lib_delegate/baking_state.ml b/src/proto_alpha/lib_delegate/baking_state.ml index 20a95f3dd5d1cd8b1bcf055dad2ee8067aef2bbe..7a0228cd31a31a32724c330aab363781af3a394a 100644 --- a/src/proto_alpha/lib_delegate/baking_state.ml +++ b/src/proto_alpha/lib_delegate/baking_state.ml @@ -152,6 +152,7 @@ type block_info = { prequorum : prequorum option; quorum : Kind.attestation operation list; payload : Operation_pool.payload; + grandparent : Block_hash.t; } type cache = { @@ -189,6 +190,7 @@ let block_info_encoding = prequorum; quorum; payload; + grandparent; } -> ( hash, shell, @@ -197,7 +199,8 @@ let block_info_encoding = round, prequorum, List.map Operation.pack quorum, - payload )) + payload, + grandparent )) (fun ( hash, shell, payload_hash, @@ -205,10 +208,12 @@ let block_info_encoding = round, prequorum, quorum, - payload ) -> + payload, + grandparent ) -> { hash; shell; + grandparent; payload_hash; payload_round; round; @@ -216,7 +221,7 @@ let block_info_encoding = quorum = List.filter_map Operation_pool.unpack_attestation quorum; payload; }) - (obj8 + (obj9 (req "hash" Block_hash.encoding) (req "shell" Block_header.shell_header_encoding) (req "payload_hash" Block_payload_hash.encoding) @@ -224,7 +229,8 @@ let block_info_encoding = (req "round" Round.encoding) (req "prequorum" (option prequorum_encoding)) (req "quorum" (list (dynamic_size Operation.encoding))) - (req "payload" Operation_pool.payload_encoding)) + (req "payload" Operation_pool.payload_encoding) + (req "grandparent" Block_hash.encoding)) module SlotMap : Map.S with type key = Slot.t = Map.Make (Slot) @@ -1233,6 +1239,7 @@ let pp_block_info fmt { hash; shell; + grandparent = _; payload_hash; round; prequorum; diff --git a/src/proto_alpha/lib_delegate/baking_state.mli b/src/proto_alpha/lib_delegate/baking_state.mli index 6ce42effd2a70e481607107cf8e0aa1278e3e71e..6dd99f47911fdab84eb64c0a52e32a4cae3c67bb 100644 --- a/src/proto_alpha/lib_delegate/baking_state.mli +++ b/src/proto_alpha/lib_delegate/baking_state.mli @@ -275,6 +275,7 @@ type block_info = { prequorum : prequorum option; quorum : Kind.attestation operation list; payload : Operation_pool.payload; + grandparent : Block_hash.t; } val block_info_encoding : block_info Data_encoding.t diff --git a/src/proto_alpha/lib_delegate/node_rpc.ml b/src/proto_alpha/lib_delegate/node_rpc.ml index 2bd8ec0dfbf3367fff9bcda2d5c6c05ddd0e84f7..eb004bb38d5a3ee623e36f3b5e208913b4dc2991 100644 --- a/src/proto_alpha/lib_delegate/node_rpc.ml +++ b/src/proto_alpha/lib_delegate/node_rpc.ml @@ -86,7 +86,8 @@ let extract_prequorum preattestations = } | _ -> None -let info_of_header_and_ops ~in_protocol block_hash block_header operations = +let info_of_header_and_ops ~in_protocol ~grandparent block_hash block_header + operations = let open Result_syntax in let shell = block_header.Tezos_base.Block_header.shell in let dummy_payload_hash = Block_payload_hash.zero in @@ -131,10 +132,11 @@ let info_of_header_and_ops ~in_protocol block_hash block_header operations = prequorum; quorum; payload; + grandparent; } let compute_block_info cctxt ~in_protocol ?operations ~chain block_hash - block_header = + ~grandparent block_header = let open Lwt_result_syntax in (let* operations = match operations with @@ -188,7 +190,12 @@ let compute_block_info cctxt ~in_protocol ?operations ~chain block_hash operations) in let*? block_info = - info_of_header_and_ops ~in_protocol block_hash block_header operations + info_of_header_and_ops + ~in_protocol + ~grandparent + block_hash + block_header + operations in return block_info) [@profiler.record_s @@ -253,10 +260,28 @@ let proposal cctxt ?(cache : block_info Block_cache.t option) ?operations ~chain raw_header_b [@profiler.record_f {verbosity = Info} "parse pred block header"]) in + let* grandparent = + let* raw_header = + Shell_services.Blocks.raw_header + cctxt + ~chain + ~block:(`Hash (predecessor_header.shell.predecessor, 0)) + () + in + let header = + (Data_encoding.Binary.of_bytes_exn + Tezos_base.Block_header.encoding + raw_header + [@profiler.record_f + {verbosity = Info} "parse grandparent block header"]) + in + return header.shell.predecessor + in compute_block_info cctxt ~in_protocol ~chain + ~grandparent predecessor_hash predecessor_header in @@ -295,6 +320,7 @@ let proposal cctxt ?(cache : block_info Block_cache.t option) ?operations ~chain ~in_protocol:is_proposal_in_protocol ?operations ~chain + ~grandparent:predecessor.shell.predecessor block_hash block_header in diff --git a/src/proto_alpha/lib_delegate/operation_worker.ml b/src/proto_alpha/lib_delegate/operation_worker.ml index ffb9ce8fab173ca964deb7637026f7a03b54d6ee..8222c9c9e5423517b65f99ba2851448007fe7542 100644 --- a/src/proto_alpha/lib_delegate/operation_worker.ml +++ b/src/proto_alpha/lib_delegate/operation_worker.ml @@ -178,20 +178,32 @@ type candidate = { level_watched : Int32.t; round_watched : Round.t; payload_hash_watched : Block_payload_hash.t; + branch_watched : Block_hash.t option; } let candidate_encoding = let open Data_encoding in conv - (fun {hash; level_watched; round_watched; payload_hash_watched} -> - (hash, level_watched, round_watched, payload_hash_watched)) - (fun (hash, level_watched, round_watched, payload_hash_watched) -> - {hash; level_watched; round_watched; payload_hash_watched}) - (obj4 + (fun { + hash; + level_watched; + round_watched; + payload_hash_watched; + branch_watched; + } -> + (hash, level_watched, round_watched, payload_hash_watched, branch_watched)) + (fun ( hash, + level_watched, + round_watched, + payload_hash_watched, + branch_watched ) -> + {hash; level_watched; round_watched; payload_hash_watched; branch_watched}) + (obj5 (req "hash" Block_hash.encoding) (req "level_watched" int32) (req "round_watched" Round.encoding) - (req "payload_hash_watched" Block_payload_hash.encoding)) + (req "payload_hash_watched" Block_payload_hash.encoding) + (req "branch_watched" (option Block_hash.encoding))) type event = | Prequorum_reached of candidate * Kind.preattestation operation list @@ -340,8 +352,14 @@ let make_initial_state ?(monitor_node_operations = true) ~constants () = committee_size; } -let is_valid_consensus_content (candidate : candidate) consensus_content = - let {hash = _; level_watched; round_watched; payload_hash_watched} = +let is_eligible (candidate : candidate) branch consensus_content = + let { + hash = _; + level_watched; + round_watched; + payload_hash_watched; + branch_watched; + } = candidate in Int32.equal (Raw_level.to_int32 consensus_content.level) level_watched @@ -349,6 +367,10 @@ let is_valid_consensus_content (candidate : candidate) consensus_content = && Block_payload_hash.equal consensus_content.block_payload_hash payload_hash_watched + && Option.fold + ~none:true + ~some:(fun branch' -> Block_hash.(branch = branch')) + branch_watched let cancel_monitoring state = state.proposal_watched <- None @@ -400,10 +422,10 @@ let update_pqc_monitoring ~pqc_watched ops = | ({ protocol_data = {contents = Single (Preattestation consensus_content); _}; - _; + shell = {branch}; } as op : Kind.preattestation Operation.t) -> ( - if is_valid_consensus_content candidate_watched consensus_content then + if is_eligible candidate_watched branch consensus_content then match get_slot_voting_power ~slot:consensus_content.slot with | Some op_power -> pqc_watched.preattestations_received <- @@ -454,10 +476,10 @@ let update_qc_monitoring ~qc_watched ops = | ({ protocol_data = {contents = Single (Attestation {consensus_content; _}); _}; - _; + shell = {branch}; } as op : Kind.attestation Operation.t) -> ( - if is_valid_consensus_content candidate_watched consensus_content then + if is_eligible candidate_watched branch consensus_content then match get_slot_voting_power ~slot:consensus_content.slot with | Some op_power -> qc_watched.attestations_received <- diff --git a/src/proto_alpha/lib_delegate/operation_worker.mli b/src/proto_alpha/lib_delegate/operation_worker.mli index 295eafeddc6c6760e5309e3351d318b0da090228..944bfbd54fb98cba72f247e0cc8f089603c6fb23 100644 --- a/src/proto_alpha/lib_delegate/operation_worker.mli +++ b/src/proto_alpha/lib_delegate/operation_worker.mli @@ -44,6 +44,7 @@ type candidate = { level_watched : Int32.t; round_watched : Round.t; payload_hash_watched : Block_payload_hash.t; + branch_watched : Block_hash.t option; } val candidate_encoding : candidate Data_encoding.t diff --git a/src/proto_alpha/lib_delegate/state_transitions.ml b/src/proto_alpha/lib_delegate/state_transitions.ml index ae70c3298bbd863b963d4123b92b533740c02d70..7c99ec4c643123e6bc1e4b09e4f90d2991b56f42 100644 --- a/src/proto_alpha/lib_delegate/state_transitions.ml +++ b/src/proto_alpha/lib_delegate/state_transitions.ml @@ -554,7 +554,7 @@ let prepare_block_to_bake ~attestations ?last_proposal Operation_pool.level = predecessor.shell.level; round = predecessor.round; payload_hash = predecessor.payload_hash; - branch = get_branch_from_proposal state.level_state.latest_proposal; + branch = predecessor.grandparent; } in let aggregate_attestation_feature_flag = @@ -660,7 +660,7 @@ let propose_block_action state delegate round ~last_proposal = Operation_pool.level = proposal.predecessor.shell.level; round = proposal.predecessor.round; payload_hash = proposal.predecessor.payload_hash; - branch = get_branch_from_proposal state.level_state.latest_proposal; + branch = proposal.predecessor.grandparent; } in let preattestation_filter = @@ -669,8 +669,7 @@ let propose_block_action state delegate round ~last_proposal = Operation_pool.level = prequorum.level; round = prequorum.round; payload_hash = prequorum.block_payload_hash; - branch = - get_branch_from_proposal state.level_state.latest_proposal; + branch = proposal.predecessor.shell.predecessor; } in let aggregate_attestation_feature_flag =