signstar_yubihsm2/
mock.rs1use signstar_crypto::{
4 openpgp::{OpenPgpKeyUsageFlags, OpenPgpUserId, OpenPgpVersion},
5 signer::openpgp::{Timestamp, generate_certificate},
6 traits::UserWithPassphrase as _,
7};
8use yubihsm::{
9 Capability,
10 Connector,
11 Credentials as YubiCredentials,
12 Domain,
13 asymmetric::Algorithm as AsymmetricAlgorithm,
14 authentication::{Algorithm as AuthenticationAlgorithm, Key},
15 client::Client,
16 object::Id,
17 opaque::Algorithm as OpaqueAlgorithm,
18};
19
20use crate::{Credentials, Error, YubiHsm2SigningKey};
21
22pub fn setup_single_key_in_mockhsm(
36 key_id: Id,
37 credentials: &Credentials,
38) -> Result<Connector, Error> {
39 let connector = Connector::mockhsm();
40 let client =
41 Client::open(connector, Default::default(), true).map_err(|source| Error::Client {
42 context: "connecting to mockhsm",
43 source,
44 })?;
45 let auth_key = Key::derive_from_password(credentials.passphrase().expose_borrowed().as_bytes());
46 let domain = Domain::DOM1;
47 client
48 .put_authentication_key(
49 credentials.id(),
50 Default::default(),
51 domain,
52 Capability::empty(),
53 Capability::SIGN_EDDSA,
54 AuthenticationAlgorithm::YubicoAes,
55 auth_key.clone(),
56 )
57 .map_err(|source| Error::Client {
58 context: "putting authentication key",
59 source,
60 })?;
61
62 let client = Client::open(
63 client.connector().clone(),
64 YubiCredentials::new(credentials.id(), auth_key),
65 true,
66 )
67 .map_err(|source| Error::Client {
68 context: "connecting to mockhsm",
69 source,
70 })?;
71
72 client
73 .generate_asymmetric_key(
74 key_id,
75 Default::default(),
76 domain,
77 Capability::SIGN_EDDSA,
78 AsymmetricAlgorithm::Ed25519,
79 )
80 .map_err(|source| Error::Client {
81 context: "generating asymmetric key",
82 source,
83 })?;
84
85 let flags = {
86 let mut flags = OpenPgpKeyUsageFlags::default();
87 flags.set_sign();
88 flags
89 };
90
91 let signer = YubiHsm2SigningKey::new(client, key_id);
92
93 let cert = generate_certificate(
94 &signer,
95 flags,
96 &[OpenPgpUserId::new("Test".to_owned()).expect("static user ID to be valid")],
97 Default::default(),
98 Timestamp::now(),
99 OpenPgpVersion::V4,
100 )
101 .map_err(|source| Error::CertificateGeneration {
102 context: "generating OpenPGP certificate",
103 source,
104 })?;
105
106 signer
107 .client()
108 .put_opaque(
109 key_id,
110 Default::default(),
111 domain,
112 Capability::empty(),
113 OpaqueAlgorithm::Data,
114 cert,
115 )
116 .map_err(|source| Error::Client {
117 context: "putting generated certificate on the device",
118 source,
119 })?;
120
121 Ok(signer.client().connector().clone())
122}