PBYTE WINAPI HashVerifyLoadData( PHASHVERIFYCONTEXT phvctx ) { PBYTE pbRawData = NULL; HANDLE hFile; if ((hFile = OpenFileForReading(phvctx->pszPath)) != INVALID_HANDLE_VALUE) { LARGE_INTEGER cbRawData; DWORD cbBytesRead; if ( (GetFileSizeEx(hFile, &cbRawData)) && (pbRawData = malloc(cbRawData.LowPart + sizeof(DWORD))) && (ReadFile(hFile, pbRawData, cbRawData.LowPart, &cbBytesRead, NULL)) && (cbRawData.LowPart == cbBytesRead) ) { // When we allocated a block of memory for the file data, we // reserved a DWORD at the end for NULL termination and to serve as // the extra buffer needed by IsTextUTF8... *((UPDWORD)(pbRawData + cbRawData.LowPart)) = 0; // Prepare the data for the parser... phvctx->pszFileData = BufferToWStr(&pbRawData, cbRawData.LowPart); HashNormalizeString(phvctx->pszFileData); } CloseHandle(hFile); } return(pbRawData); }
int64 FileSystem::GetFileSize(const String& path) { HANDLE file = OpenFileForReading(path); if (file == INVALID_HANDLE_VALUE) return -1; int64 result = GetFileSizeInternal(file); CloseHandle(file); return result; }
byte* FileSystem::ReadFile(const String& path) { HANDLE file = OpenFileForReading(path); int64 size = GetFileSizeInternal(file); byte* buffer = spnew byte[size]; bool result = ReadFileInternal(file, buffer, size); if (!result) spdel buffer; CloseHandle(file); return result ? buffer : nullptr; }
bool FileSystem::ReadFile(const String& path, void* buffer, int64 size) { HANDLE file = OpenFileForReading(path); if (file == INVALID_HANDLE_VALUE) return false; if (size < 0) size = GetFileSizeInternal(file); bool result = ReadFileInternal(file, buffer, size); CloseHandle(file); return result; }
String FileSystem::ReadTextFile(const String& path) { HANDLE file = OpenFileForReading(path); int64 size = GetFileSizeInternal(file); String result(size, 0); bool success = ReadFileInternal(file, &result[0], size); if (success) { // Strip carriage returns result.erase(std::remove(result.begin(), result.end(), '\r'), result.end()); } CloseHandle(file); return success ? result : String(); }
VOID WINAPI WorkerThreadHashFile( PCOMMONCONTEXT pcmnctx, PCTSTR pszPath, PBOOL pbSuccess, PWHCTXEX pwhctx, PWHRESULTEX pwhres, PBYTE pbuffer, PFILESIZE pFileSize, LPARAM lParam, PCRITICAL_SECTION pUpdateCritSec, volatile ULONGLONG* pcbCurrentMaxSize #ifdef _TIMED , PDWORD pdwElapsed #endif ) { HANDLE hFile; *pbSuccess = FALSE; // If the worker thread is working so fast that the UI cannot catch up, // pause for a bit to let things settle down while (pcmnctx->cSentMsgs > pcmnctx->cHandledMsgs + 50) { Sleep(50); if (pcmnctx->status == PAUSED) WaitForSingleObject(pcmnctx->hUnpauseEvent, INFINITE); if (pcmnctx->status == CANCEL_REQUESTED) return; } // Indicate that we want lower-case results (TODO: make this an option) pwhctx->uCaseMode = WHFMT_LOWERCASE; if ((hFile = OpenFileForReading(pszPath)) != INVALID_HANDLE_VALUE) { ULONGLONG cbFileSize, cbFileRead = 0; DWORD cbBufferRead; UINT lastProgress = 0; UINT8 cInner = 0; if (GetFileSizeEx(hFile, (PLARGE_INTEGER)&cbFileSize)) { // The progress bar is updates only once every 4 buffer reads; if // the file is small enough that it requires only one such cycle, // then do not bother with updating the progress bar; this improves // performance when working with large numbers of small files BOOL bUpdateProgress = cbFileSize >= READ_BUFFER_SIZE * 4, bCurrentlyUpdating = FALSE; // If the caller provides a way to return the file size, then set // the file size; send a SETSIZE notification only if it was "big" if (pFileSize) { pFileSize->ui64 = cbFileSize; StrFormatKBSize(cbFileSize, pFileSize->sz, countof(pFileSize->sz)); if (cbFileSize > READ_BUFFER_SIZE) PostMessage(pcmnctx->hWnd, HM_WORKERTHREAD_SETSIZE, (WPARAM)pcmnctx, lParam != -1 ? lParam : (LPARAM)pFileSize); } #ifdef _TIMED DWORD dwStarted; if (pdwElapsed) dwStarted = GetTickCount(); #endif // Finally, read the file and calculate the checksum; the // progress bar is updated only once every 4 buffer reads (512K) WHInitEx(pwhctx); do // Outer loop: keep going until the end { do // Inner loop: break every 4 cycles or if the end is reached { if (pcmnctx->status == PAUSED) WaitForSingleObject(pcmnctx->hUnpauseEvent, INFINITE); if (pcmnctx->status == CANCEL_REQUESTED) { CloseHandle(hFile); return; } ReadFile(hFile, pbuffer, READ_BUFFER_SIZE, &cbBufferRead, NULL); WHUpdateEx(pwhctx, pbuffer, cbBufferRead); cbFileRead += cbBufferRead; } while (cbBufferRead == READ_BUFFER_SIZE && (++cInner & 0x03)); if (bUpdateProgress) UpdateProgressBar(pcmnctx->hWndPBFile, pUpdateCritSec, &bCurrentlyUpdating, pcbCurrentMaxSize, cbFileSize, cbFileRead, &lastProgress); } while (cbBufferRead == READ_BUFFER_SIZE); WHFinishEx(pwhctx, pwhres); #ifdef _TIMED if (pdwElapsed) *pdwElapsed = GetTickCount() - dwStarted; #endif if (cbFileRead == cbFileSize) *pbSuccess = TRUE; if (bUpdateProgress) UpdateProgressBar(pcmnctx->hWndPBFile, pUpdateCritSec, &bCurrentlyUpdating, pcbCurrentMaxSize, cbFileSize, 0, &lastProgress); } CloseHandle(hFile); } }