/* Microsoft Reference Implementation for TPM 2.0 * * The copyright in this software is being made available under the BSD License, * included below. This software may be subject to other third party and * contributor rights, including patent rights, and no such rights are granted * under this license. * * Copyright (c) Microsoft Corporation * * All rights reserved. * * BSD License * * Redistribution and use in source and binary forms, with or without modification, * are permitted provided that the following conditions are met: * * Redistributions of source code must retain the above copyright notice, this list * of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright notice, this * list of conditions and the following disclaimer in the documentation and/or * other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ""AS IS"" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ //** Index Type Definitions // These definitions allow the same code to be used pre and post 1.21. The main // action is to redefine the index type values from the bit values. // Use TPM_NT_ORDINARY to indicate if the TPM_NT type is defined #ifndef _NV_H_ #define _NV_H_ #ifdef TPM_NT_ORDINARY // If TPM_NT_ORDINARY is defined, then the TPM_NT field is present in a TPMA_NV # define GET_TPM_NT(attributes) GET_ATTRIBUTE(attributes, TPMA_NV, TPM_NT) #else // If TPM_NT_ORDINARY is not defined, then need to synthesize it from the // attributes # define GetNv_TPM_NV(attributes) \ ( IS_ATTRIBUTE(attributes, TPMA_NV, COUNTER) \ + (IS_ATTRIBUTE(attributes, TPMA_NV, BITS) << 1) \ + (IS_ATTRIBUTE(attributes, TPMA_NV, EXTEND) << 2) \ ) # define TPM_NT_ORDINARY (0) # define TPM_NT_COUNTER (1) # define TPM_NT_BITS (2) # define TPM_NT_EXTEND (4) #endif //** Attribute Macros // These macros are used to isolate the differences in the way that the index type // changed in version 1.21 of the specification # define IsNvOrdinaryIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_ORDINARY) # define IsNvCounterIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_COUNTER) # define IsNvBitsIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_BITS) # define IsNvExtendIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_EXTEND) #ifdef TPM_NT_PIN_PASS # define IsNvPinPassIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_PIN_PASS) #endif #ifdef TPM_NT_PIN_FAIL # define IsNvPinFailIndex(attributes) \ (GET_TPM_NT(attributes) == TPM_NT_PIN_FAIL) #endif typedef struct { UINT32 size; TPM_HANDLE handle; } NV_ENTRY_HEADER; #define NV_EVICT_OBJECT_SIZE \ (sizeof(UINT32) + sizeof(TPM_HANDLE) + sizeof(OBJECT)) #define NV_INDEX_COUNTER_SIZE \ (sizeof(UINT32) + sizeof(NV_INDEX) + sizeof(UINT64)) #define NV_RAM_INDEX_COUNTER_SIZE \ (sizeof(NV_RAM_HEADER) + sizeof(UINT64)) typedef struct { UINT32 size; TPM_HANDLE handle; TPMA_NV attributes; } NV_RAM_HEADER; // Defines the end-of-list marker for NV. The list terminator is // a UINT32 of zero, followed by the current value of s_maxCounter which is a // 64-bit value. The structure is defined as an array of 3 UINT32 values so that // there is no padding between the UINT32 list end marker and the UINT64 maxCounter // value. typedef UINT32 NV_LIST_TERMINATOR[3]; //** Orderly RAM Values // The following defines are for accessing orderly RAM values. // This is the initialize for the RAM reference iterator. #define NV_RAM_REF_INIT 0 // This is the starting address of the RAM space used for orderly data #define RAM_ORDERLY_START \ (&s_indexOrderlyRam[0]) // This is the offset within NV that is used to save the orderly data on an // orderly shutdown. #define NV_ORDERLY_START \ (NV_INDEX_RAM_DATA) // This is the end of the orderly RAM space. It is actually the first byte after the // last byte of orderly RAM data #define RAM_ORDERLY_END \ (RAM_ORDERLY_START + sizeof(s_indexOrderlyRam)) // This is the end of the orderly space in NV memory. As with RAM_ORDERLY_END, it is // actually the offset of the first byte after the end of the NV orderly data. #define NV_ORDERLY_END \ (NV_ORDERLY_START + sizeof(s_indexOrderlyRam)) // Macro to check that an orderly RAM address is with range. #define ORDERLY_RAM_ADDRESS_OK(start, offset) \ ((start >= RAM_ORDERLY_START) && ((start + offset - 1) < RAM_ORDERLY_END)) #define RETURN_IF_NV_IS_NOT_AVAILABLE \ { \ if(g_NvStatus != TPM_RC_SUCCESS) \ return g_NvStatus; \ } // Routinely have to clear the orderly flag and fail if the // NV is not available so that it can be cleared. #define RETURN_IF_ORDERLY \ { \ if(NvClearOrderly() != TPM_RC_SUCCESS) \ return g_NvStatus; \ } #define NV_IS_AVAILABLE (g_NvStatus == TPM_RC_SUCCESS) #define IS_ORDERLY(value) (value < SU_DA_USED_VALUE) #define NV_IS_ORDERLY (IS_ORDERLY(gp.orderlyState)) // Macro to set the NV UPDATE_TYPE. This deals with the fact that the update is // possibly a combination of UT_NV and UT_ORDERLY. #define SET_NV_UPDATE(type) g_updateNV |= (type) #endif // _NV_H_