1use std::marker::PhantomData;
6use std::str::FromStr;
7
8use dom_struct::dom_struct;
9use itertools::Itertools;
10use js::context::NoGC;
11use js::conversions::ToJSValConvertible;
12use js::jsapi::{Heap, JSObject, Value};
13use js::rooted;
14use js::rust::MutableHandleObject;
15use jstraceable_derive::JSTraceable;
16use malloc_size_of::{MallocSizeOf, MallocSizeOfOps};
17use malloc_size_of_derive::MallocSizeOf;
18use rustc_hash::FxHashMap;
19use script_bindings::DomTypes;
20use script_bindings::codegen::GenericBindings::CryptoKeyBinding::{
21 CryptoKeyMethods, CryptoKeyPair, KeyType, KeyUsage, Wrap as CryptoKeyWrap,
22};
23use script_bindings::error::{Error, ErrorResult};
24use script_bindings::reflector::{Reflector, reflect_dom_object_with_wrap};
25use script_bindings::root::DomRoot;
26use script_bindings::serializable::Serializable;
27use script_bindings::structuredclone::StructuredData;
28use servo_base::id::{CryptoKeyId, CryptoKeyIndex};
29use servo_constellation_traits::{SerializableCryptoKey, SerializableCryptoKeyHandle};
30use strum::VariantArray;
31use zeroize::Zeroizing;
32
33use crate::subtlecrypto::KeyAlgorithmAndDerivatives;
34use crate::traits::Equivalence;
35
36pub(crate) enum CryptoKeyOrCryptoKeyPair<D: DomTypes> {
37 CryptoKey(DomRoot<CryptoKey<D>>),
38 CryptoKeyPair(CryptoKeyPair<D>),
39}
40
41pub(crate) enum Handle {
47 RsaPrivateKey(rsa::RsaPrivateKey),
48 RsaPublicKey(rsa::RsaPublicKey),
49 P256PrivateKey(p256::SecretKey),
50 P384PrivateKey(p384::SecretKey),
51 P521PrivateKey(p521::SecretKey),
52 P256PublicKey(p256::PublicKey),
53 P384PublicKey(p384::PublicKey),
54 P521PublicKey(p521::PublicKey),
55 Ed25519PrivateKey(ed25519_dalek::SigningKey),
56 Ed25519PublicKey(ed25519_dalek::VerifyingKey),
57 X25519PrivateKey(x25519_dalek::StaticSecret),
58 X25519PublicKey(x25519_dalek::PublicKey),
59 Ed448PrivateKey(ed448_goldilocks::SigningKey),
60 Ed448PublicKey(ed448_goldilocks::VerifyingKey),
61 X448PrivateKey(x448::StaticSecret),
62 X448PublicKey(x448::PublicKey),
63 Aes128Key(aes::cipher::common::Key<aes::Aes128>),
64 Aes192Key(aes::cipher::common::Key<aes::Aes192>),
65 Aes256Key(aes::cipher::common::Key<aes::Aes256>),
66 HkdfSecret(Zeroizing<Vec<u8>>),
67 Pbkdf2Password(Zeroizing<Vec<u8>>),
68 Hmac(Zeroizing<Vec<u8>>),
69 MlKem512PrivateKey(ml_kem::DecapsulationKey<ml_kem::MlKem512>),
70 MlKem768PrivateKey(ml_kem::DecapsulationKey<ml_kem::MlKem768>),
71 MlKem1024PrivateKey(ml_kem::DecapsulationKey<ml_kem::MlKem1024>),
72 MlKem512PublicKey(ml_kem::EncapsulationKey<ml_kem::MlKem512>),
73 MlKem768PublicKey(ml_kem::EncapsulationKey<ml_kem::MlKem768>),
74 MlKem1024PublicKey(ml_kem::EncapsulationKey<ml_kem::MlKem1024>),
75 MlKem768X25519PrivateKey(x_wing::DecapsulationKey),
76 MlKem768X25519PublicKey(x_wing::EncapsulationKey),
77 MlDsa44PrivateKey(ml_dsa::SigningKey<ml_dsa::MlDsa44>),
78 MlDsa65PrivateKey(ml_dsa::SigningKey<ml_dsa::MlDsa65>),
79 MlDsa87PrivateKey(ml_dsa::SigningKey<ml_dsa::MlDsa87>),
80 MlDsa44PublicKey(ml_dsa::VerifyingKey<ml_dsa::MlDsa44>),
81 MlDsa65PublicKey(ml_dsa::VerifyingKey<ml_dsa::MlDsa65>),
82 MlDsa87PublicKey(ml_dsa::VerifyingKey<ml_dsa::MlDsa87>),
83 ChaCha20Poly1305Key(chacha20poly1305::Key),
84 KmacKey(Zeroizing<Vec<u8>>),
85 Argon2Password(Zeroizing<Vec<u8>>),
86}
87
88#[dom_struct]
90pub struct CryptoKey<D: DomTypes> {
91 reflector_: Reflector,
92
93 key_type: KeyType,
95
96 extractable: bool,
98
99 #[no_trace]
104 algorithm: KeyAlgorithmAndDerivatives,
105
106 #[ignore_malloc_size_of = "Defined in mozjs"]
108 algorithm_cached: Heap<*mut JSObject>,
109
110 usages: Vec<KeyUsage>,
114
115 #[ignore_malloc_size_of = "Defined in mozjs"]
117 usages_cached: Heap<*mut JSObject>,
118
119 #[no_trace]
121 handle: Handle,
122
123 #[no_trace = "PhantomData does not exist"]
124 phantom: PhantomData<D>,
125}
126
127impl<D> CryptoKey<D>
128where
129 D: Equivalence,
130{
131 fn new_inherited(
132 key_type: KeyType,
133 extractable: bool,
134 algorithm: KeyAlgorithmAndDerivatives,
135 usages: Vec<KeyUsage>,
136 handle: Handle,
137 ) -> CryptoKey<D> {
138 CryptoKey {
139 reflector_: Reflector::new(),
140 key_type,
141 extractable,
142 algorithm,
143 algorithm_cached: Heap::default(),
144 usages,
145 usages_cached: Heap::default(),
146 handle,
147 phantom: PhantomData,
148 }
149 }
150
151 pub(crate) fn new(
152 cx: &mut js::context::JSContext,
153 global: &D::GlobalScope,
154 key_type: KeyType,
155 extractable: bool,
156 algorithm: KeyAlgorithmAndDerivatives,
157 usages: Vec<KeyUsage>,
158 handle: Handle,
159 ) -> DomRoot<CryptoKey<D>> {
160 let crypto_key = reflect_dom_object_with_wrap::<D, _, _>(
161 cx,
162 Box::new(CryptoKey::new_inherited(
163 key_type,
164 extractable,
165 algorithm.clone(),
166 usages.clone(),
167 handle,
168 )),
169 global,
170 CryptoKeyWrap::<D>,
171 );
172
173 rooted!(&in(cx) let mut algorithm_object_value: Value);
175 algorithm.to_jsval(cx, algorithm_object_value.handle_mut());
176 crypto_key
177 .algorithm_cached
178 .set(algorithm_object_value.to_object());
179
180 rooted!(&in(cx) let mut usages_object_value: Value);
182 usages.to_jsval(cx, usages_object_value.handle_mut());
183 crypto_key
184 .usages_cached
185 .set(usages_object_value.to_object());
186
187 crypto_key
188 }
189
190 pub(crate) fn algorithm(&self) -> &KeyAlgorithmAndDerivatives {
191 &self.algorithm
192 }
193
194 pub(crate) fn usages(&self) -> &[KeyUsage] {
195 &self.usages
196 }
197
198 pub(crate) fn handle(&self) -> &Handle {
199 &self.handle
200 }
201
202 pub(crate) fn ensure_type(&self, expected: KeyType) -> ErrorResult {
205 if self.key_type == expected {
206 Ok(())
207 } else {
208 Err(Error::InvalidAccess(Some(match expected {
209 KeyType::Public => "The key is not a public key".into(),
210 KeyType::Private => "The key is not a private key".into(),
211 KeyType::Secret => "The key is not a secret key".into(),
212 })))
213 }
214 }
215}
216
217impl<D> CryptoKeyMethods<D> for CryptoKey<D>
218where
219 D: DomTypes,
220{
221 fn Type(&self) -> KeyType {
223 self.key_type
225 }
226
227 fn Extractable(&self) -> bool {
229 self.extractable
232 }
233
234 fn Algorithm(&self, mut return_value: MutableHandleObject) {
236 return_value.set(self.algorithm_cached.get())
238 }
239
240 fn Usages(&self, mut return_value: MutableHandleObject) {
242 return_value.set(self.usages_cached.get())
245 }
246}
247
248impl<D> Serializable<D> for CryptoKey<D>
249where
250 D: Equivalence,
251{
252 type Index = CryptoKeyIndex;
253 type Data = SerializableCryptoKey;
254
255 fn serialize(&self, _no_gc: &NoGC) -> Result<(CryptoKeyId, Self::Data), ()> {
257 let serialized = SerializableCryptoKey {
265 key_type: self.key_type.as_str().into(),
266 extractable: self.extractable,
267 algorithm: (&self.algorithm).into(),
268 usages: self
269 .usages
270 .iter()
271 .map(|usage| usage.as_str().into())
272 .collect(),
273 handle: (&self.handle).try_into()?,
274 };
275 Ok((CryptoKeyId::new(), serialized))
276 }
277
278 fn deserialize(
280 cx: &mut js::context::JSContext,
281 owner: &D::GlobalScope,
282 serialized: Self::Data,
283 ) -> Result<DomRoot<Self>, ()> {
284 Ok(CryptoKey::new(
293 cx,
294 owner,
295 KeyType::from_str(&serialized.key_type)?,
296 serialized.extractable,
297 serialized.algorithm.try_into()?,
298 serialized
299 .usages
300 .iter()
301 .map(|usage| KeyUsage::from_str(usage))
302 .collect::<Result<Vec<_>, _>>()?,
303 serialized.handle.try_into()?,
304 ))
305 }
306
307 fn serialized_storage<'a>(
308 reader: StructuredData<'a, '_>,
309 ) -> &'a mut Option<FxHashMap<CryptoKeyId, Self::Data>> {
310 match reader {
311 StructuredData::Reader(reader) => &mut reader.crypto_keys,
312 StructuredData::Writer(writer) => &mut writer.crypto_keys,
313 }
314 }
315}
316
317impl Handle {
318 pub(crate) fn as_bytes(&self) -> &[u8] {
319 match self {
320 Self::Hmac(bytes) => bytes,
321 _ => unreachable!(),
322 }
323 }
324}
325
326impl MallocSizeOf for Handle {
327 fn size_of(&self, ops: &mut MallocSizeOfOps) -> usize {
328 match self {
329 Handle::RsaPrivateKey(private_key) => private_key.size_of(ops),
330 Handle::RsaPublicKey(public_key) => public_key.size_of(ops),
331 Handle::P256PrivateKey(private_key) => private_key.size_of(ops),
332 Handle::P384PrivateKey(private_key) => private_key.size_of(ops),
333 Handle::P521PrivateKey(private_key) => private_key.size_of(ops),
334 Handle::P256PublicKey(public_key) => public_key.size_of(ops),
335 Handle::P384PublicKey(public_key) => public_key.size_of(ops),
336 Handle::P521PublicKey(public_key) => public_key.size_of(ops),
337 Handle::Ed25519PrivateKey(bytes) => bytes.size_of(ops),
338 Handle::Ed25519PublicKey(bytes) => bytes.size_of(ops),
339 Handle::X25519PrivateKey(private_key) => private_key.size_of(ops),
340 Handle::X25519PublicKey(public_key) => public_key.size_of(ops),
341 Handle::Ed448PrivateKey(private_key) => private_key.size_of(ops),
342 Handle::Ed448PublicKey(public_key) => public_key.size_of(ops),
343 Handle::X448PrivateKey(private_key) => private_key.size_of(ops),
344 Handle::X448PublicKey(public_key) => public_key.size_of(ops),
345 Handle::Aes128Key(key) => key.size_of(ops),
346 Handle::Aes192Key(key) => key.size_of(ops),
347 Handle::Aes256Key(key) => key.size_of(ops),
348 Handle::HkdfSecret(secret) => secret.size_of(ops),
349 Handle::Pbkdf2Password(password) => password.size_of(ops),
350 Handle::Hmac(bytes) => bytes.size_of(ops),
351 Handle::MlKem512PrivateKey(private_key) => private_key.size_of(ops),
352 Handle::MlKem768PrivateKey(private_key) => private_key.size_of(ops),
353 Handle::MlKem1024PrivateKey(private_key) => private_key.size_of(ops),
354 Handle::MlKem512PublicKey(public_key) => public_key.size_of(ops),
355 Handle::MlKem768PublicKey(public_key) => public_key.size_of(ops),
356 Handle::MlKem1024PublicKey(public_key) => public_key.size_of(ops),
357 Handle::MlKem768X25519PrivateKey(private_key) => private_key.size_of(ops),
358 Handle::MlKem768X25519PublicKey(public_key) => public_key.size_of(ops),
359 Handle::MlDsa44PrivateKey(private_key) => private_key.size_of(ops),
360 Handle::MlDsa65PrivateKey(private_key) => private_key.size_of(ops),
361 Handle::MlDsa87PrivateKey(private_key) => private_key.size_of(ops),
362 Handle::MlDsa44PublicKey(public_key) => public_key.size_of(ops),
363 Handle::MlDsa65PublicKey(public_key) => public_key.size_of(ops),
364 Handle::MlDsa87PublicKey(public_key) => public_key.size_of(ops),
365 Handle::ChaCha20Poly1305Key(key) => key.size_of(ops),
366 Handle::KmacKey(key) => key.size_of(ops),
367 Handle::Argon2Password(password) => password.size_of(ops),
368 }
369 }
370}
371
372impl TryFrom<SerializableCryptoKeyHandle> for Handle {
373 type Error = ();
374
375 fn try_from(value: SerializableCryptoKeyHandle) -> Result<Self, Self::Error> {
376 match &value {
377 SerializableCryptoKeyHandle::RsaPrivateKey(private_key) => Ok(Handle::RsaPrivateKey(
378 rsa::pkcs8::DecodePrivateKey::from_pkcs8_der(private_key).map_err(|_| ())?,
379 )),
380 SerializableCryptoKeyHandle::RsaPublicKey(public_key) => Ok(Handle::RsaPublicKey(
381 rsa::pkcs8::spki::DecodePublicKey::from_public_key_der(public_key)
382 .map_err(|_| ())?,
383 )),
384 SerializableCryptoKeyHandle::P256PrivateKey(private_key) => Ok(Handle::P256PrivateKey(
385 p256::SecretKey::from_slice(private_key).map_err(|_| ())?,
386 )),
387 SerializableCryptoKeyHandle::P384PrivateKey(private_key) => Ok(Handle::P384PrivateKey(
388 p384::SecretKey::from_slice(private_key).map_err(|_| ())?,
389 )),
390 SerializableCryptoKeyHandle::P521PrivateKey(private_key) => Ok(Handle::P521PrivateKey(
391 p521::SecretKey::from_slice(private_key).map_err(|_| ())?,
392 )),
393 SerializableCryptoKeyHandle::P256PublicKey(public_key) => Ok(Handle::P256PublicKey(
394 p256::PublicKey::from_sec1_bytes(public_key).map_err(|_| ())?,
395 )),
396 SerializableCryptoKeyHandle::P384PublicKey(public_key) => Ok(Handle::P384PublicKey(
397 p384::PublicKey::from_sec1_bytes(public_key).map_err(|_| ())?,
398 )),
399 SerializableCryptoKeyHandle::P521PublicKey(public_key) => Ok(Handle::P521PublicKey(
400 p521::PublicKey::from_sec1_bytes(public_key).map_err(|_| ())?,
401 )),
402 SerializableCryptoKeyHandle::Ed25519PrivateKey(private_key) => Ok(
403 Handle::Ed25519PrivateKey(ed25519_dalek::SigningKey::from_bytes(private_key)),
404 ),
405 SerializableCryptoKeyHandle::Ed25519PublicKey(public_key) => {
406 Ok(Handle::Ed25519PublicKey(
407 ed25519_dalek::VerifyingKey::from_bytes(public_key).map_err(|_| ())?,
408 ))
409 },
410 SerializableCryptoKeyHandle::X25519PrivateKey(private_key) => {
411 Ok(Handle::X25519PrivateKey((*private_key).into()))
412 },
413 SerializableCryptoKeyHandle::X25519PublicKey(public_key) => {
414 Ok(Handle::X25519PublicKey((*public_key).into()))
415 },
416 SerializableCryptoKeyHandle::Ed448PrivateKey(private_key) => {
417 Ok(Handle::Ed448PrivateKey(
418 ed448_goldilocks::SigningKey::try_from(private_key).map_err(|_| ())?,
419 ))
420 },
421 SerializableCryptoKeyHandle::Ed448PublicKey(public_key) => Ok(Handle::Ed448PublicKey(
422 ed448_goldilocks::VerifyingKey::from_bytes(
423 public_key.as_slice().try_into().map_err(|_| ())?,
424 )
425 .map_err(|_| ())?,
426 )),
427 SerializableCryptoKeyHandle::X448PrivateKey(private_key) => {
428 Ok(Handle::X448PrivateKey(x448::StaticSecret::from(
429 <[u8; 56]>::try_from(private_key.as_slice()).map_err(|_| ())?,
430 )))
431 },
432 SerializableCryptoKeyHandle::X448PublicKey(public_key) => Ok(Handle::X448PublicKey(
433 x448::PublicKey::from_bytes_unchecked(public_key).ok_or(())?,
434 )),
435 SerializableCryptoKeyHandle::Aes128Key(key) => Ok(Handle::Aes128Key(
436 aes::cipher::common::Key::<aes::Aes128>::try_from(key).map_err(|_| ())?,
437 )),
438 SerializableCryptoKeyHandle::Aes192Key(key) => Ok(Handle::Aes192Key(
439 aes::cipher::common::Key::<aes::Aes192>::try_from(key).map_err(|_| ())?,
440 )),
441 SerializableCryptoKeyHandle::Aes256Key(key) => Ok(Handle::Aes256Key(
442 aes::cipher::common::Key::<aes::Aes256>::try_from(key).map_err(|_| ())?,
443 )),
444 SerializableCryptoKeyHandle::Hmac(bytes) => Ok(Handle::Hmac(bytes.clone().into())),
445 SerializableCryptoKeyHandle::HkdfSecret(bytes) => {
446 Ok(Handle::HkdfSecret(bytes.clone().into()))
447 },
448 SerializableCryptoKeyHandle::Pbkdf2Password(password) => {
449 Ok(Handle::Pbkdf2Password(password.clone().into()))
450 },
451 SerializableCryptoKeyHandle::MlKem512PrivateKey(private_key) => {
452 Ok(Handle::MlKem512PrivateKey(
453 ml_kem::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
454 ))
455 },
456 SerializableCryptoKeyHandle::MlKem768PrivateKey(private_key) => {
457 Ok(Handle::MlKem768PrivateKey(
458 ml_kem::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
459 ))
460 },
461 SerializableCryptoKeyHandle::MlKem1024PrivateKey(private_key) => {
462 Ok(Handle::MlKem1024PrivateKey(
463 ml_kem::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
464 ))
465 },
466 SerializableCryptoKeyHandle::MlKem512PublicKey(public_key) => {
467 Ok(Handle::MlKem512PublicKey(
468 ml_kem::TryKeyInit::new_from_slice(public_key).map_err(|_| ())?,
469 ))
470 },
471 SerializableCryptoKeyHandle::MlKem768PublicKey(public_key) => {
472 Ok(Handle::MlKem768PublicKey(
473 ml_kem::TryKeyInit::new_from_slice(public_key).map_err(|_| ())?,
474 ))
475 },
476 SerializableCryptoKeyHandle::MlKem1024PublicKey(public_key) => {
477 Ok(Handle::MlKem1024PublicKey(
478 ml_kem::TryKeyInit::new_from_slice(public_key).map_err(|_| ())?,
479 ))
480 },
481 SerializableCryptoKeyHandle::MlKem768X25519PrivateKey(private_key) => {
482 Ok(Handle::MlKem768X25519PrivateKey(
483 x_wing::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
484 ))
485 },
486 SerializableCryptoKeyHandle::MlKem768X25519PublicKey(public_key) => {
487 Ok(Handle::MlKem768X25519PublicKey(
488 x_wing::TryKeyInit::new_from_slice(public_key).map_err(|_| ())?,
489 ))
490 },
491 SerializableCryptoKeyHandle::MlDsa44PrivateKey(private_key) => {
492 Ok(Handle::MlDsa44PrivateKey(
493 ml_dsa::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
494 ))
495 },
496 SerializableCryptoKeyHandle::MlDsa65PrivateKey(private_key) => {
497 Ok(Handle::MlDsa65PrivateKey(
498 ml_dsa::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
499 ))
500 },
501 SerializableCryptoKeyHandle::MlDsa87PrivateKey(private_key) => {
502 Ok(Handle::MlDsa87PrivateKey(
503 ml_dsa::KeyInit::new_from_slice(private_key).map_err(|_| ())?,
504 ))
505 },
506 SerializableCryptoKeyHandle::MlDsa44PublicKey(public_key) => {
507 Ok(Handle::MlDsa44PublicKey(
508 ml_dsa::KeyInit::new_from_slice(public_key).map_err(|_| ())?,
509 ))
510 },
511 SerializableCryptoKeyHandle::MlDsa65PublicKey(public_key) => {
512 Ok(Handle::MlDsa65PublicKey(
513 ml_dsa::KeyInit::new_from_slice(public_key).map_err(|_| ())?,
514 ))
515 },
516 SerializableCryptoKeyHandle::MlDsa87PublicKey(public_key) => {
517 Ok(Handle::MlDsa87PublicKey(
518 ml_dsa::KeyInit::new_from_slice(public_key).map_err(|_| ())?,
519 ))
520 },
521 SerializableCryptoKeyHandle::ChaCha20Poly1305Key(key) => Ok(
522 Handle::ChaCha20Poly1305Key(chacha20poly1305::Key::try_from(key).map_err(|_| ())?),
523 ),
524 SerializableCryptoKeyHandle::KmacKey(key) => Ok(Handle::KmacKey(key.clone().into())),
525 SerializableCryptoKeyHandle::Argon2Password(password) => {
526 Ok(Handle::Argon2Password(password.clone().into()))
527 },
528 }
529 }
530}
531
532impl TryFrom<&Handle> for SerializableCryptoKeyHandle {
538 type Error = ();
539
540 fn try_from(value: &Handle) -> Result<Self, Self::Error> {
541 match value {
542 Handle::RsaPrivateKey(private_key) => Ok(SerializableCryptoKeyHandle::RsaPrivateKey(
543 rsa::pkcs8::EncodePrivateKey::to_pkcs8_der(private_key)
544 .map_err(|_| ())?
545 .as_bytes()
546 .to_vec(),
547 )),
548 Handle::RsaPublicKey(public_key) => Ok(SerializableCryptoKeyHandle::RsaPublicKey(
549 rsa::pkcs8::spki::EncodePublicKey::to_public_key_der(public_key)
550 .map_err(|_| ())?
551 .into_vec(),
552 )),
553 Handle::P256PrivateKey(private_key) => Ok(SerializableCryptoKeyHandle::P256PrivateKey(
554 private_key.to_bytes().as_slice().to_vec(),
555 )),
556 Handle::P384PrivateKey(private_key) => Ok(SerializableCryptoKeyHandle::P384PrivateKey(
557 private_key.to_bytes().as_slice().to_vec(),
558 )),
559 Handle::P521PrivateKey(private_key) => Ok(SerializableCryptoKeyHandle::P521PrivateKey(
560 private_key.to_bytes().as_slice().to_vec(),
561 )),
562 Handle::P256PublicKey(public_key) => Ok(SerializableCryptoKeyHandle::P256PublicKey(
563 public_key.to_sec1_bytes().to_vec(),
564 )),
565 Handle::P384PublicKey(public_key) => Ok(SerializableCryptoKeyHandle::P384PublicKey(
566 public_key.to_sec1_bytes().to_vec(),
567 )),
568 Handle::P521PublicKey(public_key) => Ok(SerializableCryptoKeyHandle::P521PublicKey(
569 public_key.to_sec1_bytes().to_vec(),
570 )),
571 Handle::Ed25519PrivateKey(private_key) => Ok(
572 SerializableCryptoKeyHandle::Ed25519PrivateKey(private_key.to_bytes()),
573 ),
574 Handle::Ed25519PublicKey(public_key) => Ok(
575 SerializableCryptoKeyHandle::Ed25519PublicKey(public_key.to_bytes()),
576 ),
577 Handle::X25519PrivateKey(private_key) => Ok(
578 SerializableCryptoKeyHandle::X25519PrivateKey(private_key.to_bytes()),
579 ),
580 Handle::X25519PublicKey(public_key) => Ok(
581 SerializableCryptoKeyHandle::X25519PublicKey(public_key.to_bytes()),
582 ),
583 Handle::Ed448PrivateKey(private_key) => Ok(
584 SerializableCryptoKeyHandle::Ed448PrivateKey(private_key.as_bytes().to_vec()),
585 ),
586 Handle::Ed448PublicKey(public_key) => Ok(SerializableCryptoKeyHandle::Ed448PublicKey(
587 public_key.as_bytes().to_vec(),
588 )),
589 Handle::X448PrivateKey(private_key) => Ok(SerializableCryptoKeyHandle::X448PrivateKey(
590 private_key.as_bytes().to_vec(),
591 )),
592 Handle::X448PublicKey(public_key) => Ok(SerializableCryptoKeyHandle::X448PublicKey(
593 public_key.as_bytes().to_vec(),
594 )),
595 Handle::Aes128Key(key) => Ok(SerializableCryptoKeyHandle::Aes128Key(key.to_vec())),
596 Handle::Aes192Key(key) => Ok(SerializableCryptoKeyHandle::Aes192Key(key.to_vec())),
597 Handle::Aes256Key(key) => Ok(SerializableCryptoKeyHandle::Aes256Key(key.to_vec())),
598 Handle::Hmac(bytes) => Ok(SerializableCryptoKeyHandle::Hmac(bytes.to_vec())),
599 Handle::HkdfSecret(bytes) => {
600 Ok(SerializableCryptoKeyHandle::HkdfSecret(bytes.to_vec()))
601 },
602 Handle::Pbkdf2Password(password) => Ok(SerializableCryptoKeyHandle::Pbkdf2Password(
603 password.to_vec(),
604 )),
605 Handle::MlKem512PrivateKey(private_key) => {
606 Ok(SerializableCryptoKeyHandle::MlKem512PrivateKey(
607 private_key
608 .to_seed()
609 .expect("This decapsulation key should contain seed value")
610 .as_slice()
611 .to_vec(),
612 ))
613 },
614 Handle::MlKem768PrivateKey(private_key) => {
615 Ok(SerializableCryptoKeyHandle::MlKem768PrivateKey(
616 private_key
617 .to_seed()
618 .expect("This decapsulation key should contain seed value")
619 .as_slice()
620 .to_vec(),
621 ))
622 },
623 Handle::MlKem1024PrivateKey(private_key) => {
624 Ok(SerializableCryptoKeyHandle::MlKem1024PrivateKey(
625 private_key
626 .to_seed()
627 .expect("This decapsulation key should contain seed value")
628 .as_slice()
629 .to_vec(),
630 ))
631 },
632 Handle::MlKem512PublicKey(public_key) => {
633 Ok(SerializableCryptoKeyHandle::MlKem512PublicKey(
634 ml_kem::KeyExport::to_bytes(public_key).as_slice().to_vec(),
635 ))
636 },
637 Handle::MlKem768PublicKey(public_key) => {
638 Ok(SerializableCryptoKeyHandle::MlKem768PublicKey(
639 ml_kem::KeyExport::to_bytes(public_key).as_slice().to_vec(),
640 ))
641 },
642 Handle::MlKem1024PublicKey(public_key) => {
643 Ok(SerializableCryptoKeyHandle::MlKem1024PublicKey(
644 ml_kem::KeyExport::to_bytes(public_key).as_slice().to_vec(),
645 ))
646 },
647 Handle::MlKem768X25519PrivateKey(private_key) => {
648 Ok(SerializableCryptoKeyHandle::MlKem768X25519PrivateKey(
649 private_key.as_bytes().to_vec(),
650 ))
651 },
652 Handle::MlKem768X25519PublicKey(public_key) => {
653 Ok(SerializableCryptoKeyHandle::MlKem768X25519PublicKey(
654 x_wing::KeyExport::to_bytes(public_key).to_vec(),
655 ))
656 },
657 Handle::MlDsa44PrivateKey(private_key) => {
658 Ok(SerializableCryptoKeyHandle::MlDsa44PrivateKey(
659 private_key.as_seed().as_slice().to_vec(),
660 ))
661 },
662 Handle::MlDsa65PrivateKey(private_key) => {
663 Ok(SerializableCryptoKeyHandle::MlDsa65PrivateKey(
664 private_key.as_seed().as_slice().to_vec(),
665 ))
666 },
667 Handle::MlDsa87PrivateKey(private_key) => {
668 Ok(SerializableCryptoKeyHandle::MlDsa87PrivateKey(
669 private_key.as_seed().as_slice().to_vec(),
670 ))
671 },
672 Handle::MlDsa44PublicKey(public_key) => {
673 Ok(SerializableCryptoKeyHandle::MlDsa44PublicKey(
674 ml_dsa::KeyExport::to_bytes(public_key).as_slice().to_vec(),
675 ))
676 },
677 Handle::MlDsa65PublicKey(public_key) => {
678 Ok(SerializableCryptoKeyHandle::MlDsa65PublicKey(
679 ml_dsa::KeyExport::to_bytes(public_key).as_slice().to_vec(),
680 ))
681 },
682 Handle::MlDsa87PublicKey(public_key) => {
683 Ok(SerializableCryptoKeyHandle::MlDsa87PublicKey(
684 ml_dsa::KeyExport::to_bytes(public_key).as_slice().to_vec(),
685 ))
686 },
687 Handle::ChaCha20Poly1305Key(key) => Ok(
688 SerializableCryptoKeyHandle::ChaCha20Poly1305Key(key.as_slice().to_vec()),
689 ),
690 Handle::KmacKey(key) => Ok(SerializableCryptoKeyHandle::KmacKey(key.to_vec())),
691 Handle::Argon2Password(password) => Ok(SerializableCryptoKeyHandle::Argon2Password(
692 password.to_vec(),
693 )),
694 }
695 }
696}
697
698pub(crate) trait KeyUsageSliceHelper {
700 fn usage_intersection(&self, other: &[KeyUsage]) -> Vec<KeyUsage>;
702
703 fn normalized_value(&self) -> Vec<KeyUsage>;
705
706 fn ensure_only_contain_entries_from(&self, allowed: &[KeyUsage]) -> ErrorResult;
710}
711
712impl KeyUsageSliceHelper for [KeyUsage] {
713 fn usage_intersection(&self, other: &[KeyUsage]) -> Vec<KeyUsage> {
714 let mut intersection = self
720 .iter()
721 .filter(|usage| other.contains(usage))
722 .cloned()
723 .collect::<Vec<KeyUsage>>();
724 intersection.sort();
725 intersection.dedup();
726
727 intersection
728 }
729
730 fn normalized_value(&self) -> Vec<KeyUsage> {
731 self.usage_intersection(KeyUsage::VARIANTS)
735 }
736
737 fn ensure_only_contain_entries_from(&self, allowed: &[KeyUsage]) -> ErrorResult {
738 if self.iter().all(|usage| allowed.contains(usage)) {
739 Ok(())
740 } else {
741 Err(Error::Syntax(Some(if allowed.is_empty() {
742 "Usages is not empty".into()
743 } else {
744 format!(
745 "Usages contains an entry which is not {}",
746 allowed.iter().map(|usage| usage.as_ref()).join(" or "),
747 )
748 })))
749 }
750 }
751}