ser_server_state.rs (13088B)
1 use super::{ 2 super::super::bin::{ 3 Decode, DecodeBuffer, EncDecErr, Encode, EncodeBuffer, EncodeBufferFallible, 4 }, 5 AuthenticationServerState, CredInfo, CredentialId, DiscoverableAuthenticationServerState, 6 ExtensionReq, NonDiscoverableAuthenticationServerState, SentChallenge, 7 ServerCredSpecificExtensionInfo, ServerExtensionInfo, ServerPrfInfo, 8 SignatureCounterEnforcement, UserVerificationRequirement, 9 }; 10 #[cfg(doc)] 11 use super::{AllowedCredential, NonDiscoverableCredentialRequestOptions}; 12 use core::{ 13 error::Error, 14 fmt::{self, Display, Formatter}, 15 }; 16 #[cfg(doc)] 17 use std::time::UNIX_EPOCH; 18 use std::time::{SystemTime, SystemTimeError}; 19 impl EncodeBuffer for ServerPrfInfo { 20 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) { 21 match *self { 22 Self::None => 0u8.encode_into_buffer(buffer), 23 Self::One(req) => { 24 1u8.encode_into_buffer(buffer); 25 req.encode_into_buffer(buffer); 26 } 27 Self::Two(req) => { 28 2u8.encode_into_buffer(buffer); 29 req.encode_into_buffer(buffer); 30 } 31 } 32 } 33 } 34 impl<'a> DecodeBuffer<'a> for ServerPrfInfo { 35 type Err = EncDecErr; 36 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 37 u8::decode_from_buffer(data).and_then(|val| match val { 38 0 => Ok(Self::None), 39 1 => ExtensionReq::decode_from_buffer(data).map(Self::One), 40 2 => ExtensionReq::decode_from_buffer(data).map(Self::Two), 41 _ => Err(EncDecErr), 42 }) 43 } 44 } 45 impl EncodeBuffer for ServerCredSpecificExtensionInfo { 46 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) { 47 self.prf.encode_into_buffer(buffer); 48 } 49 } 50 impl<'a> DecodeBuffer<'a> for ServerCredSpecificExtensionInfo { 51 type Err = EncDecErr; 52 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 53 ServerPrfInfo::decode_from_buffer(data).map(|prf| Self { prf }) 54 } 55 } 56 impl EncodeBuffer for CredInfo { 57 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) { 58 CredentialId::<&[u8]>::from(&self.id).encode_into_buffer(buffer); 59 self.ext.encode_into_buffer(buffer); 60 } 61 } 62 impl<'a> DecodeBuffer<'a> for CredInfo { 63 type Err = EncDecErr; 64 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 65 CredentialId::<Vec<u8>>::decode_from_buffer(data).and_then(|id| { 66 ServerCredSpecificExtensionInfo::decode_from_buffer(data).map(|ext| Self { id, ext }) 67 }) 68 } 69 } 70 impl EncodeBuffer for ServerExtensionInfo { 71 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) { 72 self.prf.encode_into_buffer(buffer); 73 } 74 } 75 impl<'a> DecodeBuffer<'a> for ServerExtensionInfo { 76 type Err = EncDecErr; 77 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 78 ServerPrfInfo::decode_from_buffer(data).map(|prf| Self { prf }) 79 } 80 } 81 impl EncodeBuffer for SignatureCounterEnforcement { 82 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) { 83 match *self { 84 Self::Fail => 0u8, 85 Self::Update => 1, 86 Self::Ignore => 2, 87 } 88 .encode_into_buffer(buffer); 89 } 90 } 91 impl<'a> DecodeBuffer<'a> for SignatureCounterEnforcement { 92 type Err = EncDecErr; 93 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 94 u8::decode_from_buffer(data).and_then(|val| match val { 95 0 => Ok(Self::Fail), 96 1 => Ok(Self::Update), 97 2 => Ok(Self::Ignore), 98 _ => Err(EncDecErr), 99 }) 100 } 101 } 102 impl EncodeBufferFallible for &[CredInfo] { 103 type Err = EncDecErr; 104 /// # Errors 105 /// 106 /// Errors iff `self.len() > usize::from(u16::MAX)`. 107 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) -> Result<(), EncDecErr> { 108 u16::try_from(self.len()) 109 .map_err(|_e| EncDecErr) 110 .map(|len| { 111 len.encode_into_buffer(buffer); 112 self.iter().fold((), |(), val| { 113 val.encode_into_buffer(buffer); 114 }); 115 }) 116 } 117 } 118 impl<'a> DecodeBuffer<'a> for Vec<CredInfo> { 119 type Err = EncDecErr; 120 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 121 u16::decode_from_buffer(data).and_then(|len| { 122 let l = usize::from(len); 123 let mut creds = Self::with_capacity(l); 124 while creds.len() < l { 125 creds.push(CredInfo::decode_from_buffer(data)?); 126 } 127 Ok(creds) 128 }) 129 } 130 } 131 impl EncodeBufferFallible for AuthenticationServerState { 132 type Err = SystemTimeError; 133 fn encode_into_buffer(&self, buffer: &mut Vec<u8>) -> Result<(), Self::Err> { 134 self.challenge.encode_into_buffer(buffer); 135 self.user_verification.encode_into_buffer(buffer); 136 self.extensions.encode_into_buffer(buffer); 137 self.expiration.encode_into_buffer(buffer) 138 } 139 } 140 impl Encode for DiscoverableAuthenticationServerState { 141 type Output<'a> 142 = Vec<u8> 143 where 144 Self: 'a; 145 type Err = SystemTimeError; 146 #[expect( 147 clippy::arithmetic_side_effects, 148 reason = "comment justifies correctness" 149 )] 150 #[inline] 151 fn encode(&self) -> Result<Self::Output<'_>, Self::Err> { 152 // Length of the anticipated most common output: 153 // * 16 for `SentChallenge` 154 // * 1 for `UserVerificationRequirement` 155 // * 1 or 2 for `ServerExtensionInfo` 156 // * 12 for `SystemTime` 157 // Clearly cannot overflow. 158 let mut buffer = Vec::with_capacity( 159 16 + 1 + 1 + usize::from(!matches!(self.0.extensions.prf, ServerPrfInfo::None)) + 12, 160 ); 161 self.0.encode_into_buffer(&mut buffer).map(|()| buffer) 162 } 163 } 164 /// Error returned from [`NonDiscoverableAuthenticationServerState::encode`]. 165 #[derive(Debug)] 166 pub enum EncodeNonDiscoverableAuthenticationServerStateErr { 167 /// Variant returned when 168 /// [`NonDiscoverableAuthenticationServerState::expiration`](../struct.AuthenticationServerState.html#method.expiration-1) 169 /// is before [`UNIX_EPOCH`]. 170 SystemTime(SystemTimeError), 171 /// Variant returned when the corresponding [`NonDiscoverableCredentialRequestOptions::allow_credentials`] has more 172 /// than [`u16::MAX`] [`AllowedCredential`]s. 173 AllowedCredentialsCount, 174 } 175 impl Display for EncodeNonDiscoverableAuthenticationServerStateErr { 176 #[inline] 177 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { 178 match *self { 179 Self::SystemTime(ref err) => err.fmt(f), 180 Self::AllowedCredentialsCount => { 181 f.write_str("there were more than 65,535 AllowedCredentials") 182 } 183 } 184 } 185 } 186 impl Error for EncodeNonDiscoverableAuthenticationServerStateErr {} 187 impl Encode for NonDiscoverableAuthenticationServerState { 188 type Output<'a> 189 = Vec<u8> 190 where 191 Self: 'a; 192 type Err = EncodeNonDiscoverableAuthenticationServerStateErr; 193 #[inline] 194 fn encode(&self) -> Result<Self::Output<'_>, Self::Err> { 195 // Length of the anticipated most common output: 196 // * 16 for `SentChallenge` 197 // * 2 + Σ(2 + len(id_i) + (1|2)) from i = 1 to i = `self.allow_credentials.len()` where i is the 198 // 1-based index of the `AllowedCredential` and len(id_i) is the number of bytes that makes up 199 // the ith `CredentialId`. Since `self.allow_credentials.len()` is inclusively between 1 and 200 // 65,535, the smallest this can be is 2 + 2 + 16 + 1 = 21; and the largest this can be is 201 // 2 + 65535(2 + 1023 + 2) = 67,304,447. We assume no credential-specific PRF is sent and the 202 // the average length of the `CredentialId`s is 128. 203 // * 1 for `UserVerificationRequirement` 204 // * 1 or 2 for `ServerExtensionInfo` where we assume 1 is the most common 205 // * 12 for `SystemTime` 206 // This is just an estimate; thus we rely on wrapping arithmetic. If the actual needed capacity is too big, 207 // then a `panic` will happen anyway once we serialize the entire payload. 208 let mut buffer = Vec::with_capacity( 209 (16usize + 2 + 1 + 1 + 12) 210 .wrapping_add(self.allow_credentials.len().wrapping_mul(2 + 128 + 1)), 211 ); 212 self.state 213 .encode_into_buffer(&mut buffer) 214 .map_err(EncodeNonDiscoverableAuthenticationServerStateErr::SystemTime) 215 .and_then(|()| { 216 self.allow_credentials 217 .as_slice() 218 .encode_into_buffer(&mut buffer) 219 .map_err(|_e| { 220 EncodeNonDiscoverableAuthenticationServerStateErr::AllowedCredentialsCount 221 }) 222 .map(|()| buffer) 223 }) 224 } 225 } 226 impl<'a> DecodeBuffer<'a> for AuthenticationServerState { 227 type Err = EncDecErr; 228 fn decode_from_buffer(data: &mut &'a [u8]) -> Result<Self, Self::Err> { 229 SentChallenge::decode_from_buffer(data).and_then(|challenge| { 230 UserVerificationRequirement::decode_from_buffer(data).and_then(|user_verification| { 231 ServerExtensionInfo::decode_from_buffer(data).and_then(|extensions| { 232 SystemTime::decode_from_buffer(data).map(|expiration| Self { 233 challenge, 234 user_verification, 235 extensions, 236 expiration, 237 }) 238 }) 239 }) 240 }) 241 } 242 } 243 /// Error returned from [`DiscoverableAuthenticationServerState::decode`]. 244 #[derive(Clone, Copy, Debug, Eq, PartialEq)] 245 pub enum DecodeDiscoverableAuthenticationServerStateErr { 246 /// Variant returned when there was trailing data after decoding a [`DiscoverableAuthenticationServerState`]. 247 TrailingData, 248 /// Variant returned for all other errors. 249 Other, 250 } 251 impl Display for DecodeDiscoverableAuthenticationServerStateErr { 252 #[inline] 253 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { 254 f.write_str(match *self { 255 Self::TrailingData => { 256 "trailing data after decoding DiscoverableAuthenticationServerState" 257 } 258 Self::Other => "DiscoverableAuthenticationServerState could not be decoded", 259 }) 260 } 261 } 262 impl Error for DecodeDiscoverableAuthenticationServerStateErr {} 263 impl Decode for DiscoverableAuthenticationServerState { 264 type Input<'a> = &'a [u8]; 265 type Err = DecodeDiscoverableAuthenticationServerStateErr; 266 #[inline] 267 fn decode(mut input: Self::Input<'_>) -> Result<Self, Self::Err> { 268 AuthenticationServerState::decode_from_buffer(&mut input) 269 .map_err(|_e| DecodeDiscoverableAuthenticationServerStateErr::Other) 270 .and_then(|state| { 271 if input.is_empty() { 272 Ok(Self(state)) 273 } else { 274 Err(DecodeDiscoverableAuthenticationServerStateErr::TrailingData) 275 } 276 }) 277 } 278 } 279 /// Error returned from [`NonDiscoverableAuthenticationServerState::decode`]. 280 #[derive(Clone, Copy, Debug, Eq, PartialEq)] 281 pub enum DecodeNonDiscoverableAuthenticationServerStateErr { 282 /// Variant returned when there was trailing data after decoding a [`NonDiscoverableAuthenticationServerState`]. 283 TrailingData, 284 /// Variant returned for all other errors. 285 Other, 286 } 287 impl Display for DecodeNonDiscoverableAuthenticationServerStateErr { 288 #[inline] 289 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { 290 f.write_str(match *self { 291 Self::TrailingData => { 292 "trailing data after decoding NonDiscoverableAuthenticationServerState" 293 } 294 Self::Other => "NonDiscoverableAuthenticationServerState could not be decoded", 295 }) 296 } 297 } 298 impl Error for DecodeNonDiscoverableAuthenticationServerStateErr {} 299 impl Decode for NonDiscoverableAuthenticationServerState { 300 type Input<'a> = &'a [u8]; 301 type Err = DecodeNonDiscoverableAuthenticationServerStateErr; 302 #[inline] 303 fn decode(mut input: Self::Input<'_>) -> Result<Self, Self::Err> { 304 AuthenticationServerState::decode_from_buffer(&mut input) 305 .map_err(|_e| DecodeNonDiscoverableAuthenticationServerStateErr::Other) 306 .and_then(|state| { 307 Vec::decode_from_buffer(&mut input) 308 .map_err(|_e| DecodeNonDiscoverableAuthenticationServerStateErr::Other) 309 .and_then(|allow_credentials| { 310 if allow_credentials.is_empty() { 311 Err(DecodeNonDiscoverableAuthenticationServerStateErr::Other) 312 } else if input.is_empty() { 313 Ok(Self { 314 state, 315 allow_credentials, 316 }) 317 } else { 318 Err(DecodeNonDiscoverableAuthenticationServerStateErr::TrailingData) 319 } 320 }) 321 }) 322 } 323 }