From beccbcefaf62211ffbb3f9250e50e8d108ff1d13 Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 13 May 2025 21:57:02 -0700 Subject: [PATCH 1/7] feat: define signed message --- Cargo.lock | 54 ++++++++++- crates/contracts/core/Cargo.toml | 3 + crates/contracts/core/src/error.rs | 2 + crates/contracts/core/src/handler/execute.rs | 1 + .../core/src/handler/execute/signed.rs | 27 ++++++ crates/contracts/core/src/msg/execute.rs | 1 + .../contracts/core/src/msg/execute/signed.rs | 90 +++++++++++++++++++ crates/contracts/core/src/state.rs | 4 + 8 files changed, 179 insertions(+), 3 deletions(-) create mode 100644 crates/contracts/core/src/handler/execute/signed.rs create mode 100644 crates/contracts/core/src/msg/execute/signed.rs diff --git a/Cargo.lock b/Cargo.lock index 64211d1a..72e06bbc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -262,6 +262,12 @@ version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76a2e8124351fda1ef8aaaa3bbd7ebbcb486bbcd4225aca0aa0d84bb2db8fecb" +[[package]] +name = "arrayvec" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" + [[package]] name = "arrayvec" version = "0.7.6" @@ -578,6 +584,17 @@ dependencies = [ "digest 0.10.7", ] +[[package]] +name = "blake2b_simd" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "afa748e348ad3be8263be728124b24a24f268266f6f5d58af9d75f6a40b5c587" +dependencies = [ + "arrayref", + "arrayvec 0.5.2", + "constant_time_eq 0.1.5", +] + [[package]] name = "blake3" version = "1.8.1" @@ -585,10 +602,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "389a099b34312839e16420d499a9cad9650541715937ffbdd40d36f49e77eeb3" dependencies = [ "arrayref", - "arrayvec", + "arrayvec 0.7.6", "cc", "cfg-if", - "constant_time_eq", + "constant_time_eq 0.3.1", ] [[package]] @@ -956,6 +973,12 @@ dependencies = [ "unicode-xid", ] +[[package]] +name = "constant_time_eq" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" + [[package]] name = "constant_time_eq" version = "0.3.1" @@ -1376,6 +1399,30 @@ dependencies = [ "x509-cert", ] +[[package]] +name = "decaf377" +version = "0.10.1" +source = "git+https://github.com/hu55a1n1/decaf377.git#0945efd1eaf5e2d45441eb99c6f3a0cb3b928512" +dependencies = [ + "cfg-if", + "hex", + "subtle", + "zeroize", +] + +[[package]] +name = "decaf377-rdsa" +version = "0.11.0" +source = "git+https://github.com/dangush/decaf377-rdsa.git#d5b4d57ad8080315064878fcaa6954d6536c6d9b" +dependencies = [ + "blake2b_simd", + "decaf377", + "digest 0.9.0", + "hex", + "rand_core 0.6.4", + "zeroize", +] + [[package]] name = "der" version = "0.7.9" @@ -3897,7 +3944,7 @@ version = "3.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c9fde3d0718baf5bc92f577d652001da0f8d54cd03a7974e118d04fc888dc23d" dependencies = [ - "arrayvec", + "arrayvec 0.7.6", "bitvec", "byte-slice-cast", "const_format", @@ -4346,6 +4393,7 @@ dependencies = [ "cosmwasm-schema", "cosmwasm-std", "cw-storage-plus", + "decaf377-rdsa", "hex", "k256", "quartz-dcap-verifier-msgs", diff --git a/crates/contracts/core/Cargo.toml b/crates/contracts/core/Cargo.toml index 94a239fe..3dbe247a 100644 --- a/crates/contracts/core/Cargo.toml +++ b/crates/contracts/core/Cargo.toml @@ -40,5 +40,8 @@ quartz-dcap-verifier-msgs.workspace = true quartz-tee-ra.workspace = true quartz-tcbinfo-msgs.workspace = true +# fork +decaf377-rdsa = { git = "https://github.com/dangush/decaf377-rdsa.git", default-features = false } + [dev-dependencies] serde_json.workspace = true diff --git a/crates/contracts/core/src/error.rs b/crates/contracts/core/src/error.rs index b9f59401..2f43c23d 100644 --- a/crates/contracts/core/src/error.rs +++ b/crates/contracts/core/src/error.rs @@ -21,6 +21,8 @@ pub enum Error { DcapVerificationQueryError(String), #[error("contract address mismatch")] ContractAddrMismatch, + #[error("invalid session due to missing public key")] + MissingSessionPublicKey, } impl From for Error { diff --git a/crates/contracts/core/src/handler/execute.rs b/crates/contracts/core/src/handler/execute.rs index c4e3dffa..2cbb4df2 100644 --- a/crates/contracts/core/src/handler/execute.rs +++ b/crates/contracts/core/src/handler/execute.rs @@ -2,6 +2,7 @@ pub mod attested; pub mod sequenced; pub mod session_create; pub mod session_set_pub_key; +pub mod signed; use cosmwasm_std::{DepsMut, Env, MessageInfo, Response}; diff --git a/crates/contracts/core/src/handler/execute/signed.rs b/crates/contracts/core/src/handler/execute/signed.rs new file mode 100644 index 00000000..16346d20 --- /dev/null +++ b/crates/contracts/core/src/handler/execute/signed.rs @@ -0,0 +1,27 @@ +use cosmwasm_std::{DepsMut, Env, MessageInfo, Response}; + +use crate::{ + error::Error, + handler::Handler, + msg::execute::signed::{Signed, Verifier}, + state::SESSION, +}; + +impl Handler for Signed +where + M: Handler + AsRef<[u8]>, + S: Verifier, +{ + fn handle( + self, + mut deps: DepsMut<'_>, + env: &Env, + info: &MessageInfo, + ) -> Result { + let session = SESSION.load(deps.storage).map_err(Error::Std)?; + let pub_key = session.pub_key().ok_or(Error::MissingSessionPublicKey)?; + let (msg, sig) = self.into_tuple(); + sig.verify(pub_key, &msg)?; + Handler::handle(msg, deps.branch(), env, info) + } +} diff --git a/crates/contracts/core/src/msg/execute.rs b/crates/contracts/core/src/msg/execute.rs index caa59f1b..4fd883e8 100644 --- a/crates/contracts/core/src/msg/execute.rs +++ b/crates/contracts/core/src/msg/execute.rs @@ -2,6 +2,7 @@ pub mod attested; pub mod sequenced; pub mod session_create; pub mod session_set_pub_key; +pub mod signed; use cosmwasm_schema::cw_serde; use cosmwasm_std::StdError; diff --git a/crates/contracts/core/src/msg/execute/signed.rs b/crates/contracts/core/src/msg/execute/signed.rs new file mode 100644 index 00000000..083b65e2 --- /dev/null +++ b/crates/contracts/core/src/msg/execute/signed.rs @@ -0,0 +1,90 @@ +use crate::error::Error; +use cosmwasm_schema::cw_serde; +use cosmwasm_std::{HexBinary, StdError}; +use decaf377_rdsa::{Signature, SpendAuth, VerificationKey}; + +use crate::msg::HasDomainType; + +#[derive(Clone, Debug, PartialEq)] +pub struct Signed { + msg: M, + sig: S, +} + +impl Signed { + pub fn new(msg: M, sig: S) -> Self { + Self { msg, sig } + } + + pub fn into_tuple(self) -> (M, S) { + let Self { msg, sig } = self; + (msg, sig) + } + + pub fn msg(&self) -> &M { + &self.msg + } + + pub fn sig(&self) -> &S { + &self.sig + } +} + +#[cw_serde] +pub struct RawSigned { + pub msg: RM, + pub sig: RS, +} + +impl TryFrom> for Signed +where + RM: HasDomainType, + RS: HasDomainType, +{ + type Error = StdError; + + fn try_from(value: RawSigned) -> Result { + Ok(Self { + msg: value.msg.try_into()?, + sig: value.sig.try_into()?, + }) + } +} + +impl From> for RawSigned +where + RM: HasDomainType, + RS: HasDomainType, +{ + fn from(value: Signed) -> Self { + Self { + msg: value.msg.into(), + sig: value.sig.into(), + } + } +} + +impl HasDomainType for RawSigned +where + RM: HasDomainType, + RS: HasDomainType, +{ + type DomainType = Signed; +} + +pub trait Verifier { + fn verify(&self, pub_key: HexBinary, msg: impl AsRef<[u8]>) -> Result<(), Error>; +} + +impl Verifier for Signature { + fn verify(&self, pub_key: HexBinary, msg: impl AsRef<[u8]>) -> Result<(), Error> { + let vk: VerificationKey = pub_key.as_slice().try_into().map_err(|e| { + StdError::generic_err(format!("Failed to decode verification key: {e}")) + })?; + + vk.verify(msg.as_ref(), self) + .map_err(|e| StdError::generic_err(format!("Failed to verify signature: {e}")))?; + + Ok(()) + } +} diff --git a/crates/contracts/core/src/state.rs b/crates/contracts/core/src/state.rs index 986bf54a..6a84724d 100644 --- a/crates/contracts/core/src/state.rs +++ b/crates/contracts/core/src/state.rs @@ -244,4 +244,8 @@ impl Session { pub fn nonce(&self) -> Nonce { self.nonce.to_array().expect("correct by construction") } + + pub fn pub_key(self) -> Option { + self.pub_key + } } From f4965b768e770ae6ee1f7a3988279dcaedab25db Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 13 May 2025 22:01:11 -0700 Subject: [PATCH 2/7] fix: cargo fmt --- crates/contracts/core/src/msg/execute/signed.rs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/crates/contracts/core/src/msg/execute/signed.rs b/crates/contracts/core/src/msg/execute/signed.rs index 083b65e2..f4e9faa3 100644 --- a/crates/contracts/core/src/msg/execute/signed.rs +++ b/crates/contracts/core/src/msg/execute/signed.rs @@ -1,9 +1,8 @@ -use crate::error::Error; use cosmwasm_schema::cw_serde; use cosmwasm_std::{HexBinary, StdError}; use decaf377_rdsa::{Signature, SpendAuth, VerificationKey}; -use crate::msg::HasDomainType; +use crate::{error::Error, msg::HasDomainType}; #[derive(Clone, Debug, PartialEq)] pub struct Signed { From 0cb10a893f8a28a7f664975c034696f28c063d07 Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 13 May 2025 22:04:54 -0700 Subject: [PATCH 3/7] fix: update transfer Cargo.lock --- examples/transfers/contracts/Cargo.lock | 81 ++++++++++++++++++++++--- 1 file changed, 72 insertions(+), 9 deletions(-) diff --git a/examples/transfers/contracts/Cargo.lock b/examples/transfers/contracts/Cargo.lock index 98675a9b..9f428b79 100644 --- a/examples/transfers/contracts/Cargo.lock +++ b/examples/transfers/contracts/Cargo.lock @@ -76,7 +76,7 @@ dependencies = [ "ark-serialize", "ark-std", "derivative", - "digest", + "digest 0.10.7", "itertools 0.10.5", "num-bigint", "num-traits", @@ -130,7 +130,7 @@ checksum = "adb7b85a02b83d2f22f89bd5cac66c9c89474240cb6207cb1efc16d098e822a5" dependencies = [ "ark-serialize-derive", "ark-std", - "digest", + "digest 0.10.7", "num-bigint", ] @@ -156,6 +156,18 @@ dependencies = [ "rayon", ] +[[package]] +name = "arrayref" +version = "0.3.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "76a2e8124351fda1ef8aaaa3bbd7ebbcb486bbcd4225aca0aa0d84bb2db8fecb" + +[[package]] +name = "arrayvec" +version = "0.5.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" + [[package]] name = "asn1-rs" version = "0.6.2" @@ -254,6 +266,17 @@ version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de" +[[package]] +name = "blake2b_simd" +version = "0.5.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "afa748e348ad3be8263be728124b24a24f268266f6f5d58af9d75f6a40b5c587" +dependencies = [ + "arrayref", + "arrayvec", + "constant_time_eq", +] + [[package]] name = "block-buffer" version = "0.10.4" @@ -361,6 +384,12 @@ version = "0.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c2459377285ad874054d797f3ccebf984978aa39129f6eafde5cdc8315b612f8" +[[package]] +name = "constant_time_eq" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" + [[package]] name = "cosmwasm-core" version = "2.1.4" @@ -378,7 +407,7 @@ dependencies = [ "ark-ff", "ark-serialize", "cosmwasm-core", - "digest", + "digest 0.10.7", "ecdsa", "ed25519-zebra", "k256", @@ -519,7 +548,7 @@ dependencies = [ "cfg-if", "cpufeatures", "curve25519-dalek-derive", - "digest", + "digest 0.10.7", "fiat-crypto", "rustc_version", "subtle", @@ -622,6 +651,30 @@ version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e8566979429cf69b49a5c740c60791108e86440e8be149bbea4fe54d2c32d6e2" +[[package]] +name = "decaf377" +version = "0.10.1" +source = "git+https://github.com/hu55a1n1/decaf377.git#0945efd1eaf5e2d45441eb99c6f3a0cb3b928512" +dependencies = [ + "cfg-if", + "hex", + "subtle", + "zeroize", +] + +[[package]] +name = "decaf377-rdsa" +version = "0.11.0" +source = "git+https://github.com/dangush/decaf377-rdsa.git#d5b4d57ad8080315064878fcaa6954d6536c6d9b" +dependencies = [ + "blake2b_simd", + "decaf377", + "digest 0.9.0", + "hex", + "rand_core", + "zeroize", +] + [[package]] name = "der" version = "0.7.9" @@ -701,6 +754,15 @@ dependencies = [ "unicode-xid", ] +[[package]] +name = "digest" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066" +dependencies = [ + "generic-array", +] + [[package]] name = "digest" version = "0.10.7" @@ -737,7 +799,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ee27f32b5c5292967d2d4a9d7f1e0b0aed2c15daded5a60300e4abb9d8020bca" dependencies = [ "der", - "digest", + "digest 0.10.7", "elliptic-curve", "rfc6979", "signature", @@ -782,7 +844,7 @@ checksum = "b5e6043086bf7973472e0c7dff2142ea0b680d30e18d9cc40f267efbf222bd47" dependencies = [ "base16ct", "crypto-bigint", - "digest", + "digest 0.10.7", "ff", "generic-array", "group", @@ -922,7 +984,7 @@ version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6c49c37c09c17a53d937dfbb742eb3a961d65a994e6bcdcf37e7399d0cc8ab5e" dependencies = [ - "digest", + "digest 0.10.7", ] [[package]] @@ -1311,6 +1373,7 @@ dependencies = [ "cosmwasm-schema", "cosmwasm-std", "cw-storage-plus", + "decaf377-rdsa", "hex", "k256", "quartz-dcap-verifier-msgs", @@ -1641,7 +1704,7 @@ checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" dependencies = [ "cfg-if", "cpufeatures", - "digest", + "digest 0.10.7", ] [[package]] @@ -1656,7 +1719,7 @@ version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "77549399552de45a898a580c1b41d445bf730df867cc44e6c0233bbc4b8329de" dependencies = [ - "digest", + "digest 0.10.7", "rand_core", ] From b86f64ecc2a6b2bbb9d495cd942cd069db63c9d7 Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 20 May 2025 13:35:49 -0700 Subject: [PATCH 4/7] refactor: more flexible/general-purpose design --- crates/contracts/core/src/error.rs | 2 + .../core/src/handler/execute/signed.rs | 16 +- .../contracts/core/src/msg/execute/signed.rs | 168 ++++++++++++++---- 3 files changed, 140 insertions(+), 46 deletions(-) diff --git a/crates/contracts/core/src/error.rs b/crates/contracts/core/src/error.rs index 2f43c23d..c6f970dd 100644 --- a/crates/contracts/core/src/error.rs +++ b/crates/contracts/core/src/error.rs @@ -9,6 +9,8 @@ pub enum Error { Std(#[from] StdError), #[error("{0}")] RaVerification(#[from] RaVerificationError), + #[error("Signature verification error: {0}")] + SignatureVerification(String), #[error("Not Secp256K1")] K256(K256Error), #[error("invalid session nonce or attempt to reset pub_key")] diff --git a/crates/contracts/core/src/handler/execute/signed.rs b/crates/contracts/core/src/handler/execute/signed.rs index 16346d20..65902673 100644 --- a/crates/contracts/core/src/handler/execute/signed.rs +++ b/crates/contracts/core/src/handler/execute/signed.rs @@ -3,14 +3,13 @@ use cosmwasm_std::{DepsMut, Env, MessageInfo, Response}; use crate::{ error::Error, handler::Handler, - msg::execute::signed::{Signed, Verifier}, - state::SESSION, + msg::execute::signed::{Auth, MsgVeifier, Signed}, }; -impl Handler for Signed +impl Handler for Signed where - M: Handler + AsRef<[u8]>, - S: Verifier, + M: Handler + MsgVeifier, + A: Auth, { fn handle( self, @@ -18,10 +17,9 @@ where env: &Env, info: &MessageInfo, ) -> Result { - let session = SESSION.load(deps.storage).map_err(Error::Std)?; - let pub_key = session.pub_key().ok_or(Error::MissingSessionPublicKey)?; - let (msg, sig) = self.into_tuple(); - sig.verify(pub_key, &msg)?; + let (msg, auth) = self.into_tuple(); + let pub_key = auth.pub_key(deps.as_ref())?; + msg.verify(pub_key, auth.sig())?; Handler::handle(msg, deps.branch(), env, info) } } diff --git a/crates/contracts/core/src/msg/execute/signed.rs b/crates/contracts/core/src/msg/execute/signed.rs index f4e9faa3..b09ddd71 100644 --- a/crates/contracts/core/src/msg/execute/signed.rs +++ b/crates/contracts/core/src/msg/execute/signed.rs @@ -1,89 +1,183 @@ +use std::fmt::Debug; + use cosmwasm_schema::cw_serde; -use cosmwasm_std::{HexBinary, StdError}; -use decaf377_rdsa::{Signature, SpendAuth, VerificationKey}; +use cosmwasm_std::{Deps, HexBinary, StdError}; + +use super::attested::Noop; +use crate::{error::Error, msg::HasDomainType, state::SESSION}; -use crate::{error::Error, msg::HasDomainType}; +pub type AnySigned = Signed>; +pub type EnclaveSigned = Signed>; +pub type UserSigned = Signed>; #[derive(Clone, Debug, PartialEq)] -pub struct Signed { +pub struct Signed { msg: M, - sig: S, + auth: A, } -impl Signed { - pub fn new(msg: M, sig: S) -> Self { - Self { msg, sig } +impl Signed { + pub fn new(msg: M, auth: A) -> Self { + Self { msg, auth } } - pub fn into_tuple(self) -> (M, S) { - let Self { msg, sig } = self; - (msg, sig) + pub fn into_tuple(self) -> (M, A) { + let Self { msg, auth } = self; + (msg, auth) } pub fn msg(&self) -> &M { &self.msg } - pub fn sig(&self) -> &S { - &self.sig + pub fn auth(&self) -> &A { + &self.auth } } #[cw_serde] -pub struct RawSigned { +pub struct RawSigned { pub msg: RM, - pub sig: RS, + pub auth: RA, +} + +impl RawSigned { + pub fn new(msg: RM, auth: RA) -> Self { + Self { msg, auth } + } +} + +impl HasDomainType for RawSigned +where + RM: HasDomainType, + RA: HasDomainType, +{ + type DomainType = Signed; } -impl TryFrom> for Signed +impl TryFrom> for Signed where RM: HasDomainType, - RS: HasDomainType, + RA: HasDomainType, { type Error = StdError; - fn try_from(value: RawSigned) -> Result { + fn try_from(value: RawSigned) -> Result { Ok(Self { msg: value.msg.try_into()?, - sig: value.sig.try_into()?, + auth: value.auth.try_into()?, }) } } -impl From> for RawSigned +impl From> for RawSigned where RM: HasDomainType, - RS: HasDomainType, + RA: HasDomainType, { - fn from(value: Signed) -> Self { + fn from(value: Signed) -> Self { Self { msg: value.msg.into(), - sig: value.sig.into(), + auth: value.auth.into(), } } } -impl HasDomainType for RawSigned +pub trait MsgVeifier { + type PubKey; + type Sig; + + fn verify(&self, pub_key: Self::PubKey, sig: Self::Sig) -> Result<(), Error>; +} + +pub trait Auth { + fn pub_key(&self, deps: Deps<'_>) -> Result; + fn sig(self) -> S; +} + +#[derive(Clone, Debug, PartialEq)] +pub enum AnyAuth { + Enclave(EnclaveAuth), + User(UserAuth), +} + +impl Auth for AnyAuth where - RM: HasDomainType, - RS: HasDomainType, + P: TryFrom + Clone, +

