// This file was extracted from the TCG Published
// Trusted Platform Module Library
// Part 3: Commands
// Family "2.0"
// Level 00 Revision 01.16
// October 30, 2014
#include "InternalRoutines.h"
#include "EvictControl_fp.h"
//
//
// Error Returns Meaning
//
// TPM_RC_ATTRIBUTES an object with temporary, stClear or publicOnly attribute SET cannot
// be made persistent
// TPM_RC_HIERARCHY auth cannot authorize the operation in the hierarchy of evictObject
// TPM_RC_HANDLE evictHandle of the persistent object to be evicted is not the same as
// the persistentHandle argument
// TPM_RC_NV_HANDLE persistentHandle is unavailable
// TPM_RC_NV_SPACE no space in NV to make evictHandle persistent
// TPM_RC_RANGE persistentHandle is not in the range corresponding to the hierarchy of
// evictObject
//
TPM_RC
TPM2_EvictControl(
EvictControl_In *in // IN: input parameter list
)
{
TPM_RC result;
OBJECT *evictObject;
// The command needs NV update. Check if NV is available.
// A TPM_RC_NV_UNAVAILABLE or TPM_RC_NV_RATE error may be returned at
// this point
result = NvIsAvailable();
if(result != TPM_RC_SUCCESS) return result;
// Input Validation
// Get internal object pointer
evictObject = ObjectGet(in->objectHandle);
// Temporary, stClear or public only objects can not be made persistent
if( evictObject->attributes.temporary == SET
|| evictObject->attributes.stClear == SET
|| evictObject->attributes.publicOnly == SET
)
return TPM_RC_ATTRIBUTES + RC_EvictControl_objectHandle;
// If objectHandle refers to a persistent object, it should be the same as
// input persistentHandle
if( evictObject->attributes.evict == SET
&& evictObject->evictHandle != in->persistentHandle
)
return TPM_RC_HANDLE + RC_EvictControl_objectHandle;
// Additional auth validation
if(in->auth == TPM_RH_PLATFORM)
{
// To make persistent
if(evictObject->attributes.evict == CLEAR)
{
// Platform auth can not set evict object in storage or endorsement
// hierarchy
if(evictObject->attributes.ppsHierarchy == CLEAR)
return TPM_RC_HIERARCHY + RC_EvictControl_objectHandle;
// Platform cannot use a handle outside of platform persistent range.
if(!NvIsPlatformPersistentHandle(in->persistentHandle))
return TPM_RC_RANGE + RC_EvictControl_persistentHandle;
}
// Platform auth can delete any persistent object
}
else if(in->auth == TPM_RH_OWNER)
{
// Owner auth can not set or clear evict object in platform hierarchy
if(evictObject->attributes.ppsHierarchy == SET)
return TPM_RC_HIERARCHY + RC_EvictControl_objectHandle;
// Owner cannot use a handle outside of owner persistent range.
if( evictObject->attributes.evict == CLEAR
&& !NvIsOwnerPersistentHandle(in->persistentHandle)
)
return TPM_RC_RANGE + RC_EvictControl_persistentHandle;
}
else
{
// Other auth is not allowed in this command and should be filtered out
// at unmarshal process
pAssert(FALSE);
}
// Internal Data Update
// Change evict state
if(evictObject->attributes.evict == CLEAR)
{
// Make object persistent
// A TPM_RC_NV_HANDLE or TPM_RC_NV_SPACE error may be returned at this
// point
result = NvAddEvictObject(in->persistentHandle, evictObject);
if(result != TPM_RC_SUCCESS) return result;
}
else
{
// Delete the persistent object in NV
NvDeleteEntity(evictObject->evictHandle);
}
return TPM_RC_SUCCESS;
}