//************************************
// 函數名:CEncryptionDlg::CalculateHash
// 傳回類型:BOOL
// 功能: 計算hash值
// 參數1:BYTE *pData 需要計算哈希值的資料
// 參數2:DWORD dwDataLength 需要計算哈希值的資料長度
// 參數3:ALG_ID algHashType 需要計算哈希值的資料的類型
// 參數4:BYTE **ppHashData 計算出來的哈希資料
// 參數5:DWORD *pdwHashDataLength 計算出來的哈希資料長度
//************************************
BOOL CalculateHash(BYTE *pData, DWORD dwDataLength, ALG_ID algHashType, BYTE **ppHashData, DWORD *pdwHashDataLength);
//************************************
// 函數名:CEncryptionDlg::AesEncrypt
// 傳回類型:BOOL
// 功能: AES加密
// 參數1:BYTE *pPassword 密鑰
// 參數2:DWORD dwPasswordLength 密鑰長度
// 參數3:BYTE *pData 需要AES加密的資料
// 參數4:DWORD &dwDataLength 需要AES加密的資料長度
// 參數5:DWORD dwBufferLength 緩沖區長度
//************************************
BOOL AesEncrypt(BYTE *pPassword, DWORD dwPasswordLength, BYTE *pData, DWORD &dwDataLength, DWORD dwBufferLength);
//************************************
// 函數名:CEncryptionDlg::AesDecrypt
// 傳回類型:BOOL
// 功能: AES解密
// 參數1:BYTE *pPassword 密鑰
// 參數2:DWORD dwPasswordLength 密鑰長度
// 參數3:BYTE *pData 需要AES解密的資料
// 參數4:DWORD &dwDataLength 需要AES解密的資料長度
//************************************
BOOL AesDecrypt(BYTE *pPassword, DWORD dwPasswordLength, BYTE *pData, DWORD &dwDataLength);
//************************************
// 函數名:CEncryptionDlg::GenerateKey
// 傳回類型:BOOL
// 功能: 生成公鑰和私鑰
// 參數1:BYTE **ppPublicKey 公鑰
// 參數2:DWORD *pdwPublicKeyLength 公鑰長度
// 參數3:BYTE **ppPrivateKey 私鑰
// 參數4:DWORD *pdwPrivateKeyLength 私鑰長度
//************************************
BOOL GenerateKey(BYTE **ppPublicKey, DWORD *pdwPublicKeyLength, BYTE **ppPrivateKey, DWORD *pdwPrivateKeyLength);
//************************************
// 函數名:CEncryptionDlg::RsaEncrypt
// 傳回類型:BOOL
// 功能: RAS加密
// 參數1:BYTE *pPublicKey 公鑰
// 參數2:DWORD dwPublicKeyLength 公鑰長度
// 參數3:BYTE *pData 需要加密的資料
// 參數4:DWORD &dwDataLength 需要加密的資料長度
// 參數5:DWORD dwBufferLength 緩沖區長度
//************************************
BOOL RsaEncrypt(BYTE *pPublicKey, DWORD dwPublicKeyLength, BYTE *pData, DWORD &dwDataLength, DWORD dwBufferLength);
//************************************
// 函數名:CEncryptionDlg::RsaDecrypt
// 傳回類型:BOOL
// 功能: RAS解密
// 參數1:BYTE **ppPrivateKey 私鑰
// 參數2:DWORD *pdwPrivateKeyLength 私鑰長度
// 參數3:BYTE *pData 需要解密的資料
// 參數4:DWORD &dwDataLength 需要解密的資料長度
//************************************
BOOL RsaDecrypt(BYTE *pPrivateKey, DWORD dwProvateKeyLength, BYTE *pData, DWORD &dwDataLength);
//計算hash值
BOOL CEncryptionDlg::CalculateHash(BYTE *pData, DWORD dwDataLength, ALG_ID algHashType, BYTE **ppHashData, DWORD *pdwHashDataLength)
{
BOOL bRet = FALSE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTHASH hCryptHash = NULL;
DWORD dwTemp = 0;
DWORD dwHashDataLength = 0;
BYTE* pHashData = NULL;
// 獲得指定CSP的密鑰容器的句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
return FALSE;
}
// 建立一個HASH對象, 指定HASH算法
bRet = ::CryptCreateHash(hCryptProv, algHashType, NULL, NULL, &hCryptHash);
if (FALSE == bRet)
{
MessageBox(_T("CryptCreateHash Error\r\n"));
CryptReleaseContext(hCryptProv, 0);
return FALSE;
}
// 計算HASH資料
bRet = ::CryptHashData(hCryptHash, pData, dwDataLength, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptHashData Error\r\n"));
CryptDestroyHash(hCryptHash);
CryptReleaseContext(hCryptProv, 0);
return FALSE;
}
// 擷取HASH結果的大小
dwTemp = sizeof(dwHashDataLength);
bRet = ::CryptGetHashParam(hCryptHash, HP_HASHSIZE, (BYTE *)(&dwHashDataLength), &dwTemp, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptGetHashParam Error\r\n"));
CryptDestroyHash(hCryptHash);
CryptReleaseContext(hCryptProv, 0);
return FALSE;
}
// 申請記憶體
pHashData = new BYTE[dwHashDataLength]{ 0 };
if (NULL == pHashData)
{
MessageBox(_T("new Error\r\n"));
CryptDestroyHash(hCryptHash);
CryptReleaseContext(hCryptProv, 0);
return FALSE;
}
// 擷取HASH結果資料
bRet = ::CryptGetHashParam(hCryptHash, HP_HASHVAL, pHashData, &dwHashDataLength, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptGetHashParam Error\r\n"));
delete[] pHashData;
pHashData = NULL;
CryptDestroyHash(hCryptHash);
CryptReleaseContext(hCryptProv, 0);
return FALSE;
}
// 傳回資料
*ppHashData = pHashData;
*pdwHashDataLength = dwHashDataLength;
// 釋放關閉
CryptDestroyHash(hCryptHash);
CryptReleaseContext(hCryptProv, 0);
return TRUE;
}
// AES加密
BOOL CEncryptionDlg::AesEncrypt(BYTE *pPassword, DWORD dwPasswordLength, BYTE *pData, DWORD &dwDataLength, DWORD dwBufferLength)
{
BOOL bRet = TRUE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTHASH hCryptHash = NULL;
HCRYPTKEY hCryptKey = NULL;
do {
// 擷取CSP句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
break;
}
// 建立HASH對象
bRet = ::CryptCreateHash(hCryptProv, CALG_MD5, NULL, 0, &hCryptHash);
if (FALSE == bRet)
{
MessageBox(_T("CryptCreateHash Error\r\n"));
break;
}
// 對密鑰進行HASH計算 計算出密鑰的MD5值
bRet = ::CryptHashData(hCryptHash, pPassword, dwPasswordLength, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptHashData Error\r\n"));
break;
}
// 使用HASH來生成密鑰
bRet = ::CryptDeriveKey(hCryptProv, CALG_AES_128, hCryptHash, CRYPT_EXPORTABLE, &hCryptKey);
if (FALSE == bRet)
{
MessageBox(_T("CryptDeriveKey Error\r\n"));
break;
}
// 加密資料
bRet = ::CryptEncrypt(hCryptKey, NULL, TRUE, 0, pData, &dwDataLength, dwBufferLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptEncrypt Error\r\n"));
break;
}
} while (FALSE);
// 關閉釋放
if (hCryptKey)
{
CryptDestroyKey(hCryptKey);
}
if (hCryptHash)
{
CryptDestroyHash(hCryptHash);
}
if (hCryptProv)
{
CryptReleaseContext(hCryptProv, 0);
}
return bRet;
}
// AES解密
BOOL CEncryptionDlg::AesDecrypt(BYTE *pPassword, DWORD dwPasswordLength, BYTE *pData, DWORD &dwDataLength)
{
// 變量
BOOL bRet = TRUE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTHASH hCryptHash = NULL;
HCRYPTKEY hCryptKey = NULL;
do
{
// 擷取CSP句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
break;
}
// 建立HASH對象
bRet = ::CryptCreateHash(hCryptProv, CALG_MD5, NULL, 0, &hCryptHash);
if (FALSE == bRet)
{
MessageBox(_T("CryptCreateHash Error\r\n"));
break;
}
// 對密鑰進行HASH計算
bRet = ::CryptHashData(hCryptHash, pPassword, dwPasswordLength, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptCreateHash Error\r\n"));
break;
}
// 使用HASH來生成密鑰
bRet = ::CryptDeriveKey(hCryptProv, CALG_AES_128, hCryptHash, CRYPT_EXPORTABLE, &hCryptKey);
if (FALSE == bRet)
{
MessageBox(_T("CryptDeriveKey Error\r\n"));
break;
}
// 解密資料
bRet = ::CryptDecrypt(hCryptKey, NULL, TRUE, 0, pData, &dwDataLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptDecrypt Error\r\n"));
break;
}
} while (FALSE);
// 關閉釋放
if (hCryptKey)
{
CryptDestroyKey(hCryptKey);
}
if (hCryptHash)
{
CryptDestroyHash(hCryptHash);
}
if (hCryptProv)
{
CryptReleaseContext(hCryptProv, 0);
}
return bRet;
}
// 生成公鑰和私鑰
BOOL CEncryptionDlg::GenerateKey(BYTE **ppPublicKey, DWORD *pdwPublicKeyLength, BYTE **ppPrivateKey, DWORD *pdwPrivateKeyLength)
{
// 變量
BOOL bRet = TRUE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTKEY hCryptKey = NULL;
DWORD dwPublicKeyLength = 0;
BYTE* pPublicKey = NULL;
DWORD dwPrivateKeyLength = 0;
BYTE* pPrivateKey = NULL;
do
{
// 擷取CSP句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_FULL, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
break;
}
// 生成公/私密鑰對
bRet = ::CryptGenKey(hCryptProv, AT_KEYEXCHANGE, CRYPT_EXPORTABLE, &hCryptKey);
if (FALSE == bRet)
{
MessageBox(_T("CryptGenKey Error\r\n"));
break;
}
// 擷取公鑰密鑰的長度和内容
bRet = ::CryptExportKey(hCryptKey, NULL, PUBLICKEYBLOB, 0, NULL, &dwPublicKeyLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptExportKey Error\r\n"));
break;
}
pPublicKey = new BYTE[dwPublicKeyLength]{0};
bRet = ::CryptExportKey(hCryptKey, NULL, PUBLICKEYBLOB, 0, pPublicKey, &dwPublicKeyLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptExportKey Error\r\n"));
break;
}
// 擷取私鑰密鑰的長度和内容
bRet = ::CryptExportKey(hCryptKey, NULL, PRIVATEKEYBLOB, 0, NULL, &dwPrivateKeyLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptExportKey Error\r\n"));
break;
}
pPrivateKey = new BYTE[dwPrivateKeyLength]{0};
bRet = ::CryptExportKey(hCryptKey, NULL, PRIVATEKEYBLOB, 0, pPrivateKey, &dwPrivateKeyLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptExportKey Error\r\n"));
break;
}
// 傳回資料
*ppPublicKey = pPublicKey;
*pdwPublicKeyLength = dwPublicKeyLength;
*ppPrivateKey = pPrivateKey;
*pdwPrivateKeyLength = dwPrivateKeyLength;
} while (FALSE);
// 釋放關閉
if (hCryptKey)
{
CryptDestroyKey(hCryptKey);
}
if (hCryptProv)
{
CryptReleaseContext(hCryptProv, 0);
}
return bRet;
}
// 公鑰加密資料
BOOL CEncryptionDlg::RsaEncrypt(BYTE *pPublicKey, DWORD dwPublicKeyLength, BYTE *pData, DWORD &dwDataLength, DWORD dwBufferLength)
{
// 變量
BOOL bRet = TRUE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTKEY hCryptKey = NULL;
do
{
// 擷取CSP句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_FULL, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
break;
}
// 導入公鑰
bRet = ::CryptImportKey(hCryptProv, pPublicKey, dwPublicKeyLength, NULL, 0, &hCryptKey);
if (FALSE == bRet)
{
MessageBox(_T("CryptImportKey Error\r\n"));
break;
}
// 加密資料
bRet = ::CryptEncrypt(hCryptKey, NULL, TRUE, 0, pData, &dwDataLength, dwBufferLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptEncrypt Error\r\n"));
break;
}
} while (FALSE);
// 關閉句柄
if (hCryptKey)
{
CryptDestroyKey(hCryptKey);
}
if (hCryptProv)
{
CryptReleaseContext(hCryptProv, 0);
}
return bRet;
}
// 私鑰解密資料
BOOL CEncryptionDlg::RsaDecrypt(BYTE *pPrivateKey, DWORD dwProvateKeyLength, BYTE *pData, DWORD &dwDataLength)
{
// 變量
BOOL bRet = TRUE;
HCRYPTPROV hCryptProv = NULL;
HCRYPTKEY hCryptKey = NULL;
do
{
// 擷取CSP句柄
bRet = ::CryptAcquireContext(&hCryptProv, NULL, NULL, PROV_RSA_FULL, 0);
if (FALSE == bRet)
{
MessageBox(_T("CryptAcquireContext Error\r\n"));
break;
}
// 導入私鑰
bRet = ::CryptImportKey(hCryptProv, pPrivateKey, dwProvateKeyLength, NULL, 0, &hCryptKey);
if (FALSE == bRet)
{
MessageBox(_T("CryptImportKey Error\r\n"));
break;
}
// 解密資料
bRet = ::CryptDecrypt(hCryptKey, NULL, TRUE, 0, pData, &dwDataLength);
if (FALSE == bRet)
{
MessageBox(_T("CryptDecrypt Error\r\n"));
break;
}
} while (FALSE);
// 關閉句柄
if (hCryptKey)
{
CryptDestroyKey(hCryptKey);
}
if (hCryptProv)
{
CryptReleaseContext(hCryptProv, 0);
}
return bRet;
}