>::Error: Debug, { - type DomainType = Signed; + fn pub_key(&self, deps: Deps<'_>) -> Result { + match self { + Self::Enclave(e) => e.pub_key(deps), + Self::User(u) => u.pub_key(deps), + } + } + + fn sig(self) -> S { + match self { + Self::Enclave(e) => Auth::::sig(e), + Self::User(u) => u.sig(), + } + } +} + +#[derive(Clone, Debug, PartialEq)] +pub struct EnclaveAuth { + pub sig: S, +} + +impl EnclaveAuth { + pub fn new(sig: S) -> Self { + Self { sig } + } +} + +impl Auth for EnclaveAuth +where + P: TryFrom, +

>::Error: Debug, +{ + fn pub_key(&self, deps: Deps<'_>) -> Result { + let session = SESSION.load(deps.storage).map_err(Error::Std)?; + let raw_pub_key = session.pub_key().ok_or(Error::MissingSessionPublicKey)?; + let pub_key = raw_pub_key + .try_into() + .map_err(|e| StdError::generic_err(format!("{e:?}")))?; + Ok(pub_key) + } + + fn sig(self) -> S { + self.sig + } } -pub trait Verifier { - fn verify(&self, pub_key: HexBinary, msg: impl AsRef<[u8]>) -> Result<(), Error>; +#[derive(Clone, Debug, PartialEq)] +pub struct UserAuth { + pub pub_key: P, + pub sig: S, } -impl Verifier for Signature { - fn verify(&self, pub_key: HexBinary, msg: impl AsRef<[u8]>) -> Result<(), Error> { - let vk: VerificationKey = pub_key.as_slice().try_into().map_err(|e| { - StdError::generic_err(format!("Failed to decode verification key: {e}")) - })?; +impl UserAuth { + pub fn new(pub_key: P, sig: S) -> Self { + Self { pub_key, sig } + } +} + +impl Auth for UserAuth { + fn pub_key(&self, _deps: Deps<'_>) -> Result { + Ok(self.pub_key.clone()) + } + + fn sig(self) -> S { + self.sig + } +} - vk.verify(msg.as_ref(), self) - .map_err(|e| StdError::generic_err(format!("Failed to verify signature: {e}")))?; +impl MsgVeifier for Noop { + type PubKey = M::PubKey; + type Sig = M::Sig; - Ok(()) + fn verify(&self, pub_key: Self::PubKey, sig: Self::Sig) -> Result<(), Error> { + self.0.verify(pub_key, sig) } } From d2654bec9884e29599a4bbd881cfbfad95e7a846 Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 20 May 2025 17:00:36 -0700 Subject: [PATCH 5/7] fix: typo --- crates/contracts/core/src/handler/execute/signed.rs | 4 ++-- crates/contracts/core/src/msg/execute/signed.rs | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/crates/contracts/core/src/handler/execute/signed.rs b/crates/contracts/core/src/handler/execute/signed.rs index 65902673..2057bdd6 100644 --- a/crates/contracts/core/src/handler/execute/signed.rs +++ b/crates/contracts/core/src/handler/execute/signed.rs @@ -3,12 +3,12 @@ use cosmwasm_std::{DepsMut, Env, MessageInfo, Response}; use crate::{ error::Error, handler::Handler, - msg::execute::signed::{Auth, MsgVeifier, Signed}, + msg::execute::signed::{Auth, MsgVerifier, Signed}, }; impl Handler for Signed where - M: Handler + MsgVeifier, + M: Handler + MsgVerifier, A: Auth, { fn handle( diff --git a/crates/contracts/core/src/msg/execute/signed.rs b/crates/contracts/core/src/msg/execute/signed.rs index b09ddd71..d6ffa0a7 100644 --- a/crates/contracts/core/src/msg/execute/signed.rs +++ b/crates/contracts/core/src/msg/execute/signed.rs @@ -83,7 +83,7 @@ where } } -pub trait MsgVeifier { +pub trait MsgVerifier { type PubKey; type Sig; @@ -173,7 +173,7 @@ impl Auth for UserAuth { } } -impl MsgVeifier for Noop { +impl MsgVerifier for Noop { type PubKey = M::PubKey; type Sig = M::Sig; From 222c7060a42362a4895c52bedb44f280451cbc1c Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 20 May 2025 18:21:57 -0700 Subject: [PATCH 6/7] refactor: require pub_key for any signed msg --- .../core/src/handler/execute/signed.rs | 2 +- .../contracts/core/src/msg/execute/signed.rs | 90 ++++--------------- 2 files changed, 17 insertions(+), 75 deletions(-) diff --git a/crates/contracts/core/src/handler/execute/signed.rs b/crates/contracts/core/src/handler/execute/signed.rs index 2057bdd6..57dc884a 100644 --- a/crates/contracts/core/src/handler/execute/signed.rs +++ b/crates/contracts/core/src/handler/execute/signed.rs @@ -18,7 +18,7 @@ where info: &MessageInfo, ) -> Result { let (msg, auth) = self.into_tuple(); - let pub_key = auth.pub_key(deps.as_ref())?; + let pub_key = auth.pub_key(); msg.verify(pub_key, auth.sig())?; Handler::handle(msg, deps.branch(), env, info) } diff --git a/crates/contracts/core/src/msg/execute/signed.rs b/crates/contracts/core/src/msg/execute/signed.rs index d6ffa0a7..62ba2649 100644 --- a/crates/contracts/core/src/msg/execute/signed.rs +++ b/crates/contracts/core/src/msg/execute/signed.rs @@ -1,14 +1,12 @@ use std::fmt::Debug; use cosmwasm_schema::cw_serde; -use cosmwasm_std::{Deps, HexBinary, StdError}; +use cosmwasm_std::StdError; use super::attested::Noop; -use crate::{error::Error, msg::HasDomainType, state::SESSION}; +use crate::{error::Error, msg::HasDomainType}; pub type AnySigned = Signed>; -pub type EnclaveSigned = Signed>; -pub type UserSigned = Signed>; #[derive(Clone, Debug, PartialEq)] pub struct Signed { @@ -87,89 +85,33 @@ pub trait MsgVerifier { type PubKey; type Sig; - fn verify(&self, pub_key: Self::PubKey, sig: Self::Sig) -> Result<(), Error>; -} - -pub trait Auth { - fn pub_key(&self, deps: Deps<'_>) -> Result; - fn sig(self) -> S; -} - -#[derive(Clone, Debug, PartialEq)] -pub enum AnyAuth { - Enclave(EnclaveAuth), - User(UserAuth), -} - -impl Auth for AnyAuth -where - P: TryFrom + Clone, -

>::Error: Debug, -{ - fn pub_key(&self, deps: Deps<'_>) -> Result { - match self { - Self::Enclave(e) => e.pub_key(deps), - Self::User(u) => u.pub_key(deps), - } - } - - fn sig(self) -> S { - match self { - Self::Enclave(e) => Auth::::sig(e), - Self::User(u) => u.sig(), - } - } -} - -#[derive(Clone, Debug, PartialEq)] -pub struct EnclaveAuth { - pub sig: S, -} - -impl EnclaveAuth { - pub fn new(sig: S) -> Self { - Self { sig } - } -} - -impl Auth for EnclaveAuth -where - P: TryFrom, -

>::Error: Debug, -{ - fn pub_key(&self, deps: Deps<'_>) -> Result { - let session = SESSION.load(deps.storage).map_err(Error::Std)?; - let raw_pub_key = session.pub_key().ok_or(Error::MissingSessionPublicKey)?; - let pub_key = raw_pub_key - .try_into() - .map_err(|e| StdError::generic_err(format!("{e:?}")))?; - Ok(pub_key) - } - - fn sig(self) -> S { - self.sig - } + fn verify(&self, pub_key: &Self::PubKey, sig: &Self::Sig) -> Result<(), Error>; } #[derive(Clone, Debug, PartialEq)] -pub struct UserAuth { +pub struct AnyAuth { pub pub_key: P, pub sig: S, } -impl UserAuth { +impl AnyAuth { pub fn new(pub_key: P, sig: S) -> Self { Self { pub_key, sig } } } -impl Auth for UserAuth { - fn pub_key(&self, _deps: Deps<'_>) -> Result { - Ok(self.pub_key.clone()) +pub trait Auth { + fn pub_key(&self) -> &P; + fn sig(&self) -> &S; +} + +impl Auth for AnyAuth { + fn pub_key(&self) -> &P { + &self.pub_key } - fn sig(self) -> S { - self.sig + fn sig(&self) -> &S { + &self.sig } } @@ -177,7 +119,7 @@ impl MsgVerifier for Noop { type PubKey = M::PubKey; type Sig = M::Sig; - fn verify(&self, pub_key: Self::PubKey, sig: Self::Sig) -> Result<(), Error> { + fn verify(&self, pub_key: &Self::PubKey, sig: &Self::Sig) -> Result<(), Error> { self.0.verify(pub_key, sig) } } From 74d7183f84789d4eb5cba8be52fd0077b2b5e362 Mon Sep 17 00:00:00 2001 From: Farhad Shabani Date: Tue, 20 May 2025 18:29:47 -0700 Subject: [PATCH 7/7] fix: misc clean-ups + cargo clippy --- Cargo.lock | 54 +------------ crates/contracts/core/Cargo.toml | 3 - crates/contracts/core/src/error.rs | 2 - .../contracts/dcap-verifier/src/contract.rs | 2 +- crates/contracts/tee-ra/src/intel_sgx.rs | 2 +- examples/transfers/contracts/Cargo.lock | 81 +++---------------- examples/transfers/contracts/src/contract.rs | 4 +- 7 files changed, 16 insertions(+), 132 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 72e06bbc..64211d1a 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -262,12 +262,6 @@ version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76a2e8124351fda1ef8aaaa3bbd7ebbcb486bbcd4225aca0aa0d84bb2db8fecb" -[[package]] -name = "arrayvec" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" - [[package]] name = "arrayvec" version = "0.7.6" @@ -584,17 +578,6 @@ dependencies = [ "digest 0.10.7", ] -[[package]] -name = "blake2b_simd" -version = "0.5.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "afa748e348ad3be8263be728124b24a24f268266f6f5d58af9d75f6a40b5c587" -dependencies = [ - "arrayref", - "arrayvec 0.5.2", - "constant_time_eq 0.1.5", -] - [[package]] name = "blake3" version = "1.8.1" @@ -602,10 +585,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "389a099b34312839e16420d499a9cad9650541715937ffbdd40d36f49e77eeb3" dependencies = [ "arrayref", - "arrayvec 0.7.6", + "arrayvec", "cc", "cfg-if", - "constant_time_eq 0.3.1", + "constant_time_eq", ] [[package]] @@ -973,12 +956,6 @@ dependencies = [ "unicode-xid", ] -[[package]] -name = "constant_time_eq" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" - [[package]] name = "constant_time_eq" version = "0.3.1" @@ -1399,30 +1376,6 @@ dependencies = [ "x509-cert", ] -[[package]] -name = "decaf377" -version = "0.10.1" -source = "git+https://github.com/hu55a1n1/decaf377.git#0945efd1eaf5e2d45441eb99c6f3a0cb3b928512" -dependencies = [ - "cfg-if", - "hex", - "subtle", - "zeroize", -] - -[[package]] -name = "decaf377-rdsa" -version = "0.11.0" -source = "git+https://github.com/dangush/decaf377-rdsa.git#d5b4d57ad8080315064878fcaa6954d6536c6d9b" -dependencies = [ - "blake2b_simd", - "decaf377", - "digest 0.9.0", - "hex", - "rand_core 0.6.4", - "zeroize", -] - [[package]] name = "der" version = "0.7.9" @@ -3944,7 +3897,7 @@ version = "3.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c9fde3d0718baf5bc92f577d652001da0f8d54cd03a7974e118d04fc888dc23d" dependencies = [ - "arrayvec 0.7.6", + "arrayvec", "bitvec", "byte-slice-cast", "const_format", @@ -4393,7 +4346,6 @@ dependencies = [ "cosmwasm-schema", "cosmwasm-std", "cw-storage-plus", - "decaf377-rdsa", "hex", "k256", "quartz-dcap-verifier-msgs", diff --git a/crates/contracts/core/Cargo.toml b/crates/contracts/core/Cargo.toml index 3dbe247a..94a239fe 100644 --- a/crates/contracts/core/Cargo.toml +++ b/crates/contracts/core/Cargo.toml @@ -40,8 +40,5 @@ quartz-dcap-verifier-msgs.workspace = true quartz-tee-ra.workspace = true quartz-tcbinfo-msgs.workspace = true -# fork -decaf377-rdsa = { git = "https://github.com/dangush/decaf377-rdsa.git", default-features = false } - [dev-dependencies] serde_json.workspace = true diff --git a/crates/contracts/core/src/error.rs b/crates/contracts/core/src/error.rs index c6f970dd..9783a093 100644 --- a/crates/contracts/core/src/error.rs +++ b/crates/contracts/core/src/error.rs @@ -23,8 +23,6 @@ pub enum Error { DcapVerificationQueryError(String), #[error("contract address mismatch")] ContractAddrMismatch, - #[error("invalid session due to missing public key")] - MissingSessionPublicKey, } impl From for Error { diff --git a/crates/contracts/dcap-verifier/src/contract.rs b/crates/contracts/dcap-verifier/src/contract.rs index 9118ba35..6d37e64b 100644 --- a/crates/contracts/dcap-verifier/src/contract.rs +++ b/crates/contracts/dcap-verifier/src/contract.rs @@ -57,7 +57,7 @@ pub fn query(_deps: Deps, _env: Env, msg: QueryMsg) -> StdResult { to_json_binary(&()) } else { Err(StdError::generic_err( - Error::Dcap(verification_output).to_string(), + Error::Dcap(Box::new(verification_output)).to_string(), )) } } diff --git a/crates/contracts/tee-ra/src/intel_sgx.rs b/crates/contracts/tee-ra/src/intel_sgx.rs index 4fba1409..a06d1b52 100644 --- a/crates/contracts/tee-ra/src/intel_sgx.rs +++ b/crates/contracts/tee-ra/src/intel_sgx.rs @@ -9,5 +9,5 @@ pub enum Error { #[error("Specified MRENCLAVE does not match the report")] MrEnclaveMismatch, #[error("DCAP specific error: {0:?}")] - Dcap(dcap::VerificationOutput), + Dcap(Box>), } diff --git a/examples/transfers/contracts/Cargo.lock b/examples/transfers/contracts/Cargo.lock index 9f428b79..98675a9b 100644 --- a/examples/transfers/contracts/Cargo.lock +++ b/examples/transfers/contracts/Cargo.lock @@ -76,7 +76,7 @@ dependencies = [ "ark-serialize", "ark-std", "derivative", - "digest 0.10.7", + "digest", "itertools 0.10.5", "num-bigint", "num-traits", @@ -130,7 +130,7 @@ checksum = "adb7b85a02b83d2f22f89bd5cac66c9c89474240cb6207cb1efc16d098e822a5" dependencies = [ "ark-serialize-derive", "ark-std", - "digest 0.10.7", + "digest", "num-bigint", ] @@ -156,18 +156,6 @@ dependencies = [ "rayon", ] -[[package]] -name = "arrayref" -version = "0.3.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "76a2e8124351fda1ef8aaaa3bbd7ebbcb486bbcd4225aca0aa0d84bb2db8fecb" - -[[package]] -name = "arrayvec" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b" - [[package]] name = "asn1-rs" version = "0.6.2" @@ -266,17 +254,6 @@ version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de" -[[package]] -name = "blake2b_simd" -version = "0.5.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "afa748e348ad3be8263be728124b24a24f268266f6f5d58af9d75f6a40b5c587" -dependencies = [ - "arrayref", - "arrayvec", - "constant_time_eq", -] - [[package]] name = "block-buffer" version = "0.10.4" @@ -384,12 +361,6 @@ version = "0.9.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c2459377285ad874054d797f3ccebf984978aa39129f6eafde5cdc8315b612f8" -[[package]] -name = "constant_time_eq" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "245097e9a4535ee1e3e3931fcfcd55a796a44c643e8596ff6566d68f09b87bbc" - [[package]] name = "cosmwasm-core" version = "2.1.4" @@ -407,7 +378,7 @@ dependencies = [ "ark-ff", "ark-serialize", "cosmwasm-core", - "digest 0.10.7", + "digest", "ecdsa", "ed25519-zebra", "k256", @@ -548,7 +519,7 @@ dependencies = [ "cfg-if", "cpufeatures", "curve25519-dalek-derive", - "digest 0.10.7", + "digest", "fiat-crypto", "rustc_version", "subtle", @@ -651,30 +622,6 @@ version = "2.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e8566979429cf69b49a5c740c60791108e86440e8be149bbea4fe54d2c32d6e2" -[[package]] -name = "decaf377" -version = "0.10.1" -source = "git+https://github.com/hu55a1n1/decaf377.git#0945efd1eaf5e2d45441eb99c6f3a0cb3b928512" -dependencies = [ - "cfg-if", - "hex", - "subtle", - "zeroize", -] - -[[package]] -name = "decaf377-rdsa" -version = "0.11.0" -source = "git+https://github.com/dangush/decaf377-rdsa.git#d5b4d57ad8080315064878fcaa6954d6536c6d9b" -dependencies = [ - "blake2b_simd", - "decaf377", - "digest 0.9.0", - "hex", - "rand_core", - "zeroize", -] - [[package]] name = "der" version = "0.7.9" @@ -754,15 +701,6 @@ dependencies = [ "unicode-xid", ] -[[package]] -name = "digest" -version = "0.9.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066" -dependencies = [ - "generic-array", -] - [[package]] name = "digest" version = "0.10.7" @@ -799,7 +737,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ee27f32b5c5292967d2d4a9d7f1e0b0aed2c15daded5a60300e4abb9d8020bca" dependencies = [ "der", - "digest 0.10.7", + "digest", "elliptic-curve", "rfc6979", "signature", @@ -844,7 +782,7 @@ checksum = "b5e6043086bf7973472e0c7dff2142ea0b680d30e18d9cc40f267efbf222bd47" dependencies = [ "base16ct", "crypto-bigint", - "digest 0.10.7", + "digest", "ff", "generic-array", "group", @@ -984,7 +922,7 @@ version = "0.12.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6c49c37c09c17a53d937dfbb742eb3a961d65a994e6bcdcf37e7399d0cc8ab5e" dependencies = [ - "digest 0.10.7", + "digest", ] [[package]] @@ -1373,7 +1311,6 @@ dependencies = [ "cosmwasm-schema", "cosmwasm-std", "cw-storage-plus", - "decaf377-rdsa", "hex", "k256", "quartz-dcap-verifier-msgs", @@ -1704,7 +1641,7 @@ checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" dependencies = [ "cfg-if", "cpufeatures", - "digest 0.10.7", + "digest", ] [[package]] @@ -1719,7 +1656,7 @@ version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "77549399552de45a898a580c1b41d445bf730df867cc44e6c0233bbc4b8329de" dependencies = [ - "digest 0.10.7", + "digest", "rand_core", ] diff --git a/examples/transfers/contracts/src/contract.rs b/examples/transfers/contracts/src/contract.rs index 301806cd..eba97cc0 100644 --- a/examples/transfers/contracts/src/contract.rs +++ b/examples/transfers/contracts/src/contract.rs @@ -246,10 +246,10 @@ mod query { } pub fn get_requests(deps: Deps) -> StdResult> { - Ok(REQUESTS.load(deps.storage)?) + REQUESTS.load(deps.storage) } pub fn get_state(deps: Deps) -> StdResult { - Ok(STATE.load(deps.storage)?) + STATE.load(deps.storage) } }