diff --git a/Cargo.lock b/Cargo.lock index 4cfee86d64..51e4866c37 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2576,7 +2576,6 @@ name = "itp-ocall-api" version = "0.8.0" dependencies = [ "itp-types", - "its-primitives", "parity-scale-codec", "sgx_types", "sp-runtime", diff --git a/core-primitives/enclave-api/src/lib.rs b/core-primitives/enclave-api/src/lib.rs index 9e513f0738..b69716029a 100644 --- a/core-primitives/enclave-api/src/lib.rs +++ b/core-primitives/enclave-api/src/lib.rs @@ -21,7 +21,7 @@ pub mod enclave_base; pub mod enclave_test; pub mod error; pub mod remote_attestation; -pub mod side_chain; +pub mod sidechain; pub mod teerex_api; pub mod utils; diff --git a/core-primitives/enclave-api/src/side_chain.rs b/core-primitives/enclave-api/src/sidechain.rs similarity index 96% rename from core-primitives/enclave-api/src/side_chain.rs rename to core-primitives/enclave-api/src/sidechain.rs index 9f4cea88c6..d2c7002064 100644 --- a/core-primitives/enclave-api/src/side_chain.rs +++ b/core-primitives/enclave-api/src/sidechain.rs @@ -24,7 +24,7 @@ use sgx_types::sgx_status_t; use sp_runtime::{generic::SignedBlock, traits::Block}; /// trait for handling blocks on the side chain -pub trait SideChain: Send + Sync + 'static { +pub trait Sidechain: Send + Sync + 'static { /// Sync parentchain blocks and execute pending tops in the enclave fn sync_parentchain( &self, @@ -37,7 +37,7 @@ pub trait SideChain: Send + Sync + 'static { fn execute_trusted_calls(&self) -> EnclaveResult<()>; } -impl SideChain for Enclave { +impl Sidechain for Enclave { fn sync_parentchain( &self, blocks: &[SignedBlock], diff --git a/core-primitives/ocall-api/Cargo.toml b/core-primitives/ocall-api/Cargo.toml index 1b6a48ced3..0407159156 100644 --- a/core-primitives/ocall-api/Cargo.toml +++ b/core-primitives/ocall-api/Cargo.toml @@ -17,7 +17,6 @@ sgx_types = { rev = "v1.1.3", git = "https://github.com/apache/teaclave-sgx-sdk. # local deps itp-types = { path = "../types", default-features = false } -its-primitives = { path = "../../sidechain/primitives", default-features = false } [features] default = ["std"] @@ -26,5 +25,4 @@ std = [ "sp-runtime/std", "sp-std/std", "itp-types/std", - "its-primitives/std", ] diff --git a/core-primitives/ocall-api/src/lib.rs b/core-primitives/ocall-api/src/lib.rs index 9a0c788bce..22499f2048 100644 --- a/core-primitives/ocall-api/src/lib.rs +++ b/core-primitives/ocall-api/src/lib.rs @@ -23,7 +23,6 @@ use alloc::vec::Vec; use codec::{Decode, Encode}; use core::fmt::Debug; use itp_types::{TrustedOperationStatus, WorkerRequest, WorkerResponse}; -use its_primitives::traits::SignedBlock; use sgx_types::*; use sp_runtime::OpaqueExtrinsic; @@ -64,11 +63,7 @@ pub trait EnclaveRpcOCallApi: Clone + Debug + Send + Sync + Default { /// trait for o-calls related to on-chain interactions pub trait EnclaveOnChainOCallApi: Clone + Debug + Send + Sync { - fn send_block_and_confirmation( - &self, - confirmations: Vec, - signed_blocks: Vec, - ) -> SgxResult<()>; + fn send_to_parentchain(&self, extrinsics: Vec) -> SgxResult<()>; fn worker_request( &self, @@ -76,6 +71,10 @@ pub trait EnclaveOnChainOCallApi: Clone + Debug + Send + Sync { ) -> SgxResult>>; } +pub trait EnclaveSidechainOCallApi: Clone + Debug + Send + Sync { + fn propose_sidechain_blocks(&self, signed_blocks: Vec) -> SgxResult<()>; +} + /// Newtype for IPFS CID pub struct IpfsCid(pub [u8; 46]); diff --git a/enclave-runtime/Cargo.lock b/enclave-runtime/Cargo.lock index ee1aa116e4..771fa6db90 100644 --- a/enclave-runtime/Cargo.lock +++ b/enclave-runtime/Cargo.lock @@ -1220,7 +1220,6 @@ name = "itp-ocall-api" version = "0.8.0" dependencies = [ "itp-types", - "its-primitives", "parity-scale-codec", "sgx_types", "sp-runtime", diff --git a/enclave-runtime/Enclave.edl b/enclave-runtime/Enclave.edl index 88f4a3951d..b5801c02c5 100644 --- a/enclave-runtime/Enclave.edl +++ b/enclave-runtime/Enclave.edl @@ -138,11 +138,14 @@ enclave { [out, size = resp_size] uint8_t * response, uint32_t resp_size ); - sgx_status_t ocall_send_block_and_confirmation( - [in, size = confirmations_size] uint8_t * confirmations, uint32_t confirmations_size, + sgx_status_t ocall_propose_sidechain_blocks( [in, size = signed_blocks_size] uint8_t * signed_blocks, uint32_t signed_blocks_size ); + sgx_status_t ocall_send_to_parentchain( + [in, size = extrinsics_size] uint8_t * extrinsics, uint32_t extrinsics_size + ); + sgx_status_t ocall_update_status_event( [in, size = hash_size] uint8_t * hash_encoded, uint32_t hash_size, [in, size = status_size] uint8_t * status_update_encoded, uint32_t status_size diff --git a/enclave-runtime/src/lib.rs b/enclave-runtime/src/lib.rs index 56bebf99d9..a399ece91f 100644 --- a/enclave-runtime/src/lib.rs +++ b/enclave-runtime/src/lib.rs @@ -291,16 +291,19 @@ pub unsafe extern "C" fn mock_register_enclave_xt( sgx_status_t::SGX_SUCCESS } -fn create_extrinsics( +fn create_extrinsics( genesis_hash: HashFor, + signer: Signer, calls: Vec, - nonce: &mut u32, -) -> Result> + mut nonce: u32, +) -> Result<(Vec, u32)> where PB: BlockT, + Signer: Pair, + Signer::Public: Encode, + Signer::Signature: Into, { // get information for composing the extrinsic - let signer = Ed25519Seal::unseal()?; debug!("Restored ECC pubkey: {:?}", signer.public()); let extrinsics_buffer: Vec = calls @@ -309,7 +312,7 @@ where let xt = compose_extrinsic_offline!( signer.clone(), call, - *nonce, + nonce, Era::Immortal, genesis_hash, genesis_hash, @@ -317,7 +320,7 @@ where RUNTIME_TRANSACTION_VERSION ) .encode(); - *nonce += 1; + nonce += 1; xt }) .map(|xt| { @@ -326,7 +329,7 @@ where }) .collect(); - Ok(extrinsics_buffer) + Ok((extrinsics_buffer, nonce)) } /// this is reduced to the side chain block import RPC interface (i.e. worker-worker communication) @@ -627,15 +630,15 @@ where { Some(slot) => { let shards = state_handler.list_shards()?; - let env = ProposerFactory::new(rpc_author, stf_executor); + let env = ProposerFactory::new(rpc_author, stf_executor, authority.clone()); - exec_aura_on_slot::<_, _, SignedSidechainBlock, _, _, _>( + *nonce = exec_aura_on_slot::<_, _, SignedSidechainBlock, _, _, _>( slot, authority, &mut validator, OcallApi, env, - &mut nonce, + *nonce, shards, )? }, @@ -685,15 +688,17 @@ where let _light_client_lock = EnclaveLock::write_light_client_db()?; let mut validator = LightClientSeal::::unseal()?; + let signer = Ed25519Seal::unseal()?; let mut nonce = NONCE.write().expect("Encountered poisoned NONCE lock"); let stf_executor = StfExecutor::new(Arc::new(OcallApi), Arc::new(GlobalFileStateHandler)); - sync_blocks_on_light_client( + *nonce = sync_blocks_on_light_client( blocks_to_sync, &mut validator, + signer, &OcallApi, &stf_executor, - &mut *nonce, + *nonce, )?; // store updated state in light client in case we fail afterwards. @@ -702,19 +707,23 @@ where Ok(()) } -fn sync_blocks_on_light_client( +fn sync_blocks_on_light_client( blocks_to_sync: Vec>, validator: &mut V, + signer: Signer, on_chain_ocall_api: &OCallApi, stf_executor: &StfExecutor, - nonce: &mut u32, -) -> Result<()> + nonce: u32, +) -> Result where PB: BlockT, NumberFor: BlockNumberOps, V: Validator + LightClientState, OCallApi: EnclaveOnChainOCallApi + EnclaveAttestationOCallApi, StfExecutor: StfUpdateState + StfExecuteTrustedCall + StfExecuteShieldFunds, + Signer: Pair, + Signer::Public: Encode, + Signer::Signature: Into, { let mut calls = Vec::::new(); let mrenclave: ShardIdentifier = on_chain_ocall_api.get_mrenclave_of_self()?.m.into(); @@ -759,32 +768,29 @@ where ))); } - prepare_and_send_xts_and_block::<_, SignedSidechainBlock, _, _>( - validator, - on_chain_ocall_api, - calls, - Default::default(), - nonce, - ) + prepare_and_send_xts::<_, _, _, Signer>(validator, signer, on_chain_ocall_api, calls, nonce) } -fn prepare_and_send_xts_and_block( +fn prepare_and_send_xts( validator: &mut V, + signer: Signer, ocall_api: &OCallApi, calls: Vec, - blocks: Vec, - nonce: &mut u32, -) -> Result<()> + nonce: u32, +) -> Result where Block: BlockT, - SB: SignedBlockT + 'static, NumberFor: BlockNumberOps, V: Validator + LightClientState, OCallApi: EnclaveOnChainOCallApi, + Signer: Pair, + Signer::Public: Encode, + Signer::Signature: Into, { // store extrinsics in light client for finalization check - let extrinsics = create_extrinsics::( + let (extrinsics, nonce_updated) = create_extrinsics::( validator.genesis_hash(validator.num_relays()).unwrap(), + signer, calls, nonce, )?; @@ -794,8 +800,10 @@ where } ocall_api - .send_block_and_confirmation::(extrinsics, blocks) - .map_err(|e| Error::Other(format!("Failed to send block and confirmation: {}", e).into())) + .send_to_parentchain(extrinsics) + .map_err(|e| Error::Other(format!("Failed to send extrinsics: {}", e).into()))?; + + Ok(nonce_updated) } /// Execute pending trusted operations for all shards until the [`max_exec_duration`] is reached. @@ -805,22 +813,33 @@ where /// /// Todo: This will probably be used again if we decide to make sidechain optional? #[allow(unused)] -fn execute_top_pool_trusted_calls_for_all_shards( +fn execute_top_pool_trusted_calls_for_all_shards< + PB, + SB, + RpcAuthor, + StateHandler, + StfExecutor, + Signer, +>( rpc_author: &RpcAuthor, state_handler: &StateHandler, stf_executor: &StfExecutor, + signer: Signer, latest_onchain_header: &PB::Header, max_exec_duration: Duration, ) -> Result<(Vec, Vec)> where PB: BlockT, - SB: SignedBlockT, + SB: SignedBlockT, SB::Block: SidechainBlockT, + SB::Signature: From, RpcAuthor: AuthorApi + SendState + OnBlockCreated, StateHandler: QueryShardState, StfExecutor: StfExecuteTimedCallsBatch + StfExecuteGenericUpdate, + Signer: Pair, + Signer::Public: Encode, { let shards = state_handler.list_shards()?; let mut calls: Vec = Vec::new(); @@ -841,9 +860,10 @@ where }, }; - match execute_top_pool_trusted_calls::( + match execute_top_pool_trusted_calls::( rpc_author, stf_executor, + signer.clone(), &latest_onchain_header, shard, shard_exec_time, @@ -871,20 +891,24 @@ where /// /// Todo: This function does too much, but it needs anyhow some refactoring here to make the code /// more readable. -fn execute_top_pool_trusted_calls( +fn execute_top_pool_trusted_calls( rpc_author: &RpcAuthor, stf_executor: &StfExecutor, + signer: Signer, latest_onchain_header: &PB::Header, shard: H256, max_exec_duration: Duration, ) -> Result<(Vec, Option)> where PB: BlockT, - SB: SignedBlockT, + SB: SignedBlockT, SB::Block: SidechainBlockT, + SB::Signature: From, RpcAuthor: AuthorApi + OnBlockCreated, StfExecutor: StfExecuteTimedCallsBatch + StfExecuteGenericUpdate, + Signer: Pair, + Signer::Public: Encode, { // retrieve trusted operations from pool let trusted_calls = rpc_author.get_pending_tops_separated(shard)?.0; @@ -933,11 +957,12 @@ where // Todo: this function should return here. Composing the block should be done by the caller. // create new block (side-chain) - let block = match compose_block_and_confirmation::( + let block = match compose_block_and_confirmation::( latest_onchain_header, executed_operation_hashes, shard, batch_execution_result.previous_state_hash, + signer, stf_executor, ) { Ok((block_confirm, signed_block)) => { @@ -1015,22 +1040,24 @@ where } /// Composes a sidechain block of a shard -fn compose_block_and_confirmation( +fn compose_block_and_confirmation( latest_onchain_header: &PB::Header, top_call_hashes: Vec, shard: ShardIdentifier, state_hash_apriori: H256, + signer: Signer, stf_executor: &StfExecutor, ) -> Result<(OpaqueCall, SB)> where PB: BlockT, SB: SignedBlockT, - SB::Block: SidechainBlockT, + SB::Block: SidechainBlockT, + SB::Signature: From, StfExecutor: StfExecuteGenericUpdate, + Signer: Pair, + Signer::Public: Encode, { - let signer_pair = Ed25519Seal::unseal()?; - - let author_public = signer_pair.public(); + let author_public = signer.public(); let (block, state_hash_new) = stf_executor.execute_update(&shard, |state| { let mut db = SidechainDB::::new(state); let state_hash_new = db.state_hash(); @@ -1078,7 +1105,7 @@ where let xt_block = [TEEREX_MODULE, BLOCK_CONFIRMED]; let opaque_call = OpaqueCall::from_tuple(&(xt_block, shard, block_hash, state_hash_new.encode())); - Ok((opaque_call, block.sign_block(&signer_pair))) + Ok((opaque_call, block.sign_block(&signer))) } /// Scans blocks for extrinsics that ask the enclave to execute some actions. diff --git a/enclave-runtime/src/ocall/ffi.rs b/enclave-runtime/src/ocall/ffi.rs index 7a5bfc8a7c..d9558c0e47 100644 --- a/enclave-runtime/src/ocall/ffi.rs +++ b/enclave-runtime/src/ocall/ffi.rs @@ -74,14 +74,18 @@ extern "C" { resp_size: u32, ) -> sgx_status_t; - pub fn ocall_send_block_and_confirmation( + pub fn ocall_propose_sidechain_blocks( ret_val: *mut sgx_status_t, - confirmations: *const u8, - confirmations_size: u32, signed_blocks: *const u8, signed_blocks_size: u32, ) -> sgx_status_t; + pub fn ocall_send_to_parentchain( + ret_val: *mut sgx_status_t, + extrinsics: *const u8, + extrinsics_size: u32, + ) -> sgx_status_t; + pub fn ocall_read_ipfs( ret_val: *mut sgx_status_t, cid: *const u8, diff --git a/enclave-runtime/src/ocall/mod.rs b/enclave-runtime/src/ocall/mod.rs index 453e06ea34..b688efaaf3 100644 --- a/enclave-runtime/src/ocall/mod.rs +++ b/enclave-runtime/src/ocall/mod.rs @@ -21,6 +21,7 @@ mod attestation_ocall; mod ffi; mod ipfs_ocall; mod on_chain_ocall; +mod sidechain_ocall; #[derive(Clone, Debug, Default)] pub struct OcallApi; diff --git a/enclave-runtime/src/ocall/on_chain_ocall.rs b/enclave-runtime/src/ocall/on_chain_ocall.rs index f3865d5bb4..22ac3fdde9 100644 --- a/enclave-runtime/src/ocall/on_chain_ocall.rs +++ b/enclave-runtime/src/ocall/on_chain_ocall.rs @@ -21,29 +21,21 @@ use codec::{Decode, Encode}; use frame_support::ensure; use itp_ocall_api::EnclaveOnChainOCallApi; use itp_types::{WorkerRequest, WorkerResponse}; -use its_sidechain::primitives::traits::SignedBlock; use log::*; use sgx_types::*; use sp_runtime::OpaqueExtrinsic; use std::vec::Vec; impl EnclaveOnChainOCallApi for OcallApi { - fn send_block_and_confirmation( - &self, - confirmations: Vec, - signed_blocks: Vec, - ) -> SgxResult<()> { + fn send_to_parentchain(&self, extrinsics: Vec) -> SgxResult<()> { let mut rt: sgx_status_t = sgx_status_t::SGX_ERROR_UNEXPECTED; - let confirmations_encoded = confirmations.encode(); - let signed_blocks_encoded = signed_blocks.encode(); + let extrinsics_encoded = extrinsics.encode(); let res = unsafe { - ffi::ocall_send_block_and_confirmation( + ffi::ocall_send_to_parentchain( &mut rt as *mut sgx_status_t, - confirmations_encoded.as_ptr(), - confirmations_encoded.len() as u32, - signed_blocks_encoded.as_ptr(), - signed_blocks_encoded.len() as u32, + extrinsics_encoded.as_ptr(), + extrinsics_encoded.len() as u32, ) }; diff --git a/enclave-runtime/src/ocall/sidechain_ocall.rs b/enclave-runtime/src/ocall/sidechain_ocall.rs new file mode 100644 index 0000000000..61e93ca732 --- /dev/null +++ b/enclave-runtime/src/ocall/sidechain_ocall.rs @@ -0,0 +1,43 @@ +/* + Copyright 2021 Integritee AG and Supercomputing Systems AG + Copyright (C) 2017-2019 Baidu, Inc. All Rights Reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +*/ + +use crate::ocall::{ffi, OcallApi}; +use codec::Encode; +use frame_support::ensure; +use itp_ocall_api::{alloc::prelude::v1::Vec, EnclaveSidechainOCallApi}; +use sgx_types::{sgx_status_t, SgxResult}; + +impl EnclaveSidechainOCallApi for OcallApi { + fn propose_sidechain_blocks(&self, signed_blocks: Vec) -> SgxResult<()> { + let mut rt: sgx_status_t = sgx_status_t::SGX_ERROR_UNEXPECTED; + let signed_blocks_encoded = signed_blocks.encode(); + + let res = unsafe { + ffi::ocall_propose_sidechain_blocks( + &mut rt as *mut sgx_status_t, + signed_blocks_encoded.as_ptr(), + signed_blocks_encoded.len() as u32, + ) + }; + + ensure!(rt == sgx_status_t::SGX_SUCCESS, rt); + ensure!(res == sgx_status_t::SGX_SUCCESS, res); + + Ok(()) + } +} diff --git a/enclave-runtime/src/sidechain_impl.rs b/enclave-runtime/src/sidechain_impl.rs index 0b0246d99d..f2997d8054 100644 --- a/enclave-runtime/src/sidechain_impl.rs +++ b/enclave-runtime/src/sidechain_impl.rs @@ -3,13 +3,11 @@ //! Todo: Once we have put the `top_pool` stuff in an entirely different crate we can //! move most parts here to the sidechain crate. -use crate::{ - execute_top_pool_trusted_calls, prepare_and_send_xts_and_block, Result as EnclaveResult, -}; +use crate::{execute_top_pool_trusted_calls, prepare_and_send_xts, Result as EnclaveResult}; use codec::Encode; use core::time::Duration; use itc_light_client::{BlockNumberOps, LightClientState, NumberFor, Validator}; -use itp_ocall_api::{EnclaveAttestationOCallApi, EnclaveOnChainOCallApi}; +use itp_ocall_api::{EnclaveAttestationOCallApi, EnclaveOnChainOCallApi, EnclaveSidechainOCallApi}; use itp_settings::sidechain::SLOT_DURATION; use itp_sgx_crypto::{Aes, AesSeal}; use itp_sgx_io::SealedIO; @@ -33,34 +31,37 @@ use sp_runtime::{traits::Block, MultiSignature}; use std::{marker::PhantomData, string::ToString, sync::Arc, vec::Vec}; ///! `SlotProposer` instance that has access to everything needed to propose a sidechain block -pub struct SlotProposer { +pub struct SlotProposer { author: Arc, stf_executor: Arc, parentchain_header: PB::Header, shard: ShardIdentifierFor, + signer: Signer, _phantom: PhantomData, } ///! `ProposerFactory` instance containing all the data to create the `SlotProposer` for the /// next `Slot` -pub struct ProposerFactory { +pub struct ProposerFactory { author: Arc, stf_executor: Arc, + signer: Signer, _phantom: PhantomData, } -impl ProposerFactory { - pub fn new(author: Arc, stf_executor: Arc) -> Self { - Self { author, stf_executor, _phantom: Default::default() } +impl ProposerFactory { + pub fn new(author: Arc, stf_executor: Arc, signer: Signer) -> Self { + Self { author, stf_executor, signer, _phantom: Default::default() } } } -impl, SB, Author, StfExecutor> Environment - for ProposerFactory +impl, SB, Author, StfExecutor, Signer> Environment + for ProposerFactory where NumberFor: BlockNumberOps, - SB: SignedBlock + 'static, + SB: SignedBlock + 'static, SB::Block: SidechainBlockT, + SB::Signature: From, Author: AuthorApi + SendState + OnBlockCreated @@ -71,8 +72,10 @@ where + Send + Sync + 'static, + Signer: Pair, + Signer::Public: Encode, { - type Proposer = SlotProposer; + type Proposer = SlotProposer; type Error = ConsensusError; fn init( @@ -85,17 +88,20 @@ where stf_executor: self.stf_executor.clone(), parentchain_header: parent_header, shard, + signer: self.signer.clone(), _phantom: PhantomData, }) } } -impl Proposer for SlotProposer +impl Proposer + for SlotProposer where PB: Block, NumberFor: BlockNumberOps, - SB: SignedBlock, + SB: SignedBlock, SB::Block: SidechainBlockT, + SB::Signature: From, Author: AuthorApi + SendState + OnBlockCreated, StfExecutor: StfExecuteTimedCallsBatch @@ -103,11 +109,14 @@ where + Send + Sync + 'static, + Signer: Pair, + Signer::Public: Encode, { fn propose(&self, max_duration: Duration) -> Result, ConsensusError> { - let (calls, blocks) = execute_top_pool_trusted_calls::( + let (calls, blocks) = execute_top_pool_trusted_calls::( self.author.as_ref(), self.stf_executor.as_ref(), + self.signer.clone(), &self.parentchain_header, self.shard, max_duration, @@ -122,33 +131,38 @@ where } /// Executes aura for the given `slot` -pub fn exec_aura_on_slot( +pub fn exec_aura_on_slot( slot: SlotInfo, authority: Authority, validator: &mut LightValidator, - ocall_api: OcallApi, + ocall_api: OCallApi, proposer_environment: PEnvironment, - nonce: &mut u32, + nonce: u32, shards: Vec>, -) -> EnclaveResult<()> +) -> EnclaveResult where // setting the public type is necessary due to some non-generic downstream code. - Authority: Pair, - Authority::Public: Encode, PB: Block, SB: SignedBlock + 'static, SB::Block: SidechainBlockT, - OcallApi: EnclaveOnChainOCallApi + EnclaveAttestationOCallApi + 'static, + SB::Signature: From, + Authority: Pair, + Authority::Public: Encode, + OCallApi: + EnclaveSidechainOCallApi + EnclaveOnChainOCallApi + EnclaveAttestationOCallApi + 'static, LightValidator: Validator + LightClientState + Clone + Send + Sync + 'static, NumberFor: BlockNumberOps, PEnvironment: Environment + Send + Sync, { log::info!("[Aura] Executing aura for slot: {:?}", slot); - let mut aura = - Aura::<_, _, SB, PEnvironment, _>::new(authority, ocall_api.clone(), proposer_environment) - .with_claim_strategy(SlotClaimStrategy::Always) - .with_allow_delayed_proposal(true); + let mut aura = Aura::<_, _, SB, PEnvironment, _>::new( + authority.clone(), + ocall_api.clone(), + proposer_environment, + ) + .with_claim_strategy(SlotClaimStrategy::Always) + .with_allow_delayed_proposal(true); let (blocks, xts): (Vec<_>, Vec<_>) = PerShardSlotWorkerScheduler::on_slot(&mut aura, slot, shards) @@ -156,11 +170,14 @@ where .map(|r| (r.block, r.parentchain_effects)) .unzip(); - prepare_and_send_xts_and_block::<_, SB, _, _>( + ocall_api.propose_sidechain_blocks(blocks)?; + let signer = authority; + + prepare_and_send_xts::<_, _, _, _>( validator, + signer, &ocall_api, xts.into_iter().flatten().collect(), - blocks, nonce, ) } diff --git a/enclave-runtime/src/tests.rs b/enclave-runtime/src/tests.rs index 7f2c463fd0..5784a990f5 100644 --- a/enclave-runtime/src/tests.rs +++ b/enclave-runtime/src/tests.rs @@ -49,7 +49,7 @@ use its_sidechain::{ state::{LastBlockExt, SidechainDB, SidechainState, SidechainSystemExt}, top_pool::{basic_pool::BasicPool, pool::ExtrinsicHash}, top_pool_rpc_author::{ - api::SideChainApi, + api::SidechainApi, author::Author, author_tests, test_utils::{get_pending_tops_separated, submit_and_execute_top}, @@ -64,8 +64,8 @@ use sp_core::{crypto::Pair, ed25519 as spEd25519, hashing::blake2_256, H256}; use sp_runtime::traits::Header as HeaderT; use std::{string::String, sync::Arc, vec::Vec}; -type TestRpcResponder = RpcResponderMock>>; -type TestTopPool = BasicPool, Block, TestRpcResponder>; +type TestRpcResponder = RpcResponderMock>>; +type TestTopPool = BasicPool, Block, TestRpcResponder>; type TestRpcAuthor = Author; #[no_mangle] @@ -132,11 +132,12 @@ fn test_compose_block_and_confirmation() { // when let (opaque_call, signed_block) = - crate::compose_block_and_confirmation::( + crate::compose_block_and_confirmation::( &latest_parentchain_header(), signed_top_hashes, shard, previous_state_hash, + test_account(), &stf_executor, ) .unwrap(); @@ -237,10 +238,11 @@ fn test_create_block_and_confirmation_works() { // when let (confirm_calls, signed_blocks) = - crate::execute_top_pool_trusted_calls_for_all_shards::( + crate::execute_top_pool_trusted_calls_for_all_shards::( &rpc_author, state_handler.as_ref(), &stf_executor, + test_account(), &latest_parentchain_header(), MAX_TRUSTED_OPS_EXEC_DURATION, ) @@ -287,10 +289,11 @@ fn test_create_state_diff() { // when let (_, signed_blocks) = - crate::execute_top_pool_trusted_calls_for_all_shards::( + crate::execute_top_pool_trusted_calls_for_all_shards::( &rpc_author, state_handler.as_ref(), &stf_executor, + test_account(), &latest_parentchain_header(), MAX_TRUSTED_OPS_EXEC_DURATION, ) @@ -330,10 +333,11 @@ fn test_executing_call_updates_account_nonce() { // when let (_, _) = - crate::execute_top_pool_trusted_calls_for_all_shards::( + crate::execute_top_pool_trusted_calls_for_all_shards::( &rpc_author, state_handler.as_ref(), &stf_executor, + test_account(), &latest_parentchain_header(), MAX_TRUSTED_OPS_EXEC_DURATION, ) @@ -361,10 +365,11 @@ fn test_invalid_nonce_call_is_not_executed() { // when let (_, _) = - crate::execute_top_pool_trusted_calls_for_all_shards::( + crate::execute_top_pool_trusted_calls_for_all_shards::( &rpc_author, state_handler.as_ref(), &stf_executor, + test_account(), &latest_parentchain_header(), MAX_TRUSTED_OPS_EXEC_DURATION, ) @@ -396,10 +401,11 @@ fn test_non_root_shielding_call_is_not_executed() { // when let (_, _) = - crate::execute_top_pool_trusted_calls_for_all_shards::( + crate::execute_top_pool_trusted_calls_for_all_shards::( &rpc_author, state_handler.as_ref(), &stf_executor, + test_account(), &latest_parentchain_header(), MAX_TRUSTED_OPS_EXEC_DURATION, ) @@ -450,7 +456,7 @@ fn init_state>( } fn test_top_pool() -> TestTopPool { - let chain_api = Arc::new(SideChainApi::::new()); + let chain_api = Arc::new(SidechainApi::::new()); let top_pool = BasicPool::create(Default::default(), chain_api, Arc::new(TestRpcResponder::new())); @@ -498,6 +504,10 @@ fn unfunded_public() -> spEd25519::Public { spEd25519::Public::from_raw(*b"asdfasdfadsfasdfasfasdadfadfasdf") } +pub fn test_account() -> spEd25519::Pair { + spEd25519::Pair::from_seed(b"42315678901234567890123456789012") +} + /// transforms `call` into `TrustedOperation::direct(call)` fn direct_top(call: TrustedCallSigned) -> TrustedOperation { call.into_trusted_operation(true) diff --git a/service/src/main.rs b/service/src/main.rs index 9af5062381..a1de25d17b 100644 --- a/service/src/main.rs +++ b/service/src/main.rs @@ -43,7 +43,7 @@ use itp_enclave_api::{ direct_request::DirectRequest, enclave_base::EnclaveBase, remote_attestation::{RemoteAttestation, TlsRemoteAttestation}, - side_chain::SideChain, + sidechain::Sidechain, teerex_api::TeerexApi, }; use itp_settings::{ @@ -245,7 +245,7 @@ fn start_worker( T: GetTokioHandle, E: EnclaveBase + DirectRequest - + SideChain + + Sidechain + RemoteAttestation + TlsRemoteAttestation + TeerexApi @@ -416,7 +416,7 @@ fn start_worker( } /// Triggers the enclave to produce a block based on a fixed time schedule. -fn start_interval_block_production(enclave_api: &E) { +fn start_interval_block_production(enclave_api: &E) { use itp_settings::sidechain::SLOT_DURATION; schedule_on_repeating_intervals( @@ -430,7 +430,7 @@ fn start_interval_block_production(enclave_api: &E) /// Starts the execution of trusted getters in repeating intervals. /// /// The getters are executed in a pre-defined slot duration. -fn start_interval_trusted_getter_execution(enclave_api: &E) { +fn start_interval_trusted_getter_execution(enclave_api: &E) { use itp_settings::enclave::TRUSTED_GETTERS_SLOT_DURATION; schedule_on_repeating_intervals( @@ -566,7 +566,7 @@ fn print_events(events: Events, _sender: Sender) { } } -pub fn init_light_client( +pub fn init_light_client( api: &Api, enclave_api: &E, ) -> Header { @@ -597,7 +597,7 @@ pub fn init_light_client( /// Subscribe to the node API finalized heads stream and trigger a parent chain sync /// upon receiving a new header -fn subscribe_to_parentchain_new_headers( +fn subscribe_to_parentchain_new_headers( enclave_api: &E, api: &Api, mut last_synced_header: Header, @@ -623,7 +623,7 @@ fn subscribe_to_parentchain_new_headers( /// Gets the amount of blocks to sync from the parentchain and feeds them to the enclave. /// /// -pub fn sync_parentchain( +pub fn sync_parentchain( enclave_api: &E, api: &Api, last_synced_header: Header, @@ -665,7 +665,7 @@ pub fn sync_parentchain( /// Execute trusted operations in the enclave /// /// -fn execute_trusted_calls(enclave_api: &E) { +fn execute_trusted_calls(enclave_api: &E) { if let Err(e) = enclave_api.execute_trusted_calls() { error!("{:?}", e); }; diff --git a/service/src/ocall_bridge/bridge_api.rs b/service/src/ocall_bridge/bridge_api.rs index 19bbe9dfc3..6ad2633b78 100644 --- a/service/src/ocall_bridge/bridge_api.rs +++ b/service/src/ocall_bridge/bridge_api.rs @@ -54,6 +54,14 @@ impl Bridge { .get_ra_api() } + pub fn get_sidechain_api() -> Arc { + COMPONENT_FACTORY + .read() + .as_ref() + .expect("Component factory has not been set. Use `initialize()`") + .get_sidechain_api() + } + pub fn get_oc_api() -> Arc { debug!("Requesting WorkerOnChain OCall API instance"); @@ -97,7 +105,10 @@ pub trait GetOCallBridgeComponents { /// remote attestation OCall API fn get_ra_api(&self) -> Arc; - /// on chain OCall API + /// side chain OCall API + fn get_sidechain_api(&self) -> Arc; + + /// on chain (parentchain) OCall API fn get_oc_api(&self) -> Arc; /// ipfs OCall API @@ -118,8 +129,10 @@ pub enum OCallBridgeError { GetUpdateInfo(sgx_status_t), #[error("GetIasSocket Error: {0}")] GetIasSocket(String), - #[error("SendBlockAndConfirmation Error: {0}")] - SendBlockAndConfirmation(String), + #[error("Propose sidechain block failed: {0}")] + ProposeSidechainBlock(String), + #[error("Sending extrinsics to parentchain failed: {0}")] + SendExtrinsicsToParentchain(String), #[error("IPFS Error: {0}")] IpfsError(String), #[error("DirectInvocation Error: {0}")] @@ -133,7 +146,8 @@ impl From for sgx_status_t { OCallBridgeError::InitQuote(s) => s, OCallBridgeError::GetUpdateInfo(s) => s, OCallBridgeError::GetIasSocket(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, - OCallBridgeError::SendBlockAndConfirmation(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, + OCallBridgeError::ProposeSidechainBlock(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, + OCallBridgeError::SendExtrinsicsToParentchain(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, OCallBridgeError::IpfsError(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, OCallBridgeError::DirectInvocationError(_) => sgx_status_t::SGX_ERROR_UNEXPECTED, } @@ -169,16 +183,18 @@ pub trait RemoteAttestationBridge { ) -> OCallBridgeResult; } -/// Trait for all the OCalls related to on-chain operations +/// Trait for all the OCalls related to parentchain operations #[cfg_attr(test, automock)] pub trait WorkerOnChainBridge { fn worker_request(&self, request: Vec) -> OCallBridgeResult>; - fn send_block_and_confirmation( - &self, - confirmations: Vec, - signed_blocks: Vec, - ) -> OCallBridgeResult<()>; + fn send_to_parentchain(&self, extrinsics_encoded: Vec) -> OCallBridgeResult<()>; +} + +/// Trait for all the OCalls related to sidechain operations +#[cfg_attr(test, automock)] +pub trait SidechainBridge { + fn propose_sidechain_blocks(&self, signed_blocks_encoded: Vec) -> OCallBridgeResult<()>; } /// type for IPFS diff --git a/service/src/ocall_bridge/component_factory.rs b/service/src/ocall_bridge/component_factory.rs index 423a2d8ede..c5e12744ac 100644 --- a/service/src/ocall_bridge/component_factory.rs +++ b/service/src/ocall_bridge/component_factory.rs @@ -24,10 +24,11 @@ use crate::{ ocall_bridge::{ bridge_api::{ DirectInvocationBridge, GetOCallBridgeComponents, IpfsBridge, RemoteAttestationBridge, - WorkerOnChainBridge, + SidechainBridge, WorkerOnChainBridge, }, ipfs_ocall::IpfsOCall, remote_attestation_ocall::RemoteAttestationOCall, + sidechain_ocall::SidechainOCall, worker_on_chain_ocall::WorkerOnChainOCall, }, sidechain_storage::BlockStorage, @@ -78,12 +79,12 @@ where Arc::new(RemoteAttestationOCall::new(self.enclave_api.clone())) } + fn get_sidechain_api(&self) -> Arc { + Arc::new(SidechainOCall::new(self.block_gossiper.clone(), self.block_storage.clone())) + } + fn get_oc_api(&self) -> Arc { - Arc::new(WorkerOnChainOCall::new( - self.node_api_factory.clone(), - self.block_gossiper.clone(), - self.block_storage.clone(), - )) + Arc::new(WorkerOnChainOCall::new(self.node_api_factory.clone())) } fn get_ipfs_api(&self) -> Arc { diff --git a/service/src/ocall_bridge/ffi/mod.rs b/service/src/ocall_bridge/ffi/mod.rs index 2be6431526..ee231d8c67 100644 --- a/service/src/ocall_bridge/ffi/mod.rs +++ b/service/src/ocall_bridge/ffi/mod.rs @@ -25,7 +25,8 @@ pub mod get_quote; pub mod get_update_info; pub mod init_quote; pub mod ipfs; -pub mod send_block_and_confirmation; +pub mod propose_sidechain_blocks; pub mod send_status; +pub mod send_to_parentchain; pub mod update_status_event; pub mod worker_request; diff --git a/service/src/ocall_bridge/ffi/send_block_and_confirmation.rs b/service/src/ocall_bridge/ffi/propose_sidechain_blocks.rs similarity index 60% rename from service/src/ocall_bridge/ffi/send_block_and_confirmation.rs rename to service/src/ocall_bridge/ffi/propose_sidechain_blocks.rs index 873f7fb653..21ff07d0bb 100644 --- a/service/src/ocall_bridge/ffi/send_block_and_confirmation.rs +++ b/service/src/ocall_bridge/ffi/propose_sidechain_blocks.rs @@ -16,47 +16,34 @@ */ -use crate::ocall_bridge::bridge_api::{Bridge, WorkerOnChainBridge}; +use crate::ocall_bridge::bridge_api::{Bridge, SidechainBridge}; use log::*; use sgx_types::sgx_status_t; -use std::{slice, sync::Arc, vec::Vec}; +use std::{slice, sync::Arc}; /// # Safety /// /// FFI are always unsafe #[no_mangle] -pub unsafe extern "C" fn ocall_send_block_and_confirmation( - confirmations: *const u8, - confirmations_size: u32, +pub unsafe extern "C" fn ocall_propose_sidechain_blocks( signed_blocks_ptr: *const u8, signed_blocks_size: u32, ) -> sgx_status_t { - send_block_and_confirmation( - confirmations, - confirmations_size, - signed_blocks_ptr, - signed_blocks_size, - Bridge::get_oc_api(), - ) + propose_sidechain_blocks(signed_blocks_ptr, signed_blocks_size, Bridge::get_sidechain_api()) } -fn send_block_and_confirmation( - confirmations: *const u8, - confirmations_size: u32, +fn propose_sidechain_blocks( signed_blocks_ptr: *const u8, signed_blocks_size: u32, - oc_api: Arc, + sidechain_api: Arc, ) -> sgx_status_t { - let confirmations_vec: Vec = - unsafe { Vec::from(slice::from_raw_parts(confirmations, confirmations_size as usize)) }; - let signed_blocks_vec: Vec = unsafe { Vec::from(slice::from_raw_parts(signed_blocks_ptr, signed_blocks_size as usize)) }; - match oc_api.send_block_and_confirmation(confirmations_vec, signed_blocks_vec) { + match sidechain_api.propose_sidechain_blocks(signed_blocks_vec) { Ok(_) => sgx_status_t::SGX_SUCCESS, Err(e) => { - error!("send block and confirmation failed: {:?}", e); + error!("send sidechain blocks failed: {:?}", e); sgx_status_t::SGX_ERROR_UNEXPECTED }, } diff --git a/service/src/ocall_bridge/ffi/send_to_parentchain.rs b/service/src/ocall_bridge/ffi/send_to_parentchain.rs new file mode 100644 index 0000000000..19bf289c24 --- /dev/null +++ b/service/src/ocall_bridge/ffi/send_to_parentchain.rs @@ -0,0 +1,51 @@ +/* + Copyright 2021 Integritee AG and Supercomputing Systems AG + Copyright (C) 2017-2019 Baidu, Inc. All Rights Reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +*/ + +use crate::ocall_bridge::bridge_api::{Bridge, WorkerOnChainBridge}; +use log::*; +use sgx_types::sgx_status_t; +use std::{slice, sync::Arc, vec::Vec}; + +/// # Safety +/// +/// FFI are always unsafe +#[no_mangle] +pub unsafe extern "C" fn ocall_send_to_parentchain( + extrinsics_encoded: *const u8, + extrinsics_encoded_size: u32, +) -> sgx_status_t { + send_to_parentchain(extrinsics_encoded, extrinsics_encoded_size, Bridge::get_oc_api()) +} + +fn send_to_parentchain( + extrinsics_encoded: *const u8, + extrinsics_encoded_size: u32, + oc_api: Arc, +) -> sgx_status_t { + let extrinsics_encoded_vec: Vec = unsafe { + Vec::from(slice::from_raw_parts(extrinsics_encoded, extrinsics_encoded_size as usize)) + }; + + match oc_api.send_to_parentchain(extrinsics_encoded_vec) { + Ok(_) => sgx_status_t::SGX_SUCCESS, + Err(e) => { + error!("send extrinsics_encoded failed: {:?}", e); + sgx_status_t::SGX_ERROR_UNEXPECTED + }, + } +} diff --git a/service/src/ocall_bridge/mod.rs b/service/src/ocall_bridge/mod.rs index e7f8be02a4..bef7aabc9d 100644 --- a/service/src/ocall_bridge/mod.rs +++ b/service/src/ocall_bridge/mod.rs @@ -22,4 +22,5 @@ pub mod component_factory; mod ffi; mod ipfs_ocall; mod remote_attestation_ocall; +mod sidechain_ocall; mod worker_on_chain_ocall; diff --git a/service/src/ocall_bridge/sidechain_ocall.rs b/service/src/ocall_bridge/sidechain_ocall.rs new file mode 100644 index 0000000000..faba0f114a --- /dev/null +++ b/service/src/ocall_bridge/sidechain_ocall.rs @@ -0,0 +1,81 @@ +/* + Copyright 2021 Integritee AG and Supercomputing Systems AG + Copyright (C) 2017-2019 Baidu, Inc. All Rights Reserved. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +*/ + +use crate::{ + ocall_bridge::bridge_api::{OCallBridgeError, OCallBridgeResult, SidechainBridge}, + sidechain_storage::BlockStorage, + sync_block_gossiper::GossipBlocks, +}; +use codec::Decode; +use its_primitives::types::SignedBlock as SignedSidechainBlock; +use log::*; +use std::sync::Arc; + +pub struct SidechainOCall { + block_gossiper: Arc, + block_storage: Arc, +} + +impl SidechainOCall { + pub fn new(block_gossiper: Arc, block_storage: Arc) -> Self { + SidechainOCall { block_gossiper, block_storage } + } +} + +impl SidechainBridge for SidechainOCall +where + S: GossipBlocks, + D: BlockStorage, +{ + fn propose_sidechain_blocks(&self, signed_blocks_encoded: Vec) -> OCallBridgeResult<()> { + // TODO: improve error handling, using a mut status is not good design? + let mut status: OCallBridgeResult<()> = Ok(()); + + // handle blocks + let signed_blocks: Vec = + match Decode::decode(&mut signed_blocks_encoded.as_slice()) { + Ok(blocks) => blocks, + Err(_) => { + status = Err(OCallBridgeError::ProposeSidechainBlock( + "Could not decode signed blocks".to_string(), + )); + vec![] + }, + }; + + if !signed_blocks.is_empty() { + info!( + "Enclave produced sidechain blocks: {:?}", + signed_blocks.iter().map(|b| b.block.block_number).collect::>() + ); + } else { + debug!("Enclave did not produce sidechain blocks"); + } + + if let Err(e) = self.block_gossiper.gossip_blocks(signed_blocks.clone()) { + error!("Error gossiping blocks: {:?}", e); + // Fixme: returning an error here results in a `HeaderAncestryMismatch` error. + // status = sgx_status_t::SGX_ERROR_UNEXPECTED; + } + + if let Err(e) = self.block_storage.store_blocks(signed_blocks) { + error!("Error storing blocks: {:?}", e); + } + status + } +} diff --git a/service/src/ocall_bridge/worker_on_chain_ocall.rs b/service/src/ocall_bridge/worker_on_chain_ocall.rs index ecbb14faa2..a76ac79fd2 100644 --- a/service/src/ocall_bridge/worker_on_chain_ocall.rs +++ b/service/src/ocall_bridge/worker_on_chain_ocall.rs @@ -19,36 +19,29 @@ use crate::{ node_api_factory::CreateNodeApi, ocall_bridge::bridge_api::{OCallBridgeError, OCallBridgeResult, WorkerOnChainBridge}, - sidechain_storage::BlockStorage, - sync_block_gossiper::GossipBlocks, utils::hex_encode, }; use codec::{Decode, Encode}; use itp_types::{WorkerRequest, WorkerResponse}; -use its_primitives::types::SignedBlock as SignedSidechainBlock; use log::*; use sp_core::storage::StorageKey; use sp_runtime::OpaqueExtrinsic; use std::{sync::Arc, vec::Vec}; use substrate_api_client::XtStatus; -pub struct WorkerOnChainOCall { +pub struct WorkerOnChainOCall { node_api_factory: Arc, - block_gossiper: Arc, - block_storage: Arc, } -impl WorkerOnChainOCall { - pub fn new(node_api_factory: Arc, block_gossiper: Arc, block_storage: Arc) -> Self { - WorkerOnChainOCall { node_api_factory, block_gossiper, block_storage } +impl WorkerOnChainOCall { + pub fn new(node_api_factory: Arc) -> Self { + WorkerOnChainOCall { node_api_factory } } } -impl WorkerOnChainBridge for WorkerOnChainOCall +impl WorkerOnChainBridge for WorkerOnChainOCall where F: CreateNodeApi, - S: GossipBlocks, - D: BlockStorage, { fn worker_request(&self, request: Vec) -> OCallBridgeResult> { debug!(" Entering ocall_worker_request"); @@ -79,66 +72,29 @@ where Ok(encoded_response) } - fn send_block_and_confirmation( - &self, - confirmations: Vec, - signed_blocks_encoded: Vec, - ) -> OCallBridgeResult<()> { - debug!(" Entering ocall_send_block_and_confirmation"); - + fn send_to_parentchain(&self, extrinsics_encoded: Vec) -> OCallBridgeResult<()> { // TODO: improve error handling, using a mut status is not good design? let mut status: OCallBridgeResult<()> = Ok(()); let api = self.node_api_factory.create_api(); - // send confirmations to layer one - let confirmation_calls: Vec = - match Decode::decode(&mut confirmations.as_slice()) { + let extrinsics: Vec = + match Decode::decode(&mut extrinsics_encoded.as_slice()) { Ok(calls) => calls, Err(_) => { - status = Err(OCallBridgeError::SendBlockAndConfirmation( - "Could not decode confirmation calls".to_string(), + status = Err(OCallBridgeError::SendExtrinsicsToParentchain( + "Could not decode extrinsics".to_string(), )); Default::default() }, }; - if !confirmation_calls.is_empty() { - debug!("Enclave wants to send {} extrinsics", confirmation_calls.len()); - for call in confirmation_calls.into_iter() { + if !extrinsics.is_empty() { + debug!("Enclave wants to send {} extrinsics", extrinsics.len()); + for call in extrinsics.into_iter() { api.send_extrinsic(hex_encode(call.encode()), XtStatus::Ready).unwrap(); } } - // handle blocks - let signed_blocks: Vec = - match Decode::decode(&mut signed_blocks_encoded.as_slice()) { - Ok(blocks) => blocks, - Err(_) => { - status = Err(OCallBridgeError::SendBlockAndConfirmation( - "Could not decode signed blocks".to_string(), - )); - vec![] - }, - }; - - if !signed_blocks.is_empty() { - info!( - "Enclave produced sidechain blocks: {:?}", - signed_blocks.iter().map(|b| b.block.block_number).collect::>() - ); - } else { - debug!("Enclave did not produce sidechain blocks"); - } - - if let Err(e) = self.block_gossiper.gossip_blocks(signed_blocks.clone()) { - error!("Error gossiping blocks: {:?}", e); - // Fixme: returning an error here results in a `HeaderAncestryMismatch` error. - // status = sgx_status_t::SGX_ERROR_UNEXPECTED; - } - - if let Err(e) = self.block_storage.store_blocks(signed_blocks) { - error!("Error storing blocks: {:?}", e); - } status } } @@ -147,19 +103,13 @@ where mod tests { use super::*; - use crate::{ - node_api_factory::MockCreateNodeApi, sidechain_storage::interface::MockBlockStorage, - sync_block_gossiper::MockGossipBlocks, - }; + use crate::node_api_factory::MockCreateNodeApi; #[test] fn given_empty_worker_request_when_submitting_then_return_empty_response() { let mock_node_api_factory = Arc::new(MockCreateNodeApi::new()); - let mock_block_gossiper = Arc::new(MockGossipBlocks::new()); - let mock_block_storage = Arc::new(MockBlockStorage::new()); - let on_chain_ocall = - WorkerOnChainOCall::new(mock_node_api_factory, mock_block_gossiper, mock_block_storage); + let on_chain_ocall = WorkerOnChainOCall::new(mock_node_api_factory); let response = on_chain_ocall.worker_request(Vec::::new().encode()).unwrap(); diff --git a/service/src/tests/integration_tests.rs b/service/src/tests/integration_tests.rs index a7fd047700..4944be7ad4 100644 --- a/service/src/tests/integration_tests.rs +++ b/service/src/tests/integration_tests.rs @@ -30,7 +30,7 @@ use substrate_api_client::{compose_extrinsic, extrinsic::xt_primitives::Unchecke use crate::tests::commons::*; use itp_api_client_extensions::TEEREX; use itp_enclave_api::{ - enclave_base::EnclaveBase, remote_attestation::RemoteAttestation, side_chain::SideChain, + enclave_base::EnclaveBase, remote_attestation::RemoteAttestation, sidechain::Sidechain, }; use itp_settings::files::SIGNING_KEY_FILE; @@ -53,7 +53,7 @@ pub fn perform_ra_works(enclave_api: &E, por let _xt = enclave_api.perform_ra(genesis_hash, nonce, w_url.encode()).unwrap(); } -pub fn call_worker_encrypted_set_balance_works( +pub fn call_worker_encrypted_set_balance_works( enclave_api: &E, port: &str, last_synced_head: Header, @@ -74,7 +74,7 @@ pub fn call_worker_encrypted_set_balance_works( crate::sync_parentchain(enclave_api, &api, last_synced_head) } -pub fn forward_encrypted_unshield_works( +pub fn forward_encrypted_unshield_works( enclave_api: &E, port: &str, last_synced_head: Header, @@ -96,12 +96,12 @@ pub fn forward_encrypted_unshield_works( crate::sync_parentchain(enclave_api, &api, last_synced_head) } -pub fn init_light_client(port: &str, enclave_api: &E) -> Header { +pub fn init_light_client(port: &str, enclave_api: &E) -> Header { let (api, _, _) = setup(enclave_api, None, port); crate::init_light_client(&api, enclave_api) } -pub fn shield_funds_workds( +pub fn shield_funds_workds( enclave_api: &E, port: &str, last_synced_head: Header, diff --git a/service/src/worker.rs b/service/src/worker.rs index 71d0ee89f9..54ed3cbda0 100644 --- a/service/src/worker.rs +++ b/service/src/worker.rs @@ -49,7 +49,6 @@ impl Worker>) -> WorkerResult<()>; async fn gossip_blocks(&self, blocks: Vec) -> WorkerResult<()>; fn peers(&self) -> WorkerResult>; } diff --git a/sidechain/consensus/slots/src/slots.rs b/sidechain/consensus/slots/src/slots.rs index 5f064c8b91..3039e0a837 100644 --- a/sidechain/consensus/slots/src/slots.rs +++ b/sidechain/consensus/slots/src/slots.rs @@ -186,7 +186,7 @@ pub mod sgx { mod tests { use super::*; use itp_sgx_io::SealedIO; - use itp_types::{Block as ParentchainBlock, Header as ParentChainHeader}; + use itp_types::{Block as ParentchainBlock, Header as ParentchainHeader}; use its_primitives::{ traits::{Block as BlockT, SignBlock}, types::block::{Block, SignedBlock}, @@ -233,7 +233,7 @@ mod tests { timestamp: duration_now(), duration: SLOT_DURATION, ends_at: duration_now() + SLOT_DURATION, - parentchain_head: ParentChainHeader { + parentchain_head: ParentchainHeader { parent_hash: Default::default(), number: 1, state_root: Default::default(), @@ -243,8 +243,8 @@ mod tests { } } - pub fn default_header() -> ParentChainHeader { - ParentChainHeader::new( + pub fn default_header() -> ParentchainHeader { + ParentchainHeader::new( Default::default(), Default::default(), Default::default(), diff --git a/sidechain/top-pool-rpc-author/src/api.rs b/sidechain/top-pool-rpc-author/src/api.rs index 8541cb733b..980f0f208e 100644 --- a/sidechain/top-pool-rpc-author/src/api.rs +++ b/sidechain/top-pool-rpc-author/src/api.rs @@ -43,24 +43,24 @@ use std::{boxed::Box, marker::PhantomData, pin::Pin, vec, vec::Vec}; pub type Result = core::result::Result; /// The operation pool logic for full client. -pub struct SideChainApi { +pub struct SidechainApi { _marker: PhantomData, } -impl SideChainApi { +impl SidechainApi { /// Create new operation pool logic. pub fn new() -> Self { - SideChainApi { _marker: Default::default() } + SidechainApi { _marker: Default::default() } } } -impl Default for SideChainApi { +impl Default for SidechainApi { fn default() -> Self { Self::new() } } -impl ChainApi for SideChainApi +impl ChainApi for SidechainApi where Block: BlockT, { diff --git a/sidechain/top-pool-rpc-author/src/initializer.rs b/sidechain/top-pool-rpc-author/src/initializer.rs index ea1653c165..17b086c749 100644 --- a/sidechain/top-pool-rpc-author/src/initializer.rs +++ b/sidechain/top-pool-rpc-author/src/initializer.rs @@ -16,7 +16,7 @@ */ use crate::{ - api::SideChainApi, + api::SidechainApi, author::{Author, AuthorTopFilter}, global_author_container::GlobalAuthorContainer, pool_types::{BPool, EnclaveRpcConnectionRegistry}, @@ -38,7 +38,7 @@ pub fn initialize_top_pool_rpc_author( ) { let rpc_responder = Arc::new(RpcResponder::new(connection_registry)); - let side_chain_api = Arc::new(SideChainApi::::new()); + let side_chain_api = Arc::new(SidechainApi::::new()); let top_pool = Arc::new(BPool::create(PoolOptions::default(), side_chain_api, rpc_responder)); let state_handler = Arc::new(GlobalFileStateHandler); diff --git a/sidechain/top-pool-rpc-author/src/pool_types.rs b/sidechain/top-pool-rpc-author/src/pool_types.rs index bd4521ef81..693340d123 100644 --- a/sidechain/top-pool-rpc-author/src/pool_types.rs +++ b/sidechain/top-pool-rpc-author/src/pool_types.rs @@ -15,7 +15,7 @@ */ -use crate::api::SideChainApi; +use crate::api::SidechainApi; use itc_direct_rpc_server::{ rpc_connection_registry::ConnectionRegistry, rpc_responder::RpcResponder, }; @@ -30,4 +30,4 @@ pub(crate) type EnclaveRpcConnectionRegistry = ConnectionRegistry; -pub type BPool = BasicPool, Block, EnclaveRpcResponder>; +pub type BPool = BasicPool, Block, EnclaveRpcResponder>;