2016-09-08 21:13:10 +04:00
|
|
|
(**************************************************************************)
|
|
|
|
(* *)
|
|
|
|
(* Copyright (c) 2014 - 2016. *)
|
|
|
|
(* Dynamic Ledger Solutions, Inc. <contact@tezos.com> *)
|
|
|
|
(* *)
|
|
|
|
(* All rights reserved. No warranty, explicit or implicit, provided. *)
|
|
|
|
(* *)
|
|
|
|
(**************************************************************************)
|
|
|
|
|
|
|
|
(* Tezos Protocol Implementation - Protocol Signature Instance *)
|
|
|
|
|
|
|
|
type operation = Tezos_context.operation
|
|
|
|
|
|
|
|
let parse_operation = Tezos_context.Operation.parse
|
|
|
|
|
|
|
|
let max_operation_data_length =
|
|
|
|
Tezos_context.Operation.max_operation_data_length
|
|
|
|
|
|
|
|
let max_number_of_operations =
|
|
|
|
Tezos_context.Constants.max_number_of_operations
|
|
|
|
|
2016-10-19 22:47:04 +04:00
|
|
|
let max_block_length =
|
2017-04-20 17:21:10 +04:00
|
|
|
Tezos_context.Block_header.max_header_length
|
2016-09-08 21:13:10 +04:00
|
|
|
|
|
|
|
let rpc_services = Services_registration.rpc_services
|
|
|
|
|
2016-10-20 20:54:16 +04:00
|
|
|
type validation_mode =
|
2017-04-26 17:01:39 +04:00
|
|
|
| Application of {
|
|
|
|
block_header : Tezos_context.Block_header.t ;
|
2017-11-06 17:12:19 +04:00
|
|
|
baker : Tezos_context.public_key_hash ;
|
2017-04-26 17:01:39 +04:00
|
|
|
}
|
|
|
|
| Partial_construction of {
|
|
|
|
predecessor : Block_hash.t ;
|
|
|
|
}
|
|
|
|
| Full_construction of {
|
|
|
|
predecessor : Block_hash.t ;
|
|
|
|
block_proto_header : Tezos_context.Block_header.proto_header ;
|
2017-11-06 17:12:19 +04:00
|
|
|
baker : Tezos_context.public_key_hash ;
|
2017-04-26 17:01:39 +04:00
|
|
|
}
|
2016-10-20 20:54:16 +04:00
|
|
|
|
|
|
|
type validation_state =
|
|
|
|
{ mode : validation_mode ;
|
|
|
|
ctxt : Tezos_context.t ;
|
|
|
|
op_count : int }
|
|
|
|
|
|
|
|
let current_context { ctxt } =
|
2017-04-10 14:14:11 +04:00
|
|
|
return (Tezos_context.finalize ctxt).context
|
2016-10-20 20:54:16 +04:00
|
|
|
|
|
|
|
let precheck_block
|
|
|
|
~ancestor_context:_
|
|
|
|
~ancestor_timestamp:_
|
|
|
|
raw_block =
|
2017-04-20 17:21:10 +04:00
|
|
|
Lwt.return (Tezos_context.Block_header.parse raw_block) >>=? fun _ ->
|
2016-10-20 20:54:16 +04:00
|
|
|
(* TODO: decide what other properties should be checked *)
|
|
|
|
return ()
|
|
|
|
|
|
|
|
let begin_application
|
|
|
|
~predecessor_context:ctxt
|
|
|
|
~predecessor_timestamp:pred_timestamp
|
2017-04-10 14:14:11 +04:00
|
|
|
~predecessor_fitness:pred_fitness
|
2016-10-20 20:54:16 +04:00
|
|
|
raw_block =
|
2017-04-26 17:01:39 +04:00
|
|
|
Lwt.return (Tezos_context.Block_header.parse raw_block) >>=? fun block_header ->
|
|
|
|
let level = block_header.shell.level in
|
2017-04-10 15:01:22 +04:00
|
|
|
let fitness = pred_fitness in
|
2017-04-26 17:01:39 +04:00
|
|
|
let timestamp = block_header.shell.timestamp in
|
2017-04-10 15:01:22 +04:00
|
|
|
Tezos_context.init ~level ~timestamp ~fitness ctxt >>=? fun ctxt ->
|
2017-04-26 17:01:39 +04:00
|
|
|
Apply.begin_application
|
2017-11-06 17:12:19 +04:00
|
|
|
ctxt block_header pred_timestamp >>=? fun (ctxt, baker) ->
|
|
|
|
let mode = Application { block_header ; baker } in
|
2016-10-20 20:54:16 +04:00
|
|
|
return { mode ; ctxt ; op_count = 0 }
|
|
|
|
|
|
|
|
let begin_construction
|
|
|
|
~predecessor_context:ctxt
|
2017-04-26 17:01:39 +04:00
|
|
|
~predecessor_timestamp:pred_timestamp
|
2017-04-10 15:01:22 +04:00
|
|
|
~predecessor_level:pred_level
|
2017-04-10 14:14:11 +04:00
|
|
|
~predecessor_fitness:pred_fitness
|
2017-04-26 17:01:39 +04:00
|
|
|
~predecessor
|
|
|
|
~timestamp
|
|
|
|
?proto_header
|
|
|
|
() =
|
2017-11-13 19:34:00 +04:00
|
|
|
let level = Int32.succ pred_level in
|
2017-04-10 15:01:22 +04:00
|
|
|
let fitness = pred_fitness in
|
|
|
|
Tezos_context.init ~timestamp ~level ~fitness ctxt >>=? fun ctxt ->
|
2017-04-26 17:01:39 +04:00
|
|
|
begin
|
|
|
|
match proto_header with
|
|
|
|
| None ->
|
|
|
|
Apply.begin_partial_construction ctxt >>=? fun ctxt ->
|
|
|
|
let mode = Partial_construction { predecessor } in
|
|
|
|
return (mode, ctxt)
|
|
|
|
| Some proto_header ->
|
|
|
|
Apply.begin_full_construction
|
|
|
|
ctxt pred_timestamp
|
2017-11-06 17:12:19 +04:00
|
|
|
proto_header >>=? fun (ctxt, block_proto_header, baker) ->
|
2017-04-26 17:01:39 +04:00
|
|
|
let mode =
|
2017-11-06 17:12:19 +04:00
|
|
|
Full_construction { predecessor ; baker ; block_proto_header } in
|
2017-04-26 17:01:39 +04:00
|
|
|
return (mode, ctxt)
|
|
|
|
end >>=? fun (mode, ctxt) ->
|
2016-10-20 20:54:16 +04:00
|
|
|
return { mode ; ctxt ; op_count = 0 }
|
|
|
|
|
|
|
|
let apply_operation ({ mode ; ctxt ; op_count } as data) operation =
|
2017-11-06 17:12:19 +04:00
|
|
|
let pred_block, block_prio, baker_contract =
|
2016-10-20 20:54:16 +04:00
|
|
|
match mode with
|
2017-04-26 17:01:39 +04:00
|
|
|
| Partial_construction { predecessor } ->
|
|
|
|
predecessor, 0, None
|
|
|
|
| Application
|
2017-11-06 17:12:19 +04:00
|
|
|
{ baker ; block_header = { shell = { predecessor } ;
|
2017-04-26 17:01:39 +04:00
|
|
|
proto = block_proto_header } }
|
2017-11-06 17:12:19 +04:00
|
|
|
| Full_construction { predecessor ; block_proto_header ; baker } ->
|
2017-04-26 17:01:39 +04:00
|
|
|
predecessor,
|
|
|
|
block_proto_header.priority,
|
2017-11-06 17:12:19 +04:00
|
|
|
Some (Tezos_context.Contract.default_contract baker) in
|
2016-10-20 20:54:16 +04:00
|
|
|
Apply.apply_operation
|
2017-11-06 17:12:19 +04:00
|
|
|
ctxt baker_contract pred_block block_prio operation
|
2016-10-20 20:54:16 +04:00
|
|
|
>>=? fun (ctxt, _contracts, _ignored_script_error) ->
|
|
|
|
let op_count = op_count + 1 in
|
|
|
|
return { data with ctxt ; op_count }
|
|
|
|
|
|
|
|
let finalize_block { mode ; ctxt ; op_count } = match mode with
|
2017-04-26 17:01:39 +04:00
|
|
|
| Partial_construction _ ->
|
2017-04-10 14:14:11 +04:00
|
|
|
let ctxt = Tezos_context.finalize ctxt in
|
2016-10-20 20:54:16 +04:00
|
|
|
return ctxt
|
2017-04-26 17:01:39 +04:00
|
|
|
| Application
|
2017-11-06 17:12:19 +04:00
|
|
|
{ baker ; block_header = { proto = block_proto_header } }
|
|
|
|
| Full_construction { block_proto_header ; baker } ->
|
|
|
|
Apply.finalize_application ctxt block_proto_header baker >>=? fun ctxt ->
|
2017-04-10 15:01:22 +04:00
|
|
|
let { level } : Tezos_context.Level.t =
|
|
|
|
Tezos_context. Level.current ctxt in
|
2017-04-26 17:01:39 +04:00
|
|
|
let priority = block_proto_header.priority in
|
2017-04-10 14:14:11 +04:00
|
|
|
let level = Tezos_context.Raw_level.to_int32 level in
|
|
|
|
let fitness = Tezos_context.Fitness.current ctxt in
|
|
|
|
let commit_message =
|
|
|
|
Format.asprintf
|
2017-04-10 14:50:15 +04:00
|
|
|
"lvl %ld, fit %Ld, prio %d, %d ops"
|
2017-04-10 14:14:11 +04:00
|
|
|
level fitness priority op_count in
|
|
|
|
let ctxt = Tezos_context.finalize ~commit_message ctxt in
|
2016-10-20 20:54:16 +04:00
|
|
|
return ctxt
|
2016-09-08 21:13:10 +04:00
|
|
|
|
2016-10-20 20:54:16 +04:00
|
|
|
let compare_operations op1 op2 =
|
|
|
|
Apply.compare_operations op1 op2
|
2016-09-08 21:13:10 +04:00
|
|
|
|
|
|
|
let configure_sandbox = Tezos_context.configure_sandbox
|