517 lines
11 KiB
C
517 lines
11 KiB
C
|
//----------------------------------------------------------------------------
|
||
|
//
|
||
|
// Engine interface code.
|
||
|
//
|
||
|
// Copyright (C) Microsoft Corporation, 1999-2001.
|
||
|
//
|
||
|
//----------------------------------------------------------------------------
|
||
|
|
||
|
#ifndef __ENGINE_H__
|
||
|
#define __ENGINE_H__
|
||
|
|
||
|
#define RELEASE(Unk) \
|
||
|
((Unk) != NULL ? ((Unk)->Release(), (Unk) = NULL) : NULL)
|
||
|
|
||
|
#define MAX_ENGINE_PATH 4096
|
||
|
|
||
|
//
|
||
|
// Session initialization parameters.
|
||
|
//
|
||
|
|
||
|
// Turn on verbose output or not.
|
||
|
extern BOOL g_Verbose;
|
||
|
// Dump file to open or NULL.
|
||
|
extern PTSTR g_DumpFile;
|
||
|
extern PTSTR g_DumpPageFile;
|
||
|
// Process server to use.
|
||
|
extern PSTR g_ProcessServer;
|
||
|
// Full command line with exe name.
|
||
|
extern PSTR g_DebugCommandLine;
|
||
|
// Process creation flags.
|
||
|
extern ULONG g_DebugCreateFlags;
|
||
|
// Process ID to attach to or zero.
|
||
|
extern ULONG g_PidToDebug;
|
||
|
// Process name to attach to or NULL.
|
||
|
extern PSTR g_ProcNameToDebug;
|
||
|
extern BOOL g_DetachOnExit;
|
||
|
extern ULONG g_AttachProcessFlags;
|
||
|
// Kernel connection options.
|
||
|
extern ULONG g_AttachKernelFlags;
|
||
|
extern PSTR g_KernelConnectOptions;
|
||
|
|
||
|
// Remoting options.
|
||
|
extern BOOL g_RemoteClient;
|
||
|
extern ULONG g_HistoryLines;
|
||
|
|
||
|
// Type options.
|
||
|
extern ULONG g_TypeOptions;
|
||
|
//
|
||
|
// Debug engine interfaces for the engine thread.
|
||
|
//
|
||
|
extern IDebugClient *g_pDbgClient;
|
||
|
extern IDebugClient2 *g_pDbgClient2;
|
||
|
extern IDebugControl *g_pDbgControl;
|
||
|
extern IDebugSymbols *g_pDbgSymbols;
|
||
|
extern IDebugRegisters *g_pDbgRegisters;
|
||
|
extern IDebugDataSpaces *g_pDbgData;
|
||
|
extern IDebugSystemObjects *g_pDbgSystem;
|
||
|
|
||
|
//
|
||
|
// Debug engine interfaces for the UI thread.
|
||
|
//
|
||
|
extern IDebugClient *g_pUiClient;
|
||
|
extern IDebugControl *g_pUiControl;
|
||
|
extern IDebugSymbols *g_pUiSymbols;
|
||
|
extern IDebugSymbols2 *g_pUiSymbols2;
|
||
|
extern IDebugSystemObjects *g_pUiSystem;
|
||
|
|
||
|
//
|
||
|
// Debug engine interfaces for private output capture.
|
||
|
//
|
||
|
extern IDebugClient *g_pOutCapClient;
|
||
|
extern IDebugControl *g_pOutCapControl;
|
||
|
|
||
|
//
|
||
|
// Debug engine interfaces for local source file lookup.
|
||
|
//
|
||
|
extern IDebugClient *g_pLocClient;
|
||
|
extern IDebugControl *g_pLocControl;
|
||
|
extern IDebugSymbols *g_pLocSymbols;
|
||
|
extern IDebugClient *g_pUiLocClient;
|
||
|
extern IDebugControl *g_pUiLocControl;
|
||
|
extern IDebugSymbols *g_pUiLocSymbols;
|
||
|
|
||
|
extern ULONG g_ActualProcType;
|
||
|
extern char g_ActualProcAbbrevName[32];
|
||
|
extern ULONG g_NumRegisters;
|
||
|
extern ULONG g_CommandSequence;
|
||
|
extern ULONG g_TargetClass;
|
||
|
extern ULONG g_TargetClassQual;
|
||
|
extern BOOL g_Ptr64;
|
||
|
extern ULONG g_ExecStatus;
|
||
|
extern ULONG g_EngOptModified;
|
||
|
extern ULONG g_EngineThreadId;
|
||
|
extern HANDLE g_EngineThread;
|
||
|
extern PSTR g_InitialCommand;
|
||
|
extern char g_PromptText[];
|
||
|
extern BOOL g_WaitingForEvent;
|
||
|
extern BOOL g_SessionActive;
|
||
|
extern ULONG g_NumberRadix;
|
||
|
extern BOOL g_IgnoreCodeLevelChange;
|
||
|
extern ULONG g_LastProcessExitCode;
|
||
|
extern BOOL g_CodeLevelLocked;
|
||
|
|
||
|
// Target exists and is not running.
|
||
|
#define IS_TARGET_HALTED() \
|
||
|
(g_ExecStatus == DEBUG_STATUS_BREAK)
|
||
|
|
||
|
//----------------------------------------------------------------------------
|
||
|
//
|
||
|
// Default output callbacks implementation, provides IUnknown for
|
||
|
// static classes.
|
||
|
//
|
||
|
//----------------------------------------------------------------------------
|
||
|
|
||
|
class DefOutputCallbacks :
|
||
|
public IDebugOutputCallbacks
|
||
|
{
|
||
|
public:
|
||
|
// IUnknown.
|
||
|
STDMETHOD(QueryInterface)(
|
||
|
THIS_
|
||
|
IN REFIID InterfaceId,
|
||
|
OUT PVOID* Interface
|
||
|
);
|
||
|
STDMETHOD_(ULONG, AddRef)(
|
||
|
THIS
|
||
|
);
|
||
|
STDMETHOD_(ULONG, Release)(
|
||
|
THIS
|
||
|
);
|
||
|
};
|
||
|
|
||
|
//----------------------------------------------------------------------------
|
||
|
//
|
||
|
// EventCallbacks.
|
||
|
//
|
||
|
//----------------------------------------------------------------------------
|
||
|
|
||
|
class EventCallbacks : public DebugBaseEventCallbacks
|
||
|
{
|
||
|
public:
|
||
|
// IUnknown.
|
||
|
STDMETHOD_(ULONG, AddRef)(
|
||
|
THIS
|
||
|
);
|
||
|
STDMETHOD_(ULONG, Release)(
|
||
|
THIS
|
||
|
);
|
||
|
|
||
|
// IDebugEventCallbacks.
|
||
|
STDMETHOD(GetInterestMask)(
|
||
|
THIS_
|
||
|
OUT PULONG Mask
|
||
|
);
|
||
|
|
||
|
STDMETHOD(CreateThread)(
|
||
|
THIS_
|
||
|
IN ULONG64 Handle,
|
||
|
IN ULONG64 DataOffset,
|
||
|
IN ULONG64 StartOffset
|
||
|
);
|
||
|
STDMETHOD(ExitThread)(
|
||
|
THIS_
|
||
|
IN ULONG ExitCode
|
||
|
);
|
||
|
STDMETHOD(CreateProcess)(
|
||
|
THIS_
|
||
|
IN ULONG64 ImageFileHandle,
|
||
|
IN ULONG64 Handle,
|
||
|
IN ULONG64 BaseOffset,
|
||
|
IN ULONG ModuleSize,
|
||
|
IN PCSTR ModuleName,
|
||
|
IN PCSTR ImageName,
|
||
|
IN ULONG CheckSum,
|
||
|
IN ULONG TimeDateStamp,
|
||
|
IN ULONG64 InitialThreadHandle,
|
||
|
IN ULONG64 ThreadDataOffset,
|
||
|
IN ULONG64 StartOffset
|
||
|
);
|
||
|
STDMETHOD(ExitProcess)(
|
||
|
THIS_
|
||
|
IN ULONG ExitCode
|
||
|
);
|
||
|
STDMETHOD(SessionStatus)(
|
||
|
THIS_
|
||
|
IN ULONG Status
|
||
|
);
|
||
|
STDMETHOD(ChangeDebuggeeState)(
|
||
|
THIS_
|
||
|
IN ULONG Flags,
|
||
|
IN ULONG64 Argument
|
||
|
);
|
||
|
STDMETHOD(ChangeEngineState)(
|
||
|
THIS_
|
||
|
IN ULONG Flags,
|
||
|
IN ULONG64 Argument
|
||
|
);
|
||
|
STDMETHOD(ChangeSymbolState)(
|
||
|
THIS_
|
||
|
IN ULONG Flags,
|
||
|
IN ULONG64 Argument
|
||
|
);
|
||
|
};
|
||
|
|
||
|
extern EventCallbacks g_EventCb;
|
||
|
|
||
|
//----------------------------------------------------------------------------
|
||
|
//
|
||
|
// Data space read/write support.
|
||
|
//
|
||
|
//----------------------------------------------------------------------------
|
||
|
|
||
|
//
|
||
|
// Begin types originally defined in NTIOAPI.H
|
||
|
//
|
||
|
|
||
|
|
||
|
//
|
||
|
// Define the I/O bus interface types.
|
||
|
//
|
||
|
typedef enum _INTERFACE_TYPE
|
||
|
{
|
||
|
InterfaceTypeUndefined = -1,
|
||
|
Internal,
|
||
|
Isa,
|
||
|
Eisa,
|
||
|
MicroChannel,
|
||
|
TurboChannel,
|
||
|
PCIBus,
|
||
|
VMEBus,
|
||
|
NuBus,
|
||
|
PCMCIABus,
|
||
|
CBus,
|
||
|
MPIBus,
|
||
|
MPSABus,
|
||
|
ProcessorInternal,
|
||
|
InternalPowerBus,
|
||
|
PNPISABus,
|
||
|
PNPBus,
|
||
|
MaximumInterfaceType
|
||
|
} INTERFACE_TYPE, *PINTERFACE_TYPE;
|
||
|
|
||
|
|
||
|
//
|
||
|
// Define types of bus information.
|
||
|
//
|
||
|
typedef enum _BUS_DATA_TYPE
|
||
|
{
|
||
|
ConfigurationSpaceUndefined = -1,
|
||
|
Cmos,
|
||
|
EisaConfiguration,
|
||
|
Pos,
|
||
|
CbusConfiguration,
|
||
|
PCIConfiguration,
|
||
|
VMEConfiguration,
|
||
|
NuBusConfiguration,
|
||
|
PCMCIAConfiguration,
|
||
|
MPIConfiguration,
|
||
|
MPSAConfiguration,
|
||
|
PNPISAConfiguration,
|
||
|
SgiInternalConfiguration,
|
||
|
MaximumBusDataType
|
||
|
} BUS_DATA_TYPE, *PBUS_DATA_TYPE;
|
||
|
|
||
|
//
|
||
|
// End types originally defined in NTIOAPI.H
|
||
|
//
|
||
|
|
||
|
enum MEMORY_TYPE
|
||
|
{
|
||
|
VIRTUAL_MEM_TYPE = 0,
|
||
|
MIN_MEMORY_TYPE = 0, // Placed here so that symbol lookup finds this first
|
||
|
PHYSICAL_MEM_TYPE,
|
||
|
CONTROL_MEM_TYPE,
|
||
|
IO_MEM_TYPE,
|
||
|
MSR_MEM_TYPE,
|
||
|
BUS_MEM_TYPE,
|
||
|
MAX_MEMORY_TYPE
|
||
|
};
|
||
|
|
||
|
|
||
|
struct IO_MEMORY_DATA
|
||
|
{
|
||
|
ULONG BusNumber;
|
||
|
ULONG AddressSpace;
|
||
|
INTERFACE_TYPE interface_type;
|
||
|
};
|
||
|
|
||
|
struct BUS_MEMORY_DATA
|
||
|
{
|
||
|
ULONG BusNumber;
|
||
|
ULONG SlotNumber;
|
||
|
BUS_DATA_TYPE bus_type;
|
||
|
};
|
||
|
|
||
|
struct MSR_MEMORY_DATA
|
||
|
{
|
||
|
// Placeholder in case data is needed later.
|
||
|
};
|
||
|
|
||
|
struct PHYSICAL_MEMORY_DATA
|
||
|
{
|
||
|
// Placeholder in case data is needed later.
|
||
|
};
|
||
|
|
||
|
struct VIRTUAL_MEMORY_DATA
|
||
|
{
|
||
|
// Placeholder in case data is needed later.
|
||
|
};
|
||
|
|
||
|
struct CONTROL_MEMORY_DATA
|
||
|
{
|
||
|
ULONG Processor;
|
||
|
};
|
||
|
|
||
|
struct ANY_MEMORY_DATA
|
||
|
{
|
||
|
union
|
||
|
{
|
||
|
IO_MEMORY_DATA io;
|
||
|
BUS_MEMORY_DATA bus;
|
||
|
MSR_MEMORY_DATA msr;
|
||
|
CONTROL_MEMORY_DATA control;
|
||
|
PHYSICAL_MEMORY_DATA physical;
|
||
|
VIRTUAL_MEMORY_DATA virt;
|
||
|
};
|
||
|
};
|
||
|
|
||
|
//----------------------------------------------------------------------------
|
||
|
//
|
||
|
// Inter-thread communication.
|
||
|
//
|
||
|
// UI buffers are used for transferring information between the
|
||
|
// UI thread and the engine thread, such as commands and output.
|
||
|
// They have a separate lock to avoid contention with state filling.
|
||
|
// If state buffers had individual locks this would be unnecessary.
|
||
|
//
|
||
|
// The UI reads text output from the output buffer for display
|
||
|
// in the command window.
|
||
|
//
|
||
|
// The UI queues commands to the command buffer for execution
|
||
|
// by the engine.
|
||
|
//
|
||
|
//----------------------------------------------------------------------------
|
||
|
|
||
|
// This must be at least MAX_PATH, and also must
|
||
|
// be large enough for the largest single command window
|
||
|
// command expected.
|
||
|
#define MAX_COMMAND_LEN 4096
|
||
|
|
||
|
#define LockUiBuffer(Buffer) Dbg_EnterCriticalSection(&(Buffer)->m_Lock)
|
||
|
#define UnlockUiBuffer(Buffer) Dbg_LeaveCriticalSection(&(Buffer)->m_Lock)
|
||
|
|
||
|
extern class StateBuffer g_UiOutputBuffer;
|
||
|
|
||
|
// Commands from the UI to the engine.
|
||
|
enum UiCommand
|
||
|
{
|
||
|
// Distinguish command input from other commands so
|
||
|
// that the input callbacks have a specific token to
|
||
|
// look for user input.
|
||
|
UIC_CMD_INPUT,
|
||
|
UIC_EXECUTE,
|
||
|
UIC_SILENT_EXECUTE,
|
||
|
UIC_INVISIBLE_EXECUTE,
|
||
|
UIC_SET_REG,
|
||
|
UIC_RESTART,
|
||
|
UIC_END_SESSION,
|
||
|
UIC_WRITE_DATA,
|
||
|
UIC_SYMBOL_WIN,
|
||
|
UIC_DISPLAY_CODE,
|
||
|
UIC_DISPLAY_CODE_EXPR,
|
||
|
UIC_SET_SCOPE,
|
||
|
UIC_GET_SYM_PATH,
|
||
|
UIC_SET_SYM_PATH,
|
||
|
UIC_SET_FILTER,
|
||
|
UIC_SET_FILTER_ARGUMENT,
|
||
|
UIC_SET_FILTER_COMMAND,
|
||
|
};
|
||
|
|
||
|
struct UiCommandData
|
||
|
{
|
||
|
UiCommand Cmd;
|
||
|
ULONG Len;
|
||
|
};
|
||
|
|
||
|
struct UIC_SET_REG_DATA
|
||
|
{
|
||
|
ULONG Reg;
|
||
|
DEBUG_VALUE Val;
|
||
|
};
|
||
|
|
||
|
struct UIC_WRITE_DATA_DATA
|
||
|
{
|
||
|
MEMORY_TYPE Type;
|
||
|
ANY_MEMORY_DATA Any;
|
||
|
ULONG64 Offset;
|
||
|
ULONG Length;
|
||
|
UCHAR Data[16];
|
||
|
};
|
||
|
|
||
|
enum SYMBOL_WIN_CALL_TYPE
|
||
|
{
|
||
|
ADD_SYMBOL_WIN,
|
||
|
DEL_SYMBOL_WIN_INDEX,
|
||
|
DEL_SYMBOL_WIN_NAME,
|
||
|
QUERY_NUM_SYMBOL_WIN,
|
||
|
GET_NAME,
|
||
|
GET_PARAMS,
|
||
|
EXPAND_SYMBOL,
|
||
|
EDIT_SYMBOL,
|
||
|
EDIT_TYPE,
|
||
|
DEL_SYMBOL_WIN_ALL
|
||
|
};
|
||
|
|
||
|
typedef struct UIC_SYMBOL_WIN_DATA
|
||
|
{
|
||
|
SYMBOL_WIN_CALL_TYPE Type;
|
||
|
PDEBUG_SYMBOL_GROUP *pSymbolGroup;
|
||
|
union
|
||
|
{
|
||
|
struct
|
||
|
{
|
||
|
PCSTR Name;
|
||
|
ULONG Index;
|
||
|
} Add;
|
||
|
PCSTR DelName;
|
||
|
ULONG DelIndex;
|
||
|
PULONG NumWatch;
|
||
|
struct
|
||
|
{
|
||
|
ULONG Index;
|
||
|
PSTR Buffer;
|
||
|
ULONG BufferSize;
|
||
|
PULONG NameSize;
|
||
|
} GetName;
|
||
|
struct
|
||
|
{
|
||
|
ULONG Start;
|
||
|
ULONG Count;
|
||
|
PDEBUG_SYMBOL_PARAMETERS SymbolParams;
|
||
|
} GetParams;
|
||
|
struct
|
||
|
{
|
||
|
ULONG Index;
|
||
|
BOOL Expand;
|
||
|
} ExpandSymbol;
|
||
|
struct
|
||
|
{
|
||
|
ULONG Index;
|
||
|
PSTR Value;
|
||
|
} WriteSymbol;
|
||
|
struct
|
||
|
{
|
||
|
ULONG Index;
|
||
|
PSTR Type;
|
||
|
} OutputAsType;
|
||
|
} u;
|
||
|
} UIC_SYMBOL_WIN_DATA;
|
||
|
|
||
|
struct UIC_DISPLAY_CODE_DATA
|
||
|
{
|
||
|
ULONG64 Offset;
|
||
|
};
|
||
|
|
||
|
struct UIC_SET_SCOPE_DATA
|
||
|
{
|
||
|
DEBUG_STACK_FRAME StackFrame;
|
||
|
};
|
||
|
|
||
|
struct UIC_SET_FILTER_DATA
|
||
|
{
|
||
|
ULONG Index;
|
||
|
ULONG Code;
|
||
|
ULONG Execution;
|
||
|
ULONG Continue;
|
||
|
};
|
||
|
|
||
|
struct UIC_SET_FILTER_ARGUMENT_DATA
|
||
|
{
|
||
|
ULONG Index;
|
||
|
char Argument[1];
|
||
|
};
|
||
|
|
||
|
struct UIC_SET_FILTER_COMMAND_DATA
|
||
|
{
|
||
|
ULONG Which;
|
||
|
ULONG Index;
|
||
|
char Command[1];
|
||
|
};
|
||
|
|
||
|
PVOID StartCommand(UiCommand Cmd, ULONG Len);
|
||
|
void FinishCommand(void);
|
||
|
|
||
|
BOOL AddStringCommand(UiCommand Cmd, PCSTR Str);
|
||
|
BOOL AddStringMultiCommand(UiCommand Cmd, PSTR Str);
|
||
|
BOOL __cdecl PrintStringCommand(UiCommand Cmd, PCSTR Format, ...);
|
||
|
|
||
|
#define StartStructCommand(Struct) \
|
||
|
((Struct ## _DATA*)StartCommand(Struct, sizeof(Struct ## _DATA)))
|
||
|
|
||
|
#define AddEnumCommand(Cmd) \
|
||
|
(StartCommand(Cmd, 0) != NULL ? (FinishCommand(), TRUE) : FALSE)
|
||
|
|
||
|
// Wake up the UI thread to do UI processing.
|
||
|
#define UpdateUi() \
|
||
|
PostMessage(g_hwndFrame, WM_NOTIFY, 0, 0)
|
||
|
|
||
|
// Wake up the engine thread to do engine processing.
|
||
|
void UpdateEngine(void);
|
||
|
|
||
|
void ProcessEngineCommands(BOOL Internal);
|
||
|
void DiscardEngineState(void);
|
||
|
DWORD WINAPI EngineLoop(LPVOID Param);
|
||
|
|
||
|
#endif // #ifndef __ENGINE_H__
|