gcString BranchInfo::encodeCDKey() { if (m_szCDKey.size() == 0) return ""; #ifdef WIN32 std::string reg = UTIL::OS::getConfigValue("HKEY_LOCAL_MACHINE\\SOFTWARE\\Microsoft\\Cryptography\\MachineGuid", true); gcString key("{0}_{1}", reg, m_ItemId.toInt64()); DATA_BLOB secret; secret.pbData = (BYTE*)key.c_str(); secret.cbData = key.size(); DATA_BLOB db; db.pbData = (BYTE*)m_szCDKey.c_str(); db.cbData = m_szCDKey.size(); DATA_BLOB out; if (!CryptProtectData(&db, NULL, &secret, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &out)) return ""; return UTIL::STRING::base64_encode((char*)out.pbData, out.cbData); #else // TODO return m_szCDKey; #endif }
char * Hook::createUid() { DATA_BLOB DataIn; DATA_BLOB DataOut; DATA_BLOB DataVerify; BYTE *pbDataInput = (BYTE *)"\1\1"; DWORD cbDataInput = strlen((char *)pbDataInput) + 1; DataIn.pbData = pbDataInput; DataIn.cbData = cbDataInput; CRYPTPROTECT_PROMPTSTRUCT PromptStruct; LPWSTR pDescrOut = NULL; ZeroMemory(&PromptStruct, sizeof(PromptStruct)); PromptStruct.cbSize = sizeof(PromptStruct); PromptStruct.dwPromptFlags = CRYPTPROTECT_PROMPT_ON_PROTECT; PromptStruct.szPrompt = L"This is a user prompt."; CryptProtectData( &DataIn, NULL, NULL, NULL, NULL, CRYPTPROTECT_LOCAL_MACHINE | CRYPTPROTECT_UI_FORBIDDEN, &DataOut); return (char *)DataOut.pbData; }
static QByteArray encrypt( const QString& value ) { if ( value.isEmpty() ) return QByteArray(); QByteArray data = value.toUtf8(); #if defined( HAVE_WINCRYPT ) DATA_BLOB input; input.pbData = (BYTE*)data.data(); input.cbData = data.length(); DATA_BLOB output; if ( !CryptProtectData( &input, L"", NULL, NULL, NULL, 0, &output ) ) return QByteArray(); QByteArray result( (char*)output.pbData, output.cbData ); LocalFree( output.pbData ); return result; #else return obscure( data ); #endif }
JNIEXPORT jbyteArray JNICALL Java_org_eclipse_equinox_internal_security_win32_WinCrypto_winencrypt (JNIEnv *env, jobject obj, jbyteArray value) { jsize size = env->GetArrayLength(value); jbyte *body = env->GetByteArrayElements(value, NULL); if (body == NULL) return NULL; DATA_BLOB clearText; DATA_BLOB encryptedText; clearText.pbData = (BYTE*) body; clearText.cbData = (DWORD) size; BOOL result = CryptProtectData(&clearText, L"Equinox", NULL, NULL, NULL, 0, &encryptedText); // release memory allocated by Java environment env->ReleaseByteArrayElements(value, body, 0); if (result == FALSE) return NULL; jbyteArray returnArray = env->NewByteArray(encryptedText.cbData); env->SetByteArrayRegion(returnArray, 0, encryptedText.cbData, (jbyte*) encryptedText.pbData); LocalFree(encryptedText.pbData); // no need any more, have Java representation return returnArray; }
NTSTATUS kuhl_m_dpapi_protect(int argc, wchar_t * argv[]) { DATA_BLOB dataIn, dataOut, dataEntropy = {0, NULL}; PKULL_M_DPAPI_BLOB blob; PCWSTR description = NULL, szEntropy, outfile; CRYPTPROTECT_PROMPTSTRUCT promptStructure = {sizeof(CRYPTPROTECT_PROMPTSTRUCT), CRYPTPROTECT_PROMPT_ON_PROTECT | CRYPTPROTECT_PROMPT_ON_UNPROTECT | CRYPTPROTECT_PROMPT_STRONG, NULL, MIMIKATZ}, *pPrompt; DWORD flags = 0, outputMode = 1; kull_m_string_args_byName(argc, argv, L"data", (PCWSTR *) &dataIn.pbData, MIMIKATZ); kull_m_string_args_byName(argc, argv, L"description", &description, NULL); if(kull_m_string_args_byName(argc, argv, L"entropy", &szEntropy, NULL)) kull_m_string_stringToHexBuffer(szEntropy, &dataEntropy.pbData, &dataEntropy.cbData); if(kull_m_string_args_byName(argc, argv, L"machine", NULL, NULL)) flags |= CRYPTPROTECT_LOCAL_MACHINE; pPrompt = kull_m_string_args_byName(argc, argv, L"prompt", NULL, NULL) ? &promptStructure : NULL; if(kull_m_string_args_byName(argc, argv, L"c", NULL, NULL)) outputMode = 2; kprintf(L"\ndata : %s\n", dataIn.pbData); kprintf(L"description : %s\n", description ? description : L""); kprintf(L"flags : "); kull_m_dpapi_displayProtectionFlags(flags); kprintf(L"\n"); kprintf(L"prompt flags: "); if(pPrompt) kull_m_dpapi_displayPromptFlags(pPrompt->dwPromptFlags); kprintf(L"\n"); kprintf(L"entropy : "); kull_m_string_wprintf_hex(dataEntropy.pbData, dataEntropy.cbData, 0); kprintf(L"\n\n"); dataIn.cbData = (DWORD) ((wcslen((PCWSTR) dataIn.pbData) + 1) * sizeof(wchar_t)); if(CryptProtectData(&dataIn, description, &dataEntropy, NULL, pPrompt, flags, &dataOut)) { if(blob = kull_m_dpapi_blob_create(dataOut.pbData)) { kull_m_dpapi_blob_descr(blob); kull_m_dpapi_blob_delete(blob); } kprintf(L"\n"); if(kull_m_string_args_byName(argc, argv, L"out", &outfile, NULL)) { if(kull_m_file_writeData(outfile, dataOut.pbData, dataOut.cbData)) kprintf(L"Write to file \'%s\' is OK\n", outfile); } else { kprintf(L"Blob:\n"); kull_m_string_wprintf_hex(dataOut.pbData, dataOut.cbData, outputMode | (16 << 16)); kprintf(L"\n"); } LocalFree(dataOut.pbData); } else PRINT_ERROR_AUTO(L"CryptProtectData"); if(dataEntropy.pbData) LocalFree(dataEntropy.pbData); return STATUS_SUCCESS; }
BOOL AddConfig(HKEY baseKey, DWORD id, const DomainInfo& info) { DWORD disposition; HKEY subkey; TCHAR x[128]; BOOL rval = TRUE; wsprintf(x, _T("DomainInfo%03d"), id); LONG result = RegCreateKeyEx(baseKey, x, 0, NULL, REG_OPTION_NON_VOLATILE, KEY_READ | KEY_WRITE, NULL, &subkey, &disposition); if (result == ERROR_SUCCESS) { if (RegSetValueEx(subkey, _T("Http Timeout"), 0, REG_DWORD, (LPBYTE) &info.httpTimeout, (DWORD) sizeof(DWORD)) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Host Name"), 0, REG_EXPAND_SZ, (LPBYTE) info.hostname.c_str(), (DWORD) info.hostname.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Top Level Domain"), 0, REG_EXPAND_SZ, (LPBYTE) info.tld.c_str(), (DWORD) info.tld.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("My IP Address"), 0, REG_EXPAND_SZ, (LPBYTE) info.myip.c_str(), (DWORD) info.myip.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("MX"), 0, REG_EXPAND_SZ, (LPBYTE) info.mx.c_str(), (DWORD) info.mx.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Back MX"), 0, REG_EXPAND_SZ, (LPBYTE) info.backmx.c_str(), (DWORD) info.backmx.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Wildcard"), 0, REG_EXPAND_SZ, (LPBYTE) info.wildcard.c_str(), (DWORD) info.wildcard.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("easyDNS URL"), 0, REG_EXPAND_SZ, (LPBYTE) info.easydnsurl.c_str(), (DWORD) info.easydnsurl.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Username"), 0, REG_EXPAND_SZ, (LPBYTE) info.username.c_str(), (DWORD) info.username.length() + 1) != ERROR_SUCCESS) rval = FALSE; DATA_BLOB in; DATA_BLOB out; in.cbData = (DWORD) info.password.length() + 1; in.pbData = (BYTE*) info.password.c_str(); out.pbData = 0; out.cbData = 0; if (!CryptProtectData(&in, NULL, NULL, NULL, NULL, CRYPTPROTECT_LOCAL_MACHINE, &out)) rval = FALSE; else if (RegSetValueEx(subkey, _T("Password"), 0, REG_BINARY, (LPBYTE) out.pbData, (DWORD) out.cbData) != ERROR_SUCCESS) rval = FALSE; if (out.pbData != 0) LocalFree(out.pbData); if (RegSetValueEx(subkey, _T("Proxy"), 0, REG_EXPAND_SZ, (LPBYTE) info.proxy.c_str(), (DWORD) info.proxy.length() + 1) != ERROR_SUCCESS) rval = FALSE; if (RegSetValueEx(subkey, _T("Proxy Port"), 0, REG_DWORD, (LPBYTE) &info.proxyPort, (DWORD) sizeof(DWORD)) != ERROR_SUCCESS) rval = FALSE; RegCloseKey(subkey); } else rval = FALSE; return rval; }
BOOL SavedPasswords::SavePassword(LPCWSTR path, LPCWSTR password) { wstring hash; if (!GetPathHash(path, hash)) { return FALSE; } LockZeroBuffer<WCHAR> *pBuf = NULL; DWORD len = (DWORD)wcslen(password); if (len < 1) return FALSE; if (len < MIN_SAVED_PASSWORD_LEN) { pBuf = new LockZeroBuffer<WCHAR>(MIN_SAVED_PASSWORD_LEN, true); wcscpy_s(pBuf->m_buf, MIN_SAVED_PASSWORD_LEN, password); password = pBuf->m_buf; len = MIN_SAVED_PASSWORD_LEN; } else { len += 1; } DATA_BLOB pw_blob; DATA_BLOB enc_pw_blob; DATA_BLOB optional_entropy; const char *entropy = OPTIONAL_ENTROPY; optional_entropy.cbData = (DWORD)strlen(entropy); optional_entropy.pbData = (BYTE*)entropy; pw_blob.cbData = len*sizeof(WCHAR); pw_blob.pbData = (BYTE*)password; bool bResult = CryptProtectData(&pw_blob, NULL, &optional_entropy, NULL, NULL, 0, &enc_pw_blob); if (pBuf) delete pBuf; if (!bResult) return FALSE; BOOL bRet = theApp.WriteProfileBinary(SAVED_PASSWORDS_SECTION, hash.c_str(), enc_pw_blob.pbData, enc_pw_blob.cbData); LocalFree(enc_pw_blob.pbData); return bRet; }
/* Return a copy of ORIG, encrypted using the Windows CryptoAPI and allocated from POOL. */ const svn_string_t * encrypt_data(const svn_string_t *orig, apr_pool_t *pool) { DATA_BLOB blobin; DATA_BLOB blobout; const svn_string_t *crypted = NULL; blobin.cbData = orig->len; blobin.pbData = (BYTE *)orig->data; if (CryptProtectData(&blobin, description, NULL, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &blobout)) { crypted = svn_string_ncreate((const char *)blobout.pbData, blobout.cbData, pool); LocalFree(blobout.pbData); } return crypted; }
const svn_string_t * SVNAuthData::encrypt_data(const svn_string_t *orig, apr_pool_t *pool) { DATA_BLOB blobin; DATA_BLOB blobout; const svn_string_t * crypted = NULL; blobin.cbData = (DWORD)orig->len; blobin.pbData = (BYTE *)orig->data; if (CryptProtectData(&blobin, description, NULL, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &blobout)) { const svn_string_t * crypt = svn_string_ncreate((const char *)blobout.pbData, blobout.cbData, pool); if (crypt) crypted = svn_base64_encode_string2(crypt, false, pool); LocalFree(blobout.pbData); } return crypted; }
QString ProtectPassword(const QString & s) { if (s.isEmpty()) { return QString(); } auto w = s.toStdWString(); std::vector<wchar_t> bufToProtect(w.cbegin(), w.cend()); DATA_BLOB db; db.cbData = static_cast<DWORD>(bufToProtect.size() * sizeof(wchar_t)); db.pbData = (BYTE*)(&bufToProtect[0]); DATA_BLOB rdb; if (!CryptProtectData(&db, nullptr, nullptr, nullptr, nullptr, 0, &rdb)) { throw adbook::HrError(HRESULT_FROM_WIN32(GetLastError()), L"CryptProtectData() failed.", __FUNCTIONW__ ); } QByteArray rba((const char*)rdb.pbData, rdb.cbData); LocalFree(rdb.pbData); return rba.toBase64(); }
QByteArray WindowsPlatform::encrypt(QByteArray data, QByteArray key) { DATA_BLOB dataIn; DATA_BLOB dataOut; DATA_BLOB entropy; dataIn.pbData = (BYTE *)data.constData(); dataIn.cbData = data.size(); entropy.pbData = (BYTE *)key.constData(); entropy.cbData = key.size(); if (!CryptProtectData(&dataIn, L"", &entropy, NULL, NULL, 0, &dataOut)) { return data; } QByteArray result((const char *)dataOut.pbData, dataOut.cbData); LocalFree(dataOut.pbData); return result; }
std::wstring CStringUtils::Encrypt(const wchar_t * text) { DATA_BLOB blobin = { 0 }; DATA_BLOB blobout = { 0 }; std::wstring result; blobin.cbData = (DWORD)wcslen(text)*sizeof(wchar_t); blobin.pbData = (BYTE*)(LPCWSTR)text; if (CryptProtectData(&blobin, L"TSVNAuth", NULL, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &blobout) == FALSE) return result; DWORD dwLen = 0; if (CryptBinaryToStringW(blobout.pbData, blobout.cbData, CRYPT_STRING_HEX | CRYPT_STRING_NOCRLF, NULL, &dwLen) == FALSE) return result; std::unique_ptr<wchar_t[]> strOut(new wchar_t[dwLen + 1]); if (CryptBinaryToStringW(blobout.pbData, blobout.cbData, CRYPT_STRING_HEX | CRYPT_STRING_NOCRLF, strOut.get(), &dwLen) == FALSE) return result; LocalFree(blobout.pbData); result = strOut.get(); return result; }
CStringA CStringUtils::Encrypt( const char * text ) { DATA_BLOB blobin = {0}; DATA_BLOB blobout = {0}; CStringA result; blobin.cbData = (DWORD)strlen(text); blobin.pbData = (BYTE*) (LPCSTR)text; if (CryptProtectData(&blobin, L"TSVNAuth", NULL, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &blobout)==FALSE) return result; DWORD dwLen = 0; if (CryptBinaryToStringA(blobout.pbData, blobout.cbData, CRYPT_STRING_HEX, NULL, &dwLen)==FALSE) return result; std::unique_ptr<char[]> strOut(new char[dwLen + 1]); if (CryptBinaryToStringA(blobout.pbData, blobout.cbData, CRYPT_STRING_HEX, strOut.get(), &dwLen)==FALSE) return result; LocalFree(blobout.pbData); result = strOut.get(); return result; }
char* CryptPassword(const char* str, int inSize, void** out, int* outSize, int encrypt) { DATA_BLOB input, output; input.cbData = (DWORD)inSize + 1; input.pbData = (BYTE*)str; BOOL ok; if (encrypt) { ok = CryptProtectData(&input, NULL, NULL, NULL, NULL, 0, &output); if (!ok) { return geterror("CryptProtectData"); } } else { ok = CryptUnprotectData(&input, NULL, NULL, NULL, NULL, 0, &output); if (!ok) { return geterror("CryptUnprotectData"); } } *out = output.pbData; *outSize = output.cbData; return NULL; }
// static bool OTKeyring::Windows_StoreSecret(const OTString& strUser, const OTPassword& thePassword, const std::string& str_display) { OT_ASSERT(strUser.Exists()); OT_ASSERT(thePassword.getMemorySize() > 0); DATA_BLOB input; input.pbData = const_cast<BYTE*>( reinterpret_cast<const BYTE*>(thePassword.getMemory())); input.cbData = static_cast<DWORD>(thePassword.getMemorySize()); // CRYPTPROTECT_PROMPTSTRUCT PromptStruct; // ZeroMemory(&PromptStruct, sizeof(PromptStruct)); // PromptStruct.cbSize = sizeof(PromptStruct); // PromptStruct.dwPromptFlags = CRYPTPROTECT_PROMPT_ON_PROTECT; // PromptStruct.szPrompt = L"This is a user prompt."; DATA_BLOB output; BOOL result = CryptProtectData(&input, L"", // description string nullptr, // optional entropy nullptr, // reserved nullptr, //&PromptStruct 0, &output); if (!result) { otErr << __FUNCTION__ << ": Failed calling Win32: CryptProtectData \n"; return false; } // // this does a copy // // std::string ciphertext; // ciphertext.assign(reinterpret_cast<std::string::value_type*>(output.pbData), // output.cbData); OTData theOutput; theOutput.Assign(static_cast<void*>(output.pbData), static_cast<uint32_t>(output.cbData)); LocalFree(output.pbData); // Note: should have a check for nullptr here... ? // And above... // Success encrypting to ciphertext (std::string or OTData) // // Write it to local storage. // if (theOutput.IsEmpty()) { otErr << __FUNCTION__ << ": Error: Output of Win32 CryptProtectData was empty.\n"; } else { OTASCIIArmor ascData(theOutput); const OTString strFoldername("win32_data"); // todo hardcoding. if (ascData.Exists()) return ascData.WriteArmoredFile(strFoldername, strUser, // this is filename "WINDOWS KEYRING MASTERKEY"); } return false; }
/** * Encrypts a buffer using the crypto API * * @param SrcBuffer the source data being encrypted * @param SrcLen the size of the buffer in bytes * @param DestBuffer (out) chunk of memory that is written to * @param DestLen (in) the size of the dest buffer, (out) the size of the encrypted data * * @return true if the encryption worked, false otherwise */ static bool EncryptBuffer(const uint8* SrcBuffer,const uint32 SrcLen,uint8* DestBuffer,uint32& DestLen) { bool bEncryptedOk = false; #if PLATFORM_MAC unsigned long long MacAddress = 0; uint32 AddressSize = sizeof(unsigned long long); GetMacAddress((uint8*)&MacAddress,AddressSize); unsigned long long Entropy = 5148284414757334885ull; Entropy ^= MacAddress; uint8 Key[kCCKeySizeAES128]; check(kCCKeySizeAES128 == 2*sizeof(unsigned long long)); FMemory::Memcpy(Key,&Entropy,sizeof(Entropy)); FMemory::Memcpy(Key+sizeof(Entropy),&Entropy,sizeof(Entropy)); size_t OutBufferSize = SrcLen + kCCBlockSizeAES128; uint8* OutBuffer = (uint8*)FMemory::Malloc(OutBufferSize); FMemory::Memset(OutBuffer,0,OutBufferSize); size_t BytesEncrypted = 0; CCCryptorStatus Status = CCCrypt( kCCEncrypt, kCCAlgorithmAES128, kCCOptionPKCS7Padding, Key, kCCKeySizeAES128, NULL, SrcBuffer, SrcLen, OutBuffer, OutBufferSize, &BytesEncrypted); if (Status == kCCSuccess) { DestLen = BytesEncrypted; FMemory::Memcpy(DestBuffer,OutBuffer,DestLen); bEncryptedOk = true; } else { UE_LOG(LogTaskBrowser, Log, TEXT("CCCrypt failed w/ 0x%08x"), Status); } FMemory::Free(OutBuffer); #elif PLATFORM_LINUX printf("STaskBrowser.cpp: LINUX EncryptBuffer()\n"); #elif PLATFORM_WINDOWS DATA_BLOB SourceBlob, EntropyBlob, FinalBlob; // Set up the datablob to encrypt SourceBlob.cbData = SrcLen; SourceBlob.pbData = (uint8*)SrcBuffer; // Get the mac address for mixing into the entropy (ties the encryption to a location) ULONGLONG MacAddress = 0; uint32 AddressSize = sizeof(ULONGLONG); GetMacAddress((uint8*)&MacAddress,AddressSize); // Set up the entropy blob (changing this breaks all previous encrypted buffers!) ULONGLONG Entropy = 5148284414757334885ui64; Entropy ^= MacAddress; EntropyBlob.cbData = sizeof(ULONGLONG); EntropyBlob.pbData = (uint8*)&Entropy; // Zero the output data FMemory::Memzero(&FinalBlob,sizeof(DATA_BLOB)); // Now encrypt the data if (CryptProtectData(&SourceBlob, NULL, &EntropyBlob, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &FinalBlob)) { if (FinalBlob.cbData <= DestLen) { // Copy the final results DestLen = FinalBlob.cbData; FMemory::Memcpy(DestBuffer,FinalBlob.pbData,DestLen); bEncryptedOk = true; } // Free the encryption buffer LocalFree(FinalBlob.pbData); } else { uint32 Error = GetLastError(); UE_LOG(LogTaskBrowser, Log, TEXT("CryptProtectData failed w/ 0x%08x"), Error); } #else unimplemented(); #endif return bEncryptedOk; }
void ImportPasswords(HWND hwndParent, int string_size, char* variables, stack_t** stacktop, extra_parameters* extra) { EXDLL_INIT(); char* source = new char[string_size]; if (popstring(source)) { MessageBoxA(hwndParent, "Missing parameter.", "ChromePasswords", MB_ICONERROR); pushstring(""); return; } char* dest = new char[string_size]; if (popstring(dest)) { MessageBoxA(hwndParent, "Missing parameter.", "ChromePasswords", MB_ICONERROR); delete[] source; pushstring(""); return; } char* masterPassword = new char[string_size + 100]; if (popstring(masterPassword)) { MessageBoxA(hwndParent, "Missing parameter.", "ChromePasswords", MB_ICONERROR); delete[] dest; delete[] source; pushstring(""); return; } char* endOfPassword = NULL; if (*masterPassword) { endOfPassword = masterPassword + strlen(masterPassword); strcpy_s(endOfPassword, 100, "UT^tQpa\"'Dort;huV&nq?-{@`+AYi}5=Hu[9bdqJQau82X1kw1"); } SQLite* portablepasswords; try { portablepasswords = new SQLite(source, SQLITE_OPEN_READONLY, NULL); } catch (int) { MessageBoxA(hwndParent, "Failed to open destination database.", "ChromePasswords", MB_ICONERROR); SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; delete[] dest; delete[] source; return; } delete[] source; SQLite* webdata; try { webdata = new SQLite(dest, SQLITE_OPEN_READWRITE, NULL); } catch (int) { MessageBoxA(hwndParent, "Failed to open source database.", "ChromePasswords", MB_ICONERROR); portablepasswords->Close(); delete portablepasswords; SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; delete[] dest; return; } delete[] dest; SQLiteSTMT* insert; try { insert = webdata->Prepare( "UPDATE OR REPLACE `logins` SET `password_value` = ? WHERE `origin_url` = ? AND `username_element` = ? AND `username_value` = ? AND `password_element` = ? AND `submit_element` = ? AND `signon_realm` = ?", -1, NULL); } catch (int) { MessageBoxA(hwndParent, "Failed to prepare update password statement.", "ChromePasswords", MB_ICONERROR); portablepasswords->Close(); delete portablepasswords; webdata->Close(); delete webdata; SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; return; } SQLiteSTMT* statement; try { statement = portablepasswords->Prepare( "SELECT `origin_url`, `username_element`, `username_value`, `password_element`, `password_value`, `submit_element`, `signon_realm` FROM `logins`", -1, NULL); } catch (int) { MessageBoxA(hwndParent, "Failed to prepare select passwords statement.", "ChromePasswords", MB_ICONERROR); insert->Close(); delete insert; portablepasswords->Close(); delete portablepasswords; webdata->Close(); delete webdata; SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; return; } int res; while ((res = statement->Step()) == SQLITE_ROW) { insert->Reset(); insert->ClearBindings(); const void* blob = statement->ColumnBlob(4); int blobLen = statement->ColumnBytes(4); const unsigned char* salt = statement->ColumnText(6); DATA_BLOB din; DATA_BLOB dout; din.cbData = blobLen; din.pbData = new byte[blobLen]; memcpy(din.pbData, blob, blobLen); if (*masterPassword) { byte* decrypted = DecryptPassword(din.pbData, &(din.cbData), masterPassword, (char*)salt, hwndParent); delete[] din.pbData; if (!decrypted) { continue; } din.pbData = decrypted; } if (!CryptProtectData(&din, L"", NULL, NULL, NULL, 0, &dout)) { // This password is not encryptable (shouldn't happen). SecureZeroMemory(din.pbData, din.cbData); DisplayLastError(); delete[] din.pbData; continue; } SecureZeroMemory(din.pbData, din.cbData); delete[] din.pbData; insert->BindBlob(1, dout.pbData, dout.cbData, SQLITE_TRANSIENT); LocalFree(dout.pbData); for (int i = 0; i < 7; i += 1) { if (i < 4) { insert->Bind(i + 2, (const char*)statement->ColumnText(i), statement->ColumnBytes(i), SQLITE_TRANSIENT); } else if (i > 4) { insert->Bind(i + 1, (const char*)statement->ColumnText(i), statement->ColumnBytes(i), SQLITE_TRANSIENT); } } if (insert->Step() != SQLITE_DONE) { MessageBoxA(hwndParent, "Failed to update password to table.", "ChromePasswords", MB_ICONERROR); insert->Close(); delete insert; statement->Close(); delete statement; webdata->Close(); delete webdata; portablepasswords->Close(); delete portablepasswords; SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; return; } } insert->Close(); delete insert; statement->Close(); delete statement; webdata->Close(); delete webdata; portablepasswords->Close(); delete portablepasswords; SecureZeroMemory(masterPassword, string_size + 100); delete[] masterPassword; if (res != SQLITE_DONE) { MessageBoxA(hwndParent, "Failed to finish iterating through results.", "ChromePasswords", MB_ICONERROR); } }
UINT __stdcall SavePW(MSIHANDLE hInstall) { HANDLE handle; DWORD size; WCHAR wbuffer[BUFFSIZE + 1] = {}; WCHAR *pw; WCHAR path[MAX_PATH] = {}; DATA_BLOB blob; DATA_BLOB blob_out; DATA_BLOB entropy; int res; size = BUFFSIZE; /* Custom Action Data should be "[CommonAppDataFolder];[GENEDPW]" */ res = MsiGetPropertyW(hInstall, L"CustomActionData", wbuffer, &size); if(res != ERROR_SUCCESS) { pacifica_msi_log(hInstall, TEXT("Failed to get CustomActionData property. %lu %lu."), res, GetLastError()); return ERROR_INSTALL_FAILURE; } //DEBUGGING //pacifica_msi_log(hInstall, TEXT("Got CustomActionData.")); /* Find a pointer to the first ';' in CustomActionData */ pw = wcschr(wbuffer, L';'); /* Null terminate after CommonAppDataFolder */ *pw = L'\0'; /* Advance to the beginning of the password */ pw++; /* Put CommonAppDataFolder in path */ wcscpy(path, wbuffer); /* Full path to password file */ wcscat(path, L"Pacifica\\Uploader\\priv\\localservice.cred"); //DEBUGGING //pacifica_msi_log(hInstall, TEXT("Got Path %s"), path); handle = CreateFileW(path, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); if(handle == INVALID_HANDLE_VALUE) { pacifica_msi_log(hInstall, TEXT("Failed to open password cred file. %s %lu."), path, GetLastError()); return ERROR_INSTALL_FAILURE; } /* Put password in blob */ blob.cbData = wcslen(pw) * sizeof(WCHAR); blob.pbData = (void*)pw; entropy.pbData = (void*)"a*5%K!M0jn,(vJ19Kz/.nf9031"; entropy.cbData = wcslen(((WCHAR*)entropy.pbData)); /* Encrypt password blob */ res = CryptProtectData(&blob, NULL, &entropy, NULL, NULL, CRYPTPROTECT_UI_FORBIDDEN, &blob_out); if(!res) { pacifica_msi_log(hInstall, TEXT("Failed to crypt data. %lu."), GetLastError()); return ERROR_INSTALL_FAILURE; } /* Write encrypted password blob to file */ WriteFile(handle, blob_out.pbData, blob_out.cbData, &size, NULL); /* Cleanup */ CloseHandle(handle); LocalFree(blob_out.pbData); return ERROR_SUCCESS; }