Code: void DeriveKeyTest::Testkey(DWORD ulALG) { HCRYPTPROV hCryptProv = NULL; HCRYPTKEY hKey = 0; HCRYPTHASH hHash = 0; char *szPassword = "UsbToken Derive key test!"; DWORD dwLength = 0; cout << endl << "Test CSP: " << TEST_CSP_NAME << endl << endl; // Create a keyset(aka container), if the keyset already exists, // delete it and re-create it. BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { DWORD dwLastErr = GetLastError(); ActionFailed(dwLastErr); if(0x8009000F == dwLastErr) // Object already exists. { BeginAction("CryptAcquireContext() CRYPT_DELETEKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_DELETEKEYSET)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { ActionFailed(dwLastErr); return; } else { ActionSuccess(); } } } else return; } else { ActionSuccess(); } // Hold the handle and release when this function return. HCRYPTPROV_Holder holder(hCryptProv); // Create a hash object. BeginAction("CryptCreateHash()"); if(!CryptCreateHash(hCryptProv, CALG_MD5, 0, 0, &hHash)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } // Hash the password string. dwLength = lstrlen(szPassword); BeginAction("CryptHashData()"); if(!CryptHashData(hHash, (BYTE *) szPassword, dwLength, 0)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } // Create a block cipher session key based on the hash of the password. BeginAction("CryptDeriveKey()"); if(!CryptDeriveKey(hCryptProv, ulALG, hHash, CRYPT_EXPORTABLE, &hKey)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } //Encrypt Data with RC2 key: BYTE pData[1024] = "UsbToken: Encrypt Data with the derive key (des or rc4) /!\0"; DWORD dwLen = lstrlen((LPCTSTR) pData);//60; cout << "Data to be encrypted:" << endl; ShowData(pData, dwLen); //encrypt: BeginAction("CryptEncrypt()"); if(!CryptEncrypt(hKey, NO_HASH, LAST_DATA, 0, pData, &dwLen, 1024)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after encrypted:" << endl; ShowData(pData, dwLen); } //Decrypt Data with RC2 key: BeginAction("CryptDecrypt()"); if(!CryptDecrypt(hKey, NO_HASH, LAST_DATA, 0, pData, &dwLen)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after decrypted:" << endl; ShowData(pData, dwLen); } }
more... Code: void GetProvParam(void) { HCRYPTPROV hCryptProv = NULL; cout << endl << "Test CSP: " << TEST_CSP_NAME << endl << endl; BeginAction("CryptAcquireContext()"); if(!CryptAcquireContext(&hCryptProv, NULL, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } // Hold the handle and release when this function return. HCRYPTPROV_Holder holder(hCryptProv); //Enum algs those CSP support: DWORD i = 0; CHAR szName[100] = {0}; // Often allocated dynamically BYTE pbData[1000] = {0}; // Often allocated dynamically DWORD cbData = 0; DWORD dwFlags = 0; CHAR *pszAlgType = NULL; // Enumerate the supported algorithms. cout<< " ALG_ID KeyLen Type Name" << endl << "----------------------------------------------------------------" << endl; for(i=0 ; ; ++i) { // Set the CRYPT_FIRST flag the first time through the loop. if(i == 0) { dwFlags = CRYPT_FIRST; } else { dwFlags = 0; } // Retrieve information about an algorithm. cbData = 1000; if(!CryptGetProvParam(hCryptProv, PP_ENUMALGS, pbData, &cbData, dwFlags)) { DWORD dwLastErr = GetLastError(); if(ERROR_NO_MORE_ITEMS == dwLastErr) { // Exit the loop. break; } else { ; return; } } // Extract algorithm information from the 'pbData' buffer. PROV_ENUMALGS* pEnum = (PROV_ENUMALGS*)pbData; // Determine the algorithm type. switch(GET_ALG_CLASS(pEnum->aiAlgid)) { case ALG_CLASS_DATA_ENCRYPT: pszAlgType = "Encrypt "; break; case ALG_CLASS_HASH: pszAlgType = "Hash "; break; case ALG_CLASS_KEY_EXCHANGE: pszAlgType = "Exchange "; break; case ALG_CLASS_SIGNATURE: pszAlgType = "Signature "; break; default: pszAlgType = "Unknown "; } // Print information about the algorithm. // printf("Algid:%8.8xh, Bits:%-4d, Type:%s, NameLen:%-2d, Name:%s\n", // aiAlgid, dwBits, pszAlgType, dwNameLen, szName // ); // cout<< "ALG_ID: " << std::setfill('0') << std::setw(8) << hex << pEnum->aiAlgid // << "KeyLen: " << std::setfill(' ') << std::setw(4) << dec << pEnum->dwBitLen // << "Type : " << pszAlgType // << "Name : " << pEnum->szName // << endl; cout<< " " << std::setfill('0') << std::setw(8) << hex << pEnum->aiAlgid << " " << std::setfill(' ') << std::setw(4) << dec << pEnum->dwBitLen << " " << pszAlgType << " " << pEnum->szName << endl; } //ActionSuccess(); }
more... Code: void CRSA::TestRSA(void) { HCRYPTPROV hCryptProv = NULL; cout << endl << "Test CSP: " << TEST_CSP_NAME << endl << endl; // Create a keyset(aka container), if the keyset already exists, // delete it and re-create it. BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { DWORD dwLastErr = GetLastError(); ActionFailed(dwLastErr); if(0x8009000F == dwLastErr) // Object already exists. { BeginAction("CryptAcquireContext() CRYPT_DELETEKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_DELETEKEYSET)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { ActionFailed(dwLastErr); return; } else { ActionSuccess(); } } } else return; } else { ActionSuccess(); } // Hold the handle and release when this function return. HCRYPTPROV_Holder holder(hCryptProv); HCRYPTKEY hKey; BeginAction("CryptGenKey()"); if(!CryptGenKey(hCryptProv, AT_KEYEXCHANGE, 0, &hKey)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } BYTE pData[DATALEN] = {0}; unsigned long ulDataLen = DATALEN; DWORD ulEncryptedLen = ulDataLen; BYTE *pOut = NULL; for(int i = 0; i < DATALEN; i++) { pData[i] = i % 255; } cout << "Data to be encrypt:" << endl; ShowData(pData, ulDataLen); BeginAction("CryptEncrypt()"); if(!CryptEncrypt(hKey, 0, TRUE, 0, NULL, &ulEncryptedLen, ulDataLen)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } pOut = new BYTE[ulEncryptedLen]; memset(pOut, 0, ulEncryptedLen); memcpy(pOut, pData, ulDataLen); DWORD ulTemp = ulDataLen; ulDataLen = ulEncryptedLen; ulEncryptedLen = ulTemp; BeginAction("CryptEncrypt()"); if(!CryptEncrypt(hKey, 0, TRUE, 0, pOut, &ulEncryptedLen, ulDataLen)) { delete[] pOut; pOut = NULL; ActionFailed(GetLastError()); return; } else { ActionSuccess(); // for(DWORD i = 0; i < ulEncryptedLen; i++) // { // printf("%d=%d, ", i, pOut[i]); // } cout << "Data encrypted:" << endl; ShowData(pOut, ulEncryptedLen); } BeginAction("CryptDecrypt()"); if(!CryptDecrypt(hKey, 0, TRUE, 0, pOut, &ulEncryptedLen)) { delete[] pOut; pOut = 0; ActionFailed(GetLastError()); return; } else { ActionSuccess(); // for(DWORD i = 0; i < ulEncryptedLen; i++) // { // if(pOut[i] != i % 255) // { // printf("\n%d=error!", i); // } // else // { // printf("%d=%d, ", i, pOut[i]); // } // } cout << "Data to decrypted:" << endl; ShowData(pOut, ulEncryptedLen); } if(0 != memcmp(pData, pOut, ulEncryptedLen)) { delete[] pOut; pOut = NULL; //printf("\n....RSA key Encryption and Decryption Failed!....\n"); cout << "Data not equal, encrypt/decrypt failed." << endl; } }
more... Code: void SysKeyTest::TestKey(DWORD ulALG) { HCRYPTPROV hCryptProv = NULL; cout << endl << "Test CSP: " << TEST_CSP_NAME << endl << endl; // Create a keyset(aka container), if the keyset already exists, // delete it and re-create it. BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { DWORD dwLastErr = GetLastError(); ActionFailed(dwLastErr); if(0x8009000F == dwLastErr) // Object already exists. { BeginAction("CryptAcquireContext() CRYPT_DELETEKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_DELETEKEYSET)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); BeginAction("CryptAcquireContext() CRYPT_NEWKEYSET"); if(!CryptAcquireContext(&hCryptProv, CONTAINER, TEST_CSP_NAME, PROV_RSA_FULL, CRYPT_NEWKEYSET)) { ActionFailed(dwLastErr); return; } else { ActionSuccess(); } } } else return; } else { ActionSuccess(); } // Hold the handle and release when this function return. HCRYPTPROV_Holder holder(hCryptProv); HCRYPTKEY hKey = NULL; BeginAction("CryptGenKey()"); if (!CryptGenKey(hCryptProv, ulALG, /*CRYPT_EXPORTABLE*/0, &hKey))//RC4/DES are similar!!!!!!!!!!!!!!!!!!! { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } //Encrypt Data with a key: #define BUF_SIZE 1024 BYTE pData[BUF_SIZE] = "UsbToken: Encrypt Data with the derive key (des or rc4) /!\0"; BYTE pOrinData[BUF_SIZE] = {0}; DWORD dwLen = 60; DWORD dwRetLen = dwLen; memcpy(pOrinData, pData, dwLen); cout << "Data to be encrypted:" << endl; ShowData(pData, dwLen); //encrypt, first get size. BeginAction("CryptEncrypt()"); if(!CryptEncrypt(hKey, NO_HASH, LAST_DATA, 0, NULL, &dwRetLen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } //Get encrypted value: BeginAction("CryptEncrypt()"); if(!CryptEncrypt(hKey, NO_HASH, LAST_DATA, 0, pData, &dwLen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after encrypted:" << endl; ShowData(pData, dwLen); } //Decrypt Data with a key: BeginAction("CryptDecrypt()"); if(!CryptDecrypt(hKey, NO_HASH, LAST_DATA, 0, pData, &dwLen)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after decrypted:" << endl; ShowData(pData, dwLen); } if(0 != memcmp(pData, pOrinData, dwLen)) { cout << "Data not equal, encrypt/decrypt failed." << endl; } ////////////////////////////////////////////////////////////////////////// // encrypt dulplicate dwLen = 60; memcpy(pData, pOrinData, dwLen); BYTE buf[1024] = {0}; memcpy(buf, pOrinData, dwLen); dwRetLen = dwLen/2; BeginAction("CryptEncrypt() first block"); DWORD enclen = dwLen/2; if(!CryptEncrypt(hKey, NO_HASH, FALSE, 0, NULL, &enclen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } //Get encrypted value: BeginAction("Get the first block result"); enclen = dwLen/2; if(!CryptEncrypt(hKey, NO_HASH, FALSE, 0, buf, &enclen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after encrypted:" << endl; ShowData(buf, enclen); } BeginAction("CryptEncrypt() second block"); if(!CryptEncrypt(hKey, NO_HASH, TRUE, 0, NULL, &dwRetLen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); } //Get encrypted value: BeginAction("Get the second block result"); dwRetLen = dwLen/2; memcpy(buf + enclen, pData + dwLen/2, dwRetLen); if(!CryptEncrypt(hKey, NO_HASH, TRUE, 0, buf + enclen, &dwRetLen, BUF_SIZE)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after encrypted:" << endl; ShowData(buf + enclen, dwRetLen); } //Decrypt Data with a key: // the first block BeginAction("CryptDecrypt() the first block"); dwLen = enclen + dwRetLen; enclen = 16; if(!CryptDecrypt(hKey, NO_HASH, FALSE, 0, buf, &enclen)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after decrypted:" << endl; ShowData(buf, enclen); } BeginAction("CryptDecrypt() the second block"); dwRetLen = dwLen - 16; if(!CryptDecrypt(hKey, NO_HASH, TRUE, 0, buf + 16, &dwRetLen)) { ActionFailed(GetLastError()); return; } else { ActionSuccess(); cout << "Data after decrypted:" << endl; ShowData(buf + 16, dwRetLen); } memcpy(buf + enclen, buf + 16, dwRetLen); if (dwRetLen + enclen != 60) { cout << "Data not equal, encrypt/decrypt failed." << endl; } cout << "the whole decrypt data is" << endl; ShowData(buf, dwRetLen + enclen); if(0 != memcmp(buf, pOrinData, dwRetLen + enclen)) { cout << "Data not equal, encrypt/decrypt failed." << endl; } }