Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions tss-esapi/examples/certify.rs
Original file line number Diff line number Diff line change
Expand Up @@ -267,7 +267,7 @@ fn main() {
// challenge encryption.
let (_public, ak_name, _qualified_name) = context_2
.execute_with_nullauth_session(|ctx| {
let ak_handle = ctx.load_external_public(ak_public.clone(), Hierarchy::Null)?;
let ak_handle = ctx.load_external(None, ak_public.clone(), Hierarchy::Null)?;
let r = ctx.read_public(ak_handle);
ctx.flush_context(ak_handle.into())?;
r
Expand All @@ -291,7 +291,7 @@ fn main() {
// Now we load the ek_public, and create our encrypted challenge.
let (idobject, encrypted_secret) = context_2
.execute_with_nullauth_session(|ctx| {
let ek_handle = ctx.load_external_public(ek_public, Hierarchy::Null)?;
let ek_handle = ctx.load_external(None, ek_public, Hierarchy::Null)?;
let r = ctx.make_credential(ek_handle, challenge.clone(), ak_name);
ctx.flush_context(ek_handle.into())?;
r
Expand Down Expand Up @@ -510,7 +510,8 @@ fn main() {
// First, load the public from the aik
let ak_handle = context_2
.execute_with_nullauth_session(|ctx| {
ctx.load_external_public(
ctx.load_external(
None,
ak_public,
// We put it into the null hierarchy as this is ephemeral.
Hierarchy::Null,
Expand Down
2 changes: 1 addition & 1 deletion tss-esapi/examples/duplication.rs
Original file line number Diff line number Diff line change
Expand Up @@ -303,7 +303,7 @@ fn main() {
.execute_without_session(|ctx| {
// Ensure we load the new parent handle before we start
let new_parent_handle = ctx
.load_external_public(primary_key_2_public, Hierarchy::Null)
.load_external(None, primary_key_2_public, Hierarchy::Null)
.unwrap();

// IMPORTANT! After you start the policy session, you can't do *anything* else except
Expand Down
2 changes: 1 addition & 1 deletion tss-esapi/examples/rsa_oaep.rs
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ fn main() {
let encrypted_data = context
.execute_with_nullauth_session(|ctx| {
let rsa_pub_key = ctx
.load_external_public(public.clone(), Hierarchy::Null)
.load_external(None, public.clone(), Hierarchy::Null)
.unwrap();

ctx.rsa_encrypt(
Expand Down
7 changes: 2 additions & 5 deletions tss-esapi/src/abstraction/transient/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -194,9 +194,7 @@ impl TransientKeyContext {
) -> Result<KeyMaterial> {
let public = TransientKeyContext::get_public_from_params(params, Some(public_key.clone()))?;
self.set_session_attrs()?;
let key_handle = self
.context
.load_external_public(public, Hierarchy::Owner)?;
let key_handle = self.context.load_external(None, public, Hierarchy::Owner)?;
self.context.flush_context(key_handle.into())?;
Ok(KeyMaterial {
public: public_key,
Expand Down Expand Up @@ -522,8 +520,7 @@ impl TransientKeyContext {

self.set_session_attrs()?;
let key_handle = if material.private.is_empty() {
self.context
.load_external_public(public, Hierarchy::Owner)?
self.context.load_external(None, public, Hierarchy::Owner)?
} else {
self.context
.load(self.root_key_handle, material.private.try_into()?, public)?
Expand Down
148 changes: 109 additions & 39 deletions tss-esapi/src/context/tpm_commands/object_commands.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ use crate::{
Esys_ActivateCredential, Esys_Create, Esys_Load, Esys_LoadExternal, Esys_MakeCredential,
Esys_ObjectChangeAuth, Esys_ReadPublic, Esys_Unseal,
},
Context, Result, ReturnCode,
Context, Error, Result, ReturnCode, WrapperErrorKind,
};
use create_command_input::CreateCommandInputHandler;
use create_command_output::CreateCommandOutputHandler;
Expand Down Expand Up @@ -123,22 +123,127 @@ impl Context {
}

/// Load an external key into the TPM and return its new handle.
///
/// # Details
/// This command is used to load an object that is not a Protected Object into the TPM. The command allows
/// loading of a public area or both a public and sensitive area.
///
/// # Arguments
/// * `private` - The optional sensitive portion of the object.
/// * `public` - The public portion of the object.
/// * `hierarchy` - The hierarchy with which the object area is associated.
///
/// # Returns
/// The handle to the loaded key.
///
/// # Example
///
/// ```rust
/// # use tss_esapi::{
/// # Context, TctiNameConf,
/// # attributes::ObjectAttributesBuilder,
/// # constants::SessionType,
/// # interface_types::{
/// # algorithm::{HashingAlgorithm, PublicAlgorithm, RsaSchemeAlgorithm},
/// # key_bits::RsaKeyBits,
/// # reserved_handles::Hierarchy,
/// # },
/// # structures::{
/// # Public, PublicBuilder, PublicKeyRsa, PublicRsaParametersBuilder, RsaScheme,
/// # SymmetricDefinition,
/// # },
/// # };
/// #
/// # const KEY: [u8; 256] = [
/// # 231, 97, 201, 180, 0, 1, 185, 150, 85, 90, 174, 188, 105, 133, 188, 3, 206, 5, 222, 71, 185, 1,
/// # 209, 243, 36, 130, 250, 116, 17, 0, 24, 4, 25, 225, 250, 198, 245, 210, 140, 23, 139, 169, 15,
/// # 193, 4, 145, 52, 138, 149, 155, 238, 36, 74, 152, 179, 108, 200, 248, 250, 100, 115, 214, 166,
/// # 165, 1, 27, 51, 11, 11, 244, 218, 157, 3, 174, 171, 142, 45, 8, 9, 36, 202, 171, 165, 43, 208,
/// # 186, 232, 15, 241, 95, 81, 174, 189, 30, 213, 47, 86, 115, 239, 49, 214, 235, 151, 9, 189, 174,
/// # 144, 238, 200, 201, 241, 157, 43, 37, 6, 96, 94, 152, 159, 205, 54, 9, 181, 14, 35, 246, 49,
/// # 150, 163, 118, 242, 59, 54, 42, 221, 215, 248, 23, 18, 223, 179, 229, 0, 204, 65, 69, 166, 180,
/// # 11, 49, 131, 96, 163, 96, 158, 7, 109, 119, 208, 17, 237, 125, 187, 121, 94, 65, 2, 86, 105,
/// # 68, 51, 197, 73, 108, 185, 231, 126, 199, 81, 1, 251, 211, 45, 47, 15, 113, 135, 197, 152, 239,
/// # 180, 111, 18, 192, 136, 222, 11, 99, 41, 248, 205, 253, 209, 56, 214, 32, 225, 3, 49, 161, 58,
/// # 57, 190, 69, 86, 95, 185, 184, 155, 76, 8, 122, 104, 81, 222, 234, 246, 40, 98, 182, 90, 160,
/// # 111, 74, 102, 36, 148, 99, 69, 207, 214, 104, 87, 128, 238, 26, 121, 107, 166, 4, 64, 5, 210,
/// # 164, 162, 189,
/// # ];
/// #
/// # // Create context
/// # let mut context =
/// # Context::new(
/// # TctiNameConf::from_environment_variable().expect("Failed to get TCTI"),
/// # ).expect("Failed to create Context");
/// #
/// # let session = context
/// # .start_auth_session(
/// # None,
/// # None,
/// # None,
/// # SessionType::Hmac,
/// # SymmetricDefinition::AES_256_CFB,
/// # tss_esapi::interface_types::algorithm::HashingAlgorithm::Sha256,
/// # )
/// # .expect("Failed to create session")
/// # .expect("Received invalid handle");
/// #
/// let object_attributes = ObjectAttributesBuilder::new()
/// .with_user_with_auth(true)
/// .with_decrypt(false)
/// .with_sign_encrypt(true)
/// .with_restricted(false)
/// .build()
/// .expect("Failed to build object attributes");
///
/// let public = PublicBuilder::new()
/// .with_public_algorithm(PublicAlgorithm::Rsa)
/// .with_name_hashing_algorithm(HashingAlgorithm::Sha256)
/// .with_object_attributes(object_attributes)
/// .with_rsa_parameters(
/// PublicRsaParametersBuilder::new_unrestricted_signing_key(
/// RsaScheme::create(RsaSchemeAlgorithm::RsaSsa, Some(HashingAlgorithm::Sha256))
/// .expect("Failed to create rsa scheme"),
/// RsaKeyBits::Rsa2048,
/// Default::default(),
/// )
/// .build()
/// .expect("Failed to create rsa parameters for public structure"),
/// )
/// .with_rsa_unique_identifier(
/// PublicKeyRsa::from_bytes(&KEY[..256])
/// .expect("Failed to create Public RSA key from buffer"),
/// )
/// .build()
/// .expect("Failed to build Public structure");
///
/// // Load public key into Owner hierarchy.
/// let key_handle = context.load_external(None, public, Hierarchy::Owner)
/// .expect("The load_external should have returned a valid key handle.");
/// ```
pub fn load_external(
&mut self,
private: Sensitive,
private: impl Into<Option<Sensitive>>,
public: Public,
hierarchy: Hierarchy,
) -> Result<KeyHandle> {
let potential_private = private.into();
if (hierarchy != Hierarchy::Null) && potential_private.is_some() {
error!("Only NULL hierarchy is valid in load_external when loading both private and public part.");
return Err(Error::local_error(WrapperErrorKind::InvalidParam));
}
let mut object_handle = ObjectHandle::None.into();
let potential_private_in = potential_private.map(|v| v.try_into()).transpose()?;
let public_in = public.try_into()?;
ReturnCode::ensure_success(
unsafe {
Esys_LoadExternal(
self.mut_context(),
self.optional_session_1(),
self.optional_session_2(),
self.optional_session_3(),
&private.try_into()?,
&public.try_into()?,
potential_private_in.as_ref().map_or_else(null, |v| v),
&public_in,
if cfg!(hierarchy_is_esys_tr) {
ObjectHandle::from(hierarchy).into()
} else {
Expand All @@ -158,41 +263,6 @@ impl Context {
Ok(key_handle)
}

/// Load the public part of an external key and return its new handle.
pub fn load_external_public(
&mut self,
public: Public,
hierarchy: Hierarchy,
) -> Result<KeyHandle> {
let mut object_handle = ObjectHandle::None.into();
ReturnCode::ensure_success(
unsafe {
Esys_LoadExternal(
self.mut_context(),
self.optional_session_1(),
self.optional_session_2(),
self.optional_session_3(),
null(),
&public.try_into()?,
if cfg!(hierarchy_is_esys_tr) {
ObjectHandle::from(hierarchy).into()
} else {
TpmHandle::from(hierarchy).into()
},
&mut object_handle,
)
},
|ret| {
error!("Error in loading external public object: {:#010X}", ret);
},
)?;

let key_handle = KeyHandle::from(object_handle);
self.handle_manager
.add_handle(key_handle.into(), HandleDropAction::Flush)?;
Ok(key_handle)
}

/// Read the public part of a key currently in the TPM and return it.
pub fn read_public(&mut self, key_handle: KeyHandle) -> Result<(Public, Name, Name)> {
let mut out_public_ptr = null_mut();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -558,7 +558,7 @@ fn ctx_migration_test() {
let key_context = basic_ctx.context_save(key_handle.into()).unwrap();

let pub_key_handle = basic_ctx
.load_external_public(result.out_public.clone(), Hierarchy::Owner)
.load_external(None, result.out_public.clone(), Hierarchy::Owner)
.unwrap();
let pub_key_context = basic_ctx.context_save(pub_key_handle.into()).unwrap();

Expand Down Expand Up @@ -672,7 +672,7 @@ fn activate_credential() {
panic!("Wrong Public type");
};
let pub_handle = basic_ctx
.load_external_public(key_pub, Hierarchy::Owner)
.load_external(None, key_pub, Hierarchy::Owner)
.unwrap();

// Credential to expect back as proof for attestation
Expand Down Expand Up @@ -799,7 +799,7 @@ fn activate_credential_wrong_key() {
panic!("Wrong Public type");
};
let pub_handle = basic_ctx
.load_external_public(key_pub, Hierarchy::Owner)
.load_external(None, key_pub, Hierarchy::Owner)
.unwrap();

// Credential to expect back as proof for attestation
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -76,60 +76,6 @@ mod test_load {
}
}

mod test_load_external_public {
use crate::common::{create_ctx_with_session, KEY};
use tss_esapi::{
attributes::ObjectAttributesBuilder,
interface_types::{
algorithm::{HashingAlgorithm, PublicAlgorithm, RsaSchemeAlgorithm},
key_bits::RsaKeyBits,
reserved_handles::Hierarchy,
},
structures::{Public, PublicBuilder, PublicKeyRsa, PublicRsaParametersBuilder, RsaScheme},
};

pub fn get_ext_rsa_pub() -> Public {
let object_attributes = ObjectAttributesBuilder::new()
.with_user_with_auth(true)
.with_decrypt(false)
.with_sign_encrypt(true)
.with_restricted(false)
.build()
.expect("Failed to build object attributes");

PublicBuilder::new()
.with_public_algorithm(PublicAlgorithm::Rsa)
.with_name_hashing_algorithm(HashingAlgorithm::Sha256)
.with_object_attributes(object_attributes)
.with_rsa_parameters(
PublicRsaParametersBuilder::new_unrestricted_signing_key(
RsaScheme::create(RsaSchemeAlgorithm::RsaSsa, Some(HashingAlgorithm::Sha256))
.expect("Failed to create rsa scheme"),
RsaKeyBits::Rsa2048,
Default::default(),
)
.build()
.expect("Failed to create rsa parameters for public structure"),
)
.with_rsa_unique_identifier(
PublicKeyRsa::from_bytes(&KEY[..256])
.expect("Failed to create Public RSA key from buffer"),
)
.build()
.expect("Failed to build Public structure")
}

#[test]
fn test_load_external_public() {
let mut context = create_ctx_with_session();
let pub_key = get_ext_rsa_pub();

context
.load_external_public(pub_key, Hierarchy::Owner)
.unwrap();
}
}

mod test_load_external {
use crate::common::create_ctx_with_session;
use std::convert::TryInto;
Expand Down Expand Up @@ -218,13 +164,24 @@ mod test_load_external {
}

#[test]
fn test_load_external() {
fn test_load_external_private_and_public_parts() {
let mut context = create_ctx_with_session();
let pub_key = get_ext_rsa_pub();
let priv_key = get_ext_rsa_priv();

let key_handle = context
.load_external(priv_key, pub_key, Hierarchy::Null)
.load_external(Some(priv_key), pub_key, Hierarchy::Null)
.unwrap();
context.flush_context(key_handle.into()).unwrap();
}

#[test]
fn test_load_external_only_public_part() {
let mut context = create_ctx_with_session();
let pub_key = get_ext_rsa_pub();

let key_handle = context
.load_external(None, pub_key, Hierarchy::Null)
.unwrap();
context.flush_context(key_handle.into()).unwrap();
}
Expand Down