前言
看见反汇编中有一段算md5的代码,记录一下。
记录
// testCase1.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <windows.h>
#include <Wincrypt.h>
#include <stdlib.h>
#include <stdio.h>
BOOL __cdecl fnMd5(const BYTE* pbData, DWORD dwDataLen, BYTE* pucAryHash);
int main(int argc, char* argv[])
{
int i = 0;
BYTE cBuf[MAXBYTE] = {'\0'}; ///< 全0的buffer
BYTE ucRc[16] = {'\0'};
if (fnMd5(cBuf, MAXBYTE, ucRc)) {
for (i = 0; i < sizeof(ucRc); i++) {
printf("%.2X ", ucRc[i]);
}
printf("\r\n");
}
/** run result
6D F9 01 2B 2B 7C B3 C5 59 63 49 9A 26 30 9B BA
*/
printf("END\n");
return 0;
}
BOOL __cdecl fnMd5(const BYTE* pbData, DWORD dwDataLen, BYTE* pucAryHash)
{
BOOL bRc = FALSE;
// 这里直接假设算出的hash值为16字节
// msdn上的说法是要先算一下hash值占用的空间, CryptGetHashParam(hHash, HP_HASHSIZE
DWORD dwOutPutBufferSize = 16;
HCRYPTPROV hProv = NULL;
HCRYPTHASH hHash = NULL;
if (!CryptAcquireContextA(&hProv, 0, 0, PROV_RSA_FULL/*1u*/, CRYPT_VERIFYCONTEXT/*0xF0000000u*/)) {
return 0;
}
if (CryptCreateHash(hProv, CALG_MD5/*0x8003u*/, 0, 0, &hHash)) {
if (!CryptHashData(hHash, pbData, dwDataLen, 0)) {
CryptReleaseContext(hProv, 0);
CryptDestroyHash(hHash);
return 0;
}
if (CryptGetHashParam(hHash, HP_HASHVAL/*2u*/, pucAryHash, &dwOutPutBufferSize, 0)) {
bRc = TRUE;
}
CryptDestroyHash(hHash);
}
CryptReleaseContext(hProv, 0);
return bRc;
}
反汇编代码
; =============== S U B R O U T I N E =======================================
; Attributes: bp-based frame
; int __cdecl fnMd5(BYTE *pbData, DWORD dwDataLen, int)
fnMd5 proc near ; CODE XREF: fnMd51+68p fnMd52+18p ...
pdwDataLen = dword ptr -0Ch
hProv = dword ptr -8
hHash = dword ptr -4
pbData = dword ptr 8
dwDataLen = dword ptr 0Ch
arg_8 = dword ptr 10h
push ebp
mov ebp, esp
sub esp, 0Ch
push esi
push edi
xor esi, esi
push 0F0000000h ; dwFlags
push 1 ; dwProvType
push esi ; szProvider
lea eax, [ebp+hProv]
push esi ; szContainer
push eax ; phProv
xor edi, edi
mov [ebp+hProv], esi
mov [ebp+hHash], esi
mov [ebp+pdwDataLen], esi
call CryptAcquireContextA
test eax, eax
jz short loc_10004896
lea eax, [ebp+hHash]
push eax ; phHash
push esi ; dwFlags
push esi ; hKey
push 8003h ; Algid
push [ebp+hProv] ; hProv
call CryptCreateHash
test eax, eax
jz short loc_100048C4
push esi ; dwFlags
push [ebp+dwDataLen] ; dwDataLen
push [ebp+pbData] ; pbData
push [ebp+hHash] ; hHash
call CryptHashData
test eax, eax
jnz short loc_1000489A
push esi ; dwFlags
push [ebp+hProv] ; hProv
call CryptReleaseContext
push [ebp+hHash] ; hHash
call CryptDestroyHash
loc_10004896: ; CODE XREF: fnMd5+2Aj
xor eax, eax
jmp short loc_100048D0
; ---------------------------------------------------------------------------
loc_1000489A: ; CODE XREF: fnMd5+56j
lea eax, [ebp+pdwDataLen]
push esi ; dwFlags
push eax ; pdwDataLen
mov [ebp+pdwDataLen], 10h
push [ebp+arg_8] ; pbData
push 2 ; dwParam
push [ebp+hHash] ; hHash
call CryptGetHashParam
test eax, eax
jz short loc_100048BB
push 1
pop edi
loc_100048BB: ; CODE XREF: fnMd5+8Bj
push [ebp+hHash] ; hHash
call CryptDestroyHash
loc_100048C4: ; CODE XREF: fnMd5+42j
push esi ; dwFlags
push [ebp+hProv] ; hProv
call CryptReleaseContext
mov eax, edi
loc_100048D0: ; CODE XREF: fnMd5+6Dj
pop edi
pop esi
leave
retn
fnMd5 endp
; =============== S U B R O U T I N E =======================================