use crate::{cli::Hierarchy, command::CommandError, handle::Handle, key::Alg};
use clap::Args;
use std::path::PathBuf;
use strum::{Display, EnumString};
use tpm2_protocol::data::{Tpm2bAuth, Tpm2bDigest, TpmaObject};
#[derive(Debug, Default, Clone, Copy, PartialEq, Eq, Display, EnumString)]
#[strum(serialize_all = "kebab-case")]
pub enum OutputEncoding {
#[default]
Pem,
Der,
}
#[derive(Args, Debug, Clone)]
pub struct InputArgs {
#[arg(short = 'I', long)]
pub input: Option<PathBuf>,
}
#[derive(Args, Debug, Clone)]
pub struct OutputArgs {
#[arg(short = 'O', long)]
pub output: Option<PathBuf>,
}
#[derive(Args, Debug, Clone)]
pub struct OutputEncodingArgs {
#[arg(long = "output-encoding", default_value_t = OutputEncoding::default(), value_parser = clap::value_parser!(OutputEncoding))]
pub output_encoding: OutputEncoding,
}
#[derive(Args, Debug, Clone)]
pub struct ParenBindArgs {
#[arg(short = 'P', long)]
pub parent: Handle,
}
#[derive(Args, Debug, Clone)]
pub struct ParenLoadArgs {
#[arg(short = 'P', long)]
pub parent: Option<Handle>,
}
#[derive(Args, Debug, Clone)]
pub struct HierarchyArgs {
#[arg(short = 'H', long, default_value_t = Hierarchy::default(), value_parser = clap::value_parser!(Hierarchy))]
pub hierarchy: Hierarchy,
}
#[derive(Args, Debug, Clone, Default)]
pub struct CreationArgs {
#[arg(long = "password")]
pub password: Option<String>,
#[arg(long = "policy")]
pub policy: Option<String>,
}
impl CreationArgs {
pub fn parse(&self, alg: &Alg) -> Result<(TpmaObject, Tpm2bAuth, Tpm2bDigest), CommandError> {
let mut attributes: TpmaObject = alg.clone().into();
if self.password.is_none() && self.policy.is_none() {
attributes |= TpmaObject::USER_WITH_AUTH;
}
let user_auth = if let Some(hex_str) = &self.password {
attributes |= TpmaObject::USER_WITH_AUTH;
Tpm2bAuth::try_from(hex::decode(hex_str)?.as_slice())?
} else {
Tpm2bAuth::default()
};
let auth_policy = if let Some(hex_str) = &self.policy {
attributes |= TpmaObject::ADMIN_WITH_POLICY;
Tpm2bDigest::try_from(hex::decode(hex_str)?.as_slice())?
} else {
Tpm2bDigest::default()
};
Ok((attributes, user_auth, auth_policy))
}
}