/Source/Inject/Injector.cs
C# | 514 lines | 392 code | 83 blank | 39 comment | 17 complexity | f3c251de17beb8698ad94880d9ae507c MD5 | raw file
- using System;
- using System.Collections.Generic;
- using System.Text;
- using System.Threading;
- using System.IO;
- using System.Runtime.InteropServices;
- using EasyHook;
- using System.Windows.Forms;
- using System.Drawing.Win32;
- using System.Diagnostics;
-
- namespace HoldemHook
- {
-
- public class Injector : EasyHook.IEntryPoint
- {
- //?getDC@QWidget@@UBEPAUHDC__@@XZ
-
- public InjectClient Interface = null;
- public LocalHook CreateFileHook = null;
- public LocalHook ExtTextOutHook = null;
- public LocalHook QPainter_drawTextHook = null;
- public LocalHook QWidget_getDC = null;
- public LocalHook QWidgetPrivate_repaint_sysHook=null;
-
- public static StreamWriter Log = null;
-
- public GUINodeMap GuiNodes = new GUINodeMap();
-
- Stack<EventArgs> Queue = new Stack<EventArgs>();
-
- public Injector(
- RemoteHooking.IContext InContext,
- String InChannelName)
- {
- if(null==Log)
- Log = new StreamWriter("Injector.log");
- Log.AutoFlush = true;
- Log.WriteLine("Log Started {0}",DateTime.Now);
- Interface = RemoteHooking.IpcConnectClient<InjectClient>(InChannelName);
-
- Interface.Ping(RemoteHooking.GetCurrentProcessId());
- }
-
- public void Run(
- RemoteHooking.IContext InContext,
- String InArg1)
- {
- try
- {
- Log.WriteLine("Injector.Run {0}", InArg1);
-
- ExtTextOutHook = LocalHook.Create(
- LocalHook.GetProcAddress("gdi32.dll", "ExtTextOutW"),
- new DExtTextOutW(ExtTextOutW_Hooked),
- this);
-
- ExtTextOutHook.ThreadACL.SetExclusiveACL(new Int32[1]);
-
- Log.WriteLine("ExtTextOutW hooked");
-
- #if false
- QWidgetPrivate_repaint_sysHook = LocalHook.Create(
- LocalHook.GetProcAddress("QtGui4.dll", "?drawWidget@QWidgetPrivate@@QAEXPAVQPaintDevice@@ABVQRegion@@ABVQPoint@@HPAVQPainter@@PAVQWidgetBackingStore@@@Z"),
- new D_QWidgetPrivate_repaint_sys(QWidgetPrivate_repaint_sys_Hooked),
- this);
-
- QWidgetPrivate_repaint_sysHook.ThreadACL.SetExclusiveACL(new Int32[1]);
-
- Log.WriteLine("QWidgetPrivate::repaint_sys Hooked");
- #endif
-
-
- QPainter_drawTextHook = LocalHook.Create(
- LocalHook.GetProcAddress("QtGui4.dll", "?drawTextItem@QPainter@@QAEXABVQPointF@@ABVQTextItem@@@Z"),
- new D_QPainter_drawTextItem(
- QPainter_drawTextItem_Hooked), this);
-
- QPainter_drawTextHook.ThreadACL.SetExclusiveACL(new Int32[1]);
- Log.WriteLine("QPainter::drawText() hooked");
- #if false
- /*
- IntPtr lib=NativeAPI.LoadLibrary("InjectNative.dll");
- IntPtr fun = NativeAPI.GetProcAddress(lib, "QPainter_drawTextItem");
- if (fun != IntPtr.Zero)
- {
- QPainter_drawTextHook = LocalHook.CreateUnmanaged(LocalHook.GetProcAddress("QtGui4.dll", "?drawTextItem@QPainter@@QAEXABVQPointF@@ABVQTextItem@@@Z"),
- fun, IntPtr.Zero);
- QPainter_drawTextHook.ThreadACL.SetExclusiveACL(new Int32[1]);
- }*/
- QWidget_getDC = LocalHook.Create(
- LocalHook.GetProcAddress("QtGui4.dll", "?getDC@QWidget@@UBEPAUHDC__@@XZ"),
- new D_QWidget_getDC(
- QWidget_getDC_Hooked), this);
-
- QWidget_getDC.ThreadACL.SetExclusiveACL(new Int32[1]);
- Log.WriteLine("QWidget::getDC() hooked");
- #endif
- }
- catch (Exception e)
- {
- /*
- Now we should notice our host process about this error...
- */
- Interface.ReportError(RemoteHooking.GetCurrentProcessId(), e);
- Log.WriteLine("Exception in Injector.Run {0}", e);
- return;
- }
-
-
- // wait for host process termination...
- try
- {
- Log.Write("Getting process...");
- Process myProcess = Process.GetCurrentProcess();
- IntPtr hMainWnd = myProcess.MainWindowHandle;
- Log.WriteLine("PID={0}, hMainWnd={1}", myProcess.Id, hMainWnd);
-
- // send enum windows
- EnumWindows enuWnd = new EnumWindows();
- enuWnd.GetWindows(hMainWnd);
-
- WinWnd mainWnd = new WinWnd(hMainWnd);
- Log.WriteLine("MAIN WINDOW ({1} childs): {0}", mainWnd,enuWnd.Items.Count);
-
- Interface.FireWindowEvent(new WindowEventArgs(WindowEventType.Add, myProcess.Id, mainWnd, null));
-
- foreach (WinWnd wnd in enuWnd.Items)
- {
- Log.WriteLine("WINDOW: {0}",wnd);
- Interface.FireWindowEvent(new WindowEventArgs(WindowEventType.Add, myProcess.Id, wnd, enuWnd.Items));
- }
-
- while (Interface.Ping(RemoteHooking.GetCurrentProcessId()))
- {
- Log.WriteLine("Waiting queue...");
- Log.Flush();
- Thread.Sleep(500);
-
- // transmit newly monitored file accesses...
- lock (Queue)
- {
- while (Queue.Count > 0)
- {
- EventArgs args = Queue.Pop();
- //Log.WriteLine("InjectedCall: {0}", args);
- if (args is CallEventArgs)
- {
- // args.Process = RemoteHooking.GetCurrentProcessId();
- Interface.FireCallEvent(args as CallEventArgs);
- }
- else if (args is GUINodeEventArgs)
- {
- Interface.FireGUINodeEvent(args as GUINodeEventArgs);
- }
- }
- }
- }
- Log.WriteLine("Exiting Injector...");
- }
- catch (Exception e)
- {
- Log.WriteLine("Exiting Injector on exception: {0}", e);
- // NET Remoting will raise an exception if host is unreachable
- }
- }
- #region
- /* [DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.StdCall)]
- static extern IntPtr CreateFile(
- String InFileName,
- UInt32 InDesiredAccess,
- UInt32 InShareMode,
- IntPtr InSecurityAttributes,
- UInt32 InCreationDisposition,
- UInt32 InFlagsAndAttributes,
- IntPtr InTemplateFile);*/
- #endregion
- #region CreateFile
- [UnmanagedFunctionPointer(CallingConvention.StdCall, CharSet=CharSet.Unicode, SetLastError=true)]
- delegate IntPtr DCreateFile(
- String InFileName,
- UInt32 InDesiredAccess,
- UInt32 InShareMode,
- IntPtr InSecurityAttributes,
- UInt32 InCreationDisposition,
- UInt32 InFlagsAndAttributes,
- IntPtr InTemplateFile);
-
- delegate void DCreateFileAsync(
- Int32 InClientPID,
- IntPtr InHandle,
- String InFileName,
- UInt32 InDesiredAccess,
- UInt32 InShareMode,
- IntPtr InSecurityAttributes,
- UInt32 InCreationDisposition,
- UInt32 InFlagsAndAttributes,
- IntPtr InTemplateFile);
-
-
-
- // this is where we are intercepting all file accesses!
- static IntPtr CreateFile_Hooked(
- String InFileName,
- UInt32 InDesiredAccess,
- UInt32 InShareMode,
- IntPtr InSecurityAttributes,
- UInt32 InCreationDisposition,
- UInt32 InFlagsAndAttributes,
- IntPtr InTemplateFile)
- {
- try
- {
- Injector This = (Injector)HookRuntimeInfo.Callback;
-
- lock (This.Queue)
- {
- if(This.Queue.Count < 1000)
- This.Queue.Push(new CallEventArgs("CreateFile",null, InFileName, InDesiredAccess, InShareMode, InSecurityAttributes, InCreationDisposition, InFlagsAndAttributes, InTemplateFile));
- }
- }
- catch
- {
- }
-
- // call original API...
- return Api.CreateFile(
- InFileName,
- InDesiredAccess,
- InShareMode,
- InSecurityAttributes,
- InCreationDisposition,
- InFlagsAndAttributes,
- InTemplateFile);
- }
- #endregion
-
- #region ExtTextOutW
-
- [UnmanagedFunctionPointer(CallingConvention.StdCall,
- CharSet = CharSet.Auto,
- SetLastError = true)]
- delegate bool DExtTextOutW(
- IntPtr hdc,
- int X,
- int y,
- uint fuOptions,
- [In] ref IntPtr lprc,
- string lpString,
- uint cbCount,
- [In] IntPtr lpDx
- );
-
-
-
- // this is where we are intercepting all file accesses!
- static bool ExtTextOutW_Hooked(
- IntPtr hdc,
- int X,
- int Y,
- uint fuOptions,
- [In] ref IntPtr lprc,
- string lpString,
- uint cbCount,
- [In] IntPtr lpDx)
- {
- try
- {
- Injector This = (Injector)HookRuntimeInfo.Callback;
-
- Log.WriteLine("* ExtTextOutW "+lpString);
-
- IntPtr hwnd = Api.WindowFromDC(hdc);
-
- Log.WriteLine(" WindowFromDC({0})={1}", hdc, hwnd);
-
- lock (This.Queue)
- {
- if (This.Queue.Count < 1000)
- This.Queue.Push(new CallEventArgs("ExtTextOutW", null, hwnd, hdc, X, Y, fuOptions, lprc, lpString, cbCount, lpDx));
- }
- }
- catch
- {
- }
-
- // call original API...
- return Api.ExtTextOutW(
- hdc,
- X,
- Y,
- fuOptions,
- ref lprc,
- lpString,
- cbCount,
- lpDx
- );
-
- }
- #endregion
-
- [StructLayout(LayoutKind.Sequential, Pack=8)]
- public struct QTextItem
- {
- System.Int32 a0;
- System.Int32 a1;
- System.Int32 a2;
- System.Int32 a3;
- System.Int32 a4;
- System.Int32 a5;
- System.Int32 a6;
- System.Int32 a7;
- public System.Int32 len;
- [MarshalAs(UnmanagedType.LPWStr, SizeParamIndex = 1)]
- public string str;
- };
-
- [StructLayout(LayoutKind.Sequential, Pack = 8,Size=32)]
- public struct QPointF
- {
- public System.Double x;
- public System.Double y;
- };
-
- [StructLayout(LayoutKind.Sequential, Size=4)]
- public struct QString
- {
- public IntPtr data;
- };
-
- [StructLayout(LayoutKind.Sequential, Pack = 8, CharSet=CharSet.Unicode)]
- public struct WIDGETINFO
- {
- [MarshalAs(UnmanagedType.LPWStr, SizeParamIndex = 1)]
- public string title;
- [MarshalAs(UnmanagedType.LPWStr, SizeParamIndex = 1)]
- public string name;
- [MarshalAs(UnmanagedType.LPStr, SizeParamIndex = 1)]
- public string clazz;
- public System.Double x;
- public System.Double y;
- public System.Double w;
- public System.Double h;
- }
-
- static string widgetInfoString(IntPtr widget)
- {
- String result = "";
- WIDGETINFO wi = new WIDGETINFO();
- while (widget != IntPtr.Zero)
- {
- result += widget;
- widget = QWidget_describe(widget, ref wi);
- result += " CLASS(" + wi.clazz + ")NAME(" + wi.name + ")TITLE(" + wi.title + ")";
- result += "(" + wi.x + "," + wi.y + ",w=" + wi.w + ",h=" + wi.h + ")";
- result += " -> ";
- //Log.WriteLine("Widget-Parent "+widget+";"+(widget==IntPtr.Zero));
- }
- return result;
- }
-
- [DllImport ("QtGui4.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.ThisCall,
- EntryPoint = "?drawTextItem@QPainter@@QAEXABVQPointF@@ABVQTextItem@@@Z")] // Unicode
- public static extern void QPainter_drawTextItem(IntPtr obj, IntPtr pt, IntPtr ti);
-
- [UnmanagedFunctionPointer(CallingConvention.ThisCall,
- CharSet = CharSet.Unicode, SetLastError = true)]
- delegate void D_QPainter_drawTextItem(IntPtr obj, IntPtr pt, IntPtr ti);
-
-
- static void QPainter_drawTextItem_Hooked( IntPtr obj, IntPtr pt, IntPtr ti)
- {
-
- QTextItem qti = (QTextItem)Marshal.PtrToStructure
- (ti, typeof(QTextItem));
-
- QPointF qpt = (QPointF)Marshal.PtrToStructure
- (pt, typeof(QPointF));
-
- IntPtr widget = QPainter_getWidget(obj);
-
- Log.Write("* QPainter::drawTextItem("+qti.str+";("+qpt.x+","+qpt.y+");");
- Log.WriteLine(" with widget="+widgetInfoString(widget));
-
-
- try
- {
- Injector This = (Injector)HookRuntimeInfo.Callback;
-
- lock (This.Queue)
- {
- WIDGETINFO wi = new WIDGETINFO();
- List<GUINode> nodes = new List<GUINode>();
- int handle = widget.ToInt32();
- while (widget != IntPtr.Zero)
- {
- widget = QWidget_describe(widget, ref wi);
- GUINode guiNode = new GUINode();
- guiNode.Handle = handle;
- guiNode.Bounds = new System.Drawing.RectangleF((float)wi.x, (float)wi.y, (float)wi.w, (float)wi.h);
- guiNode.Class = wi.clazz + ":" + wi.name;
- guiNode.Title = wi.title;
- guiNode.ParentHandle = widget.ToInt32();
- nodes.Add(guiNode);
- handle = widget.ToInt32();
- }
-
- for (int i = 0; i < nodes.Count - 1; i++)
- {
- nodes[i].Parent = nodes[i + 1];
- }
-
- for (int i = 0; i < nodes.Count; i++)
- {
- if (!This.GuiNodes.Contains(nodes[i].Handle))
- {
- This.GuiNodes.Add(nodes[i]);
- This.Queue.Push(new GUINodeEventArgs(nodes[i]));
- }
- }
-
- if (This.Queue.Count < 1000)
- This.Queue.Push(new CallEventArgs("QPainter::drawtextItem", null,qti.str, qpt.x, qpt.y, handle));
- }
- }
- catch
- {
- }
-
-
- QPainter_drawTextItem( obj, pt, ti);
- }
-
- #if false
- [DllImport("QtGui4.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.ThisCall,
- EntryPoint = "?getDC@QWidget@@UBEPAUHDC__@@XZ")] // Unicode
- public static extern IntPtr QWidget_getDC_real(IntPtr obj);
-
- [UnmanagedFunctionPointer(CallingConvention.ThisCall,
- CharSet = CharSet.Unicode, SetLastError = true)]
- delegate IntPtr D_QWidget_getDC(IntPtr obj);
-
- static IntPtr QWidget_getDC_Hooked(IntPtr obj)
- {
- IntPtr dc = QWidget_getDC_real(obj);
-
- Log.WriteLine(string.Format("* QWidget::getDC()={0:x}",dc));
-
-
- try
- {
- Injector This = (Injector)HookRuntimeInfo.Callback;
-
- lock (This.Queue)
- {
- if (This.Queue.Count < 1000)
- This.Queue.Push(new CallEventArgs("QWidget::getDC", dc));
- }
- }
- catch
- {
- }
- return dc;
-
-
- }
-
- [DllImport("QtGui4.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.ThisCall,
- EntryPoint = "?drawWidget@QWidgetPrivate@@QAEXPAVQPaintDevice@@ABVQRegion@@ABVQPoint@@HPAVQPainter@@PAVQWidgetBackingStore@@@Z")] // Unicode
- public static extern void QWidgetPrivate_repaint_sys_real(IntPtr obj, IntPtr qpdev, IntPtr qrgn, IntPtr qpt,int i,IntPtr qpaint,IntPtr qbacksto);
-
- [UnmanagedFunctionPointer(CallingConvention.ThisCall,
- CharSet = CharSet.Unicode, SetLastError = true)]
- delegate void D_QWidgetPrivate_repaint_sys(IntPtr obj, IntPtr qpdev, IntPtr qrgn, IntPtr qpt,int i,IntPtr qpaint,IntPtr qbacksto);
-
- static void QWidgetPrivate_repaint_sys_Hooked(IntPtr obj, IntPtr qpdev, IntPtr qrgn, IntPtr qpt,int i,IntPtr qpaint,IntPtr qbacksto)
- {
- Log.WriteLine(string.Format("*==> QWidget::drawWidget {{ "+obj));
- IntPtr qwidget = QWidgetPrivate_qfunc(obj);
- Log.WriteLine("+qfunc "+ qwidget);
- IntPtr q2 = Marshal.ReadIntPtr(obj, 4);
- Log.WriteLine("+q2 " + q2);
- string wtitle = QWidget_title(qwidget);
- Log.WriteLine("+windowtitle "+wtitle);
- /*IntPtr data = Marshal.ReadIntPtr(wtitle);
- Log.WriteLine("+dataptr "+data);
- IntPtr chrs = Marshal.ReadIntPtr(data, 12);
- Log.WriteLine("+charptr "+chrs);
- string s = Marshal.PtrToStringUni(chrs);
- Log.WriteLine("title="+s);*/
- QWidgetPrivate_repaint_sys_real(obj, qpdev, qrgn, qpt,i,qpaint,qbacksto);
-
- Log.WriteLine(string.Format("*<== QWidget::drawWidget}}"));
- }
-
-
- [DllImport("QtGui4.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.ThisCall,
- EntryPoint = "?q_func@QWidgetPrivate@@AAEPAVQWidget@@XZ")] // Unicode
- public static extern IntPtr QWidgetPrivate_qfunc(IntPtr obj);
-
- [DllImport("QtGui4.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.ThisCall,
- EntryPoint = "?windowTitle@QWidget@@QBE?AVQString@@XZ")] // Unicode
- public static extern QString QWidget_windowTitle(IntPtr obj);
- #endif
- [DllImport("InjectNative.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.StdCall,
- EntryPoint = "QWidget_describe")] // Unicode
- public static extern IntPtr QWidget_describe(IntPtr obj, ref WIDGETINFO info);
-
- [DllImport("InjectNative.dll", CharSet = CharSet.Unicode, SetLastError = true, CallingConvention = CallingConvention.StdCall,
- EntryPoint = "QPainter_getWidget")] // Unicode
- public static extern IntPtr QPainter_getWidget(IntPtr obj);
-
- }
- }