bool ConcreteDatabase::asyncQuery( QueryCallback::FuncType func, const char* sql ) { if (!sql) return false; return this->doDelay(sql, QueryCallback(func)); }
QueryCallback DatabaseWorkerPool<T>::AsyncQuery(PreparedStatement* stmt) { PreparedStatementTask* task = new PreparedStatementTask(stmt, true); // Store future result before enqueueing - task might get already processed and deleted before returning from this method PreparedQueryResultFuture result = task->GetFuture(); Enqueue(task); return QueryCallback(std::move(result)); }
QueryCallback DatabaseWorkerPool<T>::AsyncQuery(const char* sql) { BasicStatementTask* task = new BasicStatementTask(sql, true); // Store future result before enqueueing - task might get already processed and deleted before returning from this method QueryResultFuture result = task->GetFuture(); Enqueue(task); return QueryCallback(std::move(result)); }
void LOCATOR::NotifyMiscPath(const wchar_t *wszMiscPath) { if (!m_fPfnNotifyMiscPath) { m_fPfnNotifyMiscPath = true; m_pfnNotifyMiscPath = (PfnPDBNotifyMiscPath) QueryCallback(povcNotifyMiscPath); } if (m_pfnNotifyMiscPath == 0) { return; } (*m_pfnNotifyMiscPath)(m_pvClient, wszMiscPath); }
void LOCATOR::NotifyDebugDir(BOOL fExecutable, const struct _IMAGE_DEBUG_DIRECTORY *pdbgdir) { if (!m_fPfnNotifyDebugDir) { m_fPfnNotifyDebugDir = true; m_pfnNotifyDebugDir = (PfnPDBNotifyDebugDir) QueryCallback(povcNotifyDebugDir); } if (m_pfnNotifyDebugDir == 0) { return; } (*m_pfnNotifyDebugDir)(m_pvClient, fExecutable, (const _IMAGE_DEBUG_DIRECTORY *)pdbgdir); }
void LOCATOR::NotifyOpenDBG(const wchar_t *wszDbgPath, PDBErrors ec, const wchar_t *wszError) { SetError(ec, wszError); if (!m_fPfnNotifyOpenDBG) { m_fPfnNotifyOpenDBG = true; m_pfnNotifyOpenDBG = (PfnPDBNotifyOpenDBG) QueryCallback(povcNotifyOpenDBG); } if (m_pfnNotifyOpenDBG == 0) { return; } (*m_pfnNotifyOpenDBG)(m_pvClient, wszDbgPath, ec, wszError); }
bool LOCATOR::FRestrictSystemRoot() { if (!m_fPfnRestrictSystemRoot) { m_fPfnRestrictSystemRoot = true; m_pfnRestrictSystemRoot = (PfnPDBRestrictSystemRoot) QueryCallback(povcRestrictSystemRoot); } if (m_pfnRestrictSystemRoot == 0) { return false; } HRESULT hr = (*m_pfnRestrictSystemRoot)(m_pvClient); return (hr != S_OK); }
bool LOCATOR::FRestrictSymsrv() { if (!m_fPfnRestrictSymsrv) { m_fPfnRestrictSymsrv = true; m_pfnRestrictSymsrv = (PfnPDBRestrictSymsrv) QueryCallback(povcRestrictSymsrv); } if (m_pfnRestrictSymsrv == 0) { return false; } HRESULT hr = (*m_pfnRestrictSymsrv)(m_pvClient); return (hr != S_OK); }
bool LOCATOR::FRestrictRegistry() { if (!m_fPfnRestrictRegistry) { m_fPfnRestrictRegistry = true; m_pfnRestrictRegistry = (PfnPDBRestrictRegistry) QueryCallback(povcRestrictRegistry); } if (m_pfnRestrictRegistry == 0) { return false; } HRESULT hr = (*m_pfnRestrictRegistry)(m_pvClient); return (hr != S_OK); }
bool LOCATOR::FRestrictReferencePath() { if (!m_fPfnRestrictReferencePath) { m_fPfnRestrictReferencePath = true; m_pfnPdbRestrictReferencePath = (PfnPdbRestrictReferencePath) QueryCallback(povcRestrictReferencePath); } if (m_pfnPdbRestrictReferencePath == 0) { return false; } HRESULT hr = (*m_pfnPdbRestrictReferencePath)(m_pvClient); return (hr != S_OK); }
bool LOCATOR::FRestrictDBG() { if(!m_fPfnRestrictDBG) { m_fPfnRestrictDBG = true; m_pfnPdbRestrictDBG = (PfnPdbRestrictDBG)QueryCallback(povcRestrictDBG); } if (!m_pfnPdbRestrictDBG) { return false; } HRESULT hr = (*m_pfnPdbRestrictDBG)(m_pvClient); return hr != S_OK; }
void LOCATOR::NotifyOpenPDB(const wchar_t *wszPdbPath, PDBErrors ec, const wchar_t *wszError) { if (!m_fPfnNotifyOpenPDB) { m_fPfnNotifyOpenPDB = true; m_pfnNotifyOpenPDB = (PfnPDBNotifyOpenPDB) QueryCallback(povcNotifyOpenPDB); } if (m_pfnNotifyOpenPDB == 0) { return; } // Do some extra work to make sure we give back a full path to the file we // tried to open. SafeStackAllocator<1024> _allocator; wchar_t *wszPdbFull = NULL; DWORD cwchFullPath = GetFullPathNameW(wszPdbPath, 0, NULL, NULL); if (cwchFullPath != 0) { wszPdbFull = _allocator.Alloc<wchar_t>(cwchFullPath); if (wszPdbFull != NULL) { cwchFullPath = GetFullPathNameW(wszPdbPath, cwchFullPath, wszPdbFull, NULL); } } if (cwchFullPath == 0) { // Use the passed in PDB filename if GetFullPathNameW() failed. wszPdbFull = const_cast<wchar_t *>(wszPdbPath); } (*m_pfnNotifyOpenPDB)(m_pvClient, wszPdbFull, ec, wszError); }
bool LOCATOR::FCrackExeOrDbg(const wchar_t *wszFilename, bool fCheckNgenImage) { FILE *fd = NULL; m_pfnReadCodeViewDebugData = (PfnPDBReadCodeViewDebugData) QueryCallback(povcReadCodeViewDebugData); if (m_pfnReadCodeViewDebugData != 0) { // We'll read the actual codeview data // from the client in FLocatePdb(). m_fCvInExe = true; return true; } m_pfnReadMiscDebugData = (PfnPDBReadMiscDebugData) QueryCallback(povcReadMiscDebugData); if (m_pfnReadMiscDebugData != 0) { if (FReadMiscDebugData()) { // UNDONE : This is really true only if header has // IMAGE_FILE_DEBUG_STRIPPED bit set. But // in this case, there is no way to verify! m_fStripped = true; return FSaveFileNames(wszFilename); } } m_pfnReadExecutableAt = (PfnPDBReadExecutableAt) QueryCallback(povcReadExecutableAt); if (m_pfnReadExecutableAt == 0) { m_pfnReadExecutableAtRVA = (PfnPDBReadExecutableAtRVA) QueryCallback(povcReadExecutableAtRVA); if (m_pfnReadExecutableAtRVA == 0) { fd = PDB_wfsopen(wszFilename, L"rb", SH_DENYWR); if (fd == NULL) { SetError(EC_NOT_FOUND, wszFilename); return false; } } } IMAGE_DOS_HEADER DosHeader; if (!FReadHeader(fd, 0, sizeof(DosHeader), &DosHeader)) { InvalidExecutable: SetError(EC_INVALID_EXECUTABLE, wszFilename); Close(fd); return false; } if (fd != NULL) { // We only check for a DBG file when accessing a file locally if (DosHeader.e_magic == IMAGE_SEPARATE_DEBUG_SIGNATURE) { // The file is a DBG file Close(fd); // Set m_dwTimeStampExe so that this DBG is recognized as valid m_dwTimeStampExe = ((IMAGE_SEPARATE_DEBUG_HEADER *) &DosHeader)->TimeDateStamp; bool f = FLocateDbgValidate(wszFilename); if (!f && (Ec() == EC_FORMAT)) { // If this is an invalid format DBG then we guessed goto InvalidExecutable; } return f; } } if (DosHeader.e_magic != IMAGE_DOS_SIGNATURE) { // The file isn't an MS-DOS executable goto InvalidExecutable; } if (!FSaveFileNames(wszFilename)) { Close(fd); return false; } if (DosHeader.e_lfanew <= 0) { // There is no pointer to a PE header goto InvalidExecutable; } // Read the PE header. IMAGE_NT_HEADERS64 NtHeader; if (!FReadHeader(fd, (DWORD) DosHeader.e_lfanew, sizeof(NtHeader), &NtHeader)) { // The file isn't large enough to contain a PE header goto InvalidExecutable; } if (NtHeader.Signature != IMAGE_NT_SIGNATURE) { // The file isn't a PE executable goto InvalidExecutable; } DWORD rva = 0, cb = 0; DWORD rvaComDescriptor = 0, cbComDescriptor = 0; switch (NtHeader.OptionalHeader.Magic) { case IMAGE_NT_OPTIONAL_HDR32_MAGIC : { const IMAGE_OPTIONAL_HEADER32 *pImgOptHdr32 = (IMAGE_OPTIONAL_HEADER32 *) &NtHeader.OptionalHeader; m_dwSizeOfImage = pImgOptHdr32->SizeOfImage; if (pImgOptHdr32->NumberOfRvaAndSizes >= IMAGE_DIRECTORY_ENTRY_DEBUG) { rva = pImgOptHdr32->DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; cb = pImgOptHdr32->DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].Size; } if (fCheckNgenImage && (pImgOptHdr32->NumberOfRvaAndSizes >= IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR)) { rvaComDescriptor = pImgOptHdr32->DataDirectory[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].VirtualAddress; cbComDescriptor = pImgOptHdr32->DataDirectory[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].Size; } break; } case IMAGE_NT_OPTIONAL_HDR64_MAGIC : { const IMAGE_OPTIONAL_HEADER64 *pImgOptHdr64 = &NtHeader.OptionalHeader; m_dwSizeOfImage = pImgOptHdr64->SizeOfImage; if (pImgOptHdr64->NumberOfRvaAndSizes >= IMAGE_DIRECTORY_ENTRY_DEBUG) { rva = pImgOptHdr64->DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress; cb = pImgOptHdr64->DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].Size; } if (fCheckNgenImage && (pImgOptHdr64->NumberOfRvaAndSizes >= IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR)) { rvaComDescriptor = pImgOptHdr64->DataDirectory[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].VirtualAddress; cbComDescriptor = pImgOptHdr64->DataDirectory[IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR].Size; } break; } default : // We don't recognize this format optional header goto InvalidExecutable; } if ((rva == 0) || (cb == 0)) { // There are no debug directories in the executable. SetError(EC_NO_DEBUG_INFO, wszFilename); Close(fd); return false; } if (fCheckNgenImage && ((rvaComDescriptor == 0) || (cbComDescriptor == 0))) { // Valid ngen images should have COM descriptor directories. goto InvalidExecutable; } DWORD fo; DWORD foComDescriptor = 0; if ((m_pfnReadExecutableAt == 0) && (m_pfnReadExecutableAtRVA != 0)) { // We can avoid mapping RVA to file offset if we are using // RVAs to read from the source file fo = 0; } else { fo = (DWORD) DosHeader.e_lfanew + offsetof(IMAGE_NT_HEADERS32, OptionalHeader) + NtHeader.FileHeader.SizeOfOptionalHeader; size_t csec = (size_t) NtHeader.FileHeader.NumberOfSections; IMAGE_SECTION_HEADER SecHeader; DWORD ptrToRawDataDbgDir = 0, vaDbgDir = 0; DWORD ptrToRawDataComDescriptor = 0, vaComDescriptor = 0; size_t isec = 0; for (isec = 0; isec < csec; isec++) { if (!FReadHeader(fd, fo, sizeof(IMAGE_SECTION_HEADER), &SecHeader)) { break; } fo += sizeof(IMAGE_SECTION_HEADER); if ((SecHeader.VirtualAddress <= rva) && ((SecHeader.VirtualAddress + SecHeader.SizeOfRawData) >= (rva + cb))) { ptrToRawDataDbgDir = SecHeader.PointerToRawData; vaDbgDir = SecHeader.VirtualAddress; } if (fCheckNgenImage && (SecHeader.VirtualAddress <= rvaComDescriptor) && ((SecHeader.VirtualAddress + SecHeader.SizeOfRawData) >= (rvaComDescriptor + cbComDescriptor))) { ptrToRawDataComDescriptor = SecHeader.PointerToRawData; vaComDescriptor = SecHeader.VirtualAddress; } if ((ptrToRawDataDbgDir != 0) && (!fCheckNgenImage || ptrToRawDataComDescriptor != 0)) { break; } } if (isec == csec) { // Can't find debug directories, or // Can't find COM descriptor directories for ngen image goto InvalidExecutable; } fo = ptrToRawDataDbgDir + (rva - vaDbgDir); if (fCheckNgenImage) { foComDescriptor = ptrToRawDataComDescriptor + (rvaComDescriptor - vaComDescriptor); } } if (fCheckNgenImage) { IMAGE_COR20_HEADER corHdr; if (!FReadAt(fd, foComDescriptor, rvaComDescriptor, sizeof(IMAGE_COR20_HEADER), &corHdr)) { // Can't read the COR20 header goto InvalidExecutable; } if ((corHdr.ManagedNativeHeader.VirtualAddress == 0) || (corHdr.ManagedNativeHeader.Size == 0)) { // Invalid data directory for ManagedNativeHeader in an ngen image goto InvalidExecutable; } } IMAGE_DEBUG_DIRECTORY dbgdirCv = {0}; IMAGE_DEBUG_DIRECTORY dbgdirMisc = {0}; dbgdirCv.Type = IMAGE_DEBUG_TYPE_UNKNOWN; dbgdirMisc.Type = IMAGE_DEBUG_TYPE_UNKNOWN; size_t cdbgdir = cb / sizeof(IMAGE_DEBUG_DIRECTORY); wchar_t wszNgenFName[_MAX_FNAME]; if (fCheckNgenImage) { _wsplitpath_s(wszFilename, NULL, 0, NULL, 0, wszNgenFName, _countof(wszNgenFName), NULL, 0); } for (size_t idbgdir = 0; idbgdir < cdbgdir; idbgdir++) { IMAGE_DEBUG_DIRECTORY dbgdir; if (!FReadAt(fd, fo, rva, sizeof(IMAGE_DEBUG_DIRECTORY), &dbgdir)) { // Can't read debug directories goto InvalidExecutable; } rva += sizeof(IMAGE_DEBUG_DIRECTORY); if ((m_pfnReadExecutableAt != 0) || (m_pfnReadExecutableAtRVA == 0)) { fo += sizeof(IMAGE_DEBUG_DIRECTORY); } NotifyDebugDir(true, &dbgdir); if (dbgdir.Type == IMAGE_DEBUG_TYPE_CODEVIEW) { if (fCheckNgenImage) { m_fCvInExe = true; m_fdExe = fd; m_cbCv = dbgdir.SizeOfData; m_rvaCv = dbgdir.AddressOfRawData; m_foCv = dbgdir.PointerToRawData; if (FReadDebugDirInfo() && m_fGuid && (m_age != 0) && (m_wszPdb != NULL)) { wchar_t wszPdbFName[_MAX_FNAME]; _wsplitpath_s(m_wszPdb, NULL, 0, NULL, 0, wszPdbFName, _countof(wszPdbFName), NULL, 0); if (_wcsicmp(wszNgenFName, wszPdbFName) == 0) { dbgdirCv = dbgdir; return true; } } } else { dbgdirCv = dbgdir; } } else if (dbgdir.Type == IMAGE_DEBUG_TYPE_MISC) { dbgdirMisc = dbgdir; } } m_fdExe = fd; bool fDebugInfo = false; if (dbgdirCv.Type != IMAGE_DEBUG_TYPE_UNKNOWN) { fDebugInfo = true; m_fCvInExe = true; m_cbCv = dbgdirCv.SizeOfData; m_rvaCv = dbgdirCv.AddressOfRawData; m_foCv = dbgdirCv.PointerToRawData; } else if (fCheckNgenImage) { // When opening PDB for an ngen image, we should have found // (in the loop above) a debug directory entry of type // IMAGE_DEBUG_TYPE_CODEVIEW and the contained PDB's filename // should the same as that of the ngen image. goto InvalidExecutable; } m_fStripped = (NtHeader.FileHeader.Characteristics & IMAGE_FILE_DEBUG_STRIPPED) != 0; if (m_fStripped && (dbgdirMisc.Type != IMAGE_DEBUG_TYPE_UNKNOWN)) { fDebugInfo = true; m_dwTimeStampExe = NtHeader.FileHeader.TimeDateStamp; m_dwTimeStampDbg = dbgdirMisc.TimeDateStamp; ReadMiscPath(NULL, fd, dbgdirMisc.PointerToRawData, dbgdirMisc.AddressOfRawData, dbgdirMisc.SizeOfData); } if (!fDebugInfo) { SetError(EC_NO_DEBUG_INFO, wszFilename); } return fDebugInfo; }