diff options
Diffstat (limited to 'ReferenceCode/ME/At/AtAm/Dxe')
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/At.c | 1015 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/At.h | 280 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAm.c | 694 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAm.dxs | 41 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAm.h | 239 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAm.inf | 95 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.cif | 18 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.mak | 81 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.sdl | 33 | ||||
-rw-r--r-- | ReferenceCode/ME/At/AtAm/Dxe/AtHi.h | 1275 |
10 files changed, 3771 insertions, 0 deletions
diff --git a/ReferenceCode/ME/At/AtAm/Dxe/At.c b/ReferenceCode/ME/At/AtAm/Dxe/At.c new file mode 100644 index 0000000..a47ddeb --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/At.c @@ -0,0 +1,1015 @@ +/** @file + Implementation for the AT driver. + This driver implements the AT protocol. + +@copyright + Copyright (c) 2004 - 2012 Intel Corporation. All rights + reserved This software and associated documentation (if any) + is furnished under a license and may only be used or copied in + accordance with the terms of the license. Except as permitted + by such license, no part of this software or documentation may + be reproduced, stored in a retrieval system, or transmitted in + any form or by any means without the express written consent + of Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement + +**/ + +#include "At.h" + +AT_INSTANCE mAtInstance = { + AT_PRIVATE_DATA_SIGNATURE, + NULL, + { + (UINT8) AT_PROTOCOL_REVISION, + (EFI_AT_AUTHETICATE_CREDENTIAL) AuthenticateCredential, + (EFI_AT_COMPUTE_HASH) ComputeHash, + (EFI_AT_GET_NONCE) GetNonce, + (EFI_AT_GET_TIMER_INFO) GetTimerInfo, + (EFI_AT_GET_RECOVERY_STRING) GetRecoveryString, + (EFI_AT_GET_ISV_ID) GetIsvId, + (EFI_AT_SEND_ASSERT_STOLEN) SendAssertStolen, + (EFI_AT_SET_SUSPEND_STATE) SetSuspendState, + (EFI_AT_INIT_WWAN_RECOV) InitWWANREcov, + (EFI_AT_GET_WWAN_NIC_STATUS) GetWWANNicStatus, + (EFI_AT_GET_STATE_UNSIGNED) GetStateUnsigned + + } +}; + +EFI_HECI_PROTOCOL *mHeci = NULL; + +/** + Entry point for the AT Driver. + + @param[in] ImageHandle Image handle of this driver. + @param[in] SystemTable Global system service table. + + @retval EFI_SUCCESS Initialization complete. + @exception EFI_UNSUPPORTED The chipset is unsupported by this driver. + @retval EFI_OUT_OF_RESOURCES Do not have enough resources to initialize the driver. + @retval EFI_DEVICE_ERROR Device error, driver exits abnormally. +**/ +EFI_STATUS +EFIAPI +AtEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + + DEBUG ((EFI_D_INFO, "ATAM: AtEntryPoint()\n")); + /// + /// Install the EFI_AT_PROTOCOL interface + /// + Status = gBS->InstallMultipleProtocolInterfaces ( + &(mAtInstance.Handle), + &gEfiAtProtocolGuid, + &(mAtInstance.AtProtocol), + NULL + ); + + return Status; +} + +/** + This function sends a request to ME AT Services to validate AT + recovery credentials. The user input is captured in UTF-16 + format and then passed to this funtion. This function converts + the User recovery password into a HASH by using Salt & Nonce + and then send the password HASH to ME AT Services for + validation. ME AT Service compares the Password HASH and + returns either pass or fail. + + @param[in] This The address of protocol + @param[in] PassPhrase Passphrase that needs to be authenticated sent to ME + @param[in] PassType Password type user or server generated + @param[in][out] IsAuthenticated The return of the password match 1 for success and 0 for fail + + @retval EFI_OUT_OF_RESOURCES Unable to allocate necessary data structures + @retval EFI_SUCCESS The function completed successfully +**/ +EFI_STATUS +EFIAPI +AuthenticateCredential ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PassPhrase, + IN UINT32 *PassType, + IN OUT UINT8 *IsAuthenticated + ) +{ + UINT32 HeciLength; + EFI_STATUS Status; + EFI_HECI_PROTOCOL *mHeci; + ATHI_AUTHENTICATE_CREDENTIAL_CMD *AtAuthCmd; + ATHI_AUTHENTICATE_CREDENTIAL_RSP AtAuthRsp; + + mHeci = NULL; + + AtAuthCmd = AllocateZeroPool (sizeof (ATHI_AUTHENTICATE_CREDENTIAL_CMD) + AT_PASSWORD_LENGTH); + if (AtAuthCmd == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + ZeroMem ((VOID *) &AtAuthRsp, sizeof (ATHI_AUTHENTICATE_CREDENTIAL_RSP)); + + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential Password Type: %x\n", *PassType)); + + AtAuthCmd->Credential.Type = *PassType; + AtAuthCmd->Credential.Length = (UINT32) AT_USR_PASS_HASH_LENGTH_MAX; + AtAuthCmd->Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtAuthCmd->Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtAuthCmd->Header.Command.Category = ATHI_CMD_GROUP_RECOVERY; + AtAuthCmd->Header.Command.IsResponse = AT_COMMAND; + AtAuthCmd->Header.Command.Code = ATHI_RECOVERY_GRP_AUTH_CREDENTIAL_CMD; + AtAuthCmd->Header.Length = sizeof (AT_CREDENTIAL) + AT_USR_PASS_HASH_LENGTH_MAX - sizeof (UINT8); + + HeciLength = sizeof (ATHI_AUTHENTICATE_CREDENTIAL_CMD) + AT_USR_PASS_HASH_LENGTH_MAX - sizeof (UINT8); + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthCmd Body 1: \n")); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) AtAuthCmd, HeciLength); + ); +#endif + + CopyMem (&AtAuthCmd->Credential.Value, PassPhrase, AT_USR_PASS_HASH_LENGTH_MAX); + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthCmd Body 2: \n")); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) AtAuthCmd, HeciLength); + ); + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential PassPhrase Body 3: \n")); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) PassPhrase, AtAuthCmd->Credential.Length); + ); +#endif + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AutheticateCrdential: Locating for HECI Driver Failed!, Status = %r\n", Status)); + FreePool (AtAuthCmd); + return Status; + } + } + + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential PassPhrase Length: %x\n", AtAuthCmd->Credential.Length)); + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthCmd HeciLength: %x\n", HeciLength)); +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthCmd Body 3: \n")); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) AtAuthCmd, HeciLength); + ); +#endif + + Status = mHeci->SendMsg ( + (UINT32 *) AtAuthCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AutheticateCrdential failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + FreePool (AtAuthCmd); + return Status; + } + + FreePool (AtAuthCmd); + + HeciLength = sizeof (ATHI_AUTHENTICATE_CREDENTIAL_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtAuthRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AutheticateCrdential failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthCmd Body 4: %x\n", AtAuthCmd)); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) AtAuthCmd, HeciLength); + ); +#endif + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthRsp HeciLength: %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AT::AutheticateCrdential AtAuthRsp.CompletionCode: %x\n", AtAuthRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, + "AT::AutheticateCrdential AtAuthRsp.Header.Command.IsResponse: %x\n", AtAuthRsp.Header.Command. + IsResponse)); + DEBUG ((EFI_D_ERROR, "checkRecoveryPassword AtAuthRsp.Authenticated: %d\n", AtAuthRsp.Authenticated)); + + /// + /// Assuming 0 is for success + /// + *IsAuthenticated = AtAuthRsp.Authenticated; + + return EFI_SUCCESS; +} + +/** + This API compute the SHA1 hash of the user enterted password + + @param[in] This The address of protocol + @param[in] PassPhrase The passphrase for which SHA1 hash to be computed + @param[in][out] Hash The return value of the SHA1 hash + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +ComputeHash ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PassPhrase, + IN OUT UINT8 *Hash + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + + ATHI_COMPUTE_HASH_CMD AtComputeHashCmd; + ATHI_COMPUTE_HASH_RSP AtComputeHashRsp; + + ZeroMem ((VOID *) &AtComputeHashCmd, sizeof (ATHI_COMPUTE_HASH_CMD)); + ZeroMem ((VOID *) &AtComputeHashRsp, sizeof (ATHI_COMPUTE_HASH_RSP)); + + DEBUG ((EFI_D_ERROR, "AT::AtComputeHashRsp DEBUG in ComputHash\n")); + + AtComputeHashCmd.Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtComputeHashCmd.Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtComputeHashCmd.Header.Command.Category = ATHI_CMD_GROUP_RECOVERY; + AtComputeHashCmd.Header.Command.IsResponse = AT_COMMAND; + AtComputeHashCmd.Header.Command.Code = ATHI_RECOVERY_GRP_COMPUTE_HASH_CMD; + + AtComputeHashCmd.Algorithm = AT_HASH_ALGO_ID_SHA1; + AtComputeHashCmd.InputLength = (UINT8) AsciiStrLen ((CHAR8 *) PassPhrase); + + // + // Check for length + // + // + // 0- Length 0 only header with command is send as message + // + AtComputeHashCmd.Header.Length = sizeof (ATHI_COMPUTE_HASH_CMD) - + 48 - + sizeof (ATHI_HEADER) + + AtComputeHashCmd.InputLength; + + CopyMem (&AtComputeHashCmd.InputBuffer, PassPhrase, AtComputeHashCmd.InputLength); + HeciLength = sizeof (ATHI_COMPUTE_HASH_CMD) - AT_MAX_HASH_OUTPUT_SIZE + AtComputeHashCmd.InputLength; + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AtComputeHashCmd message length = %x\n", HeciLength)); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) &AtComputeHashCmd, HeciLength); + ); + DEBUG ((EFI_D_ERROR, "AT::Look for UINT8Pass\n")); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) PassPhrase, AtComputeHashCmd.InputLength); + ); +#endif + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtComputeHash: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + Status = mHeci->SendMsg ( + (UINT32 *) &AtComputeHashCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtComputeHashCmd failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_COMPUTE_HASH_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtComputeHashRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtComputeHashRsp failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + DEBUG ((EFI_D_ERROR, "AT::AtComputeHashRsp response message length %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtComputeHashRsp.CompletionCode = %x\n", AtComputeHashRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, "AtComputeHashRsp.OutputLength = %x\n", AtComputeHashRsp.OutputLength)); + + if (AtComputeHashRsp.OutputLength != 0) { + DEBUG ((EFI_D_ERROR, "AtComputeHashRsp.OutputLength = %x\n", AtComputeHashRsp.OutputLength)); + } + + CopyMem (Hash, &AtComputeHashRsp.OutputBuffer, AtComputeHashRsp.OutputLength); + + return EFI_SUCCESS; +} + +/** + This API get the AT Unlock Timer values + + @param[in] This The address of protocol + @param[in] Interval The return value of the Unlock Time Interval that was set by AT Server + @param[in] TimeLeft The Timeleft in the Unlock Timer + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetTimerInfo ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT32 *Interval, + IN OUT UINT32 *TimeLeft + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + + ATHI_GET_TIMER_INFO_CMD AtGetTimerInfoCmd; + ATHI_GET_TIMER_INFO_RSP AtGetTimerInfoRsp; + + ZeroMem ((VOID *) &AtGetTimerInfoCmd, sizeof (ATHI_GET_TIMER_INFO_CMD)); + ZeroMem ((VOID *) &AtGetTimerInfoRsp, sizeof (ATHI_GET_TIMER_INFO_RSP)); + + AtGetTimerInfoCmd.Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtGetTimerInfoCmd.Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtGetTimerInfoCmd.Header.Command.Category = ATHI_CMD_GROUP_THEFT_DETECTION; + AtGetTimerInfoCmd.Header.Command.IsResponse = AT_COMMAND; + AtGetTimerInfoCmd.Header.Command.Code = ATHI_THEFT_DETECT_GRP_GET_TIMER_INFO_CMD; + // + // 0- Length 0 only header with command is send as message + // + AtGetTimerInfoCmd.Header.Length = sizeof (ATHI_GET_TIMER_INFO_CMD) - sizeof (ATHI_HEADER); + AtGetTimerInfoCmd.TimerId = AT_TID_UNLOCK_TIMER; + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetTimerInfo: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + HeciLength = sizeof (ATHI_GET_TIMER_INFO_CMD); + + Status = mHeci->SendMsg ( + (UINT32 *) &AtGetTimerInfoCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetTimerInfo failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_GET_TIMER_INFO_RSP); + + DEBUG ((EFI_D_ERROR, "AT::AtGetTimerInfo response message length = %x\n", HeciLength)); + + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtGetTimerInfoRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetTimerInfoRsp failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + DEBUG ((EFI_D_ERROR, "AT::AtGetTimerInfo response message length = %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtGetTimerInfoRsp.CompletionCode = %x\n", AtGetTimerInfoRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, "AtGetTimerInfoRsp.TimerInfo.Interval = %x\n", AtGetTimerInfoRsp.TimerInfo.Interval)); + DEBUG ((EFI_D_ERROR, "AtGetTimerInfoRsp.TimerInfo.TimeLeft = %x\n", AtGetTimerInfoRsp.TimerInfo.TimeLeft)); + + *Interval = AtGetTimerInfoRsp.TimerInfo.Interval; + *TimeLeft = AtGetTimerInfoRsp.TimerInfo.TimeLeft; + + return EFI_SUCCESS; + +} + +/** + This gets the ME nonce + @param[in] This The address of protocol + @param[in][out] Nonce The return value of the 16 Byte nonce received from ME + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetNonce ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT8 *Nonce + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + + ATHI_GET_NONCE_CMD AtGetNonceCmd; + ATHI_GET_NONCE_RSP AtGetNonceRsp; + + ZeroMem ((VOID *) &AtGetNonceCmd, sizeof (ATHI_GET_NONCE_CMD)); + ZeroMem ((VOID *) &AtGetNonceRsp, sizeof (ATHI_GET_NONCE_RSP)); + + AtGetNonceCmd.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtGetNonceCmd.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtGetNonceCmd.Command.Category = ATHI_CMD_GROUP_GENERAL; + AtGetNonceCmd.Command.IsResponse = AT_COMMAND; + AtGetNonceCmd.Command.Code = ATHI_GENERAL_GRP_GET_NONCE_CMD; + + // + // 0- Length 0 only header with command is send as message + // + AtGetNonceCmd.Length = sizeof (ATHI_GET_STATE_CMD) - sizeof (ATHI_HEADER); + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetNonce: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + HeciLength = sizeof (ATHI_GET_NONCE_CMD); + + Status = mHeci->SendMsg ( + (UINT32 *) &AtGetNonceCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetNonce failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_GET_NONCE_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtGetNonceRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetNonce failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AtGetNonce response message length %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtGetNonceRsp.CompletionCode = %x\n", AtGetNonceRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, "AtGetNonceRsp.Nonce = %x\n", AtGetNonceRsp.Nonce)); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) &AtGetNonceRsp.Nonce, AT_NONCE_LENGTH); + ); +#endif + + if (AtGetNonceRsp.CompletionCode == ATHI_COMPCODE_SUCCESS) { + DEBUG ((EFI_D_ERROR, "AtGetNonceRsp.CompletionCode = %x\n", AtGetNonceRsp.CompletionCode)); + } + + CopyMem (Nonce, &AtGetNonceRsp.Nonce, AT_NONCE_LENGTH); + + return EFI_SUCCESS; + +} + +/** + This retrives the ISV String stored by AT Server that BIOS will display during Platform lock state + + @param[in] This The address of protocol + @param[in] StringId The String buffer ID to retrive the ISV String + @param[out] IsvString 256 Bytes of ISV string array, the + @param[out] IsvStringLength The String length + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetRecoveryString ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 *StringId, + OUT UINT8 *IsvString, + OUT UINT32 *IsvStringLength + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + ATHI_GET_VENDOR_STRING_CMD AtIsvStringCmd; + ATHI_GET_VENDOR_STRING_RSP AtIsvStringRsp; + + ZeroMem ((VOID *) &AtIsvStringCmd, sizeof (ATHI_GET_VENDOR_STRING_CMD)); + ZeroMem ((VOID *) &AtIsvStringRsp, sizeof (ATHI_GET_VENDOR_STRING_RSP)); + // + // Setting the length of IsvString to 0 here. + // + *IsvStringLength = 0; + + AtIsvStringCmd.Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtIsvStringCmd.Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtIsvStringCmd.Header.Command.Category = ATHI_CMD_GROUP_DATA_STORAGE; + AtIsvStringCmd.Header.Command.IsResponse = AT_COMMAND; + AtIsvStringCmd.Header.Command.Code = ATHI_DATA_STORE_GRP_GET_VENDOR_STRING_CMD; + AtIsvStringCmd.Header.Length = sizeof (ATHI_GET_VENDOR_STRING_CMD) - sizeof (ATHI_HEADER); + AtIsvStringCmd.Id = (UINT8) *StringId; + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtIsvStringCmd: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + HeciLength = sizeof (ATHI_GET_VENDOR_STRING_CMD); + + PERF_START_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8200); + Status = mHeci->SendMsg ( + (UINT32 *) &AtIsvStringCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtIsvStringCmd failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_GET_VENDOR_STRING_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtIsvStringRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtIsvStringRsp failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8202); + return Status; + } + + PERF_END_EX (NULL, EVENT_REC_TOK, NULL, AsmReadTsc(), 0x8201); + +#ifdef EFI_DEBUG + DEBUG ((EFI_D_ERROR, "AT::AtIsvStringRsp response message length = %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtIsvStringRsp.CompletionCode = %x\n", AtIsvStringRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, "AtIsvStringRsp.String.Length = %x\n", AtIsvStringRsp.String.Length)); + DEBUG_CODE ( + ShowBuffer ((UINT8 *) &AtIsvStringRsp.String.Value, (UINT32) AtIsvStringRsp.String.Length); + ); +#endif + + if ((AtIsvStringRsp.CompletionCode == 0) && + (AtIsvStringRsp.String.Length > 0 && AtIsvStringRsp.String.Length < 256) + ) { + + CopyMem (IsvString, &AtIsvStringRsp.String.Value, AtIsvStringRsp.String.Length); + *IsvStringLength = AtIsvStringRsp.String.Length; + return EFI_SUCCESS; + } + + return EFIERR (AtIsvStringRsp.CompletionCode);; +} + +/** + This send an AssertStolen Message to ME when OEM has set the AllowAssertStolen bit to be accepted by BIOS. + + @param[in] This The address of protocol + @param[out] CompletionCode The return ME Firmware return code for this request + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +SendAssertStolen ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *CompletionCode + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + ATHI_ASSERT_STOLEN_CMD AtAssertStolenCmd; + ATHI_ASSERT_STOLEN_RSP AtAssertStolenRsp; + + // + // Initialize Variables + // + ZeroMem ((VOID *) &AtAssertStolenCmd, sizeof (ATHI_ASSERT_STOLEN_CMD)); + ZeroMem ((VOID *) &AtAssertStolenRsp, sizeof (ATHI_ASSERT_STOLEN_RSP)); + + /// + /// Populate AtAssertStolenCmd + /// + AtAssertStolenCmd.Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtAssertStolenCmd.Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtAssertStolenCmd.Header.Command.Category = ATHI_CMD_GROUP_THEFT_DETECTION; + AtAssertStolenCmd.Header.Command.IsResponse = AT_COMMAND; + AtAssertStolenCmd.Header.Command.Code = ATHI_THEFT_DETECT_GRP_UNSIGNED_ASSERT_STOLEN_CMD; + AtAssertStolenCmd.Header.Length = sizeof (ATHI_ASSERT_STOLEN_CMD) - sizeof (ATHI_HEADER); + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "SendAssertStolen: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + /// + /// Send AtAssertStolenCmd Request + /// + HeciLength = sizeof (ATHI_ASSERT_STOLEN_CMD); + + Status = mHeci->SendMsg ( + (UINT32 *) &AtAssertStolenCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtAssertStolenCmd failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + /// + /// Receive AtAssertStolenCmd Response + /// + HeciLength = sizeof (ATHI_ASSERT_STOLEN_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtAssertStolenRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtAssertStolenRsp failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + DEBUG ((EFI_D_ERROR, "ATAM: AtAssertStolen response message length %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "ATAM: AtAssertStolenRsp.CompletionCode = %x\n", AtAssertStolenRsp.CompletionCode)); + + *CompletionCode = AtAssertStolenRsp.CompletionCode; + + return EFI_SUCCESS; + +} + +/** + This receives the ISV ID from ME and display the ID, when the platform is in stolen state + + @param[in] This The address of protocol + @param[out] IsvId The pointer to 4 byte ISV ID + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetIsvId ( + IN EFI_AT_PROTOCOL *This, + OUT UINT32 *IsvId + ) +{ + + UINT32 HeciLength; + EFI_STATUS Status; + + ATHI_GET_ISVID_CMD AtGetIsvIdCmd; + ATHI_GET_ISVID_RSP AtGetIsvIdRsp; + + ZeroMem ((VOID *) &AtGetIsvIdCmd, sizeof (ATHI_GET_ISVID_CMD)); + ZeroMem ((VOID *) &AtGetIsvIdRsp, sizeof (ATHI_GET_ISVID_RSP)); + + AtGetIsvIdCmd.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtGetIsvIdCmd.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtGetIsvIdCmd.Command.Category = ATHI_CMD_GROUP_RECOVERY; + AtGetIsvIdCmd.Command.IsResponse = AT_COMMAND; + AtGetIsvIdCmd.Command.Code = ATHI_RECOVERY_GRP_GET_ISVID_CMD; + AtGetIsvIdCmd.Length = sizeof (ATHI_GET_ISVID_CMD) - sizeof (ATHI_HEADER); + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "GetIsvId: Locating for HECI Driver Failed!, Status = %r\n", Status)); + return Status; + } + } + + HeciLength = sizeof (ATHI_GET_ISVID_CMD); + + Status = mHeci->SendMsg ( + (UINT32 *) &AtGetIsvIdCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "GetIsvId failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_GET_ISVID_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtGetIsvIdRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "GetIsvId failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + DEBUG ((EFI_D_ERROR, "AT::AtGetIsvIdRsp response message length = %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtGetIsvIdRsp.CompletionCode = %x\n", AtGetIsvIdRsp.CompletionCode)); + DEBUG ((EFI_D_ERROR, "AtGetIsvIdRsp.IsvId = %x\n", AtGetIsvIdRsp.IsvId)); + + if (!AtGetIsvIdRsp.CompletionCode) { + *IsvId = AtGetIsvIdRsp.IsvId; + } + + return EFI_SUCCESS; + +} + +/** + This requests FW to enter or exit Suspend mode based on user input + + @param[in] This The address of protocol + @param[in] TransitionState 0: Exit Suspend Mode + 1: Enter Suspend Mode + @param[in] Token SSTK generated Token + + @retval EFI_SUCCESS The function completed successfully. + @retval EFI_OUT_OF_RESOURCES Unable to allocate necessary data structures. +**/ +EFI_STATUS +EFIAPI +SetSuspendState ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 TransitionState, + IN UINT8 *Token + ) +{ + UINT32 HeciLength; + EFI_STATUS Status; + EFI_HECI_PROTOCOL *Heci; + + ATHI_SET_SUSPEND_STATE_CMD *AtSetSuspendStateCmd; + ATHI_SET_SUSPEND_STATE_RSP AtSetSuspendStateRsp; + + AtSetSuspendStateCmd = AllocateZeroPool (sizeof (ATHI_SET_SUSPEND_STATE_CMD) + AT_USR_PASS_HASH_LENGTH_MAX); + if (AtSetSuspendStateCmd == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + ZeroMem ((VOID *) &AtSetSuspendStateRsp, sizeof (ATHI_SET_SUSPEND_STATE_RSP)); + + AtSetSuspendStateCmd->Header.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtSetSuspendStateCmd->Header.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtSetSuspendStateCmd->Header.Command.Category = ATHI_CMD_GROUP_GENERAL; + AtSetSuspendStateCmd->Header.Command.IsResponse = AT_COMMAND; + AtSetSuspendStateCmd->Header.Command.Code = ATHI_GENERAL_GRP_SET_SUSPEND_CMD; + AtSetSuspendStateCmd->TransitionState = TransitionState; + + // + // AT_CREDENTIAL has extra UINT8 (can't have zero length array like FW) that must be subtracted + // + AtSetSuspendStateCmd->Header.Length = (sizeof (ATHI_SET_SUSPEND_STATE_CMD) - sizeof (UINT8)) - (sizeof (ATHI_HEADER)) + AT_USR_PASS_HASH_LENGTH_MAX; + AtSetSuspendStateCmd->Credential.Type = AT_CREDENTIAL_TYPE_SSTK; + AtSetSuspendStateCmd->Credential.Length = AT_USR_PASS_HASH_LENGTH_MAX; + CopyMem (AtSetSuspendStateCmd->Credential.Value, Token, AT_USR_PASS_HASH_LENGTH_MAX); + + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &Heci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "SetSuspendState: Locating for HECI Driver Failed!, Status = %r\n", Status)); + FreePool (AtSetSuspendStateCmd); + return Status; + } + + HeciLength = sizeof (ATHI_SET_SUSPEND_STATE_CMD) - sizeof (UINT8) + AT_USR_PASS_HASH_LENGTH_MAX; + + Status = Heci->SendMsg ( + (UINT32 *) AtSetSuspendStateCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "SetSuspendState failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + FreePool (AtSetSuspendStateCmd); + return Status; + } + + FreePool (AtSetSuspendStateCmd); + + HeciLength = sizeof (ATHI_SET_SUSPEND_STATE_RSP); + Status = Heci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtSetSuspendStateRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "SetSuspendState failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + DEBUG ((EFI_D_ERROR, "AT::SetSuspendState response message length %x\n", HeciLength)); + DEBUG ((EFI_D_ERROR, "AtSetSuspendStateRsp.CompletionCode = %x\n", AtSetSuspendStateRsp.CompletionCode)); + + if (AtSetSuspendStateRsp.CompletionCode) { + return EFIERR (AtSetSuspendStateRsp.CompletionCode); + } + + return EFI_SUCCESS; +} + +/** + This instructs FW that a WWAN recovery is desired and thus the Radio needs to be initialized. + + This command in not supported. + + @param[in] This The address of protocol +**/ +EFI_STATUS +InitWWANREcov ( + IN EFI_AT_PROTOCOL *This + ) +{ + /// + /// This command in not supported. + /// + return EFI_UNSUPPORTED; +} + +/** + This queries FW of the NIC Radio Status + + This command in not supported. + + @param[in] This The address of protocol + @param[in] RadioStatus Radio status + @param[in] NetworkStatus Network status +**/ +EFI_STATUS +GetWWANNicStatus ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT8 *RadioStatus, + IN OUT UINT8 *NetworkStatus + ) +{ + /// + /// This command in not supported. + /// + return EFI_UNSUPPORTED; +} + +/** + This queries FW of the AT Status in Unsigned mode + + @param[in] This The address of protocol + @param[out] StateUnsigned Structure retrieved from ME describing current AT state + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +GetStateUnsigned ( + IN EFI_AT_PROTOCOL *This, + OUT AT_STATE_INFO *StateUnsigned + ) +{ + UINT32 HeciLength; + EFI_STATUS Status; + + ATHI_GET_STATE_CMD AtGetStateCmd; + ATHI_GET_STATE_RSP AtGetStateRsp; + + ZeroMem ((VOID *) &AtGetStateCmd, sizeof (ATHI_GET_STATE_CMD)); + ZeroMem ((VOID *) &AtGetStateRsp, sizeof (ATHI_GET_STATE_RSP)); + + AtGetStateCmd.Version.Major = ATHI_PROTOCOL_VERSION_MAJOR; + AtGetStateCmd.Version.Minor = ATHI_PROTOCOL_VERSION_MINOR; + AtGetStateCmd.Command.Code = ATHI_THEFT_DETECT_GRP_GET_STATE_UNSIGNED; + AtGetStateCmd.Command.Category = ATHI_CMD_GROUP_THEFT_DETECTION; + AtGetStateCmd.Command.IsResponse = AT_COMMAND; + AtGetStateCmd.Length = sizeof (ATHI_GET_STATE_CMD) - sizeof (ATHI_HEADER); + + if (mHeci == NULL) { + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &mHeci + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetStateUnsigned: Locating HECI Protocol failed!, Status = %r\n", Status)); + return Status; + } + } + + HeciLength = sizeof (ATHI_GET_STATE_CMD); + + Status = mHeci->SendMsg ( + (UINT32 *) &AtGetStateCmd, + HeciLength, + BIOS_FIXED_HOST_ADDR, + HECI_AT_MESSAGE_ADDR + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetStateUnsigned failed to send message over HECI!(SendMsg), Status = %r\n", Status)); + return Status; + } + + HeciLength = sizeof (ATHI_GET_STATE_RSP); + Status = mHeci->ReadMsg ( + BLOCKING, + (UINT32 *) &AtGetStateRsp, + &HeciLength + ); + + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "AtGetStateUnsigned failed to receive message over HECI!(ReadMsg), Status = %r\n", Status)); + return Status; + } + + if (AtGetStateRsp.CompletionCode == ATHI_COMPCODE_SUCCESS) { + DEBUG ((EFI_D_ERROR, "AtGetStateRsp.CompletionCode = %x\n", AtGetStateRsp.CompletionCode)); + CopyMem (StateUnsigned, &(AtGetStateRsp.StateInfo), sizeof (AT_STATE_INFO)); + } + + return EFI_SUCCESS; +} diff --git a/ReferenceCode/ME/At/AtAm/Dxe/At.h b/ReferenceCode/ME/At/AtAm/Dxe/At.h new file mode 100644 index 0000000..cc19c9d --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/At.h @@ -0,0 +1,280 @@ +/** @file + Defines and prototypes for the AT driver. + This driver implements the AT protocol. + +@copyright + Copyright (c) 2004 - 2012 Intel Corporation. All rights + reserved This software and associated documentation (if any) + is furnished under a license and may only be used or copied in + accordance with the terms of the license. Except as permitted + by such license, no part of this software or documentation may + be reproduced, stored in a retrieval system, or transmitted in + any form or by any means without the express written consent + of Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement + +**/ +#ifndef _AT_H_ +#define _AT_H_ +#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000) +#include "EdkIIGlueDxe.h" +#include "AtHi.h" +#include "MeLib.h" +#include "AtAmHelper.h" +#endif + +// +// Used during initialization +// +#include EFI_PROTOCOL_CONSUMER (FirmwareVolume) +#include EFI_PROTOCOL_CONSUMER (HECI) + +// +// Driver Produced Protocols +// +#include EFI_PROTOCOL_PRODUCER (At) + +// +// extern EFI_GUID gDxePlatformAtGuid; +// +#define AT_PRIVATE_DATA_SIGNATURE EFI_SIGNATURE_32 ('A', 'T', 'D', 'R') + +#pragma pack(1) +/// +/// MKHI host message header. This header is part of HECI message sent from MEBx via +/// Host Configuration Interface (HCI). ME Configuration Manager or Power Configuration +/// Manager also include this header with appropriate fields set as part of the +/// response message to the HCI. +/// +typedef struct { + UINTN Signature; + EFI_HANDLE Handle; + EFI_AT_PROTOCOL AtProtocol; + +} AT_INSTANCE; + +#define AT_INSTANCE_FROM_AT_PROTOCOL(a) CR (a, AT_INSTANCE, At, AT_PRIVATE_DATA_SIGNATURE) + +#pragma pack() + +/** + Entry point for the AT Driver. + + @param[in] ImageHandle Image handle of this driver. + @param[in] SystemTable Global system service table. + + @retval EFI_SUCCESS Initialization complete. + @exception EFI_UNSUPPORTED The chipset is unsupported by this driver. + @retval EFI_OUT_OF_RESOURCES Do not have enough resources to initialize the driver. + @retval EFI_DEVICE_ERROR Device error, driver exits abnormally. +**/ +EFI_STATUS +EFIAPI +AtEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +; + +/** + This function sends a request to ME AT Services to validate AT + recovery credentials. The user input is captured in UTF-16 + format and then passed to this funtion. This function converts + the User recovery password into a HASH by using Salt & Nonce + and then send the password HASH to ME AT Services for + validation. ME AT Service compares the Password HASH and + returns either pass or fail. + + @param[in] This The address of protocol + @param[in] PassPhrase Passphrase that needs to be authenticated sent to ME + @param[in] PassType Password type user or server generated + @param[in][out] IsAuthenticated The return of the password match 1 for success and 0 for fail + + @retval EFI_OUT_OF_RESOURCES Unable to allocate necessary data structures + @retval EFI_SUCCESS The function completed successfully +**/ +EFI_STATUS +EFIAPI +AuthenticateCredential ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PassPhrase, + IN UINT32 *PassType, + IN OUT UINT8 *IsAuthenticated + ) +; + +/** + This API compute the SHA1 hash of the user enterted password + + @param[in] This The address of protocol + @param[in] PassPhrase The passphrase for which SHA1 hash to be computed + @param[in][out] Hash The return value of the SHA1 hash + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +ComputeHash ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PassPhrase, + IN OUT UINT8 *Hash + ) +; + +/** + This API get the AT Unlock Timer values + + @param[in] This The address of protocol + @param[in] Interval The return value of the Unlock Time Interval that was set by AT Server + @param[in] TimeLeft The Timeleft in the Unlock Timer + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetTimerInfo ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT32 *Interval, + IN OUT UINT32 *TimeLeft + ) +; + +/** + This gets the ME nonce + @param[in] This The address of protocol + @param[in][out] Nonce The return value of the 16 Byte nonce received from ME + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetNonce ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT8 *Nonce + ) +; + +/** + This retrives the ISV String stored by AT Server that BIOS will display during Platform lock state + + @param[in] This The address of protocol + @param[in] StringId The String buffer ID to retrive the ISV String + @param[out] IsvString 256 Bytes of ISV string array, the + @param[out] IsvStringLength The String length + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetRecoveryString ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 *StringId, + OUT UINT8 *IsvString, + OUT UINT32 *IsvStringLength + ) +; + +/** + This send an AssertStolen Message to ME when OEM has set the AllowAssertStolen bit to be accepted by BIOS. + + @param[in] This The address of protocol + @param[out] CompletionCode The return ME Firmware return code for this request + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +SendAssertStolen ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *CompletionCode + ) +; + +/** + This receives the ISV ID from ME and display the ID, when the platform is in stolen state + + @param[in] This The address of protocol + @param[out] IsvId The pointer to 4 byte ISV ID + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +EFIAPI +GetIsvId ( + IN EFI_AT_PROTOCOL *This, + OUT UINT32 *IsvId + ) +; + +/** + This requests FW to enter or exit Suspend mode based on user input + + @param[in] This The address of protocol + @param[in] TransitionState 0: Exit Suspend Mode + 1: Enter Suspend Mode + @param[in] Token SRTK generated Token + + @retval EFI_SUCCESS The function completed successfully. + @retval EFI_OUT_OF_RESOURCES Unable to allocate necessary data structures. +**/ +EFI_STATUS +EFIAPI +SetSuspendState ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 TransitionState, + IN UINT8 *Token + ) +; + +/** + This instructs FW that a WWAN recovery is desired and thus the Radio needs to be initialized. + + This command in not supported. + + @param[in] This The address of protocol +**/ +EFI_STATUS +InitWWANREcov ( + IN EFI_AT_PROTOCOL *This + ) +; + +/** + This queries FW of the NIC Radio Status + + This command in not supported. + + @param[in] This The address of protocol + @param[in] RadioStatus Radio status + @param[in] NetworkStatus Network status +**/ +EFI_STATUS +GetWWANNicStatus ( + IN EFI_AT_PROTOCOL *This, + IN OUT UINT8 *RadioStatus, + IN OUT UINT8 *NetworkStatus + ) +; + +/** + This queries FW of the AT Status in Unsigned mode + + @param[in] This The address of protocol + @param[out] StateUnsigned Structure retrieved from ME describing current AT state + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +GetStateUnsigned ( + IN EFI_AT_PROTOCOL *This, + OUT AT_STATE_INFO *StateUnsigned + ) +; + +#endif diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAm.c b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.c new file mode 100644 index 0000000..4be107f --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.c @@ -0,0 +1,694 @@ +/** @file + This file contines routines responsible for hangling AT and provide interface for creating UI. + +@copyright + Copyright (c) 2013 Intel Corporation. All rights + reserved This software and associated documentation (if any) + is furnished under a license and may only be used or copied in + accordance with the terms of the license. Except as permitted + by such license, no part of this software or documentation may + be reproduced, stored in a retrieval system, or transmitted in + any form or by any means without the express written consent + of Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement + +**/ +#include "AtAm.h" + +DXE_AT_POLICY_PROTOCOL *mDxePlatformAtPolicy; +static AT_BIOS_RECOVERY_CONFIG gBiosRecoveryGlobalVar; +static AT_STATE_INFO gAtStateGlobalVar; +static UINT16 gRecoveryAMGlobalVar; +static BOOLEAN gAtAmPrefUpdatedToATAM = FALSE; + +EFI_GUID gEfiPBAVariableGuid = PBA_FAILED_COUNT_VARIABLE_GUID; +EFI_GUID gEfiAtAmProtocolGuid = EFI_ATAM_PROTOCOL_GUID; + +extern AT_INSTANCE mAtInstance; + +ATAM_INSTANCE AtAmInstance = { + ATAM_PRIVATE_DATA_SIGNATURE, + NULL, + { + (UINT8) ATAM_PROTOCOL_REVISION, + (EFI_ATAM_GET_ISV_ID) AtAmGetIsvId, + (EFI_ATAM_GET_RECOVERY_CONFIG) AtAmGetRecoveryConfig, + (EFI_ATAM_GET_TIMER) AtAmGetTimer, + (EFI_ATAM_GET_NONCE) AtAmGetNonce, + (EFI_ATAM_VERIFY_PASSWORD) AtAmVerifyPassword, + (EFI_ATAM_SET_SUSPEND_STATE) AtAmSetSuspendState, + (EFI_ATAM_GET_AT_STATE_INFO) AtAmGetAtStateInfo, + (EFI_ATAM_GET_PBA_COUNTER) AtAmGetPbaCounter + } +}; + +/** + Driver entry point. + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + UINT32 MeStatus; + EFI_HECI_PROTOCOL *Heci; + UINT8 AtState; + UINT16 AtAmPref; + DXE_MBP_DATA_PROTOCOL *MbpData; + + + MeStatus = 0; + AtState = 0; + AtAmPref = 0; + + /// + ///Install AT protocol + /// + Status = AtEntryPoint(0, 0); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: AT Protocol isn't installed, Status = %r\n", Status)); + return Status; + } + + Status = gBS->LocateProtocol ( + &gDxePlatformAtPolicyGuid, + NULL, + (VOID **) &mDxePlatformAtPolicy + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: No AT Platform Policy Protocol available")); + return Status; + } + ASSERT_EFI_ERROR (Status); + +#ifdef EFI_DEBUG + /// + /// Dump the AT platform policy + /// + DxeAtPolicyDebugDump (); +#endif + + Status = gBS->LocateProtocol ( + &gEfiHeciProtocolGuid, + NULL, + (VOID **) &Heci + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: failed to locate HECI driver, Status = %r\n", Status)); + return Status; + } + + Status = Heci->GetMeStatus (&MeStatus); + ASSERT_EFI_ERROR (Status); + + if (mDxePlatformAtPolicy->At.AtAmBypass == 0) { + + /// + /// Check if ME is Normal State or Recovery Mode + /// + if (ME_STATUS_ME_STATE_ONLY (MeStatus) == ME_READY || + ME_STATUS_ME_STATE_ONLY (MeStatus) == ME_IN_RECOVERY_MODE || + ME_STATUS_ME_STATE_ONLY (MeStatus) == ME_FW_UPDATES_IN_PROGRESS) { + /// + /// Get the MBP Data. + /// + Status = gBS->LocateProtocol (&gMeBiosPayloadDataProtocolGuid, NULL, (VOID **) &MbpData); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: No MBP Data Protocol available - Exit Early")); + return EFI_SUCCESS; + } + + if (!MbpData->MeBiosPayload.FwCapsSku.FwCapabilities.Fields.IntelAT) { + DEBUG ((EFI_D_INFO, "ATAM: Exit Early - MEFWCAPS_SKU_RULE_ID indicates AT does not exist")); + return EFI_SUCCESS; + } else { + DEBUG ((EFI_D_INFO, "ATAM: ME FW SKU Info Variables indicates that AT exists")); + } + + DEBUG ((EFI_D_INFO, "ATAM::GetMeStatus is ME_READY\n", Status)); + + Status = GetAtStateInfo ( + &gAtStateGlobalVar + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM::GetAtStateInfo failed, Status = %r\n", Status)); + return Status; + } + + /// + /// Update Static Variable + /// + gRecoveryAMGlobalVar = gAtStateGlobalVar.flags.AuthenticateModule; + + DEBUG ((EFI_D_INFO, "ATAM: MeAtRuleDate AtState = %x\n", gAtStateGlobalVar.State)); + DEBUG ((EFI_D_INFO, "ATAM: MeAtRuleDate AtAmPref = %x\n", gAtStateGlobalVar.flags.AuthenticateModule)); + + /// + /// Check for PBA_ERROR_THRESHOLDS Level .... i.e. if PBA fails for x number of times then BIOS AM will + /// Ignore the PREFERRED_AM Selection + /// + AtAmPref = gAtStateGlobalVar.flags.AuthenticateModule; + AtState = gAtStateGlobalVar.State; + + Status = AtAmValidatePreferredAM (&AtState, &AtAmPref); + DEBUG ((EFI_D_INFO, "ATAM: ValidatePreferredAM, AtAmPref = %d\n", AtAmPref)); + + /// + /// Ignore the PREFERRED_AM Selection + /// + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_INFO, "ATAM: ValidatePreferredAM failed, Status = %r\n", Status)); + } + } else { + DEBUG ((EFI_D_INFO, "ATAM: ME_READY Failed\n")); + Status = EFI_DEVICE_ERROR; + } + } else { + DEBUG ((EFI_D_INFO, "ATAM: AT Disabled in the BIOS\n")); + + Status = GetAtStateInfo ( + &gAtStateGlobalVar + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM::GetAtStateInfo failed, Status = %r\n", Status)); + return Status; + } + } + + Status = gBS->InstallMultipleProtocolInterfaces ( + &(AtAmInstance.Handle), + &gEfiAtAmProtocolGuid, + &(AtAmInstance.AtAmProtocol), + NULL + ); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: ATAM Protocol NOT Installed, Status = %r\n", Status)); + } else { + DEBUG ((EFI_D_ERROR, "ATAM: ATAM Protocol Installed, Status = %r\n", Status)); + } + + return Status; +} + +/** + This function gets the ISV Strings stored by AT Server that BIOS will display. + + @param[in] This The address of protocol + @param[out] IsvString Isv string pointer + @param[out] IsvId Intel(R) Anti-Theft service provider Id + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmGetIsvId ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *IsvString, + OUT UINT32 *IsvId + ) +{ + EFI_STATUS Status; + UINT32 StringLength; + UINT32 StringId; + + StringLength = 0; + + Status = mAtInstance.AtProtocol.GetIsvId (&mAtInstance.AtProtocol, IsvId); + if (EFI_ERROR (Status)) { + /// + /// Let it continue even if the error .... + /// + DEBUG ((EFI_D_ERROR, "ATAM: GetIsvId failed, Status = %r\n", Status)); + } else { + DEBUG ((EFI_D_ERROR, "ATAM: GetIsvId IsvId = %r\n", *IsvId)); + } + + StringId = AT_VENDOR_STRING_ID_RECOVERY_HELP; + Status = mAtInstance.AtProtocol.GetRecoveryString (&mAtInstance.AtProtocol, &StringId, IsvString, &StringLength); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: GetRecoveryString AT_VENDOR_STRING_ID_RECOVERY_HELP failed, Status = %r\n", Status)); + /// + /// Let it continue even if the error + /// + } + + return Status; +} + +/** + This function returns time left to enter password. + + @param[in] This The address of protocol + @param[out] TimeLeft Time + @param[out] TimeInterval Time interval + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetTimer ( + IN EFI_AT_PROTOCOL *This, + OUT UINT32 *TimeLeft, + OUT UINT32 *TimeInterval + ) +{ + EFI_STATUS Status; + + Status = mAtInstance.AtProtocol.GetTimerInfo (&mAtInstance.AtProtocol, TimeInterval, TimeLeft); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: GetTimerInfo failed, Status = %r\n", Status)); + } + + return Status; +} + +/** + This function gets 16 bytes nonce from firmware and also converts it to string according to format "XXXX-XXXX-XXXX-XXXX-XXXX-XXXX-XX". + + @param[in] This The address of protocol + @param[out] NonceStr Pointer to Nonce string + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetNonce ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *NonceStr + ) +{ + EFI_STATUS Status; + UINTN StrNonceLength; + UINT8 Nonce[NONCE_LENGTH]; + CHAR16 *UniCodeNonceStr; + + StrNonceLength = STR_NONCE_LENGTH; + + UniCodeNonceStr = AllocateZeroPool ((STR_NONCE_LENGTH + 1) * sizeof (CHAR16)); + if (UniCodeNonceStr == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + Status = mAtInstance.AtProtocol.GetNonce (&mAtInstance.AtProtocol, Nonce); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: GetSuspendAuthentication::GetNonce failed, Status = %r\n", Status)); + return Status; + } + + Base32Encode (NonceStr, &StrNonceLength, Nonce, NONCE_LENGTH); + Uint8ToUnicode ((CHAR8 *) NonceStr, UniCodeNonceStr); + + FreePool (UniCodeNonceStr); + + return Status; +} + +/** + This function gets recovery config. + + @param[in] This The address of protocol + @param[out] RecoveryConfig Pointer to structure + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmGetRecoveryConfig ( + IN EFI_AT_PROTOCOL *This, + OUT AT_BIOS_RECOVERY_CONFIG *RecoveryConfig + ) +{ + EFI_STATUS Status; + UINT32 StringId; + UINT32 StringLength; + + StringLength = 0; + + StringId = AT_CUSTOM_RECOVERY_ID_CONFIGURATIONS; + Status = mAtInstance.AtProtocol.GetRecoveryString (&mAtInstance.AtProtocol, &StringId, (UINT8 *) RecoveryConfig, &StringLength); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: GetRecoveryString failed, Status = %r\n", Status)); + /// + /// Let it continue even if the error + /// + } else { + DEBUG ((EFI_D_ERROR, "ATAM: GetRecoveryString StringLength = %d\n", StringLength)); + DEBUG ((EFI_D_ERROR, "ATAM: GetRecoveryString *IsvString = %d\n", *RecoveryConfig)); + DEBUG ((EFI_D_ERROR, "ATAM: GetRecoveryString StringId = %d\n", StringId)); + } + + return Status; +} + +/** + This routine receives the data (passphrase or SRTK) from UI and verifies it if the password (either passphrase or SRTK) is acceptable. + + @param[in] This The address of protocol + @param[in] PasswordEntered Pointer to string + @param[in] PassType Password type + @param[out] IsAuthenticated Pointer to result of verification + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmVerifyPassword ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PasswordEntered, + IN UINT32 PassType, + OUT UINT8 *IsAuthenticated + ) +{ + EFI_STATUS Status; + UINT8 *Hash; + UINT8 *PasswordHex; + UINT8 AtState; + UINT16 AtAmPref; + UINT8 IsAuthTmp = 0; + + Status = EFI_SUCCESS; + + PasswordHex = AllocateZeroPool ((ATAM_SETUP_PASSWORD_LENGTH + 1) * sizeof (UINT8)); + Hash = AllocateZeroPool ((ATAM_SETUP_PASSWORD_LENGTH + 1) * sizeof (UINT8)); + if (Hash == NULL || PasswordHex == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + if (PassType == AT_CREDENTIAL_TYPE_USER_PASSPHRASE) { + + Status = mAtInstance.AtProtocol.ComputeHash (&mAtInstance.AtProtocol, PasswordEntered, Hash); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: ComputeHash failed, Status = %r\n", Status)); + } + + Status = mAtInstance.AtProtocol.AuthenticateCredential (&mAtInstance.AtProtocol, Hash, &PassType, &IsAuthTmp); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: AuthenticateCredential, Status = %r\n", Status)); + } + + } else if (PassType == AT_CREDENTIAL_TYPE_SRTK) { + /// + /// User selected Base32 based Server based recovery, for BASE32 the length is always 32 + /// + if (AsciiStrLen((CHAR8 *) PasswordEntered) == 32) { + DEBUG ((EFI_D_ERROR, "ATAM: Password entered is SRTK BASE32 PASSWORD\n")); + /// + /// Decoded value is 20 byte hex + /// + Base32Decode (PasswordEntered, PasswordHex); + } else if (AsciiStrLen((CHAR8 *) PasswordEntered) > 40) { + /// + /// User selected Basee10 based Server based recovery, for BASE10 the length is always more than 40 + /// + DEBUG ((EFI_D_ERROR, "ATAM: Password entered is SRTK BASE10 PASSWORD\n")); + /// + /// Decoded value is 20 byte hex + /// + DecimalToHexString ((CHAR8 *) PasswordEntered, PasswordHex, MAX_HEX_BYTES - 1); + } + + Status = mAtInstance.AtProtocol.AuthenticateCredential (&mAtInstance.AtProtocol, PasswordHex, &PassType, &IsAuthTmp); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: AuthenticateCredential, Status = %r\n", Status)); + } + } else { + DEBUG ((EFI_D_ERROR, "ATAM: Unknown Pass type \n")); + } + + /// + /// Calling ValidatePreferredAM to reset the PbafailedCount + /// + if (gAtStateGlobalVar.flags.AuthenticateModule == AT_AM_SELECTION_PBAM && IsAuthTmp == 1) { + AtState = AT_STATE_ACTIVE; + AtAmPref = AT_AM_SELECTION_PBAM; + Status = AtAmValidatePreferredAM (&AtState, &AtAmPref); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: AtAmValidatePreferredAM failed, Status = %r\n", Status)); + } + } + + *IsAuthenticated = IsAuthTmp; + + ZeroMem (Hash, (ATAM_SETUP_PASSWORD_LENGTH + 1) * sizeof (UINT8)); + ZeroMem (PasswordHex, (ATAM_SETUP_PASSWORD_LENGTH + 1) * sizeof (UINT8)); + FreePool (Hash); + FreePool (PasswordHex); + + return Status; +} + +/** + This routine receives the SSTK from UI and verifies it if the password is acceptable. This requests FW to enter or exit Suspend mode based on user input. + + @param[in] This The address of protocol + @param[in] TransitionState 1- enter suspend state, 0 - exit suspend state + @param[in] Token Pointer to token + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmSetSuspendState ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 TransitionState, + IN UINT8 *Token + ) +{ + EFI_STATUS Status; + UINT8 TokenHex[ATAM_SETUP_PASSWORD_LENGTH]; + + DEBUG ((EFI_D_ERROR, "ATAM: SetSuspendState: Transition state = %x\n", TransitionState)); + + if(AsciiStrLen((CHAR8 *)Token) == 32) { + DEBUG ((EFI_D_ERROR, "ATAM: Suspend Password entered is in Base32\n")); + Base32Decode(Token, TokenHex); + } else if(AsciiStrLen((CHAR8 *)Token) > 40) { + DEBUG ((EFI_D_ERROR, "ATAM: Password entered is in Base10\n")); + DecimalToHexString((CHAR8 *) Token,TokenHex, MAX_HEX_BYTES - 1); + } else { + return EFI_INVALID_PARAMETER; + } + + DEBUG ((EFI_D_ERROR, "ATAM: SrtkPass = %x\n", TokenHex)); + + Status = mAtInstance.AtProtocol.SetSuspendState (&mAtInstance.AtProtocol, TransitionState, TokenHex); + if (EFI_ERROR (Status)) { + DEBUG ((EFI_D_ERROR, "ATAM: SetSuspendState failed, Status = %r\n", Status)); + } else { + DEBUG ((EFI_D_ERROR, "ATAM: Successfully set suspended state\n")); + } + + return Status; +} + +/** + This routine gets AT state. + + @param[in] This The address of protocol + @param[out] AtStateInfo State of AT + + @retval EFI_SUCCESS The function completed successfully +**/ +EFI_STATUS +AtAmGetAtStateInfo ( + IN EFI_AT_PROTOCOL *This, + OUT AT_STATE_INFO *AtStateInfo + ) +{ + + AtStateInfo->State = gAtStateGlobalVar.State; + AtStateInfo->LastTheftTrigger = gAtStateGlobalVar.LastTheftTrigger; + AtStateInfo->flags.LockState = gAtStateGlobalVar.flags.LockState; + AtStateInfo->flags.AuthenticateModule = gAtStateGlobalVar.flags.AuthenticateModule; + AtStateInfo->flags.S3Authentication = gAtStateGlobalVar.flags.S3Authentication; + AtStateInfo->flags.FlashVariableSecurity = gAtStateGlobalVar.flags.FlashVariableSecurity; + AtStateInfo->flags.FlashWearOut = gAtStateGlobalVar.flags.FlashWearOut; + if (gAtAmPrefUpdatedToATAM == TRUE) { + AtStateInfo->flags.AuthenticateModule = AT_AM_SELECTION_ATAM; + } + + return EFI_SUCCESS; +} + +/** + Validate preffered AM. + + @param[in] AtState State of AT + @param[in] AtAmPref Preferred AT authentication method + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmValidatePreferredAM ( + IN UINT8 *AtState, + IN UINT16 *AtAmPref + ) +{ + EFI_STATUS Status; + UINTN VarSize; + UINT8 PbaFailedCount; + UINT32 Attributes; + AT_BIOS_RECOVERY_CONFIG RecoveryConfig; + + VarSize = sizeof (UINT8); + + if (*AtAmPref == AT_AM_SELECTION_ATAM) { + return EFI_SUCCESS; + } + + if (*AtState == AT_STATE_ACTIVE) { + + Attributes = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS; + Status = gRT->GetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + &Attributes, + &VarSize, + &PbaFailedCount + ); + if (EFI_ERROR (Status) && Status != EFI_NOT_FOUND) { + DEBUG ((EFI_D_ERROR, "ATAM: ValidatePreferredAM failed, Status = %r\n", Status)); + return Status; + } + + if (Status == EFI_NOT_FOUND || PbaFailedCount > 0) { + + DEBUG ((EFI_D_INFO, "ATAM: ValidatePreferredAM In State Active PbaFailedCount not yet defined\n")); + /// + /// This will be the case 1st time after enrollment when PbaFailedCount i.e PREFERRED_AM is not defined + /// Define this variable here + /// + PbaFailedCount = 0; + Status = gRT->SetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS, + sizeof (UINT8), + &PbaFailedCount + ); + } + } + /// + /// Now get NVRAM Varible that store the PBA_Preferred_Failed count .. i.e. STOLEN_STATE which + /// which is incremented every boot + /// + if (*AtState == AT_STATE_STOLEN && *AtAmPref == AT_AM_SELECTION_PBAM) { + + AtAmGetRecoveryConfig (NULL, &RecoveryConfig); + + VarSize = sizeof (UINT8); + Attributes = EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS; + Status = gRT->GetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + &Attributes, + &VarSize, + &PbaFailedCount + ); + if (EFI_ERROR (Status) && Status != EFI_NOT_FOUND) { + DEBUG ((EFI_D_ERROR, "ATAM: ValidatePreferredAM failed, Status = %r\n", Status)); + return Status; + } + + if (Status == EFI_NOT_FOUND) { + DEBUG ((EFI_D_ERROR, "ATAM: ValidatePreferredAM In State Stolen PbaFailedCount not yet defined\n")); + + /// + /// This will be the case 1st time after enrollment when PbaFailedCount i.e PREFERRED_AM is not defined and + /// AT somehow got into stolen mode + /// Define this variable here + /// + PbaFailedCount = 0; + Status = gRT->SetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS, + sizeof (UINT8), + &PbaFailedCount + ); + } else if (PbaFailedCount > 0 && PbaFailedCount >= (UINT8) RecoveryConfig.PbaOverRideThreshold) { + /// + /// Set the PREFERRED_AM to BIOS AM here + /// + *AtAmPref = AT_AM_SELECTION_ATAM; + gAtAmPrefUpdatedToATAM = TRUE; + DEBUG ((EFI_D_ERROR, "ATAM: ValidatePreferredAM PbaFailedCount = %d\n", PbaFailedCount)); + } + /// + /// Increment the PbaFailedCount count here + /// + PbaFailedCount = PbaFailedCount + 1; + Status = gRT->SetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS, + sizeof (UINT8), + &PbaFailedCount + ); + + DEBUG((EFI_D_INFO, "ATAM: ValidatePreferredAM PbaFailedCount incremented here:%d\n", PbaFailedCount)); + DEBUG((EFI_D_INFO, "ATAM: ValidatePreferredAM gBiosRecoveryGlobalVar.PbaOverRideThreshold:%d\n", + RecoveryConfig.PbaOverRideThreshold)); + + } + + return EFI_SUCCESS; +} + +/** + This routine checks if the PbaOverrideThreshold is exceeded. + + @param[out] PbaFailedExceeded TRUE when the PbaOverrideThreshold is exceeded + @param[out] PbaFailedAttempts Number of failed attempts + @param[out] PbaFailedThreshold Pba failed count treshold + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetPbaCounter ( + OUT UINT8* PbaFailedExceeded, + OUT UINT16* PbaFailedAttempts, + OUT UINT16* PbaFailedThreshold + ) +{ + EFI_STATUS Status; + UINTN VarSize; + UINT32 Attributes; + UINT8 PbaCount; + AT_BIOS_RECOVERY_CONFIG RecoveryConfig; + + DEBUG ((EFI_D_ERROR, "ATAM: AtAmGetPbaCounter\n")); + + *PbaFailedExceeded = FALSE; + VarSize = sizeof (UINT8); + + AtAmGetRecoveryConfig (NULL, &RecoveryConfig); + + Status = gRT->GetVariable ( + L"PBA_FAILED_COUNT", + &gEfiPBAVariableGuid, + &Attributes, + &VarSize, + &PbaCount + ); + + DEBUG ((EFI_D_ERROR, "ATAM: PbaCount = %d\n", PbaCount)); + DEBUG ((EFI_D_ERROR, "ATAM: PbaOverRideThreshold = %d\n", RecoveryConfig.PbaOverRideThreshold)); + + *PbaFailedAttempts = PbaCount; + *PbaFailedThreshold = RecoveryConfig.PbaOverRideThreshold; + + if (PbaCount >= (UINT8) RecoveryConfig.PbaOverRideThreshold) { + *PbaFailedExceeded = TRUE; + } + + return Status; +} diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAm.dxs b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.dxs new file mode 100644 index 0000000..5aac1dc --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.dxs @@ -0,0 +1,41 @@ +/** @file + Dependency expression file for ATAM Invocation Driver. + +@copyright + Copyright (c) 2012 Intel Corporation. All rights reserved + This software and associated documentation (if any) is furnished + under a license and may only be used or copied in accordance + with the terms of the license. Except as permitted by such + license, no part of this software or documentation may be + reproduced, stored in a retrieval system, or transmitted in any + form or by any means without the express written consent of + Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement + +**/ + + +#include "AutoGen.h" +#include "DxeDepex.h" + +#if defined (BUILD_WITH_GLUELIB) || defined (BUILD_WITH_EDKII_GLUE_LIB) +#include "EfiDepex.h" +#include EFI_PROTOCOL_DEFINITION (LegacyBios) +#include EFI_PROTOCOL_DEFINITION (BootScriptSave) +#include EFI_PROTOCOL_DEFINITION (At) +#include EFI_PROTOCOL_DEFINITION (Heci) +#include EFI_PROTOCOL_DEPENDENCY (MeBiosPayloadData) +#include EFI_PROTOCOL_DEFINITION (AtPlatformPolicy) +#endif + +DEPENDENCY_START + DXE_PLATFORM_AT_POLICY_GUID AND + EFI_HECI_PROTOCOL_GUID AND + ME_BIOS_PAYLOAD_DATA_PROTOCOL_GUID +DEPENDENCY_END diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAm.h b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.h new file mode 100644 index 0000000..ece69d8 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.h @@ -0,0 +1,239 @@ +/** @file + Header file for hangling AT and provide interface for creating UI. + +@copyright + Copyright (c) 2012 - 2013 Intel Corporation. All rights + reserved This software and associated documentation (if any) + is furnished under a license and may only be used or copied in + accordance with the terms of the license. Except as permitted + by such license, no part of this software or documentation may + be reproduced, stored in a retrieval system, or transmitted in + any form or by any means without the express written consent + of Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement +**/ + +#ifndef _ATAM_H_ +#define _ATAM_H_ + +#if !defined(EDK_RELEASE_VERSION) || (EDK_RELEASE_VERSION < 0x00020000) +#include "EdkIIGlueDxe.h" +#include "AtHi.h" +#include "MeLib.h" +#include "AtAmHelper.h" +#include "AtPolicyLib.h" +#include "At.h" +#endif + +// +// Used during initialization +// +#include EFI_PROTOCOL_CONSUMER (FirmwareVolume) +#include EFI_PROTOCOL_CONSUMER (HECI) +#include EFI_PROTOCOL_CONSUMER (At) +#include EFI_PROTOCOL_CONSUMER (AtPlatformPolicy) + +// +// Driver Produced Protocols +// +#include EFI_PROTOCOL_PRODUCER (AtAm) + +#define ATAM_PRIVATE_DATA_SIGNATURE EFI_SIGNATURE_32 ('A', 'T', 'A', 'M') + +#define MAX_HEX_BYTES 20 +#define ATAM_ENTER_SUSPEND_STATE 1 +#define ATAM_EXIT_SUSPEND_STATE 0 + +#define PBA_FAILED_COUNT_VARIABLE_GUID \ + { \ + 0x7c66ffdc, 0x423c, 0xe5d4, 0x25, 0x1b, 0x55, 0xad, 0xba, 0x95, 0x26, 0x98 \ + } + +#pragma pack(1) + +typedef struct { + UINTN Signature; + EFI_HANDLE Handle; + EFI_ATAM_PROTOCOL AtAmProtocol; +} ATAM_INSTANCE; + +#define ATAM_INSTANCE_FROM_ATAM_PROTOCOL(a) CR (a, ATAM_INSTANCE, AtAm, ATAM_PRIVATE_DATA_SIGNATURE) + +#pragma pack() + +#define NONCE_LENGTH 16 +#define STR_NONCE_LENGTH 33 +#define ATAM_SETUP_PASSWORD_LENGTH 49 +#define ATAM_TIMER_STRING_LENGTH 10 +#define ISV_PLATFORM_ID_LENGTH 16 +#define SERVER_SHORTCODE_LENGTH 16 +#define DEFAULT_LANGUAGE_STRING 4 +#define RECOVERY_STRING_LENGTH 256 +#define MX_SMS_MESSAGES 99 + +typedef enum _AT_AM_SELECTION +{ + AT_AM_SELECTION_ATAM = 0, + AT_AM_SELECTION_PBAM, + AT_AM_SELECTION_MAX +} AT_AM_SELECTION; + +/** + This function gets the ISV Strings stored by AT Server that BIOS will display. + + @param[in] This The address of protocol + @param[out] IsvString Isv string pointer + @param[out] IsvId Intel(R) Anti-Theft service provider Id + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmGetIsvId ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *IsvString, + OUT UINT32 *IsvId + ) +; + +/** + This function returns time left to enter password. + + @param[in] This The address of protocol + @param[out] TimeLeft Time + @param[out] TimeInterval Time interval + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetTimer ( + IN EFI_AT_PROTOCOL *This, + OUT UINT32 *TimeLeft, + OUT UINT32 *TimeInterval + ) +; + +/** + This function gets 16 bytes nonce from firmware and also converts it to string according to format "XXXX-XXXX-XXXX-XXXX-XXXX-XXXX-XX". + + @param[in] This The address of protocol + @param[out] NonceStr Pointer to Nonce string + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetNonce ( + IN EFI_AT_PROTOCOL *This, + OUT UINT8 *NonceStr + ) +; + +/** + This function gets recovery config. + + @param[in] This The address of protocol + @param[out] RecoveryConfig Pointer to structure + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmGetRecoveryConfig ( + IN EFI_AT_PROTOCOL *This, + OUT AT_BIOS_RECOVERY_CONFIG *RecoveryConfig + ) +; + +/** + This routine receives the data (passphrase or SRTK) from UI and verifies it if the password (either passphrase or SRTK) is acceptable. + + @param[in] This The address of protocol + @param[in] PasswordEntered Pointer to string + @param[in] PassType Password type + @param[out] IsAuthenticated Pointer to result of verification + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmVerifyPassword ( + IN EFI_AT_PROTOCOL *This, + IN UINT8 *PasswordEntered, + IN UINT32 PassType, + OUT UINT8 *IsAuthenticated + ) +; + +/** + This routine receives the SSTK from UI and verifies it if the password is acceptable. This requests FW to enter or exit Suspend mode based on user input. + + @param[in] This The address of protocol + @param[in] TransitionState 1- enter suspend state, 0 - exit suspend state + @param[in] Token Pointer to token + + @retval EFI_SUCCESS The function completed successfully. +**/ +EFI_STATUS +AtAmSetSuspendState ( + IN EFI_AT_PROTOCOL *This, + IN UINT32 TransitionState, + IN UINT8 *Token + ) +; + +/** + This routine gets AT state. + + @param[in] This The address of protocol + @param[out] AtStateInfo State of AT + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetAtStateInfo ( + IN EFI_AT_PROTOCOL *This, + OUT AT_STATE_INFO *AtStateInfo + ) +; + +/** + Validate preffered AM. + + @param[in] AtState State of AT + @param[in] AtAmPref Preferred AT authentication + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmValidatePreferredAM ( + IN UINT8 *AtState, + IN UINT16 *AtAmPref + ) +; + +/** + This routine checks if the PbaOverrideThreshold is exceeded. + + @param[out] PbaFailedExceeded TRUE when the PbaOverrideThreshold is exceeded + @param[out] PbaFailedAttempts Number of failed attempts + @param[out] PbaFailedThreshold Pba failed count treshold + + @retval EFI_SUCCESS The function completed + successfully. +**/ +EFI_STATUS +AtAmGetPbaCounter ( + OUT UINT8* PbaFailedExceeded, + OUT UINT16* PbaFailedAttempts, + OUT UINT16* PbaFailedThreshold + ) +; + +#endif // _ATAM_H_ diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAm.inf b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.inf new file mode 100644 index 0000000..8322e18 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAm.inf @@ -0,0 +1,95 @@ +## @file +# @todo ADD DESCRIPTION +# +#@copyright +# Copyright (c) 2012 Intel Corporation. All rights reserved +# This software and associated documentation (if any) is furnished +# under a license and may only be used or copied in accordance +# with the terms of the license. Except as permitted by such +# license, no part of this software or documentation may be +# reproduced, stored in a retrieval system, or transmitted in any +# form or by any means without the express written consent of +# Intel Corporation. +# +# This file contains an 'Intel Peripheral Driver' and uniquely +# identified as "Intel Reference Module" and is +# licensed for Intel CPUs and chipsets under the terms of your +# license agreement with Intel or your vendor. This file may +# be modified by the user, subject to additional terms of the +# license agreement +# + + +[defines] +BASE_NAME = AtAm +FILE_GUID = C810485E-D0EC-4e98-AAB5-120C7E554428 +COMPONENT_TYPE = BS_DRIVER + +[sources.common] + AtAm.c + AtAm.h + At.c + At.h + AtHi.h + +# +# Edk II Glue Driver Entry Point +# + EdkIIGlueDxeDriverEntryPoint.c + +[includes.common] + . + $(EFI_SOURCE) + $(EDK_SOURCE)/Foundation/Framework + $(EDK_SOURCE)/Foundation/Efi + $(EDK_SOURCE)/Foundation + $(EDK_SOURCE)/Foundation/Include + $(EDK_SOURCE)/Foundation/Efi/Include + $(EDK_SOURCE)/Foundation/Framework/Include + $(EDK_SOURCE)/Foundation/Include/IndustryStandard + $(EDK_SOURCE)/Foundation/Core/Dxe + $(EDK_SOURCE)/Foundation/Library/Dxe/Include + $(EFI_SOURCE)/$(PROJECT_ME_ROOT) + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/At + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/At/AtAm/Dxe + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Heci/Include + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/AtLibrary + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/AtLibrary/Dxe + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/Dxe + $(EFI_SOURCE)/$(PROJECT_ME_ROOT)/Library/MeKernel/include + $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include + $(EDK_SOURCE)/Foundation/Library/EdkIIGlueLib/Include/Library + $(EFI_SOURCE)/$(PROJECT_PCH_ROOT)/Include + +[libraries.common] + AtDxeLib + MeProtocolLib + MeLib + MeGuidLib + EdkIIGlueBaseLib + EdkIIGlueUefiBootServicesTableLib + EdkIIGlueUefiRuntimeServicesTableLib + EdkIIGlueDxeReportStatusCodeLib + EdkIIGlueDxeDebugLibReportStatusCode + EdkIIGlueUefiLib + EdkIIGlueDxeMemoryAllocationLib + EdkIIGlueBasePrintLib + EdkProtocolLib + +[nmake.common] + IMAGE_ENTRY_POINT=_ModuleEntryPoint + DPX_SOURCE=AtAm.dxs +# +# Module Entry Point +# + C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_MODULE_ENTRY_POINT__=AtAmEntryPoint + C_FLAGS = $(C_FLAGS) -D __EDKII_GLUE_DXE_REPORT_STATUS_CODE_LIB__ \ + -D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \ + -D __EDKII_GLUE_BASE_PCI_LIB_PCI_EXPRESS__ \ + -D __EDKII_GLUE_BASE_LIB__ \ + -D __EDKII_GLUE_BASE_MEMORY_LIB__ \ + -D __EDKII_GLUE_UEFI_DEVICE_PATH_LIB__ \ + -D __EDKII_GLUE_UEFI_LIB__\ + -D __EDKII_GLUE_DXE_MEMORY_ALLOCATION_LIB__ \ + -D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__\ + -D __EDKII_GLUE_UEFI_RUNTIME_SERVICES_TABLE_LIB__ diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.cif b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.cif new file mode 100644 index 0000000..e482950 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.cif @@ -0,0 +1,18 @@ +<component> + name = "AtAmDxe" + category = ModulePart + LocalRoot = "ReferenceCode\ME\At\AtAm\Dxe\" + RefName = "AtAmDxe" +[files] +"At.c" +"At.h" +"AtAm.c" +"AtAm.h" +"AtAm.dxs" +"AtAm.inf" +"AtAmDxe.mak" +"AtAmDxe.sdl" +"AtHi.h" +[parts] +"ATAMProtocols" +<endComponent> diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.mak b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.mak new file mode 100644 index 0000000..b129b70 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.mak @@ -0,0 +1,81 @@ +# MAK file for the ModulePart:AtAmDxe + +all : AtAmDxe + +AtAmDxe : $(BUILD_DIR)\AtAmDxe.mak AtAmDxeBin + +$(BUILD_DIR)\AtAmDxe.mak : $(AtAmDxe_DIR)\$(@B).cif $(AtAmDxe_DIR)\$(@B).mak $(BUILD_RULES) + $(CIF2MAK) $(AtAmDxe_DIR)\$(@B).cif $(CIF2MAK_DEFAULTS) + + +AtAmDxe_INCLUDES=\ + $(AT_INCLUDES)\ + $(ME_INCLUDES)\ + $(EdkIIGlueLib_INCLUDES)\ + $(EdkIIGlueInclude)\ + $(IndustryStandard_INCLUDES)\ + $(INTEL_PCH_INCLUDES)\ + + +AtAmDxe_DEFINES = $(MY_DEFINES)\ + /D"__EDKII_GLUE_MODULE_ENTRY_POINT__=AtAmEntryPoint"\ + /D __EDKII_GLUE_DXE_REPORT_STATUS_CODE_LIB__ \ + /D __EDKII_GLUE_DXE_DEBUG_LIB_REPORT_STATUS_CODE__ \ + /D __EDKII_GLUE_UEFI_BOOT_SERVICES_TABLE_LIB__\ + /D __EDKII_GLUE_BASE_PCI_LIB_PCI_EXPRESS__ \ + /D __EDKII_GLUE_BASE_LIB__ \ + /D __EDKII_GLUE_BASE_MEMORY_LIB__ \ + /D __EDKII_GLUE_UEFI_DEVICE_PATH_LIB__ \ + /D __EDKII_GLUE_UEFI_LIB__\ + /D __EDKII_GLUE_DXE_MEMORY_ALLOCATION_LIB__ \ + + +AtAmDxe_LIB_LINKS =\ + $(EDKFRAMEWORKPROTOCOLLIB)\ + $(INTEL_PCH_PROTOCOL_LIB)\ + $(EdkIIGlueBasePrintLib_LIB) \ + $(EdkIIGlueUefiLib_LIB)\ + $(TdtProtocolLib_LIB)\ + $(ProtocolLib_LIB)\ + $(EFISCRIPTLIB)\ + $(AmtLibDxe_LIB)\ + $(MeLibDxe_LIB)\ + $(EdkIIGlueBaseLib_LIB)\ + $(AmtGuidLib_LIB)\ + $(EFIGUIDLIB)\ + $(EDKPROTOCOLLIB)\ +!IF "$(x64_BUILD)"=="1" + $(EdkIIGlueBaseLibX64_LIB)\ +!ELSE + $(EdkIIGlueBaseLibIA32_LIB)\ +!ENDIF + $(EdkIIGlueBaseMemoryLib_LIB)\ + $(EdkIIGlueDxeReportStatusCodeLib_LIB)\ + $(EdkIIGlueEdkDxeRuntimeDriverLib_LIB)\ + $(EdkIIGlueDxeDebugLibReportStatusCode_LIB)\ + $(EdkIIGlueUefiBootServicesTableLib_LIB)\ + $(EdkIIGlueDxeMemoryAllocationLib_LIB)\ + $(EdkIIGlueBasePciLibPciExpress_LIB)\ + $(EFIDRIVERLIB)\ + $(MeChipsetDxeLib_LIB)\ + $(AtDxeLib_LIB)\ + $(PchPlatformDxeLib_LIB) + + + +# MAK file for the eModule:AtAmDxe + +AtAmDxeBin : $(AtAmDxe_LIB_LINKS) + $(MAKE) /$(MAKEFLAGS) $(EDKIIGLUE_DEFAULTS)\ + /f $(BUILD_DIR)\AtAmDxe.mak all\ + "MY_INCLUDES=$(AtAmDxe_INCLUDES)"\ + "MY_DEFINES=$(AtAmDxe_DEFINES)"\ + GUID=C810485E-D0EC-4e98-AAB5-120C7E554428\ + ENTRY_POINT=_ModuleEntryPoint \ + TYPE=BS_DRIVER \ + EDKIIModule=DXEDRIVER\ + DEPEX1=$(AtAmDxe_DIR)\AtAm.dxs \ + DEPEX1_TYPE=EFI_SECTION_DXE_DEPEX \ + COMPRESS=1\ + + diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.sdl b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.sdl new file mode 100644 index 0000000..513a1a6 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtAmDxe.sdl @@ -0,0 +1,33 @@ +TOKEN + Name = "AtAmDxe_SUPPORT" + Value = "1" + Help = "Main switch to enable TdtDxe support in Project" + TokenType = Boolean + TargetEQU = Yes + TargetMAK = Yes + Master = Yes + Token = "AT_SUPPORT" "=" "1" +End + +MODULE + Help = "Includes TdtDxe.mak to Project" + File = "AtAmDxe.mak" +End + +PATH + Name = "AtAmDxe_DIR" + Help = "Tdt file source directory" +End + +PATH + Name = "AtAmDxe_SOURCE" + Help = "iAMT Driver files source directory" +End + +ELINK + Name = "$(BUILD_DIR)\AtAmDxe.ffs" + Parent = "FV_MAIN" + InvokeOrder = AfterParent +End + + diff --git a/ReferenceCode/ME/At/AtAm/Dxe/AtHi.h b/ReferenceCode/ME/At/AtAm/Dxe/AtHi.h new file mode 100644 index 0000000..ee03cf8 --- /dev/null +++ b/ReferenceCode/ME/At/AtAm/Dxe/AtHi.h @@ -0,0 +1,1275 @@ +/** @file + Definition of AT Host Interface (ATHI) Protocol messages between the + AT Service and HOST Applications. + +@copyright + Copyright (c) 2007 - 2012 Intel Corporation. All rights + reserved This software and associated documentation (if any) + is furnished under a license and may only be used or copied in + accordance with the terms of the license. Except as permitted + by such license, no part of this software or documentation may + be reproduced, stored in a retrieval system, or transmitted in + any form or by any means without the express written consent + of Intel Corporation. + + This file contains an 'Intel Peripheral Driver' and uniquely + identified as "Intel Reference Module" and is + licensed for Intel CPUs and chipsets under the terms of your + license agreement with Intel or your vendor. This file may + be modified by the user, subject to additional terms of the + license agreement +**/ +#ifndef _AT_HI_H +#define _AT_HI_H + +#include "MeLib.h" + +#define AT_COMMAND 0 +#define AT_RESPONSE 1 + +#define AT_ME_RULE_ID 0xd0000 +#define AT_ME_RULE_GROUP 0x03 +#define AT_ME_RULE_COMMAND 0x02 + +#pragma pack(1) +/// +/// ATHI Protocol Identifier +/// +/// AT Host Interface protocol GUID +/// +#define ATHI_PROTOCOL_GUID \ + { \ + 0x3C4852D6, 0xD47B, 0x4f46, 0xB0, 0x5E, 0xB5, 0xED, 0xC1, 0xAA, 0x43, 0x0A \ + } + +#define ATHI_PROTOCOL_FIXED_GUID \ + { \ + 0xfa8f55e8, 0xab22, 0x42dd, 0xb9, 0x16, 0x7d, 0xce, 0x39, 0x00, 0x25, 0x74 \ + } + +/// +/// AT Host Interface protocol version (for ME FW internal use) +/// +#define ATHI_PROTOCOL_VERSION_ME 1 + +/// +/// AT Host Interface protocol major version +/// +#define ATHI_PROTOCOL_VERSION_MAJOR 5 + +/// +/// AT Host Interface protocol minor version +/// +#define ATHI_PROTOCOL_VERSION_MINOR 0 + +/// +/// ATHI Framing Structures +/// Defines the ATHI header and creates a type name. +/// +/// Refer to AtHiHeader.dot "ATHI Header" +/// +typedef struct _ATHI_HEADER { + /// + /// The version number for the ATHI protocol. + /// + struct { + /// + /// The major version number. The major version number shall advance if + /// and only if backwards compatibility is broken by a change to the + /// protocol. If ME firmware doesn't specifically support the version + /// number supplied in the header, an error shall be returned. + /// + UINT8 Major; + + /// + /// The minor version number. All minor versions under a given major + /// version shall be backwards compatible with prevision minor versions + /// under that major version. If the version number supplied in the + /// header is higher than the minor version number supported by ME + /// firmware, an error shall be returned. + + UINT8 Minor; + } Version; + + /// + /// Specifies the command or response in the message. + /// + struct { + /// + /// The operation with which the command is associated. + /// + UINT16 Code : 7; + + /// + /// Command/Response indicator: + /// 0 The message contains a command. + /// 1 The message contains a response. + /// + UINT16 IsResponse : 1; + + /// + /// The functional category of the command + /// + /// See _ATHI_CMD_GROUP + /// + UINT16 Category : 8; + } Command; + + /// + /// The length in bytes of the message. The length applies to the message + /// body (excludes the header and signature fields). + /// + UINT32 Length; +} ATHI_HEADER; + +/// +/// Maximum blob data size. +/// +#define AT_BLOB_LENGTH_MAX 256 + +/// +/// Structure that defines the format of the Blob to be stored and retrieved +/// for the ISV software. +/// +typedef struct _AT_BLOB { + /// + /// The length of the data to be securely stored + /// + UINT32 Length; + + /// + /// The data to be securely stored + /// + UINT8 Value[AT_BLOB_LENGTH_MAX]; +} AT_BLOB; + +#define AT_NONCE_LENGTH 16 ///< Maximum nonce length. + +/// +/// Type definition for a nonce. To prevent replay of commands, a nonce +/// shall be added to each command message. A nonce is a value that is used +/// once. Ideally, each nonce value should not be used more than once during +/// the lifetime of the AT laptop computer. However, a nonce generation function +/// that guarantees a very low probability of nonce values being repeated shall +/// suffice. +/// + +typedef UINT8 AT_NONCE[AT_NONCE_LENGTH]; + +/// +/// Command Completion Codes. Each response message contains a completion code +/// that indicates whether the command completed successfully, and the nature +/// of the failure if it did not. +/// +typedef enum _ATHI_COMPLETION_CODE +{ + /// + /// The command completed successfully. + /// + ATHI_COMPCODE_SUCCESS = 0, + + /// + /// The command failed due to an internal error. + /// + ATHI_COMPCODE_INTERNAL_FAILURE, + + /// + /// The command is not recognized, or is recognized but not supported. + /// + ATHI_COMPCODE_INVALID_OPERATION, + + /// + /// A parameter value does not satisfy the requirements of the command. + /// + ATHI_COMPCODE_INVALID_PARAM = 6, + + /// + /// The value of the length field in the message header is outside the + /// supported range for the command. + /// + ATHI_COMPCODE_INVALID_MSG_LEN, + + /// + /// The command failed, but no information about the nature of the failure is available. + /// + ATHI_COMPCODE_GENERAL_FAILURE, + + /// + /// Maximum value for a completion code. + /// + ATHI_COMPCODE_MAXIMUM +} ATHI_COMPLETION_CODE; + +/// +/// Useful definitions for basic commands (commands without a body) +/// + +/// +/// Type name for an unsigned command message that has no body (header only). +/// +typedef ATHI_HEADER ATHI_BASIC_CMD; + +/// +/// Definition and type name for a basic response. The basic response has a +/// header and a minimal body (just the Completion Code). +/// +typedef struct _ATHI_BASIC_RSP { + ATHI_HEADER Header; ///< Message header + + ATHI_COMPLETION_CODE CompletionCode; ///< Completion code +} ATHI_BASIC_RSP; + +/// +/// AT Command Groups +/// + +/// Related ATHI commands are grouped into several categories. Each command +/// code contains the code of its category. See #ATHI_HEADER. +/// +typedef enum _ATHI_CMD_GROUP +{ + ATHI_CMD_GROUP_RESERVED = 0, ///< Reserved + + /// + /// Commands related to the ME's theft protection capabilities. + /// + /// See _ATHI_THEFT_DETECT_GRP_CMD + /// + ATHI_CMD_GROUP_THEFT_DETECTION, + + /// + /// Commands related to non-volatile data storage services provided to + /// the FDE/FLE software present on the AT laptop computer. + /// + /// See _ATHI_DATA_STORE_GRP_CMD + /// + ATHI_CMD_GROUP_DATA_STORAGE, + + /// + /// Commands related to securely recovering the AT laptop computer for + /// AT disablement actions. + /// + /// See _ATHI_RECOVERY_GRP_CMD + /// + ATHI_CMD_GROUP_RECOVERY, + + /// + /// Commands related to ATHI infrastructure. + /// + /// See _ATHI_GENERAL_GRP_CMD + /// + ATHI_CMD_GROUP_GENERAL, + + /// + /// Event notifications serve to inform the ME AT Service when an + /// event occurs in the PBA or AT server. + /// + /// See _ATHI_NOTIFICATION_GRP_CMD + /// + ATHI_CMD_GROUP_NOTIFICATIONS, + + /// + /// 3G NIC commands allow BIOS to initialize and request Radio + /// status from FW + /// + /// See _ATHI_3G_NIC_GRP_CMD + /// + ATHI_CMD_GROUP_3G_NIC, + + /// + /// Boundary check. + /// + ATHI_CMD_GROUP_MAX +} ATHI_CMD_GROUP; + +/// +/// ATHI THEFT DETECTION Group Commands +/// + +/// Theft detection commands control and configure the theft protection +/// capabilities of the ME AT Service. +/// +typedef enum _ATHI_THEFT_DETECT_GRP_CMD +{ + /// + /// Returns the AT state of the monitored system. + /// + /// See ATHI_GET_STATE_CMD + /// + ATHI_THEFT_DETECT_GRP_GET_STATE_CMD, + + /// + /// Returns the state of the specified timer. + /// + /// See ATHI_GET_TIMER_INFO_CMD + /// + ATHI_THEFT_DETECT_GRP_GET_TIMER_INFO_CMD, + + /// + /// Resets the specified timer to its configured reset interval. + /// + /// See ATHI_RESET_TIMER_CMD + /// + ATHI_THEFT_DETECT_GRP_RST_TIMER_CMD, + + /// + /// Configures the actions that the ME AT Service shall take if the + /// specified event occurs. + /// + /// See ATHI_SET_POLICY_CMD + /// + ATHI_THEFT_DETECT_GRP_SET_POLICY_CMD, + + /// + /// Returns the actions that the ME AT Service shall take if the + /// specified event occurs. + /// + /// See ATHI_GET_POLICY_CMD + /// + ATHI_THEFT_DETECT_GRP_GET_POLICY_CMD, + + /// + /// Sets the reset interval for the specified timer. The timer counts down + /// and expires if it reaches 0. + /// + /// See ATHI_SET_TIMER_INTERVAL_CMD + /// + ATHI_THEFT_DETECT_GRP_SET_TIMER_INTERVAL_CMD, + + /// + /// Asserts that the AT laptop is stolen. The ME AT Service shall proceed + /// immediately to the Stolen state, executing all actions in the + /// AssertStolenPolicy. + /// + /// See ATHI_ASSERT_STOLEN_CMD + /// + ATHI_THEFT_DETECT_GRP_ASSERT_STOLEN_CMD, + + /// + /// Same as the AssertStolen command but not signed. + /// + /// See ATHI_ASSERT_STOLEN_CMD + /// + ATHI_THEFT_DETECT_GRP_UNSIGNED_ASSERT_STOLEN_CMD, + + /// + /// Returns the AT current state in unsigned mode. + /// + /// See GET_STATE_UNSIGNED + /// + ATHI_THEFT_DETECT_GRP_GET_STATE_UNSIGNED, + + /// + /// Boundary check. + /// + ATHI_THEFT_DETECT_GRP_MAX +} ATHI_THEFT_DETECT_GRP_CMD; + +/// +/// This flag indicates that AT is in the STOLEN state and the policies are set +/// to "do nothing". The mask must be applied to the AT state rule. +/// +/// NOTE: This flag is only cleared when the FW receives an AssertStolen +/// message. +/// +#define AT_PSEUDO_STOLEN_STATE_MASK 0x00000080 + +/// +/// Enumeration of AT theft triggers IDs +/// +typedef enum _AT_THEFT_TRIGGER +{ + /// + /// None. + /// + AT_THEFT_TRIGGER_NA = 0, + + /// + /// Theft trigger identifier for disable timer expiration + /// + AT_THEFT_TRIGGER_DISABLE_TIMER_EXPIRATION, + + /// + /// Theft trigger identifier for command driven disablement. + /// + AT_THEFT_TRIGGER_ASSERT_STOLEN, + + /// + /// Theft trigger identifier for PBA logon failure exceeded threshold. + /// + AT_THEFT_TRIGGER_THRESHOLD_EXCEEDED, + + /// + /// Theft trigger identifier for platform attack detection. + /// + AT_THEFT_TRIGGER_ATTACK_DETECTED, + + /// + /// Bounday check. + /// + AT_THEFT_TRIGGER_MAX +} AT_THEFT_TRIGGER; + +/// +/// Enumeration of AT timer types. +/// +typedef enum _AT_TIMER_ID +{ + /// + /// Reserved. + /// + AT_TID_RSVD = 0, + + /// + /// The disable timer is a variation on the watchdog timer. It is periodically + /// reset by ISV software to indicate that the system is behaving as expected. + /// If it is not reset before it expires, the ME AT Service shall execute the + /// protective actions configured in its disable timer policy. + /// The first line of defense when the system begins to exhibit behavior that + /// indicates it has been stolen is the ISV software, which may invoke the + /// ATHI SetPolicy function to protect the platform. + /// The disable timer is designed to protect the system if the ISV software + /// is disabled. In this case, the ISV software will be unable to reset the + /// disable timer before it expires, and the ME AT Service will take the + /// configured protective actions. + /// + AT_TID_DISABLE_TIMER, + + /// + /// The unlock timer used when the AT laptop computer is locked. The ME AT Service + /// sets the recovery timer when it sees that the AT state is Stolen during + /// the host boot flow. If the user doesn't successfully complete the + /// platform_enable_flow recovery flow before the unlock timer expires, + /// the ME AT Service shall power down the platform immediately. + /// The variable UnlockTimerInterval shall be configurable within a range + /// that is long enough to facilitate a bona fide recovery attempt, but short + /// enough to prevent exploitation of the platform by a thief that does not + /// have the recovery credential. + /// + AT_TID_UNLOCK_TIMER, + + /// + /// The grace timer allows the user of a AT laptop computer time to take + /// actions to cause a ResetTimer command to be issued by the AT service. + /// The grace period shall be applied if and only if the ME AT service + /// determines that the Disable Timer logically expired while the AT + /// laptop computer was in Sx (sleeping). + /// + AT_TID_GRACE_TIMER, + + /// + /// The PBA Logon Timer shall be used to count down the allotted time for + /// PBA Logon. The ME AT Service shall start a PBA Logon Timer upon + /// transition from S4/S5 to S0. If the ME AT Service receives a property + /// authenticated PBA Logon notification message before the PBA Logon Timer + /// expires, it shall stop the timer and allow operation to continue normally. + /// If instead the PBA Logon Timer expires before the ME AT Service has + /// received a properly authenticated PBA Logon notification message, the + /// ME AT Service shall power down the system immediately, but shall not + /// transition to the Stolen state. + /// + AT_TID_PBA_LOGON_TIMER, + + /// + /// The activity timer is used to extend the period of the Disable Timer in + /// the event that a ATHI client has recently invoked a ATHI command when + /// the Disable Timer expires. The intent is to allow the client to complete + /// a command flow that may include a ResetTimer command. + /// The AT activity timer shall be reset each time a ATHI command is completed. + /// The interval of the AT activity timer shall be 30 seconds. This interval + /// shall not be externally configurable. + /// + AT_TID_ACTIVITY_TIMER, + + /// + /// Bounday check. + /// + AT_TID_MAX +} AT_TIMER_ID; + +/// +/// A timer with an interval of -1 means that the timer is disabled. Applies to +/// AT_TIMER_CONFIG and AT_TIMER_INFO. +/// +#define AT_TIMER_DISABLED 0xFFFFFFFF + +/// +/// Maximum timer value besides the disabled timer value. This value is due to +/// the maximum timer value allowed by the FW resources. +/// +#define AT_TIMER_MAX (AT_TIMER_DISABLED / 1024) + +/// +/// Remaining grace timer in which the user is not assumed not to be able to +/// complete a TimerResetCmd due to OS context loading from S3 -> S0. +/// +/// Value is 30 seconds. +/// +#define AT_LOW_GRACE_THRESHOLD 30 + +/// +/// Minumium DISABLE timer value (in seconds) +/// +#define AT_TMR_DISABLE_MIN 60 + +/// +/// Minumium DISABLE timer value (in seconds) +/// +#define AT_TMR_DISABLE_MAX AT_TIMER_DISABLED + +/// +// Minumium UNLOCK timer value (in seconds) +/// +#define AT_TMR_UNLOCK_MIN 60 + +/// +/// Minumium UNLOCK timer value (in seconds) +/// +#define AT_TMR_UNLOCK_MAX AT_TIMER_MAX + +/// +/// Minumium GRACE timer value (in seconds) +/// +#define AT_TMR_GRACE_MIN 60 + +/// +/// Minumium GRACE timer value (in seconds) +/// +#define AT_TMR_GRACE_MAX AT_TIMER_MAX + +/// +// Minumium PBALOGON timer value (in seconds) +/// +#define AT_TMR_PBALOGON_MIN 60 + +/// +/// Minumium PBALOGON timer value (in seconds) +/// +#define AT_TMR_PBALOGON_MAX AT_TIMER_DISABLED + +/// +/// Structure that contains the configuration and state information for +/// a specified timer. +/// +typedef struct _AT_TIMER_INFO { + /// + /// Identifies the timer that shall be configured. See #AT_TIMER_ID. + /// + UINT8 Id; + + /// + /// Padding for now + /// + UINT8 Reserved[3]; + + /// + /// The interval configured in the timer, in seconds. + /// + UINT32 Interval; + + /// + /// The number of ticks remaining in the current timer countdown. + /// + UINT32 TimeLeft; +} AT_TIMER_INFO; + +/// +/// Structure defining the PBAM Configuration. +/// +typedef struct _AT_POLICY_PBA_CONFIG { + UINT8 RunAfterPost : 1; + UINT8 IsInstalled : 1; + UINT8 Reserved : 6; +} AT_POLICY_PBA_CONFIG; + +/// +/// Optional union defining the PBAM Configuration. +/// +typedef union _AT_POLICY_PBA_CONFIG_U { + UINT8 Value; + AT_POLICY_PBA_CONFIG Bits; +} AT_POLICY_PBA_CONFIG_U; + +/// +/// Enumeration of the platform lock state +/// +typedef enum _AT_PLATFORM_LOCKSTATE +{ + AT_PLATFORM_LOCKSTATE_NOTLOCKED = 0, + AT_PLATFORM_LOCKSTATE_LOCKED, + AT_PLATFORM_LOCKSTATE_MAX +} AT_PLATFORM_LOCKSTATE; + +// +// Command definition structures +// + +/// +/// The GetATState command. Returns the AT state of the laptop computer. +/// +/// Sender: AT AM | PBA +/// Signing Key: None | None +/// +/// Refer to AtHiGetStateCmd.dot "GetState command" +/// +/// See ATHI_GET_STATE_RSP +/// +typedef ATHI_BASIC_CMD ATHI_GET_STATE_CMD; + +/// +// The GetATState response. +/// +/// Refer to AtHiGetStateRsp.dot "GetState response" +/// +/// +typedef struct _ATHI_GET_STATE_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + AT_STATE_INFO StateInfo; +} ATHI_GET_STATE_RSP; + +/// +/// The GetTimerInfo command. Returns configuration and state information about +/// the specified timer. +/// +/// Sender: PBA +/// Signing Key: PBASK +/// +/// Refer to AtHiGetTimerInfoCmd.dot "GetTimerInfo command" +/// +/// See ATHI_GET_TIMER_INFO_RSP +/// +typedef struct _ATHI_GET_TIMER_INFO_CMD { + ATHI_HEADER Header; + UINT8 TimerId; +} ATHI_GET_TIMER_INFO_CMD; + +/// +/// ATHI_GET_TIMER_INFO response. +/// +/// Refer to AtHiGetTimerInfoRsp.dot "GetTimerInfo response" +/// +typedef struct _ATHI_GET_TIMER_INFO_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + AT_TIMER_INFO TimerInfo; +} ATHI_GET_TIMER_INFO_RSP; + +/// +/// ATHI RECOVERY Group Commands +/// +typedef enum _ATHI_RECOVERY_GRP_CMD +{ + /// + /// SetCredential stores the recovery credential in non-volatile storage, + /// where it is used for validation purposes when the credential is presented + /// by a user during recovery flow. + /// + /// See #ATHI_SET_CREDENTIAL_CMD + /// + ATHI_RECOVERY_GRP_SET_CREDENTIAL_CMD, + /// + /// AuthenticateRecoveryCredential presents the a credential to the ME AT + /// Service for validation during the recovery flow. + /// + /// See ATHI_AUTHENTICATE_CREDENTIAL_CMD + /// + ATHI_RECOVERY_GRP_AUTH_CREDENTIAL_CMD, + /// + /// The ComputeHash command computes a specified hash of input data. Maximum + /// size of the digest value shall be 384 bits (48 bytes). This command may + /// be used to preprocess authentication tokens if the specified hash + /// algorithm is not supported by the requester. + /// + /// See ATHI_COMPUTE_HASH_CMD + /// + ATHI_RECOVERY_GRP_COMPUTE_HASH_CMD, + /// + /// The DeAssertStolen command is used to recovery the platfrom from stolen state + /// by PBAM or AT server + /// See ATHI_DEASSERT_STOLEN_CMD + /// + ATHI_RECOVERY_GRP_DEASSERT_STOLEN_CMD, + /// + /// The GetIsvId command exports the identity of the service provider (ISV) + /// that activated the AT service + /// See ATHI_GET_ISVID_CMD + /// + ATHI_RECOVERY_GRP_GET_ISVID_CMD, + /// + /// Bounday check. + /// + ATHI_RECOVERY_GRP_MAX +} ATHI_RECOVERY_GRP_CMD; + +/// +/// This enumeration defines the credential types. +/// +typedef enum _AT_CREDENTIAL_TYPE +{ + /// + // Reserved. + /// + AT_CREDENTIAL_TYPE_RSVD = 0, + + /// + // User defined recovery passphrase + /// + AT_CREDENTIAL_TYPE_USER_PASSPHRASE, + + /// + /// Server generated random token + /// + AT_CREDENTIAL_TYPE_SRTK, + + /// + /// Server suspend token + /// + AT_CREDENTIAL_TYPE_SSTK, + + /// + /// Base key + /// + AT_CREDENTIAL_TYPE_BK, + + /// + /// Boundary check. + /// + AT_CREDENTIAL_TYPE_MAX +} AT_CREDENTIAL_TYPE; + +/// +// This enumeration defines the salt IDs. +/// +typedef enum _AT_HASH_ALGO_ID +{ + /// + /// Reserved. + /// + AT_HASH_ALGO_ID_RSVD = 0, + + /// + /// SHA-1 algorithm (160-bit output) + /// + AT_HASH_ALGO_ID_SHA1, + + /// + /// Boundary check + /// + AT_HASH_ALGO_ID_MAX +} AT_HASH_ALGO_ID; + +/// +/// Defines the maximum length of a user passpharse recovery hash (will be 32 in 2009). +/// +#define AT_USR_PASS_HASH_LENGTH_MAX 20 + +/// +/// Defines the maximum length of a SRTK recovery token +/// +#define AT_SRTK_LENGTH_MAX 32 + +/// +/// Maximium credential length. +/// +#define AT_CREDENTIAL_VALUE_LENGTH_MAX AT_SRTK_LENGTH_MAX + +#define AT_PASSWORD_LENGTH 64 + +/// +/// Structure that defines a credential for storage, validation, and export operations. +/// +typedef struct _AT_CREDENTIAL { + /// + /// The credential type + /// + AT_CREDENTIAL_TYPE Type; + + /// + /// The credential length + /// + UINT32 Length; + + /// + /// The credential value + /// + UINT8 Value[1]; /// Need a pointer but cannot make a zero length array +} AT_CREDENTIAL; + +/// +/// The AuthenticateCredential command. Sets the value of the specified +/// credential in the ME AT Service. +/// +/// Sender: AT AM +/// Signing Key: None +/// +/// Refer to AtHiAuthenticateCredentialCmd.dot "AuthenticateCredential command" +/// +/// See ATHI_AUTHENTICATE_CREDENTIAL_RSP +/// +typedef struct _ATHI_AUTHENTICATE_CREDENTIAL_CMD { + ATHI_HEADER Header; + AT_CREDENTIAL Credential; +} ATHI_AUTHENTICATE_CREDENTIAL_CMD; + +/// +/// The AuthenticateCredential response. +/// +/// Refer to AtHiAuthenticateCredentialRsp.dot "AuthenticateCredential response" +/// +typedef struct _ATHI_AUTHENTICATE_CREDENTIAL_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + UINT8 Authenticated; +} ATHI_AUTHENTICATE_CREDENTIAL_RSP; + +/// +/// Definition for the maximum hash output size. +/// +#define AT_MAX_HASH_OUTPUT_SIZE 48 + +/// +/// The ComputeHash command. Computes a specified hash of input data. Maximum +/// size of the digest value shall be 384 bits (48 bytes). +/// +/// Sender: AT AM +/// Signing Key: None +/// +/// Refer to AtHiComputeHashCmd.dot "ComputeHash command" +/// +/// See ATHI_COMPUTE_HASH_RSP +/// +typedef struct _ATHI_COMPUTE_HASH_CMD { + ATHI_HEADER Header; + + /// + /// see AT_HASH_ALGO_ID for values + /// + UINT8 Algorithm; + UINT8 InputLength; + UINT8 InputBuffer[AT_MAX_HASH_OUTPUT_SIZE]; +} ATHI_COMPUTE_HASH_CMD; + +/// +/// The ComputeHash response. +/// +/// Refer to AtHiComputeHashRsp.dot "ComputeHash response" +/// +/// +typedef struct _ATHI_COMPUTE_HASH_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + + /// + /// see AT_HASH_ALGO_ID for values + /// + UINT8 OutputLength; + UINT8 OutputBuffer[AT_MAX_HASH_OUTPUT_SIZE]; +} ATHI_COMPUTE_HASH_RSP; + +/// +/// The DeassertStolen command. Recover the laptop from stolen state. The ME AT +/// Service shall proceed immediately to the NotStolen state. +/// +/// Sender: ISV SW +/// Signing Key: PBASK, TSSK +/// +/// Refer to AtHiDeassertStolenCmd.dot "DeassertStolen command" +/// +/// See ATHI_DEASSERT_STOLEN_RSP +/// +typedef ATHI_BASIC_CMD ATHI_DEASSERT_STOLEN_CMD; + +typedef ATHI_BASIC_RSP ATHI_DEASSERT_STOLEN_RSP; + +/// +/// The GetIsvId command exports the identity of the service provider (ISV) that +/// activated the AT service. This allows for system recovery in cases where the user +/// may not be sure who to contact when he/she is unable to recover the system locally. +/// Note that this command is allowed only while the system in the STOLEN state +/// +/// Sender: AT AM +/// Signing Key: None +/// +/// See ATHI_GET_ISVID_RSP +/// +typedef ATHI_BASIC_CMD ATHI_GET_ISVID_CMD; + +typedef struct _ATHI_GET_ISVID_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + UINT32 IsvId; +} ATHI_GET_ISVID_RSP; + +/// +/// ATHI General Group Commands +/// +typedef enum _ATHI_GENERAL_GRP_CMD +{ + /// + /// GetNonce returns a nonce generated by the ME AT Service. The purpose of + /// this nonce is to prevent replay of AT command messages. + /// + /// See ATHI_GET_NONCE_CMD + /// + ATHI_GENERAL_GRP_GET_NONCE_CMD, + + /// + /// GetATCapabilities requests that the ME AT Service return the + /// capabilities it has implemented. + /// + /// See ATHI_GET_AT_CAPABILITIES_CMD + /// + ATHI_GENERAL_GRP_GET_AT_CAPABILITIES_CMD, + + /// + /// The SetPublicKey command saves the specified public key of an RSA + /// key-pair for use by the ME AT Service. + /// + /// See ATHI_GET_PUBLIC_KEY_CMD + /// + ATHI_GENERAL_GRP_SET_PUBLIC_KEY_CMD, + + /// + /// The GetPublicKey command returns the specified public key of an RSA + /// key-pair owned by the ME AT Service. + /// + /// See ATHI_GET_PUBLIC_KEY_CMD + /// + ATHI_GENERAL_GRP_GET_PUBLIC_KEY_CMD, + + /// + /// The GetEventHistory command retrieves entries from the AT Event History + /// in the ME. + /// + /// See ATHI_GET_EVENT_HISTORY_CMD + /// + ATHI_GENERAL_GRP_GET_EVENT_HISTORY_CMD, + + /// + /// The ClearEventHistory command deletes all entries from the AT Event + /// History in the ME. + /// + /// See ATHI_CLEAR_EVENT_HISTORY_CMD + /// + ATHI_GENERAL_GRP_CLEAR_EVENT_HISTORY_CMD, + + /// + /// The SetSysTime command synchronizes the time between the FW with the + /// AT server. + /// + /// See ATHI_SET_SYS_TIME_CMD + /// + ATHI_GENERAL_GRP_SET_SYS_TIME_CMD, + + /// + /// The Set Supend Mode command requests FW transition + /// into or out of Suspend Mode. + /// + + ATHI_GENERAL_GRP_SET_SUSPEND_CMD = 8, + + /// + /// Bounday check. + /// + ATHI_GENERAL_GRP_MAX +} ATHI_GENERAL_GRP_CMD; + +/// +/// ATHI 3G WWAN Commands +/// +typedef enum _ATHI_3G_NIC_GRP_CMD +{ /// + /// 3G NIC Init Command tells FW to intialize the NIC radio + /// + ATHI_3G_NIC_GRP_INIT_CMD = 3, + + /// + /// The 3G NIC Query Command asks FW about the status of the NIC radio + /// + ATHI_3G_NIC_GRP_QUERY_CMD, + + /// + /// Bounday check. + /// + ATHI_3G_NIC_GRP_MAX +} ATHI_3G_NIC_GRP_CMD; + +/// +/// The GetNonce command. Requests that the ME AT Service generate and return +/// a nonce to be used in a subsequent ATHI command. The nonce prevents +/// replay of a command. +/// +/// Sender: ISV SW +/// Signing Key: Any +/// +/// Refer to AtHiGetNonceCmd.dot "GetNonce command" +/// +/// See ATHI_GET_NONCE_RSP +/// +typedef ATHI_BASIC_CMD ATHI_GET_NONCE_CMD; + +/// +/// The GetNonce response. +/// +/// Refer to AtHiGetNonceRsp.dot "GetNonce response" +/// +typedef struct _ATHI_GET_NONCE_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + AT_NONCE Nonce; +} ATHI_GET_NONCE_RSP; + +/// +/// ATHI NOTIFICATION Group Commands +/// +typedef enum _ATHI_NOTIFICATION_GRP_CMD +{ + /// + /// A PBA sends a PBALogon notification message to notify the ME AT service + /// of a successful user logon. + /// + /// See ATHI_PBA_LOGON + /// + ATHI_NOTIFICATION_GRP_PBA_LOGON, + + /// + /// Bounday check. + /// + ATHI_NOTIFICATION_GRP_MAX +} ATHI_NOTIFICATION_GRP_CMD; + +/// +/// PBALogon notification. Notifies the ME AT service of a successful user logon. +/// +/// Sender: PBA +/// Signing Key: PBASK +/// +/// Refer to AtHiPbaLogonNotify.dot "PBALogon notification" +/// +/// See ATHI_GET_NONCE_RSP +/// +typedef ATHI_BASIC_CMD ATHI_PBA_LOGON_NOTIFY; + +/// +/// The GetNonce response. +/// +/// Refer to AtHiPbaLogonAck.dot "PBALogon ack" +/// +typedef ATHI_BASIC_RSP ATHI_PBA_LOGON_ACK; + +/// +/// ATHI DATA STORAGE Group Commands +/// +typedef enum _ATHI_DATA_STORE_GRP_CMD +{ + /// + /// SetBlob stores data in the ME AT FDE/FLE ISV non-volatile storage area. + /// + /// See #ATHI_SET_BLOB_CMD. + /// + ATHI_DATA_STORE_GRP_SET_BLOB_CMD, + + /// + /// GetBlob returns the data stored in the ME AT FDE/FLE ISV non-volatile + /// storage area. + /// + /// See ATHI_GET_BLOB_CMD. + /// + ATHI_DATA_STORE_GRP_GET_BLOB_CMD, + + /// + /// Stores a vendor string the ME's non-volatile storage area. + /// + /// See ATHI_SET_VENDOR_STRING_CMD + /// + ATHI_DATA_STORE_GRP_SET_VENDOR_STRING_CMD, + + /// + /// Retrieves the vendor string from the ME's non-volatile storage area. + /// + /// See ATHI_GET_VENDOR_STRING_CMD + /// + ATHI_DATA_STORE_GRP_GET_VENDOR_STRING_CMD, + + /// + /// Bounday check. + /// + ATHI_DATA_STORE_GRP_MAX +} ATHI_DATA_STORE_GRP_CMD; + +/// +/// This enumeration defines the vendor string identifiers. +/// +typedef enum _AT_VENDOR_STRING_ID +{ + /// + /// Reserved. + /// + AT_VENDOR_STRING_ID_RSVD = 0, + + /// + /// User defined recovery passphrase + /// + AT_VENDOR_STRING_ID_RECOVERY_HELP, + /// + /// AT_VENDOR_STRING_ID_RECOVERY_HELP, + /// + + /// + /// Server generated random token + /// + AT_CUSTOM_RECOVERY_ID_CONFIGURATIONS, + + /// + /// Boundary check. + /// + AT_VENDOR_STRING_ID_MAX +} AT_VENDOR_STRING_ID; + +/// +/// Maximum blob data size. +/// +#define AT_VENDOR_STRING_LENGTH_MAX 256 + +/// +/// The SetVendorString command. Stores a vendor string the ME's +/// non-volatile storage area. +/// +/// Sender: ISV SW +/// Signing Key: TSSK +/// +/// See ATHI_SET_VENDOR_STRING_RSP +/// +typedef struct _ATHI_SET_VENDOR_STRING_CMD { + ATHI_HEADER Header; + UINT8 Id; + UINT8 Reserved[3]; + AT_BLOB String; +} ATHI_SET_VENDOR_STRING_CMD; + +/// +/// The SetVendorString response. +/// +typedef ATHI_BASIC_RSP ATHI_SET_VENDOR_STRING_RSP; + +/// +/// The GetVendorString command. Retrieves the vendor string data from the ME's +/// non-volatile storage area. +/// +/// Sender: ISV SW +/// Signing Key: None +/// +/// See ATHI_GET_VENDOR_STRING_RSP +/// +typedef struct _ATHI_GET_VENDOR_STRING_CMD { + ATHI_HEADER Header; + UINT8 Id; +} ATHI_GET_VENDOR_STRING_CMD; + +/// +/// The GetVendorString response. +/// +/// Sender: ISV SW +/// Signing Key: None +/// +/// +typedef struct _ATHI_GET_VENDOR_STRING_RSP { + ATHI_HEADER Header; + ATHI_COMPLETION_CODE CompletionCode; + AT_BLOB String; +} ATHI_GET_VENDOR_STRING_RSP; + +/// +/// The SendAssertStolen Request +/// +/// Sender: ISV SW +/// Signing Key: None +/// +/// +typedef struct _ATHI_ASSERT_STOLEN_CMD { + ATHI_HEADER Header; + UINT32 DelayTime; +} ATHI_ASSERT_STOLEN_CMD; + +/// +/// The SendAssertStolen response. +/// +typedef ATHI_BASIC_RSP ATHI_ASSERT_STOLEN_RSP; + +/// +/// The Set Supend State Request Message +/// +/// Sender: BIOS +/// Signing Key: SSTK One Time Token +/// +/// +typedef struct _ATHI_SET_SUSPEND_STATE_CMD { + ATHI_HEADER Header; + UINT32 TransitionState; /// 0=Exit, 1=Enter + AT_CREDENTIAL Credential; +} ATHI_SET_SUSPEND_STATE_CMD; + +/// +/// The Set Supend State Response Message +/// +/// Sender: FW +/// Signing Key: None +/// +/// +typedef struct _ATHI_SET_SUSPEND_STATE_RSP { + ATHI_HEADER Header; + UINT32 CompletionCode; +} ATHI_SET_SUSPEND_STATE_RSP; + +/// +/// The Initialize WWAN Recovery Request Message +/// +/// Sender: BIOS +/// Signing Key: None +/// +/// +typedef struct _ATHI_INIT_WWAN_RECOV_CMD { + ATHI_HEADER Header; +} ATHI_INIT_WWAN_RECOV_CMD; + +/// +/// The Initialize WWAN Recovery Response Message +/// +/// Sender: FW +/// Signing Key: None +/// +/// +typedef struct _ATHI_INIT_WWAN_RECOV_RSP { + ATHI_HEADER Header; + UINT32 CompletionCode; +} ATHI_INIT_WWAN_RECOV_RSP; + +/// +/// The Initialize WWAN Status Request Message +/// +/// Sender: BIOS +/// Signing Key: None +/// +/// +typedef struct _ATHI_WWAN_STATUS_CMD { + ATHI_HEADER Header; +} ATHI_WWAN_STATUS_CMD; + +/// +/// The Initialize WWAN Status Response Message +/// +/// Sender: FW +/// Signing Key: None +/// +/// +typedef struct _ATHI_WWAN_STATUS_RSP { + ATHI_HEADER Header; + UINT32 CompletionCode; + UINT8 RadioStatus; + UINT8 NetworkStatus; +} ATHI_WWAN_STATUS_RSP; + +#pragma pack() + +#endif // _AT_HI_H |