From 2d7855a17bb2591b358d028f4836ca658e9612f0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Thu, 25 Jul 2024 11:57:07 +0200 Subject: [PATCH 1/7] Add dynamic estimation of remaining credential space --- Cargo.toml | 10 ++++--- fuzz/Cargo.toml | 8 +++-- src/ctap2.rs | 18 ++--------- src/ctap2/credential_management.rs | 48 ++---------------------------- src/lib.rs | 48 +++++++++++++++++++++++++++++- 5 files changed, 63 insertions(+), 69 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index f2ee0f2..13f2b6b 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -24,6 +24,7 @@ serde_bytes = { version = "0.11.14", default-features = false } serde-indexed = "0.1.0" sha2 = { version = "0.10", default-features = false } trussed = "0.1" +trussed-fs-info = "0.1.0" trussed-hkdf = { version = "0.2.0" } trussed-chunked = { version = "0.1.0", optional = true } @@ -65,7 +66,7 @@ p256 = { version = "0.13.2", features = ["ecdh"] } rand = "0.8.4" sha2 = "0.10" trussed = { version = "0.1", features = ["virt"] } -trussed-staging = { version = "0.3.0", features = ["chunked", "hkdf", "virt"] } +trussed-staging = { version = "0.3.0", features = ["chunked", "hkdf", "virt", "fs-info"] } trussed-usbip = { version = "0.0.1", default-features = false, features = ["ctaphid"] } usbd-ctaphid = "0.1.0" x509-parser = "0.16.0" @@ -78,10 +79,11 @@ cbor-smol = { git = "https://github.com/sosthene-nitrokey/cbor-smol.git", rev = ctap-types = { git = "https://github.com/trussed-dev/ctap-types.git", rev = "72eb68b61e3f14957c5ab89bd22f776ac860eb62" } ctaphid-dispatch = { git = "https://github.com/trussed-dev/ctaphid-dispatch.git", rev = "57cb3317878a8593847595319aa03ef17c29ec5b" } apdu-dispatch = { git = "https://github.com/trussed-dev/apdu-dispatch.git", rev = "915fc237103fcecc29d0f0b73391f19abf6576de" } -littlefs2 = { git = "https://github.com/trussed-dev/littlefs2.git", rev = "2b45a7559ff44260c6dd693e4cb61f54ae5efc53" } -trussed = { git = "https://github.com/trussed-dev/trussed.git", rev = "b548d379dcbd67d29453d94847b7bc33ae92e673" } +trussed = { git = "https://github.com/trussed-dev/trussed.git", rev = "a055e4f79a10122c8c0c882161442e6e02f0c5c6" } +littlefs2 = { git = "https://github.com/trussed-dev/littlefs2.git", rev = "960e57d9fc0d209308c8e15dc26252bbe1ff6ba8" } trussed-chunked = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "chunked-v0.1.0" } +trussed-fs-info = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } trussed-hkdf = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "hkdf-v0.2.0" } -trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "v0.3.0" } +trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } trussed-usbip = { git = "https://github.com/Nitrokey/pc-usbip-runner.git", tag = "v0.0.1-nitrokey.1" } usbd-ctaphid = { git = "https://github.com/trussed-dev/usbd-ctaphid.git", rev = "dcff9009c3cd1ef9e5b09f8f307aca998fc9a8c8" } diff --git a/fuzz/Cargo.toml b/fuzz/Cargo.toml index 800adbf..765d813 100644 --- a/fuzz/Cargo.toml +++ b/fuzz/Cargo.toml @@ -10,7 +10,7 @@ cargo-fuzz = true [dependencies] ctap-types = { version = "0.2.0", features = ["arbitrary"] } libfuzzer-sys = "0.4" -trussed-staging = { version = "0.3.0", features = ["chunked", "hkdf", "virt"] } +trussed-staging = { version = "0.3.0", features = ["chunked", "hkdf", "virt", "fs-info"] } [dependencies.fido-authenticator] path = ".." @@ -24,9 +24,11 @@ bench = false [patch.crates-io] ctap-types = { git = "https://github.com/trussed-dev/ctap-types.git", rev = "72eb68b61e3f14957c5ab89bd22f776ac860eb62" } -littlefs2 = { git = "https://github.com/trussed-dev/littlefs2.git", rev = "2b45a7559ff44260c6dd693e4cb61f54ae5efc53" } -trussed = { git = "https://github.com/trussed-dev/trussed.git", rev = "b548d379dcbd67d29453d94847b7bc33ae92e673" } +trussed = { git = "https://github.com/trussed-dev/trussed.git", rev = "a055e4f79a10122c8c0c882161442e6e02f0c5c6" } +littlefs2 = { git = "https://github.com/trussed-dev/littlefs2.git", rev = "960e57d9fc0d209308c8e15dc26252bbe1ff6ba8" } trussed-chunked = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "chunked-v0.1.0" } trussed-hkdf = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "hkdf-v0.2.0" } trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "v0.3.0" } cbor-smol = { git = "https://github.com/sosthene-nitrokey/cbor-smol.git", rev = "9a77dc9b528b08f531d76b44af2f5336c4ef17e0"} +trussed-fs-info = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } +trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } diff --git a/src/ctap2.rs b/src/ctap2.rs index 1ef0737..89bec75 100644 --- a/src/ctap2.rs +++ b/src/ctap2.rs @@ -393,21 +393,7 @@ impl Authenticator for crate::Authenti self.delete_resident_key_by_user_id(&rp_id_hash, &credential.user.id) .ok(); - let mut key_store_full = false; - - // then check the maximum number of RK credentials - if let Some(max_count) = self.config.max_resident_credential_count { - let mut cm = credential_management::CredentialManagement::new(self); - let metadata = cm.get_creds_metadata(); - let count = metadata - .existing_resident_credentials_count - .unwrap_or(max_count); - debug!("resident cred count: {} (max: {})", count, max_count); - if count >= max_count { - error!("maximum resident credential count reached"); - key_store_full = true; - } - } + let mut key_store_full = !self.can_fit(serialized_credential.len()); if !key_store_full { // then store key, making it resident @@ -1870,7 +1856,7 @@ impl crate::Authenticator { ); } else { info!("deleting parent {:?} as this was its last RK", &rp_path); - syscall!(self.trussed.remove_dir(Location::Internal, rp_path,)); + try_syscall!(self.trussed.remove_dir(Location::Internal, rp_path,)).ok(); } } diff --git a/src/ctap2/credential_management.rs b/src/ctap2/credential_management.rs index 527fc52..08dccd9 100644 --- a/src/ctap2/credential_management.rs +++ b/src/ctap2/credential_management.rs @@ -15,7 +15,6 @@ use ctap_types::{ }; use crate::{ - constants::MAX_RESIDENT_CREDENTIALS_GUESSTIMATE, credential::FullCredential, state::{CredentialManagementEnumerateCredentials, CredentialManagementEnumerateRps}, Authenticator, Result, TrussedRequirements, UserPresence, @@ -65,53 +64,12 @@ where info!("get metadata"); let mut response: Response = Default::default(); - let max_resident_credentials = self - .config - .max_resident_credential_count - .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE); + let max_resident_credentials = self.estimate_remaining(); response.existing_resident_credentials_count = Some(0); response.max_possible_remaining_residential_credentials_count = - Some(max_resident_credentials); + Some(max_resident_credentials.try_into().unwrap_or(u32::MAX)); - let dir = PathBuf::from(b"rk"); - let maybe_first_rp = - syscall!(self - .trussed - .read_dir_first(Location::Internal, dir.clone(), None)) - .entry; - - let first_rp = match maybe_first_rp { - None => return response, - Some(rp) => rp, - }; - - let (mut num_rks, _) = self.count_rp_rks(PathBuf::from(first_rp.path())); - let mut last_rp = PathBuf::from(first_rp.file_name()); - - loop { - syscall!(self - .trussed - .read_dir_first(Location::Internal, dir.clone(), Some(last_rp),)) - .entry - .unwrap(); - let maybe_next_rp = syscall!(self.trussed.read_dir_next()).entry; - - match maybe_next_rp { - None => { - response.existing_resident_credentials_count = Some(num_rks); - response.max_possible_remaining_residential_credentials_count = - Some(max_resident_credentials.saturating_sub(num_rks)); - return response; - } - Some(rp) => { - last_rp = PathBuf::from(rp.file_name()); - info!("counting.."); - let (this_rp_rk_count, _) = self.count_rp_rks(PathBuf::from(rp.path())); - info!("{:?}", this_rp_rk_count); - num_rks += this_rp_rk_count; - } - } - } + response } pub fn first_relying_party(&mut self) -> Result { diff --git a/src/lib.rs b/src/lib.rs index e6e576a..db3013e 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -20,7 +20,12 @@ generate_macros!(); use core::time::Duration; -use trussed::{client, syscall, types::Message, Client as TrussedClient}; +use trussed::{ + client, syscall, + types::{Location, Message}, + Client as TrussedClient, +}; +use trussed_fs_info::{FsInfoClient, FsInfoReply}; use trussed_hkdf::HkdfClient; /// Re-export of `ctap-types` authenticator errors. @@ -38,6 +43,8 @@ pub mod state; pub use ctap2::large_blobs::Config as LargeBlobsConfig; +use crate::constants::MAX_RESIDENT_CREDENTIALS_GUESSTIMATE; + /// Results with our [`Error`]. pub type Result = core::result::Result; @@ -57,6 +64,7 @@ pub trait TrussedRequirements: + client::Sha256 + client::HmacSha256 + client::Ed255 // + client::Totp + + FsInfoClient + HkdfClient + ExtensionRequirements { @@ -70,6 +78,7 @@ impl TrussedRequirements for T where + client::Sha256 + client::HmacSha256 + client::Ed255 // + client::Totp + + FsInfoClient + HkdfClient + ExtensionRequirements { @@ -266,6 +275,43 @@ where } } + fn estimate_remaining_inner(info: &FsInfoReply) -> usize { + let block_size = info.block_info.as_ref().map(|i| i.size).unwrap_or(255); + // 1 block for the directory, 1 for the private key, 400 bytes for a reasonnable key and metadata + let size_taken = 2 * block_size + 400; + // Remove 5 block kept as buffer + (info.available_space - 5 * block_size) / size_taken + } + + fn estimate_remaining(&mut self) -> usize { + let info = syscall!(self.trussed.fs_info(Location::Internal)); + debug!("Got filesystem info: {info:?}"); + Self::estimate_remaining_inner(&info).min( + self.config + .max_resident_credential_count + .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE) as usize, + ) + } + + fn can_fit_inner(info: &FsInfoReply, size: usize) -> bool { + let block_size = info.block_info.as_ref().map(|i| i.size).unwrap_or(255); + // 1 block for the rp directory, 5 block of margin, 50 bytes for a reasonnable metadata + let size_taken = 6 * block_size + size + 50; + size_taken < info.available_space + } + + /// Can a credential of size `size` be stored with safe margins + fn can_fit(&mut self, size: usize) -> bool { + debug!("Can fit for {size} bytes"); + let info = syscall!(self.trussed.fs_info(Location::Internal)); + debug!("Got filesystem info: {info:?}"); + debug!( + "Available storage: {}", + Self::estimate_remaining_inner(&info) + ); + Self::can_fit_inner(&info, size) + } + fn hash(&mut self, data: &[u8]) -> [u8; 32] { let hash = syscall!(self.trussed.hash_sha256(data)).hash; hash.as_slice().try_into().expect("hash should fit") From b43596f7376100dbe00a7c960f65328ffcf2c0bf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Fri, 26 Jul 2024 11:01:46 +0200 Subject: [PATCH 2/7] Fix credential count and add back hard limit --- src/ctap2.rs | 18 ++++++------- src/ctap2/credential_management.rs | 41 +++++++++++++++++++++++++++++- 2 files changed, 49 insertions(+), 10 deletions(-) diff --git a/src/ctap2.rs b/src/ctap2.rs index 89bec75..ee85736 100644 --- a/src/ctap2.rs +++ b/src/ctap2.rs @@ -1,5 +1,6 @@ //! The `ctap_types::ctap2::Authenticator` implementation. +use credential_management::CredentialManagement; use ctap_types::{ ctap2::{ self, client_pin::Permissions, AttestationFormatsPreference, AttestationStatement, @@ -21,15 +22,9 @@ use trussed::{ }; use crate::{ - constants, + constants::{self, MAX_RESIDENT_CREDENTIALS_GUESSTIMATE}, credential::{self, Credential, FullCredential, Key, StrippedCredential}, - format_hex, - state::{ - self, - // // (2022-02-27): 9288 bytes - // MinCredentialHeap, - }, - Result, SigningAlgorithm, TrussedRequirements, UserPresence, + format_hex, state, Result, SigningAlgorithm, TrussedRequirements, UserPresence, }; #[allow(unused_imports)] @@ -393,7 +388,12 @@ impl Authenticator for crate::Authenti self.delete_resident_key_by_user_id(&rp_id_hash, &credential.user.id) .ok(); - let mut key_store_full = !self.can_fit(serialized_credential.len()); + let mut key_store_full = !self.can_fit(serialized_credential.len()) + || CredentialManagement::new(self).count_credentials() + >= self + .config + .max_resident_credential_count + .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE); if !key_store_full { // then store key, making it resident diff --git a/src/ctap2/credential_management.rs b/src/ctap2/credential_management.rs index 08dccd9..da67813 100644 --- a/src/ctap2/credential_management.rs +++ b/src/ctap2/credential_management.rs @@ -65,13 +65,52 @@ where let mut response: Response = Default::default(); let max_resident_credentials = self.estimate_remaining(); - response.existing_resident_credentials_count = Some(0); + response.existing_resident_credentials_count = Some(self.count_credentials()); response.max_possible_remaining_residential_credentials_count = Some(max_resident_credentials.try_into().unwrap_or(u32::MAX)); response } + pub fn count_credentials(&mut self) -> u32 { + let dir = PathBuf::from(b"rk"); + let maybe_first_rp = + syscall!(self + .trussed + .read_dir_first(Location::Internal, dir.clone(), None)) + .entry; + + let first_rp = match maybe_first_rp { + None => return 0, + Some(rp) => rp, + }; + + let (mut num_rks, _) = self.count_rp_rks(PathBuf::from(first_rp.path())); + let mut last_rp = PathBuf::from(first_rp.file_name()); + + loop { + syscall!(self + .trussed + .read_dir_first(Location::Internal, dir.clone(), Some(last_rp),)) + .entry + .unwrap(); + let maybe_next_rp = syscall!(self.trussed.read_dir_next()).entry; + + match maybe_next_rp { + None => { + return num_rks; + } + Some(rp) => { + last_rp = PathBuf::from(rp.file_name()); + info!("counting.."); + let (this_rp_rk_count, _) = self.count_rp_rks(PathBuf::from(rp.path())); + info!("{:?}", this_rp_rk_count); + num_rks += this_rp_rk_count; + } + } + } + } + pub fn first_relying_party(&mut self) -> Result { info!("first rp"); From 4f8e8a4bf6e1a2102da8e9254b22cfeec2100cd7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Fri, 26 Jul 2024 11:34:24 +0200 Subject: [PATCH 3/7] Remove unnecessary conversions --- src/ctap2/credential_management.rs | 2 +- src/lib.rs | 8 ++++---- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/ctap2/credential_management.rs b/src/ctap2/credential_management.rs index da67813..2a5fa06 100644 --- a/src/ctap2/credential_management.rs +++ b/src/ctap2/credential_management.rs @@ -67,7 +67,7 @@ where let max_resident_credentials = self.estimate_remaining(); response.existing_resident_credentials_count = Some(self.count_credentials()); response.max_possible_remaining_residential_credentials_count = - Some(max_resident_credentials.try_into().unwrap_or(u32::MAX)); + Some(max_resident_credentials); response } diff --git a/src/lib.rs b/src/lib.rs index db3013e..2f93b93 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -275,21 +275,21 @@ where } } - fn estimate_remaining_inner(info: &FsInfoReply) -> usize { + fn estimate_remaining_inner(info: &FsInfoReply) -> u32 { let block_size = info.block_info.as_ref().map(|i| i.size).unwrap_or(255); // 1 block for the directory, 1 for the private key, 400 bytes for a reasonnable key and metadata let size_taken = 2 * block_size + 400; // Remove 5 block kept as buffer - (info.available_space - 5 * block_size) / size_taken + ((info.available_space - 5 * block_size) / size_taken) as u32 } - fn estimate_remaining(&mut self) -> usize { + fn estimate_remaining(&mut self) -> u32 { let info = syscall!(self.trussed.fs_info(Location::Internal)); debug!("Got filesystem info: {info:?}"); Self::estimate_remaining_inner(&info).min( self.config .max_resident_credential_count - .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE) as usize, + .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE), ) } From 4f95f963c2e69e230136e545ff17262c033f49b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Wed, 31 Jul 2024 15:20:24 +0200 Subject: [PATCH 4/7] Fix compilation --- fuzz/Cargo.toml | 1 - 1 file changed, 1 deletion(-) diff --git a/fuzz/Cargo.toml b/fuzz/Cargo.toml index 765d813..5adc5ca 100644 --- a/fuzz/Cargo.toml +++ b/fuzz/Cargo.toml @@ -28,7 +28,6 @@ trussed = { git = "https://github.com/trussed-dev/trussed.git", rev = "a055e4f79 littlefs2 = { git = "https://github.com/trussed-dev/littlefs2.git", rev = "960e57d9fc0d209308c8e15dc26252bbe1ff6ba8" } trussed-chunked = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "chunked-v0.1.0" } trussed-hkdf = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "hkdf-v0.2.0" } -trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", tag = "v0.3.0" } cbor-smol = { git = "https://github.com/sosthene-nitrokey/cbor-smol.git", rev = "9a77dc9b528b08f531d76b44af2f5336c4ef17e0"} trussed-fs-info = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } trussed-staging = { git = "https://github.com/trussed-dev/trussed-staging.git", rev = "170ab14f3bb6760399749d78e1b94e3b70106739" } From 741348fd506ddc40caad0d335f7b08666bd40c09 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Thu, 1 Aug 2024 10:49:31 +0200 Subject: [PATCH 5/7] Don't use estimate if block size is not available --- src/ctap2.rs | 2 +- src/ctap2/credential_management.rs | 11 +++++++++-- src/lib.rs | 24 +++++++++--------------- 3 files changed, 19 insertions(+), 18 deletions(-) diff --git a/src/ctap2.rs b/src/ctap2.rs index ee85736..50c5e28 100644 --- a/src/ctap2.rs +++ b/src/ctap2.rs @@ -388,7 +388,7 @@ impl Authenticator for crate::Authenti self.delete_resident_key_by_user_id(&rp_id_hash, &credential.user.id) .ok(); - let mut key_store_full = !self.can_fit(serialized_credential.len()) + let mut key_store_full = self.can_fit(serialized_credential.len()) == Some(false) || CredentialManagement::new(self).count_credentials() >= self .config diff --git a/src/ctap2/credential_management.rs b/src/ctap2/credential_management.rs index 2a5fa06..15134d3 100644 --- a/src/ctap2/credential_management.rs +++ b/src/ctap2/credential_management.rs @@ -15,6 +15,7 @@ use ctap_types::{ }; use crate::{ + constants::MAX_RESIDENT_CREDENTIALS_GUESSTIMATE, credential::FullCredential, state::{CredentialManagementEnumerateCredentials, CredentialManagementEnumerateRps}, Authenticator, Result, TrussedRequirements, UserPresence, @@ -65,9 +66,15 @@ where let mut response: Response = Default::default(); let max_resident_credentials = self.estimate_remaining(); - response.existing_resident_credentials_count = Some(self.count_credentials()); + let credential_count = self.count_credentials(); + response.existing_resident_credentials_count = Some(credential_count); response.max_possible_remaining_residential_credentials_count = - Some(max_resident_credentials); + Some(max_resident_credentials.unwrap_or_else(|| { + self.config + .max_resident_credential_count + .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE) + .saturating_sub(credential_count) + })); response } diff --git a/src/lib.rs b/src/lib.rs index 2f93b93..5a83805 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -43,8 +43,6 @@ pub mod state; pub use ctap2::large_blobs::Config as LargeBlobsConfig; -use crate::constants::MAX_RESIDENT_CREDENTIALS_GUESSTIMATE; - /// Results with our [`Error`]. pub type Result = core::result::Result; @@ -275,33 +273,29 @@ where } } - fn estimate_remaining_inner(info: &FsInfoReply) -> u32 { - let block_size = info.block_info.as_ref().map(|i| i.size).unwrap_or(255); + fn estimate_remaining_inner(info: &FsInfoReply) -> Option { + let block_size = info.block_info.as_ref()?.size; // 1 block for the directory, 1 for the private key, 400 bytes for a reasonnable key and metadata let size_taken = 2 * block_size + 400; // Remove 5 block kept as buffer - ((info.available_space - 5 * block_size) / size_taken) as u32 + Some((info.available_space.saturating_sub(5 * block_size) / size_taken) as u32) } - fn estimate_remaining(&mut self) -> u32 { + fn estimate_remaining(&mut self) -> Option { let info = syscall!(self.trussed.fs_info(Location::Internal)); debug!("Got filesystem info: {info:?}"); - Self::estimate_remaining_inner(&info).min( - self.config - .max_resident_credential_count - .unwrap_or(MAX_RESIDENT_CREDENTIALS_GUESSTIMATE), - ) + Self::estimate_remaining_inner(&info) } - fn can_fit_inner(info: &FsInfoReply, size: usize) -> bool { - let block_size = info.block_info.as_ref().map(|i| i.size).unwrap_or(255); + fn can_fit_inner(info: &FsInfoReply, size: usize) -> Option { + let block_size = info.block_info.as_ref()?.size; // 1 block for the rp directory, 5 block of margin, 50 bytes for a reasonnable metadata let size_taken = 6 * block_size + size + 50; - size_taken < info.available_space + Some(size_taken < info.available_space) } /// Can a credential of size `size` be stored with safe margins - fn can_fit(&mut self, size: usize) -> bool { + fn can_fit(&mut self, size: usize) -> Option { debug!("Can fit for {size} bytes"); let info = syscall!(self.trussed.fs_info(Location::Internal)); debug!("Got filesystem info: {info:?}"); From e763a713ac2ac7e268c7f7ef84e644f4c3a41352 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Thu, 1 Aug 2024 11:10:49 +0200 Subject: [PATCH 6/7] Apply suggestion --- src/lib.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/lib.rs b/src/lib.rs index 5a83805..2166238 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -295,6 +295,8 @@ where } /// Can a credential of size `size` be stored with safe margins + /// + /// This assumes that the key has already been generated and is stored. fn can_fit(&mut self, size: usize) -> Option { debug!("Can fit for {size} bytes"); let info = syscall!(self.trussed.fs_info(Location::Internal)); From 0f51cb707e1132ac8a7cd2e8a0d9f74097ac0e03 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sosth=C3=A8ne=20Gu=C3=A9don?= Date: Thu, 1 Aug 2024 11:26:11 +0200 Subject: [PATCH 7/7] Fix CI --- src/ctap2/large_blobs.rs | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/src/ctap2/large_blobs.rs b/src/ctap2/large_blobs.rs index 094a06e..005695e 100644 --- a/src/ctap2/large_blobs.rs +++ b/src/ctap2/large_blobs.rs @@ -1,11 +1,13 @@ use ctap_types::{sizes::LARGE_BLOB_MAX_FRAGMENT_LENGTH, Error}; use trussed::{ - client::Client, config::MAX_MESSAGE_LENGTH, - syscall, try_syscall, - types::{Bytes, Location, Mechanism, Message, PathBuf}, + try_syscall, + types::{Bytes, Location, Message, PathBuf}, }; +#[cfg(not(feature = "chunked"))] +use trussed::{syscall, types::Mechanism}; + use crate::{Result, TrussedRequirements}; const HASH_SIZE: usize = 16; @@ -151,12 +153,14 @@ type SelectedStorage = ChunkedStorage; // Basic implementation using a file in the volatile storage as a buffer based on the core Trussed // API. Maximum size for the entire large blob array: 1024 bytes. +#[cfg(not(feature = "chunked"))] struct SimpleStorage { location: Location, buffer: Message, } -impl Storage for SimpleStorage { +#[cfg(not(feature = "chunked"))] +impl Storage for SimpleStorage { fn read(client: &mut C, location: Location, offset: usize, length: usize) -> Result { let result = try_syscall!(client.read_file(location, PathBuf::from(FILENAME))); let data = if let Ok(reply) = &result {