mod error;
mod profile;
pub mod report;
mod role;
pub use self::{
error::{Error, ErrorKind},
profile::Profile,
report::Report,
role::Role,
};
use crate::{
authentication::{self, Credentials, DEFAULT_AUTHENTICATION_KEY_ID},
object, Capability, Client, Connector, Domain,
};
const SETUP_KEY_LABEL: &str = "yubihsm.rs temporary setup key";
pub fn erase_device_and_init_with_profile(
connector: Connector,
credentials: Credentials,
profile: Profile,
) -> Result<Report, Error> {
let mut client = Client::open(connector, credentials, false)?;
client.reset_device_and_reconnect(profile.reset_device_timeout)?;
init_with_profile(client, profile)
}
pub fn init_with_profile(client: Client, profile: Profile) -> Result<Report, Error> {
let setup_auth_key_id = profile
.setup_auth_key_id
.ok_or_else(|| format_err!(ErrorKind::SetupFailed, "profile setup_auth_key_id unset!"))?;
let temp_auth_key = authentication::Key::random();
client
.put_authentication_key(
setup_auth_key_id,
SETUP_KEY_LABEL.into(),
Domain::all(),
Capability::all(),
Capability::all(),
authentication::Algorithm::YubicoAes,
temp_auth_key.clone(),
)
.map_err(|e| {
format_err!(
ErrorKind::SetupFailed,
"error putting authentication key: {}",
e
)
})?;
info!(
"installed temporary setup authentication key into slot {}",
setup_auth_key_id
);
let connector = client.connector().clone();
let client = Client::open(
connector,
Credentials::new(setup_auth_key_id, temp_auth_key),
false,
)
.map_err(|e| {
format_err!(
ErrorKind::SetupFailed,
"error reconnecting to HSM with setup auth key: {}",
e
)
})?;
warn!(
"deleting default authentication key from slot {}",
DEFAULT_AUTHENTICATION_KEY_ID
);
client
.delete_object(
DEFAULT_AUTHENTICATION_KEY_ID,
object::Type::AuthenticationKey,
)
.map_err(|e| {
format_err!(
ErrorKind::SetupFailed,
"error deleting default authentication key from slot {}: {}",
DEFAULT_AUTHENTICATION_KEY_ID,
e
)
})?;
let report = profile.provision(&client)?;
if profile.delete_setup_auth_key {
warn!(
"deleting temporary setup authentication key from slot {}",
setup_auth_key_id
);
client
.delete_object(setup_auth_key_id, object::Type::AuthenticationKey)
.map_err(|e| {
format_err!(
ErrorKind::SetupFailed,
"error deleting temporary setup authentication key from slot {}: {}",
setup_auth_key_id,
e
)
})?;
}
Ok(report)
}