|
|
/*++
Copyright (c) 1999-2002 Microsoft Corporation
Module Name:
gen.c
Abstract:
Generic routines that work on all operating systems.
Author:
Matthew D Hendel (math) 20-Oct-1999
Revision History:
--*/
#pragma once
#define KBYTE (1024)
#define ARRAY_COUNT(_array) (sizeof (_array) / sizeof ((_array)[0]))
#define MAX_DYNAMIC_FUNCTION_TABLE 256
#define WIN32_LAST_STATUS() \
(GetLastError() ? HRESULT_FROM_WIN32(GetLastError()) : E_FAIL)
ULONG FORCEINLINE FileTimeToTimeDate(LPFILETIME FileTime) { ULARGE_INTEGER LargeTime; LargeTime.LowPart = FileTime->dwLowDateTime; LargeTime.HighPart = FileTime->dwHighDateTime; // Convert to seconds and from base year 1601 to base year 1970.
return (ULONG)(LargeTime.QuadPart / 10000000 - 11644473600); }
ULONG FORCEINLINE FileTimeToSeconds(LPFILETIME FileTime) { ULARGE_INTEGER LargeTime; LargeTime.LowPart = FileTime->dwLowDateTime; LargeTime.HighPart = FileTime->dwHighDateTime; // Convert to seconds.
return (ULONG)(LargeTime.QuadPart / 10000000); }
ULONG64 FORCEINLINE GenGetPointer(IN PMINIDUMP_STATE Dump, IN PVOID Data) { if (Dump->PtrSize == 8) { return *(PULONG64)Data; } else { return *(PLONG)Data; } }
void FORCEINLINE GenSetPointer(IN PMINIDUMP_STATE Dump, IN PVOID Data, IN ULONG64 Val) { if (Dump->PtrSize == 8) { *(PULONG64)Data = Val; } else { *(PULONG)Data = (ULONG)Val; } }
LPVOID AllocMemory( IN PMINIDUMP_STATE Dump, IN ULONG Size );
VOID FreeMemory( IN PMINIDUMP_STATE Dump, IN LPVOID Memory );
void GenAccumulateStatus( IN PMINIDUMP_STATE Dump, IN ULONG Status );
struct _INTERNAL_THREAD; struct _INTERNAL_PROCESS; struct _INTERNAL_MODULE; struct _INTERNAL_FUNCTION_TABLE;
BOOL GenExecuteIncludeThreadCallback( IN PMINIDUMP_STATE Dump, IN ULONG ThreadId, OUT PULONG WriteFlags );
BOOL GenExecuteIncludeModuleCallback( IN PMINIDUMP_STATE Dump, IN ULONG64 BaseOfImage, OUT PULONG WriteFlags );
HRESULT GenGetDataContributors( IN PMINIDUMP_STATE Dump, IN OUT PINTERNAL_PROCESS Process, IN PINTERNAL_MODULE Module );
HRESULT GenGetThreadInstructionWindow( IN PMINIDUMP_STATE Dump, IN struct _INTERNAL_PROCESS* Process, IN struct _INTERNAL_THREAD* Thread );
HRESULT GenGetProcessInfo( IN PMINIDUMP_STATE Dump, OUT struct _INTERNAL_PROCESS ** ProcessRet );
VOID GenFreeProcessObject( IN PMINIDUMP_STATE Dump, IN struct _INTERNAL_PROCESS * Process );
HRESULT GenAddMemoryBlock( IN PMINIDUMP_STATE Dump, IN PINTERNAL_PROCESS Process, IN MEMBLOCK_TYPE Type, IN ULONG64 Start, IN ULONG Size );
void GenRemoveMemoryRange( IN PMINIDUMP_STATE Dump, IN PINTERNAL_PROCESS Process, IN ULONG64 Start, IN ULONG Size );
HRESULT GenAddPebMemory( IN PMINIDUMP_STATE Dump, IN PINTERNAL_PROCESS Process );
HRESULT GenAddTebMemory( IN PMINIDUMP_STATE Dump, IN PINTERNAL_PROCESS Process, IN PINTERNAL_THREAD Thread );
HRESULT GenWriteHandleData( IN PMINIDUMP_STATE Dump, IN PMINIDUMP_STREAM_INFO StreamInfo );
ULONG GenProcArchToImageMachine(ULONG ProcArch);
//
// Routines reimplemented for portability.
//
PIMAGE_NT_HEADERS GenImageNtHeader( IN PVOID Base, OUT OPTIONAL PIMAGE_NT_HEADERS64 Generic );
PVOID GenImageDirectoryEntryToData( IN PVOID Base, IN BOOLEAN MappedAsImage, IN USHORT DirectoryEntry, OUT PULONG Size );
LPWSTR GenStrCopyNW( OUT LPWSTR lpString1, IN LPCWSTR lpString2, IN int iMaxLength );
size_t GenStrLengthW( const wchar_t * wcs );
int GenStrCompareW( IN LPCWSTR String1, IN LPCWSTR String2 );
void GenExRecord32ToMd(PEXCEPTION_RECORD32 Rec32, PMINIDUMP_EXCEPTION RecMd); inline void GenExRecord64ToMd(PEXCEPTION_RECORD64 Rec64, PMINIDUMP_EXCEPTION RecMd) { // Structures are the same.
memcpy(RecMd, Rec64, sizeof(*RecMd)); }
//
// Stolen from NTRTL to avoid having to include it here.
//
#ifndef InitializeListHead
#define InitializeListHead(ListHead) (\
(ListHead)->Flink = (ListHead)->Blink = (ListHead)) #endif
//
// VOID
// InsertTailList(
// PLIST_ENTRY ListHead,
// PLIST_ENTRY Entry
// );
//
#ifndef InsertTailList
#define InsertTailList(ListHead,Entry) {\
PLIST_ENTRY _EX_Blink;\ PLIST_ENTRY _EX_ListHead;\ _EX_ListHead = (ListHead);\ _EX_Blink = _EX_ListHead->Blink;\ (Entry)->Flink = _EX_ListHead;\ (Entry)->Blink = _EX_Blink;\ _EX_Blink->Flink = (Entry);\ _EX_ListHead->Blink = (Entry);\ } #endif
//
// VOID
// InsertListAfter(
// PLIST_ENTRY ListEntry,
// PLIST_ENTRY InsertEntry
// );
//
#ifndef InsertListAfter
#define InsertListAfter(ListEntry,InsertEntry) {\
(InsertEntry)->Flink = (ListEntry)->Flink;\ (InsertEntry)->Blink = (ListEntry);\ (ListEntry)->Flink->Blink = (InsertEntry);\ (ListEntry)->Flink = (InsertEntry);\ } #endif
//
// VOID
// RemoveEntryList(
// PLIST_ENTRY Entry
// );
//
#ifndef RemoveEntryList
#define RemoveEntryList(Entry) {\
PLIST_ENTRY _EX_Blink;\ PLIST_ENTRY _EX_Flink;\ _EX_Flink = (Entry)->Flink;\ _EX_Blink = (Entry)->Blink;\ _EX_Blink->Flink = _EX_Flink;\ _EX_Flink->Blink = _EX_Blink;\ } #endif
//
// BOOLEAN
// IsListEmpty(
// PLIST_ENTRY ListHead
// );
//
#ifndef IsListEmpty
#define IsListEmpty(ListHead) \
((ListHead)->Flink == (ListHead)) #endif
//
// Undefine ASSERT so we do not get RtlAssert().
//
#ifdef ASSERT
#undef ASSERT
#endif
#if DBG
#define ASSERT(_x)\
if (!(_x)){\ OutputDebugString ("ASSERT Failed");\ DebugBreak ();\ }
#else
#define ASSERT(_x)
#endif
|