From 2fdbc91e60fdb90a331772ae91b70ee78b14d584 Mon Sep 17 00:00:00 2001 From: Eric Swanson Date: Mon, 16 Nov 2020 12:45:49 -0800 Subject: [PATCH 1/9] feat: response authentication: fetch root key for dev instances https://github.com/dfinity/agent-rs/issues/78 --- ic-agent/src/agent/mod.rs | 11 +++++++++++ ic-agent/src/agent/status.rs | 11 +++++++++++ 2 files changed, 22 insertions(+) diff --git a/ic-agent/src/agent/mod.rs b/ic-agent/src/agent/mod.rs index 6e692d19..495edcfb 100644 --- a/ic-agent/src/agent/mod.rs +++ b/ic-agent/src/agent/mod.rs @@ -30,6 +30,7 @@ use status::Status; use std::convert::TryFrom; use std::str::from_utf8; +use std::sync::RwLock; use std::time::Duration; const DOMAIN_SEPARATOR: &[u8; 11] = b"\x0Aic-request"; @@ -101,6 +102,7 @@ pub struct Agent { identity: Box, password_manager: Option>, ingress_expiry_duration: Duration, + root_key: RwLock>, } impl Agent { @@ -136,9 +138,18 @@ impl Agent { ingress_expiry_duration: config .ingress_expiry_duration .unwrap_or_else(|| Duration::from_secs(300)), + root_key: RwLock::new(vec![]), }) } + pub async fn fetch_root_key(&self) -> Result<(), AgentError> { + let status = self.status().await?; + // todo something something + let mut x = self.root_key.write().unwrap(); + *x = status.root_key.unwrap().clone(); + Ok(()) + } + fn get_expiry_date(&self) -> u64 { // TODO(hansl): evaluate if we need this on the agent side (my hunch is we don't). let permitted_drift = Duration::from_secs(60); diff --git a/ic-agent/src/agent/status.rs b/ic-agent/src/agent/status.rs index 5e8d394d..bc44852d 100644 --- a/ic-agent/src/agent/status.rs +++ b/ic-agent/src/agent/status.rs @@ -52,6 +52,9 @@ pub struct Status { /// Optional. The precise git revision of the Internet Computer implementation. pub impl_revision: Option, + /// Optional. The root key + pub root_key: Option>, + /// Contains any additional values that the replica gave as status. pub values: BTreeMap>, } @@ -136,12 +139,20 @@ impl std::convert::TryFrom<&serde_cbor::Value> for Status { None } }); + let root_key: Option> = map.get("root_key").and_then(|v| { + if let Value::Bytes(bytes) = v.as_ref() { + Some(bytes.to_owned()) + } else { + None + } + }); Ok(Status { ic_api_version, impl_source, impl_version, impl_revision, + root_key, values: map, }) } From e6b61beb278df0f3759a60b65daba48f8fb112f4 Mon Sep 17 00:00:00 2001 From: Eric Swanson Date: Mon, 16 Nov 2020 17:41:43 -0800 Subject: [PATCH 2/9] checkpoint: verifies BLS signature, including delegation --- ic-agent/src/agent/agent_error.rs | 9 +++++ ic-agent/src/agent/mod.rs | 65 +++++++++++++++++++++++++++++-- ic-agent/src/agent/replica_api.rs | 11 ++++++ ref-tests/src/utils.rs | 1 + ref-tests/tests/ic-ref.rs | 4 +- 5 files changed, 85 insertions(+), 5 deletions(-) diff --git a/ic-agent/src/agent/agent_error.rs b/ic-agent/src/agent/agent_error.rs index d712c736..27ecdd05 100644 --- a/ic-agent/src/agent/agent_error.rs +++ b/ic-agent/src/agent/agent_error.rs @@ -78,6 +78,15 @@ pub enum AgentError { #[error("The request status ({1}) at path {0:?} is invalid.")] InvalidRequestStatus(Vec