From b4230ddb0bce4ee290b532311453e16ecbd6b83b Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Thu, 8 Dec 2022 15:40:17 +0100 Subject: [PATCH 01/10] DAL/Node: small refactoring --- src/bin_dal_node/daemon.ml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/bin_dal_node/daemon.ml b/src/bin_dal_node/daemon.ml index a753e897fe38..1eb148494004 100644 --- a/src/bin_dal_node/daemon.ml +++ b/src/bin_dal_node/daemon.ml @@ -160,8 +160,7 @@ module Handler = struct let new_slot_header ctxt = (* Monitor neighbor DAL nodes and download published slots as shards. *) let open Lwt_result_syntax in - let handler n_cctxt ready_ctxt slot_header = - let cryptobox = ready_ctxt.Node_context.cryptobox in + let handler n_cctxt Node_context.{cryptobox; _} slot_header = let dal_parameters = Cryptobox.parameters cryptobox in let downloaded_shard_ids = 0 @@ -182,7 +181,7 @@ module Handler = struct Slot_manager.save_shards (Node_context.get_store ctxt).shard_store (Node_context.get_store ctxt).slots_watcher - ready_ctxt.Node_context.cryptobox + cryptobox slot_header shards in -- GitLab From c229a677145655d4a21dd9b294b9cac3768291b2 Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Thu, 8 Dec 2022 14:06:13 +0100 Subject: [PATCH 02/10] Proto,DAL: have both of_int_opt and of_int for slots indices --- .../bin_sc_rollup_node/dal_slots_tracker.ml | 2 +- .../lib_protocol/alpha_context.mli | 4 +- src/proto_alpha/lib_protocol/dal_apply.ml | 2 +- src/proto_alpha/lib_protocol/dal_slot_repr.ml | 40 +++++++++++++++++-- .../lib_protocol/dal_slot_repr.mli | 12 +++++- .../lib_protocol/sc_rollup_arith.ml | 2 +- .../lib_protocol/test/helpers/dal_helpers.ml | 2 +- .../test/pbt/test_dal_slot_proof.ml | 5 ++- .../test/pbt/test_sc_rollup_encoding.ml | 4 +- .../lib_sc_rollup/sc_rollup_services.ml | 2 +- 10 files changed, 61 insertions(+), 14 deletions(-) diff --git a/src/proto_alpha/bin_sc_rollup_node/dal_slots_tracker.ml b/src/proto_alpha/bin_sc_rollup_node/dal_slots_tracker.ml index 3a1af0ef8950..fdf50dc71a16 100644 --- a/src/proto_alpha/bin_sc_rollup_node/dal_slots_tracker.ml +++ b/src/proto_alpha/bin_sc_rollup_node/dal_slots_tracker.ml @@ -140,7 +140,7 @@ let to_slot_index_list (constants : Constants.Parametric.t) bitset = then Dal.Slot_index.to_int will always return a defined value. See `src/proto_alpha/lib_protocol/constants_repr.ml`. *) - List.filter_map Dal.Slot_index.of_int filtered + List.filter_map Dal.Slot_index.of_int_opt filtered (* DAL/FIXME: https://gitlab.com/tezos/tezos/-/issues/4139. Use a shared storage between dal and rollup node to store slots data. diff --git a/src/proto_alpha/lib_protocol/alpha_context.mli b/src/proto_alpha/lib_protocol/alpha_context.mli index f106181b7224..96b234b5a2eb 100644 --- a/src/proto_alpha/lib_protocol/alpha_context.mli +++ b/src/proto_alpha/lib_protocol/alpha_context.mli @@ -2920,7 +2920,9 @@ module Dal : sig val encoding : t Data_encoding.t - val of_int : int -> t option + val of_int_opt : int -> t option + + val of_int : int -> t tzresult val to_int : t -> int diff --git a/src/proto_alpha/lib_protocol/dal_apply.ml b/src/proto_alpha/lib_protocol/dal_apply.ml index 7942e74f788b..833d788276ed 100644 --- a/src/proto_alpha/lib_protocol/dal_apply.ml +++ b/src/proto_alpha/lib_protocol/dal_apply.ml @@ -40,7 +40,7 @@ let only_if_dal_feature_enabled ctxt ~default f = let slot_of_int_e n = let open Result_syntax in - match Dal.Slot_index.of_int n with + match Dal.Slot_index.of_int_opt n with | None -> tzfail Dal_errors.Dal_slot_index_above_hard_limit | Some slot_index -> return slot_index diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.ml b/src/proto_alpha/lib_protocol/dal_slot_repr.ml index cf43da6693c9..17044f1f2d5c 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.ml +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.ml @@ -67,10 +67,44 @@ module Index = struct let zero = 0 + type error += Invalid_slot_index of {given : int; min : int; max : int} + + let () = + let open Data_encoding in + register_error_kind + `Permanent + ~id:"dal_slot_repr.index.invalid_index" + ~title:"Invalid Dal slot index" + ~description: + "The given index is out of range of representable slot indices" + ~pp:(fun ppf (given, min, max) -> + Format.fprintf + ppf + "The given index %d is out of range of representable slot indices \ + [%d, %d]" + given + min + max) + (obj3 (req "given" int31) (req "min" int31) (req "max" int31)) + (function + | Invalid_slot_index {given; min; max} -> Some (given, min, max) + | _ -> None) + (fun (given, min, max) -> Invalid_slot_index {given; min; max}) + + let check_is_in_range slot_index = + error_unless + Compare.Int.(slot_index >= zero && slot_index <= max_value) + (Invalid_slot_index {given = slot_index; min = zero; max = max_value}) + + let of_int_opt slot_index = + match check_is_in_range slot_index with + | Ok () -> Some slot_index + | Error _ -> None + let of_int slot_index = - if Compare.Int.(slot_index <= max_value && slot_index >= zero) then - Some slot_index - else None + let open Result_syntax in + let* () = check_is_in_range slot_index in + return slot_index let to_int slot_index = slot_index [@@ocaml.inline always] diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.mli b/src/proto_alpha/lib_protocol/dal_slot_repr.mli index b4db6978446c..14cce6fb94ab 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.mli +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.mli @@ -89,6 +89,8 @@ end module Index : sig type t + type error += Invalid_slot_index of {given : int; min : int; max : int} + val encoding : t Data_encoding.t val pp : Format.formatter -> t -> unit @@ -97,8 +99,14 @@ module Index : sig val max_value : t - (** [of_int n] constructs a`Slot_index.t` *) - val of_int : int -> t option + (** [of_int_opt n] constructs a value of type {!t} from [n]. Returns {!None} + in case the given value is not in the interval [zero, max_value]. *) + val of_int_opt : int -> t option + + (** [of_int n] constructs a value of type {!t} from [n]. Returns + {!Invalid_slot_index} in case the given value is not in the interval [zero, + max_value]. *) + val of_int : int -> t tzresult val to_int : t -> int diff --git a/src/proto_alpha/lib_protocol/sc_rollup_arith.ml b/src/proto_alpha/lib_protocol/sc_rollup_arith.ml index 55c930c3adc8..3fd65bd56cd6 100644 --- a/src/proto_alpha/lib_protocol/sc_rollup_arith.ml +++ b/src/proto_alpha/lib_protocol/sc_rollup_arith.ml @@ -1250,7 +1250,7 @@ module Make (Context : P) : let open Option_syntax in let* index = Option.map Int32.to_int @@ Int32.of_string_opt slot_str in if Compare.Int.(index < 0 || index >= number_of_slots) then None - else Dal_slot_repr.Index.of_int index + else Dal_slot_repr.Index.of_int_opt index in let mk_page_index page_str = let open Option_syntax in diff --git a/src/proto_alpha/lib_protocol/test/helpers/dal_helpers.ml b/src/proto_alpha/lib_protocol/test/helpers/dal_helpers.ml index c6624b11513c..a3e838947f89 100644 --- a/src/proto_alpha/lib_protocol/test/helpers/dal_helpers.ml +++ b/src/proto_alpha/lib_protocol/test/helpers/dal_helpers.ml @@ -142,7 +142,7 @@ struct let succ_slot_index index = Option.value_f - S.Index.(of_int (to_int index + 1)) + S.Index.(of_int_opt (to_int index + 1)) ~default:(fun () -> S.Index.zero) let next_char c = Char.(chr ((code c + 1) mod 255)) diff --git a/src/proto_alpha/lib_protocol/test/pbt/test_dal_slot_proof.ml b/src/proto_alpha/lib_protocol/test/pbt/test_dal_slot_proof.ml index 4d956049b5e4..3f708dfe1a49 100644 --- a/src/proto_alpha/lib_protocol/test/pbt/test_dal_slot_proof.ml +++ b/src/proto_alpha/lib_protocol/test/pbt/test_dal_slot_proof.ml @@ -71,8 +71,9 @@ struct (* Make and insert a slot. *) let add_slot level sindex (cell, cache, slots_info) skip_slot = let index = - Option.value_f (Dal_slot_repr.Index.of_int sindex) ~default:(fun () -> - assert false) + Option.value_f + (Dal_slot_repr.Index.of_int_opt sindex) + ~default:(fun () -> assert false) in let* _data, poly, slot = mk_slot ~level ~index () in let* cell, cache = diff --git a/src/proto_alpha/lib_protocol/test/pbt/test_sc_rollup_encoding.ml b/src/proto_alpha/lib_protocol/test/pbt/test_sc_rollup_encoding.ml index 5dcda40637de..db7af6fc4885 100644 --- a/src/proto_alpha/lib_protocol/test/pbt/test_sc_rollup_encoding.ml +++ b/src/proto_alpha/lib_protocol/test/pbt/test_sc_rollup_encoding.ml @@ -133,7 +133,9 @@ let gen_dal_slots_history () = genesis cell's level in the skip list. *) succ @@ try of_int32_exn (Int32.of_int level) with _ -> root) in - let index = Index.(of_int slot_index |> Option.value ~default:zero) in + let index = + Index.(of_int_opt slot_index |> Option.value ~default:zero) + in Header.{id = {published_level; index}; commitment = Commitment.zero}) list in diff --git a/src/proto_alpha/lib_sc_rollup/sc_rollup_services.ml b/src/proto_alpha/lib_sc_rollup/sc_rollup_services.ml index ad563962fe17..8a38c2910f6f 100644 --- a/src/proto_alpha/lib_sc_rollup/sc_rollup_services.ml +++ b/src/proto_alpha/lib_sc_rollup/sc_rollup_services.ml @@ -550,7 +550,7 @@ module Global = struct raise (Invalid (Format.asprintf "Invalid parameter (%d)" i)) in query (fun raw_index raw_page -> - let index = req "index" Dal.Slot_index.of_int raw_index in + let index = req "index" Dal.Slot_index.of_int_opt raw_index in let page = req "page" (fun p -> p) raw_page in match index with | None -> invalid_parameter @@ Option.value ~default:0 raw_index -- GitLab From ea951c1cf66503b210a1bf5278b39ca7a584ebfa Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Tue, 6 Dec 2022 14:12:52 +0100 Subject: [PATCH 03/10] Proto,DAL: add function Index.slots_range --- src/proto_alpha/lib_protocol/alpha_context.mli | 2 ++ src/proto_alpha/lib_protocol/dal_slot_repr.ml | 6 ++++++ src/proto_alpha/lib_protocol/dal_slot_repr.mli | 7 +++++++ 3 files changed, 15 insertions(+) diff --git a/src/proto_alpha/lib_protocol/alpha_context.mli b/src/proto_alpha/lib_protocol/alpha_context.mli index 96b234b5a2eb..b062e3f5a27b 100644 --- a/src/proto_alpha/lib_protocol/alpha_context.mli +++ b/src/proto_alpha/lib_protocol/alpha_context.mli @@ -2929,6 +2929,8 @@ module Dal : sig val compare : t -> t -> int val equal : t -> t -> bool + + val slots_range : lower:int -> upper:int -> t list tzresult end (** This module re-exports definitions from {!Dal_attestation_repr} and diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.ml b/src/proto_alpha/lib_protocol/dal_slot_repr.ml index 17044f1f2d5c..221ca3685dd1 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.ml +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.ml @@ -111,6 +111,12 @@ module Index = struct let compare = Compare.Int.compare let equal = Compare.Int.equal + + let slots_range ~lower ~upper = + let open Result_syntax in + let* () = check_is_in_range lower in + let* () = check_is_in_range upper in + return Misc.(lower --> upper) end module Header = struct diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.mli b/src/proto_alpha/lib_protocol/dal_slot_repr.mli index 14cce6fb94ab..8dae14f7fce0 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.mli +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.mli @@ -113,6 +113,13 @@ module Index : sig val compare : t -> t -> int val equal : t -> t -> bool + + (** [slots_range ~lower ~upper] returns the list of slots indexes between + [lower] and [upper]. + + If [lower] is negative or [upper] is bigger than [max_value], the function + returns {!Invalid_slot_index}. *) + val slots_range : lower:int -> upper:int -> t list tzresult end module Header : sig -- GitLab From af4db6fad2a122e665f7172ca72af62953b0645c Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Mon, 12 Dec 2022 17:10:18 +0100 Subject: [PATCH 04/10] Proto, Dal: also provide a function [slots_range_opt] --- src/proto_alpha/lib_protocol/alpha_context.mli | 2 ++ src/proto_alpha/lib_protocol/dal_slot_repr.ml | 10 +++++----- src/proto_alpha/lib_protocol/dal_slot_repr.mli | 4 ++++ 3 files changed, 11 insertions(+), 5 deletions(-) diff --git a/src/proto_alpha/lib_protocol/alpha_context.mli b/src/proto_alpha/lib_protocol/alpha_context.mli index b062e3f5a27b..feca51f15042 100644 --- a/src/proto_alpha/lib_protocol/alpha_context.mli +++ b/src/proto_alpha/lib_protocol/alpha_context.mli @@ -2931,6 +2931,8 @@ module Dal : sig val equal : t -> t -> bool val slots_range : lower:int -> upper:int -> t list tzresult + + val slots_range_opt : lower:int -> upper:int -> t list option end (** This module re-exports definitions from {!Dal_attestation_repr} and diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.ml b/src/proto_alpha/lib_protocol/dal_slot_repr.ml index 221ca3685dd1..a23776b35836 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.ml +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.ml @@ -96,16 +96,13 @@ module Index = struct Compare.Int.(slot_index >= zero && slot_index <= max_value) (Invalid_slot_index {given = slot_index; min = zero; max = max_value}) - let of_int_opt slot_index = - match check_is_in_range slot_index with - | Ok () -> Some slot_index - | Error _ -> None - let of_int slot_index = let open Result_syntax in let* () = check_is_in_range slot_index in return slot_index + let of_int_opt slot_index = Option.of_result @@ of_int slot_index + let to_int slot_index = slot_index [@@ocaml.inline always] let compare = Compare.Int.compare @@ -117,6 +114,9 @@ module Index = struct let* () = check_is_in_range lower in let* () = check_is_in_range upper in return Misc.(lower --> upper) + + let slots_range_opt ~lower ~upper = + Option.of_result @@ slots_range ~lower ~upper end module Header = struct diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.mli b/src/proto_alpha/lib_protocol/dal_slot_repr.mli index 8dae14f7fce0..750725f45d9b 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.mli +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.mli @@ -120,6 +120,10 @@ module Index : sig If [lower] is negative or [upper] is bigger than [max_value], the function returns {!Invalid_slot_index}. *) val slots_range : lower:int -> upper:int -> t list tzresult + + (** [slots_range_opt ~lower ~upper] is similar to {!slots_range}, but return + {None} in case of error instead of {!Invalid_slot_index}. *) + val slots_range_opt : lower:int -> upper:int -> t list option end module Header : sig -- GitLab From 25a657def68b5ab3408ad51185991398df656abb Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Fri, 9 Dec 2022 08:49:49 +0100 Subject: [PATCH 05/10] Proto: Dal: add identity function to_int_list to avoid 'List.map to_int' --- src/proto_alpha/lib_protocol/alpha_context.mli | 2 ++ src/proto_alpha/lib_protocol/dal_slot_repr.ml | 2 ++ src/proto_alpha/lib_protocol/dal_slot_repr.mli | 2 ++ 3 files changed, 6 insertions(+) diff --git a/src/proto_alpha/lib_protocol/alpha_context.mli b/src/proto_alpha/lib_protocol/alpha_context.mli index feca51f15042..55bf96a09fbe 100644 --- a/src/proto_alpha/lib_protocol/alpha_context.mli +++ b/src/proto_alpha/lib_protocol/alpha_context.mli @@ -2926,6 +2926,8 @@ module Dal : sig val to_int : t -> int + val to_int_list : t list -> int list + val compare : t -> t -> int val equal : t -> t -> bool diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.ml b/src/proto_alpha/lib_protocol/dal_slot_repr.ml index a23776b35836..05cf0e5fabcc 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.ml +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.ml @@ -105,6 +105,8 @@ module Index = struct let to_int slot_index = slot_index [@@ocaml.inline always] + let to_int_list l = l [@@ocaml.inline always] + let compare = Compare.Int.compare let equal = Compare.Int.equal diff --git a/src/proto_alpha/lib_protocol/dal_slot_repr.mli b/src/proto_alpha/lib_protocol/dal_slot_repr.mli index 750725f45d9b..29fc7d729c8d 100644 --- a/src/proto_alpha/lib_protocol/dal_slot_repr.mli +++ b/src/proto_alpha/lib_protocol/dal_slot_repr.mli @@ -110,6 +110,8 @@ module Index : sig val to_int : t -> int + val to_int_list : t list -> int list + val compare : t -> t -> int val equal : t -> t -> bool -- GitLab From eed29806a93f652ab8dd7071807c3e040a76b74f Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Wed, 7 Dec 2022 11:00:57 +0100 Subject: [PATCH 06/10] DAL/Node: pull all DAL proto parameters at once --- src/bin_dal_node/daemon.ml | 17 +++++++---- src/bin_dal_node/node_context.ml | 10 +++++-- src/bin_dal_node/node_context.mli | 18 +++++++---- src/lib_dal_node/dal_plugin.ml | 11 ++++++- src/lib_dal_node/dal_plugin.mli | 11 ++++++- .../lib_dal/dal_plugin_registration.ml | 30 +++++++++++++++++-- 6 files changed, 78 insertions(+), 19 deletions(-) diff --git a/src/bin_dal_node/daemon.ml b/src/bin_dal_node/daemon.ml index 1eb148494004..3d85f1281c69 100644 --- a/src/bin_dal_node/daemon.ml +++ b/src/bin_dal_node/daemon.ml @@ -53,18 +53,20 @@ let () = (function Cryptobox_initialisation_failed str -> Some str | _ -> None) (fun str -> Cryptobox_initialisation_failed str) -let init_cryptobox unsafe_srs cctxt (module Plugin : Dal_plugin.T) = +let init_cryptobox unsafe_srs (proto_parameters : Dal_plugin.proto_parameters) = let open Cryptobox in let open Lwt_result_syntax in - let* parameters = Plugin.get_constants cctxt#chain cctxt#block cctxt in - let srs_size = if unsafe_srs then Some parameters.slot_size else None in + let srs_size = + if unsafe_srs then Some proto_parameters.cryptobox_parameters.slot_size + else None + in let* () = let find_srs_files () = Tezos_base.Dal_srs.find_trusted_setup_files () in Cryptobox.Config.init_dal ~find_srs_files Cryptobox.Config.{activated = true; srs_size} in - match Cryptobox.make parameters with + match Cryptobox.make proto_parameters.cryptobox_parameters with | Ok cryptobox -> return cryptobox | Error (`Fail msg) -> fail [Cryptobox_initialisation_failed msg] @@ -108,10 +110,13 @@ module Handler = struct | Some plugin -> let (module Plugin : Dal_plugin.T) = plugin in let*! () = Event.emit_protocol_plugin_resolved Plugin.Proto.hash in + let* proto_parameters = + Plugin.get_constants cctxt#chain cctxt#block cctxt + in let* cryptobox = - init_cryptobox config.Configuration.use_unsafe_srs cctxt plugin + init_cryptobox config.Configuration.use_unsafe_srs proto_parameters in - Node_context.set_ready ctxt (module Plugin) cryptobox ; + Node_context.set_ready ctxt (module Plugin) cryptobox proto_parameters ; let*! () = Event.(emit node_is_ready ()) in stopper () ; return_unit diff --git a/src/bin_dal_node/node_context.ml b/src/bin_dal_node/node_context.ml index d9de1fe12869..5d3add62f7cb 100644 --- a/src/bin_dal_node/node_context.ml +++ b/src/bin_dal_node/node_context.ml @@ -25,7 +25,11 @@ exception Status_already_ready -type ready_ctxt = {cryptobox : Cryptobox.t; plugin : (module Dal_plugin.T)} +type ready_ctxt = { + cryptobox : Cryptobox.t; + proto_parameters : Dal_plugin.proto_parameters; + plugin : (module Dal_plugin.T); +} type status = Ready of ready_ctxt | Starting @@ -45,9 +49,9 @@ let init config store = in {status = Starting; config; store; neighbors_cctxts} -let set_ready ctxt plugin cryptobox = +let set_ready ctxt plugin cryptobox proto_parameters = match ctxt.status with - | Starting -> ctxt.status <- Ready {plugin; cryptobox} + | Starting -> ctxt.status <- Ready {plugin; cryptobox; proto_parameters} | Ready _ -> raise Status_already_ready type error += Node_not_ready diff --git a/src/bin_dal_node/node_context.mli b/src/bin_dal_node/node_context.mli index 3a88e2b0da7a..52cff222e954 100644 --- a/src/bin_dal_node/node_context.mli +++ b/src/bin_dal_node/node_context.mli @@ -26,7 +26,11 @@ (** A [ready_ctx] value contains globally needed informations for a running dal node. It is available when both cryptobox is initialized and dal plugin is loaded. *) -type ready_ctxt = {cryptobox : Cryptobox.t; plugin : (module Dal_plugin.T)} +type ready_ctxt = { + cryptobox : Cryptobox.t; + proto_parameters : Dal_plugin.proto_parameters; + plugin : (module Dal_plugin.T); +} (** The status of the dal node *) type status = Ready of ready_ctxt | Starting @@ -42,13 +46,17 @@ val init : Configuration.t -> Store.node_store -> t (** Raised by [set_ready] when the status is already [Ready _] *) exception Status_already_ready -(** [set_ready ctxt plugin dal_constants] updates in place the status - value to [Ready], and initializes the inner [ready_ctxt] value with the given - parameters. +(** [set_ready ctxt plugin cryptobox proto_parameters] updates in place the + status value to [Ready], and initializes the inner [ready_ctxt] value with + the given parameters. @raise Status_already_ready when the status is already [Ready _] *) val set_ready : - t -> (module Tezos_dal_node_lib.Dal_plugin.T) -> Cryptobox.t -> unit + t -> + (module Tezos_dal_node_lib.Dal_plugin.T) -> + Cryptobox.t -> + Dal_plugin.proto_parameters -> + unit type error += Node_not_ready diff --git a/src/lib_dal_node/dal_plugin.ml b/src/lib_dal_node/dal_plugin.ml index 104dbf770ceb..4d19ec104f2a 100644 --- a/src/lib_dal_node/dal_plugin.ml +++ b/src/lib_dal_node/dal_plugin.ml @@ -33,6 +33,15 @@ type slot_header = { commitment : Tezos_crypto_dal.Cryptobox.Verifier.commitment; } +type proto_parameters = { + feature_enable : bool; + number_of_slots : int; + attestation_lag : int; + availability_threshold : int; + cryptobox_parameters : Tezos_crypto_dal.Cryptobox.Verifier.parameters; + blocks_per_epoch : int32; +} + module type T = sig module Proto : Registered_protocol.T @@ -49,7 +58,7 @@ module type T = sig Tezos_shell_services.Chain_services.chain -> Tezos_shell_services.Block_services.block -> Client_context.full -> - Tezos_crypto_dal.Cryptobox.Verifier.parameters tzresult Lwt.t + proto_parameters tzresult Lwt.t val get_published_slot_headers : block_info -> diff --git a/src/lib_dal_node/dal_plugin.mli b/src/lib_dal_node/dal_plugin.mli index 3408f6ecf274..27228c83da14 100644 --- a/src/lib_dal_node/dal_plugin.mli +++ b/src/lib_dal_node/dal_plugin.mli @@ -42,6 +42,15 @@ type slot_header = { commitment : Tezos_crypto_dal.Cryptobox.Verifier.commitment; } +type proto_parameters = { + feature_enable : bool; + number_of_slots : int; + attestation_lag : int; + availability_threshold : int; + cryptobox_parameters : Tezos_crypto_dal.Cryptobox.Verifier.parameters; + blocks_per_epoch : int32; +} + module type T = sig module Proto : Registered_protocol.T @@ -62,7 +71,7 @@ module type T = sig Tezos_shell_services.Chain_services.chain -> Tezos_shell_services.Block_services.block -> Client_context.full -> - Tezos_crypto_dal.Cryptobox.Verifier.parameters tzresult Lwt.t + proto_parameters tzresult Lwt.t val get_published_slot_headers : block_info -> diff --git a/src/proto_alpha/lib_dal/dal_plugin_registration.ml b/src/proto_alpha/lib_dal/dal_plugin_registration.ml index 3308cda47b34..1dcc483636bb 100644 --- a/src/proto_alpha/lib_dal/dal_plugin_registration.ml +++ b/src/proto_alpha/lib_dal/dal_plugin_registration.ml @@ -23,16 +23,40 @@ (* *) (*****************************************************************************) +open Protocol +open Alpha_context + module Plugin = struct module Proto = Registerer.Registered type block_info = Protocol_client_context.Alpha_block_services.block_info - let get_constants chain block ctxt = + let parametric_constants chain block ctxt = let cpctxt = new Protocol_client_context.wrap_full ctxt in + Protocol.Constants_services.parametric cpctxt (chain, block) + + let get_constants chain block ctxt = let open Lwt_result_syntax in - let* constants = Protocol.Constants_services.all cpctxt (chain, block) in - return constants.parametric.dal.cryptobox_parameters + let* parametric = parametric_constants chain block ctxt in + let { + Constants.Parametric.feature_enable; + number_of_slots; + attestation_lag; + availability_threshold; + cryptobox_parameters; + blocks_per_epoch; + } = + parametric.dal + in + return + { + Dal_plugin.feature_enable; + number_of_slots; + attestation_lag; + availability_threshold; + cryptobox_parameters; + blocks_per_epoch; + } let block_info ?chain ?block ~metadata ctxt = let cpctxt = new Protocol_client_context.wrap_full ctxt in -- GitLab From 68a851c78b77a3ccf2a3ca8908c68412c73ea2eb Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Tue, 6 Dec 2022 17:34:54 +0100 Subject: [PATCH 07/10] DAL/Plugin: add a new function slots_headers_attestation --- src/lib_dal_node/dal_plugin.ml | 7 ++++++ src/lib_dal_node/dal_plugin.mli | 15 ++++++++++++ .../lib_dal/dal_plugin_registration.ml | 23 +++++++++++++++++++ 3 files changed, 45 insertions(+) diff --git a/src/lib_dal_node/dal_plugin.ml b/src/lib_dal_node/dal_plugin.ml index 4d19ec104f2a..ad53881fa509 100644 --- a/src/lib_dal_node/dal_plugin.ml +++ b/src/lib_dal_node/dal_plugin.ml @@ -64,6 +64,13 @@ module type T = sig block_info -> (slot_header * operation_application_result) list tzresult Lwt.t + val slot_headers_attestation : + Tezos_crypto.Block_hash.t -> + block_info -> + number_of_slots:int -> + ([`Attested of slot_index list] * [`Unattested of slot_index list]) tzresult + Lwt.t + module RPC : sig val rpc_services : reveal_data_dir:string -> diff --git a/src/lib_dal_node/dal_plugin.mli b/src/lib_dal_node/dal_plugin.mli index 27228c83da14..f8e69d05e75f 100644 --- a/src/lib_dal_node/dal_plugin.mli +++ b/src/lib_dal_node/dal_plugin.mli @@ -77,6 +77,21 @@ module type T = sig block_info -> (slot_header * operation_application_result) list tzresult Lwt.t + (** [slot_headers_attestation hash block_info number_of_slots] reads the + metadata of the given [block_info] and constructs two lists of attested + and unattested slots depending on the value of dal_attestation bitset. + The value of [number_of_slots] indicates the current maximum number of + slots on DAL per level. + + Fails with [Cannot_read_block_metadata] if [block_info]'s metadata are + stripped. *) + val slot_headers_attestation : + Tezos_crypto.Block_hash.t -> + block_info -> + number_of_slots:int -> + ([`Attested of slot_index list] * [`Unattested of slot_index list]) tzresult + Lwt.t + module RPC : sig val rpc_services : reveal_data_dir:string -> diff --git a/src/proto_alpha/lib_dal/dal_plugin_registration.ml b/src/proto_alpha/lib_dal/dal_plugin_registration.ml index 1dcc483636bb..6fe57fff1d28 100644 --- a/src/proto_alpha/lib_dal/dal_plugin_registration.ml +++ b/src/proto_alpha/lib_dal/dal_plugin_registration.ml @@ -99,6 +99,29 @@ module Plugin = struct }, status )) + let slot_headers_attestation hash (block : block_info) ~number_of_slots = + let open Lwt_result_syntax in + let*? metadata = + Option.to_result + block.metadata + ~none:(TzTrace.make @@ Layer1_services.Cannot_read_block_metadata hash) + in + let confirmed_slots = + Option.value + ~default:Dal.Attestation.empty + metadata.protocol_data.dal_attestation + in + let*? all_slots = + Dal.Slot_index.slots_range ~lower:0 ~upper:(number_of_slots - 1) + |> Environment.wrap_tzresult + in + let attested, unattested = + List.partition (Dal.Attestation.is_attested confirmed_slots) all_slots + in + return + ( `Attested (Dal.Slot_index.to_int_list attested), + `Unattested (Dal.Slot_index.to_int_list unattested) ) + module RPC = RPC end -- GitLab From f88ee83453f61bf3fb55651d674ad52ba7dba891 Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Thu, 8 Dec 2022 15:54:30 +0100 Subject: [PATCH 08/10] DAL, node: add an assert for an invariant that should hold. --- src/bin_dal_node/store.ml | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/bin_dal_node/store.ml b/src/bin_dal_node/store.ml index e455b8cd5536..4b3f84ad1d27 100644 --- a/src/bin_dal_node/store.ml +++ b/src/bin_dal_node/store.ml @@ -219,7 +219,7 @@ module Legacy = struct Lwt.return_unit) slot_headers - let add_slot_headers ~block_level:_ ~block_hash slot_headers node_store = + let add_slot_headers ~block_level ~block_hash slot_headers node_store = let open Lwt_syntax in let* () = legacy_add_slot_headers ~block_hash slot_headers node_store in let slots_store = node_store.slots_store in @@ -232,6 +232,8 @@ module Legacy = struct let Dal_plugin.{slot_index; commitment; published_level} = slot_header in + (* This invariant should hold. *) + assert (Int32.equal published_level block_level) ; match status with | Dal_plugin.Succeeded -> let index = -- GitLab From 9b1f07fcd33f9c0802902bb627552fbc76344af7 Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Fri, 9 Dec 2022 09:19:38 +0100 Subject: [PATCH 09/10] DAL/Node: add a function Path.to_string --- src/bin_dal_node/store.ml | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/src/bin_dal_node/store.ml b/src/bin_dal_node/store.ml index 4b3f84ad1d27..ddea4f2187f2 100644 --- a/src/bin_dal_node/store.ml +++ b/src/bin_dal_node/store.ml @@ -74,6 +74,8 @@ module Legacy = struct module Path : sig type t = string list + val to_string : ?prefix:string -> t -> string + module Commitment : sig val slot : Cryptobox.commitment -> slot_size:int -> Path.t @@ -106,6 +108,10 @@ module Legacy = struct let ( / ) b a = a :: b + let to_string ?prefix p = + let s = String.concat "/" p in + Option.fold ~none:s ~some:(fun pr -> pr ^ s) prefix + module Commitment = struct let root = ["commitments"] @@ -249,18 +255,13 @@ module Legacy = struct let* () = set ~msg: - (Printf.sprintf - "add_slot_headers:%s" - (String.concat "/" commitment_path)) + (Path.to_string ~prefix:"add_slot_headers:" commitment_path) slots_store commitment_path data in set - ~msg: - (Printf.sprintf - "add_slot_headers:%s" - (String.concat "/" status_path)) + ~msg:(Path.to_string ~prefix:"add_slot_headers:" status_path) slots_store status_path (Services.Types.header_attestation_status_to_string @@ -271,7 +272,7 @@ module Legacy = struct in let path = Path.Level.other_header_status index commitment in set - ~msg:"add_slot_headers:others:status" + ~msg:(Path.to_string ~prefix:"add_slot_headers:" path) slots_store path (Services.Types.header_status_to_string `Not_selected)) -- GitLab From a4aa4ed1caa6e76221cbfee1a50748785f86bdb6 Mon Sep 17 00:00:00 2001 From: "iguerNL@Functori" Date: Thu, 8 Dec 2022 15:40:23 +0100 Subject: [PATCH 10/10] DAL/Node: track attestation of selected slots headers on L1 --- src/bin_dal_node/daemon.ml | 16 ++++++++- src/bin_dal_node/slot_manager.ml | 9 +++++ src/bin_dal_node/slot_manager.mli | 17 +++++++++ src/bin_dal_node/store.ml | 57 +++++++++++++++++++++++++++++++ 4 files changed, 98 insertions(+), 1 deletion(-) diff --git a/src/bin_dal_node/daemon.ml b/src/bin_dal_node/daemon.ml index 3d85f1281c69..3fe6f2b00efb 100644 --- a/src/bin_dal_node/daemon.ml +++ b/src/bin_dal_node/daemon.ml @@ -138,7 +138,7 @@ module Handler = struct let handler _stopper (block_hash, (header : Tezos_base.Block_header.t)) = match Node_context.get_status ctxt with | Starting -> return_unit - | Ready {plugin = (module Plugin); _} -> + | Ready {plugin = (module Plugin); proto_parameters; _} -> let* block_info = Plugin.block_info cctxt @@ -153,6 +153,20 @@ module Handler = struct slot_headers (Node_context.get_store ctxt) in + let* attested_slots, unattested_slots = + Plugin.slot_headers_attestation + block_hash + block_info + ~number_of_slots:proto_parameters.number_of_slots + in + let* () = + Slot_manager.update_selected_slot_headers_statuses + ~block_level:header.shell.level + ~attestation_lag:proto_parameters.attestation_lag + attested_slots + unattested_slots + (Node_context.get_store ctxt) + in return_unit in let*! () = Event.(emit layer1_node_tracking_started ()) in diff --git a/src/bin_dal_node/slot_manager.ml b/src/bin_dal_node/slot_manager.ml index d6e1b704073d..10db4d5ed29e 100644 --- a/src/bin_dal_node/slot_manager.ml +++ b/src/bin_dal_node/slot_manager.ml @@ -99,3 +99,12 @@ let find_slot node_store cryptobox commitment = let store_slot_headers ~block_level ~block_hash slot_headers node_store = Store.Legacy.add_slot_headers ~block_level ~block_hash slot_headers node_store + +let update_selected_slot_headers_statuses ~block_level ~attestation_lag + attested_slots unattested_slots node_store = + Store.Legacy.update_selected_slot_headers_statuses + ~block_level + attested_slots + unattested_slots + node_store + ~attestation_lag diff --git a/src/bin_dal_node/slot_manager.mli b/src/bin_dal_node/slot_manager.mli index ef7b195eedc2..147c333b7378 100644 --- a/src/bin_dal_node/slot_manager.mli +++ b/src/bin_dal_node/slot_manager.mli @@ -76,3 +76,20 @@ val store_slot_headers : (Dal_plugin.slot_header * Dal_plugin.operation_application_result) list -> Store.node_store -> unit Lwt.t + +(** [update_selected_slot_headers_statuses ~block_level ~attestation_lag + attested_slots unattested_slots store] updates the statuses of the + previously selected slots at level [block_level] - [endorsement_lag] and + that were waiting for attestation. + + Slot headers whose indexes are in [attested_slots] are now set as + {!`Attested} in [store]. Those in [unattested_slots] are marked as + {!`Unattested} in the [store]. +*) +val update_selected_slot_headers_statuses : + block_level:int32 -> + attestation_lag:int -> + [`Attested of Dal_plugin.slot_index list] -> + [`Unattested of Dal_plugin.slot_index list] -> + Store.node_store -> + unit tzresult Lwt.t diff --git a/src/bin_dal_node/store.ml b/src/bin_dal_node/store.ml index ddea4f2187f2..ef56927d665c 100644 --- a/src/bin_dal_node/store.ml +++ b/src/bin_dal_node/store.ml @@ -45,6 +45,8 @@ let info message = let set ~msg store path v = set_exn store path v ~info:(fun () -> info msg) +let remove ~msg store path = remove_exn store path ~info:(fun () -> info msg) + (** Store context *) type node_store = { slots_store : t; @@ -277,4 +279,59 @@ module Legacy = struct path (Services.Types.header_status_to_string `Not_selected)) slot_headers + + let check_old_stored_value_is ?old_value ~path store : unit tzresult Lwt.t = + let open Lwt_result_syntax in + let*! data_opt = find store path in + let* data = + match data_opt with + | Some data -> return data + | None -> + failwith + "check_old_value_is: No data found under %s" + (Path.to_string path) + in + match old_value with + | None -> return_unit + | Some expected -> + if String.equal expected data then return_unit + else + failwith "check_old_value_is: expecting %s but got %s" expected data + + let update_slot_headers_attestation ~published_level store slots = + let open Lwt_result_syntax in + let attestation_status, slots = + match slots with + | `Attested l -> (`Attested, l) + | `Unattested l -> (`Unattested, l) + in + let attestation_status = + Services.Types.header_attestation_status_to_string attestation_status + in + let old_value = + Services.Types.header_attestation_status_to_string + `Waiting_for_attestations + in + List.iter_es + (fun slot_index -> + let index = Services.Types.{slot_level = published_level; slot_index} in + let status_path = Path.Level.accepted_header_status index in + let* () = + check_old_stored_value_is ~old_value ~path:status_path store + in + let msg = + Path.to_string ~prefix:"update_slot_headers_attestation:" status_path + in + let*! () = remove ~msg store status_path in + let*! () = set ~msg store status_path attestation_status in + return_unit) + slots + + let update_selected_slot_headers_statuses ~block_level ~attestation_lag + attested unattested node_store = + let open Lwt_result_syntax in + let store = node_store.slots_store in + let published_level = Int32.(sub block_level (of_int attestation_lag)) in + let* () = update_slot_headers_attestation ~published_level store attested in + update_slot_headers_attestation ~published_level store unattested end -- GitLab