Skip to content

Commit

Permalink
implement failover to backup db
Browse files Browse the repository at this point in the history
  • Loading branch information
brenzi committed Jan 16, 2024
1 parent b5409ac commit 258e17a
Show file tree
Hide file tree
Showing 3 changed files with 50 additions and 7 deletions.
45 changes: 41 additions & 4 deletions core/parentchain/light-client/src/io.rs
Original file line number Diff line number Diff line change
Expand Up @@ -126,13 +126,47 @@ impl<B: Block, LightClientState: Decode + Encode + Debug> LightClientSealing
// unseals db with automatic failover to db backup
fn unseal(&self) -> Result<LightClientState> {
Ok(unseal(self.db_path())
.or(unseal(self.backup_path()))
.or_else(|e| {
warn!(
"can't unseal db at {:?}. error {:?}. trying backup at {:?}",
self.db_path(),
e,
self.backup_path()
);
// create a copy because we will overwrite the db in the next step
fs::copy(self.db_path(), self.db_path().with_extension("cantunseal")).and_then(
|_| {
fs::copy(self.backup_path(), self.db_path()).and_then(|_| {
unseal(self.db_path()).map_err(|e| {
warn!("{:?}", e);
e
})
})
},
)
})
.map(|b| Decode::decode(&mut b.as_slice()))??)
}

// checks if either the db or its backup can be opened
// checks if either the db or its backup can be opened in opaque mode (no unseal)
fn exists(&self) -> bool {
SgxFile::open(self.db_path()).or(SgxFile::open(self.backup_path())).is_ok()
debug!("check if db exists at {:?}", self.db_path());
fs::File::open(self.db_path())
.or_else(|e| {
warn!(
"can't open db at {:?}. error: {:?}. trying restore backup at {:?}",
self.db_path(),
e,
self.backup_path()
);
fs::copy(self.backup_path(), self.db_path())
.and_then(|_| fs::File::open(self.db_path()))
.map_err(|e| {
warn!("{:?}", e);
e
})
})
.is_ok()
}

fn path(&self) -> &Path {
Expand Down Expand Up @@ -261,9 +295,11 @@ where
OCallApi: EnclaveOnChainOCallApi,
LightClientSeal: LightClientSealing<LightClientState = LightValidationState<B>>,
{
trace!("[{:?}] init light client db", parentchain_id);
if !seal.exists() {
info!(
"[Enclave] ChainRelay DB for parachain validator not found, creating new! {}",
"[{:?}] ChainRelay DB for parachain validator not found, creating new! {}",
parentchain_id,
seal.path().display()
);
let validator = init_parachain_validator::<B, OCallApi>(
Expand All @@ -276,6 +312,7 @@ where
}

let validation_state = seal.unseal()?;
info!("unseal success");
let genesis_hash = validation_state.genesis_hash()?;

let init_state = if genesis_hash == params.genesis_header.hash() {
Expand Down
10 changes: 9 additions & 1 deletion enclave-runtime/src/initialization/parentchain/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ use itc_parentchain::{
};
use itp_component_container::ComponentInitializer;
use itp_settings::worker_mode::ProvideWorkerMode;

use log::*;
use std::{path::PathBuf, vec::Vec};

mod common;
Expand All @@ -61,6 +61,10 @@ pub(crate) fn init_parentchain_components<WorkerModeProvider: ProvideWorkerMode>
) -> Result<Vec<u8>> {
match ParentchainInitParams::decode(&mut encoded_params.as_slice())? {
ParentchainInitParams::Parachain { id, shard, params } => {
info!(
"[{:?}] initializing parachain parentchain components for shard: {:?}",
id, shard
);
let shard_creation_info = get_shard_creation_info_internal(shard)?;

// todo: query timestamp of creation header to give a creation reference to target_a/b as well in order to fast-sync
Expand Down Expand Up @@ -104,6 +108,10 @@ pub(crate) fn init_parentchain_components<WorkerModeProvider: ProvideWorkerMode>
}
},
ParentchainInitParams::Solochain { id, shard, params } => {
info!(
"[{:?}] initializing solochain parentchain components for shard: {:?}",
id, shard
);
let shard_creation_info = get_shard_creation_info_internal(shard)?;
// todo: query timestamp of creation header to give a creation reference to target_a/b as well in order to fast-sync
match id {
Expand Down
2 changes: 0 additions & 2 deletions enclave-runtime/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -394,8 +394,6 @@ pub unsafe extern "C" fn init_parentchain_components(
latest_header: *mut u8,
latest_header_size: usize,
) -> sgx_status_t {
info!("Initializing light client!");

let encoded_params = slice::from_raw_parts(params, params_size);
let latest_header_slice = slice::from_raw_parts_mut(latest_header, latest_header_size);

Expand Down

0 comments on commit 258e17a

Please sign in to comment.