1 /** @file 2 Implement TPM2 DictionaryAttack related command. 3 4 Copyright (c) 2013 - 2016, Intel Corporation. All rights reserved. <BR> 5 This program and the accompanying materials 6 are licensed and made available under the terms and conditions of the BSD License 7 which accompanies this distribution. The full text of the license may be found at 8 http://opensource.org/licenses/bsd-license.php 9 10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 12 13 **/ 14 15 #include <IndustryStandard/UefiTcgPlatform.h> 16 #include <Library/Tpm2CommandLib.h> 17 #include <Library/Tpm2DeviceLib.h> 18 #include <Library/BaseMemoryLib.h> 19 #include <Library/BaseLib.h> 20 #include <Library/DebugLib.h> 21 22 #pragma pack(1) 23 24 typedef struct { 25 TPM2_COMMAND_HEADER Header; 26 TPMI_RH_LOCKOUT LockHandle; 27 UINT32 AuthSessionSize; 28 TPMS_AUTH_COMMAND AuthSession; 29 } TPM2_DICTIONARY_ATTACK_LOCK_RESET_COMMAND; 30 31 typedef struct { 32 TPM2_RESPONSE_HEADER Header; 33 UINT32 AuthSessionSize; 34 TPMS_AUTH_RESPONSE AuthSession; 35 } TPM2_DICTIONARY_ATTACK_LOCK_RESET_RESPONSE; 36 37 typedef struct { 38 TPM2_COMMAND_HEADER Header; 39 TPMI_RH_LOCKOUT LockHandle; 40 UINT32 AuthSessionSize; 41 TPMS_AUTH_COMMAND AuthSession; 42 UINT32 NewMaxTries; 43 UINT32 NewRecoveryTime; 44 UINT32 LockoutRecovery; 45 } TPM2_DICTIONARY_ATTACK_PARAMETERS_COMMAND; 46 47 typedef struct { 48 TPM2_RESPONSE_HEADER Header; 49 UINT32 AuthSessionSize; 50 TPMS_AUTH_RESPONSE AuthSession; 51 } TPM2_DICTIONARY_ATTACK_PARAMETERS_RESPONSE; 52 53 #pragma pack() 54 55 /** 56 This command cancels the effect of a TPM lockout due to a number of successive authorization failures. 57 If this command is properly authorized, the lockout counter is set to zero. 58 59 @param[in] LockHandle TPM_RH_LOCKOUT 60 @param[in] AuthSession Auth Session context 61 62 @retval EFI_SUCCESS Operation completed successfully. 63 @retval EFI_DEVICE_ERROR Unexpected device behavior. 64 **/ 65 EFI_STATUS 66 EFIAPI 67 Tpm2DictionaryAttackLockReset ( 68 IN TPMI_RH_LOCKOUT LockHandle, 69 IN TPMS_AUTH_COMMAND *AuthSession 70 ) 71 { 72 EFI_STATUS Status; 73 TPM2_DICTIONARY_ATTACK_LOCK_RESET_COMMAND SendBuffer; 74 TPM2_DICTIONARY_ATTACK_LOCK_RESET_RESPONSE RecvBuffer; 75 UINT32 SendBufferSize; 76 UINT32 RecvBufferSize; 77 UINT8 *Buffer; 78 UINT32 SessionInfoSize; 79 80 // 81 // Construct command 82 // 83 SendBuffer.Header.tag = SwapBytes16(TPM_ST_SESSIONS); 84 SendBuffer.Header.commandCode = SwapBytes32(TPM_CC_DictionaryAttackLockReset); 85 86 SendBuffer.LockHandle = SwapBytes32 (LockHandle); 87 88 // 89 // Add in Auth session 90 // 91 Buffer = (UINT8 *)&SendBuffer.AuthSession; 92 93 // sessionInfoSize 94 SessionInfoSize = CopyAuthSessionCommand (AuthSession, Buffer); 95 Buffer += SessionInfoSize; 96 SendBuffer.AuthSessionSize = SwapBytes32(SessionInfoSize); 97 98 SendBufferSize = (UINT32)((UINTN)Buffer - (UINTN)&SendBuffer); 99 SendBuffer.Header.paramSize = SwapBytes32 (SendBufferSize); 100 101 // 102 // send Tpm command 103 // 104 RecvBufferSize = sizeof (RecvBuffer); 105 Status = Tpm2SubmitCommand (SendBufferSize, (UINT8 *)&SendBuffer, &RecvBufferSize, (UINT8 *)&RecvBuffer); 106 if (EFI_ERROR (Status)) { 107 goto Done; 108 } 109 110 if (RecvBufferSize < sizeof (TPM2_RESPONSE_HEADER)) { 111 DEBUG ((EFI_D_ERROR, "Tpm2DictionaryAttackLockReset - RecvBufferSize Error - %x\n", RecvBufferSize)); 112 Status = EFI_DEVICE_ERROR; 113 goto Done; 114 } 115 if (SwapBytes32(RecvBuffer.Header.responseCode) != TPM_RC_SUCCESS) { 116 DEBUG ((EFI_D_ERROR, "Tpm2DictionaryAttackLockReset - responseCode - %x\n", SwapBytes32(RecvBuffer.Header.responseCode))); 117 Status = EFI_DEVICE_ERROR; 118 goto Done; 119 } 120 121 Done: 122 // 123 // Clear AuthSession Content 124 // 125 ZeroMem (&SendBuffer, sizeof(SendBuffer)); 126 ZeroMem (&RecvBuffer, sizeof(RecvBuffer)); 127 return Status; 128 } 129 130 /** 131 This command cancels the effect of a TPM lockout due to a number of successive authorization failures. 132 If this command is properly authorized, the lockout counter is set to zero. 133 134 @param[in] LockHandle TPM_RH_LOCKOUT 135 @param[in] AuthSession Auth Session context 136 @param[in] NewMaxTries Count of authorization failures before the lockout is imposed 137 @param[in] NewRecoveryTime Time in seconds before the authorization failure count is automatically decremented 138 @param[in] LockoutRecovery Time in seconds after a lockoutAuth failure before use of lockoutAuth is allowed 139 140 @retval EFI_SUCCESS Operation completed successfully. 141 @retval EFI_DEVICE_ERROR Unexpected device behavior. 142 **/ 143 EFI_STATUS 144 EFIAPI 145 Tpm2DictionaryAttackParameters ( 146 IN TPMI_RH_LOCKOUT LockHandle, 147 IN TPMS_AUTH_COMMAND *AuthSession, 148 IN UINT32 NewMaxTries, 149 IN UINT32 NewRecoveryTime, 150 IN UINT32 LockoutRecovery 151 ) 152 { 153 EFI_STATUS Status; 154 TPM2_DICTIONARY_ATTACK_PARAMETERS_COMMAND SendBuffer; 155 TPM2_DICTIONARY_ATTACK_PARAMETERS_RESPONSE RecvBuffer; 156 UINT32 SendBufferSize; 157 UINT32 RecvBufferSize; 158 UINT8 *Buffer; 159 UINT32 SessionInfoSize; 160 161 // 162 // Construct command 163 // 164 SendBuffer.Header.tag = SwapBytes16(TPM_ST_SESSIONS); 165 SendBuffer.Header.commandCode = SwapBytes32(TPM_CC_DictionaryAttackParameters); 166 167 SendBuffer.LockHandle = SwapBytes32 (LockHandle); 168 169 // 170 // Add in Auth session 171 // 172 Buffer = (UINT8 *)&SendBuffer.AuthSession; 173 174 // sessionInfoSize 175 SessionInfoSize = CopyAuthSessionCommand (AuthSession, Buffer); 176 Buffer += SessionInfoSize; 177 SendBuffer.AuthSessionSize = SwapBytes32(SessionInfoSize); 178 179 // 180 // Real data 181 // 182 WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32(NewMaxTries)); 183 Buffer += sizeof(UINT32); 184 WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32(NewRecoveryTime)); 185 Buffer += sizeof(UINT32); 186 WriteUnaligned32 ((UINT32 *)Buffer, SwapBytes32(LockoutRecovery)); 187 Buffer += sizeof(UINT32); 188 189 SendBufferSize = (UINT32)((UINTN)Buffer - (UINTN)&SendBuffer); 190 SendBuffer.Header.paramSize = SwapBytes32 (SendBufferSize); 191 192 // 193 // send Tpm command 194 // 195 RecvBufferSize = sizeof (RecvBuffer); 196 Status = Tpm2SubmitCommand (SendBufferSize, (UINT8 *)&SendBuffer, &RecvBufferSize, (UINT8 *)&RecvBuffer); 197 if (EFI_ERROR (Status)) { 198 goto Done; 199 } 200 201 if (RecvBufferSize < sizeof (TPM2_RESPONSE_HEADER)) { 202 DEBUG ((EFI_D_ERROR, "Tpm2DictionaryAttackParameters - RecvBufferSize Error - %x\n", RecvBufferSize)); 203 Status = EFI_DEVICE_ERROR; 204 goto Done; 205 } 206 if (SwapBytes32(RecvBuffer.Header.responseCode) != TPM_RC_SUCCESS) { 207 DEBUG ((EFI_D_ERROR, "Tpm2DictionaryAttackParameters - responseCode - %x\n", SwapBytes32(RecvBuffer.Header.responseCode))); 208 Status = EFI_DEVICE_ERROR; 209 goto Done; 210 } 211 212 Done: 213 // 214 // Clear AuthSession Content 215 // 216 ZeroMem (&SendBufferSize, sizeof(SendBufferSize)); 217 ZeroMem (&RecvBuffer, sizeof(RecvBuffer)); 218 return Status; 219 } 220