C++程序  |  113行  |  3.85 KB

// 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;

}