87 lines
2.6 KiB
C
87 lines
2.6 KiB
C
// 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 "Shutdown_fp.h"
|
|
//
|
|
//
|
|
// Error Returns Meaning
|
|
//
|
|
// TPM_RC_TYPE if PCR bank has been re-configured, a CLEAR StateSave() is
|
|
// required
|
|
//
|
|
TPM_RC
|
|
TPM2_Shutdown(
|
|
Shutdown_In *in // IN: input parameter list
|
|
)
|
|
{
|
|
TPM_RC result;
|
|
|
|
// 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
|
|
|
|
// If PCR bank has been reconfigured, a CLEAR state save is required
|
|
if(g_pcrReConfig && in->shutdownType == TPM_SU_STATE)
|
|
return TPM_RC_TYPE + RC_Shutdown_shutdownType;
|
|
|
|
// Internal Data Update
|
|
|
|
// PCR private date state save
|
|
PCRStateSave(in->shutdownType);
|
|
|
|
// Get DRBG state
|
|
CryptDrbgGetPutState(GET_STATE);
|
|
|
|
// Save all orderly data
|
|
NvWriteReserved(NV_ORDERLY_DATA, &go);
|
|
|
|
// Save RAM backed NV index data
|
|
NvStateSave();
|
|
|
|
if(in->shutdownType == TPM_SU_STATE)
|
|
{
|
|
// Save STATE_RESET and STATE_CLEAR data
|
|
NvWriteReserved(NV_STATE_CLEAR, &gc);
|
|
NvWriteReserved(NV_STATE_RESET, &gr);
|
|
}
|
|
else if(in->shutdownType == TPM_SU_CLEAR)
|
|
{
|
|
// Save STATE_RESET data
|
|
NvWriteReserved(NV_STATE_RESET, &gr);
|
|
}
|
|
|
|
// Write orderly shut down state
|
|
if(in->shutdownType == TPM_SU_CLEAR)
|
|
gp.orderlyState = TPM_SU_CLEAR;
|
|
else if(in->shutdownType == TPM_SU_STATE)
|
|
{
|
|
gp.orderlyState = TPM_SU_STATE;
|
|
// Hack for the H-CRTM and Startup locality settings
|
|
if(g_DrtmPreStartup)
|
|
gp.orderlyState |= PRE_STARTUP_FLAG;
|
|
else if(g_StartupLocality3)
|
|
gp.orderlyState |= STARTUP_LOCALITY_3;
|
|
}
|
|
else
|
|
pAssert(FALSE);
|
|
|
|
NvWriteReserved(NV_ORDERLY, &gp.orderlyState);
|
|
|
|
// If PRE_STARTUP_FLAG was SET, then it will stay set in gp.orderlyState even
|
|
// if the TPM isn't actually shut down. This is OK because all other checks
|
|
// of gp.orderlyState are to see if it is SHUTDOWN_NONE. So, having
|
|
// gp.orderlyState set to another value that is also not SHUTDOWN_NONE, is not
|
|
// an issue. This must be the case, otherwise, it would be impossible to add
|
|
// an additional shutdown type without major changes to the code.
|
|
|
|
return TPM_RC_SUCCESS;
|
|
}
|