void md5 (const void* buf, size_t len, unsigned char result_hash_value [16]) { MD5_CTX context; Md5Init (&context); while (len) { unsigned int update_size = (unsigned int)stl::min (len, (size_t)(unsigned int)-1); Md5Update (&context, (unsigned char*)buf, update_size); buf = (const char*)buf + update_size; len -= update_size; } Md5Final (result_hash_value, &context); }
/** Initator caculates its own expected hash value. @param[in] ChapIdentifier iSCSI CHAP identifier sent by authenticator. @param[in] ChapSecret iSCSI CHAP secret of the authenticator. @param[in] SecretLength The length of iSCSI CHAP secret. @param[in] ChapChallenge The challenge message sent by authenticator. @param[in] ChallengeLength The length of iSCSI CHAP challenge message. @param[out] ChapResponse The calculation of the expected hash value. @retval EFI_SUCCESS The expected hash value was caculatedly successfully. @retval EFI_PROTOCOL_ERROR The length of the secret should be at least the length of the hash value for the hashing algorithm chosen. @retval EFI_PROTOCOL_ERROR MD5 hash operation fail. @retval EFI_OUT_OF_RESOURCES Fail to allocate resource to complete MD5. **/ EFI_STATUS IScsiCHAPCalculateResponse ( IN UINT32 ChapIdentifier, IN CHAR8 *ChapSecret, IN UINT32 SecretLength, IN UINT8 *ChapChallenge, IN UINT32 ChallengeLength, OUT UINT8 *ChapResponse ) { UINTN Md5ContextSize; VOID *Md5Ctx; CHAR8 IdByte[1]; EFI_STATUS Status; if (SecretLength < ISCSI_CHAP_SECRET_MIN_LEN) { return EFI_PROTOCOL_ERROR; } Md5ContextSize = Md5GetContextSize (); Md5Ctx = AllocatePool (Md5ContextSize); if (Md5Ctx == NULL) { return EFI_OUT_OF_RESOURCES; } Status = EFI_PROTOCOL_ERROR; if (!Md5Init (Md5Ctx)) { goto Exit; } // // Hash Identifier - Only calculate 1 byte data (RFC1994) // IdByte[0] = (CHAR8) ChapIdentifier; if (!Md5Update (Md5Ctx, IdByte, 1)) { goto Exit; } // // Hash Secret // if (!Md5Update (Md5Ctx, ChapSecret, SecretLength)) { goto Exit; } // // Hash Challenge received from Target // if (!Md5Update (Md5Ctx, ChapChallenge, ChallengeLength)) { goto Exit; } if (Md5Final (Md5Ctx, ChapResponse)) { Status = EFI_SUCCESS; } Exit: FreePool (Md5Ctx); return Status; }