简体   繁体   English

使用纯托管代码的Hook API

[英]Hook API with pure managed code

I was thinking how can I hook an API with C# or VB.Net, without using a C++ Library like EasyHook or similar libs. 我在想如何使用C#或VB.Net挂钩API,而不使用像EasyHook或类似库这样的C ++库。 The purpose why I like to learn this is not for anything malicous, its just to get more experience and find the limits of whats possible with .net. 我喜欢学习这个目的的目的不是为了任何有用的东西,只是为了获得更多的经验并找到.net的可能性。 Lets say I like to hook the MessageBoxA API. 让我们说我想挂钩MessageBoxA API。 I first import it by Importing System.Runtime.InterropServices and then add the PInvoke Signiature for The MessageBoxA API Call in user32.dll 我首先通过导入System.Runtime.InterropServices导入它,然后在user32.dll中为MessageBoxA API调用添加PInvoke Signiature

<DllImport("user32.dll", EntryPoint:="MessageBoxW", 
           SetLastError:=True, Charset:=Charset.Unicode)> 
Public Function MessageBox(
     hwnd As IntPtr, 
     <MarshalAs(UnmanagedType.LPTSTR)>ByVal lpText As String, 
     <MarshalAs(UnmanagedType.LPTSTR)>ByVal lpCaption As String, 
     <MarshalAs(UnmanagedType.U4)>ByVal uType As MessageBoxOptions
) As <MarshalAs(UnmanagedType.U4)>MessageBoxResult
End Function

I basically like now to hook every process, which calls the MessageBoxA API get the normal text, but with the hook I like to append "hooked" at the end of the messageBox text. 我现在基本上喜欢挂钩每个进程,它调用MessageBoxA API获取普通文本,但是我喜欢在hookBox文本的末尾附加“hooked”。 A friend who is very experienced with .net, but unfortunately to busy to help me with this, told me its definitly possible to do that. 一位对.net非常有经验的朋友,但不幸的是忙着帮我这个,告诉我它绝对有可能做到这一点。 The steps would be, first I need the actual hooking function in a dll (library) which I will later inject in a process, then I need to determine if its a native or a managed process. 步骤将是,首先我需要一个dll(库)中的实际挂钩函数,我稍后将在一个进程中注入,然后我需要确定它是本机还是托管进程。 If its a managed then there is no problem, but if it is a native process I need a loader. 如果它是一个托管然后没有问题,但如果它是一个本机进程我需要一个加载器。 A native process doesn't have .net loaded so i need to load it manually first and then injectz the dll. 本机进程没有.net加载所以我需要先手动加载它然后注入dll。

Then I need to get the Pointer to the .net method as a pointer so I know the adress where my hook should be directed to and then I can use GetProcessAdress and LoadLibraryA to get the Pointer to the API. 然后我需要将.net方法的指针作为指针,这样我就知道我的钩子应该指向的地址,然后我可以使用GetProcessAdress和LoadLibraryA来获取指向API的指针。 The JMP I like to write at the beginning of the API can be realized by using WriteProcessMemory. 我喜欢在API开头编写的JMP可以通过使用WriteProcessMemory来实现。 Can someone show me how this can be realized on a simple example as mentioned above by hooking hte messagebox api and apending some text to it before it is called. 有人可以告诉我如何通过挂钩hte messagebox api并在调用之前将一些文本添加到上面提到的一个简单示例来实现这一点。

=) =)

I'm not sure if this is what you are looking for, but this is how I Hook into the mouse. 我不确定这是否是您正在寻找的,但这就是我如何进入鼠标。 Maybe it can help you figure out other hooks. 也许它可以帮助你弄清楚其他钩子。

Public Class MouseDetector
    Public Event MouseLeftButtonClick(ByVal sender As Object, ByVal e As MouseEventArgs)
    Public Event MouseRightButtonClick(ByVal sender As Object, ByVal e As MouseEventArgs)
    Private Delegate Function MouseHookCallback(ByVal nCode As Integer, ByVal wParam As Integer, ByVal lParam As IntPtr) As Integer
    Private MouseHookCallbackDelegate As MouseHookCallback
    Private MouseHookID As Integer

    Public Sub New()
        If MouseHookID = 0 Then
            MouseHookCallbackDelegate = AddressOf MouseHookProc
            MouseHookID = SetWindowsHookEx(CInt(14), MouseHookCallbackDelegate, Marshal.GetHINSTANCE(Assembly.GetExecutingAssembly.GetModules()(0)), 0)
            If MouseHookID = 0 Then
                'error
            End If
        End If
    End Sub

    Public Sub Dispose()
        If Not MouseHookID = -1 Then
            UnhookWindowsHookEx(MouseHookID)
            MouseHookCallbackDelegate = Nothing
        End If
        MouseHookID = -1
    End Sub

    Private Enum MouseMessages
        WM_LeftButtonDown = 513
        WM_LeftButtonUp = 514
        WM_LeftDblClick = 515
        WM_RightButtonDown = 516
        WM_RightButtonUp = 517
        WM_RightDblClick = 518
    End Enum

    <StructLayout(LayoutKind.Sequential)> Private Structure Point
        Public x As Integer
        Public y As Integer
    End Structure

    <StructLayout(LayoutKind.Sequential)> Private Structure MouseHookStruct
        Public pt As Point
        Public hwnd As Integer
        Public wHitTestCode As Integer
        Public dwExtraInfo As Integer
    End Structure

    <DllImport("user32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall)> _
    Private Shared Function CallNextHookEx(ByVal idHook As Integer, ByVal nCode As Integer, ByVal wParam As IntPtr, ByVal lParam As IntPtr) As Integer
    End Function

    <DllImport("User32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall, SetLastError:=True)> _
    Private Shared Function SetWindowsHookEx(ByVal idHook As Integer, ByVal HookProc As MouseHookCallback, ByVal hInstance As IntPtr, ByVal wParam As Integer) As Integer
    End Function

    <DllImport("user32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall, SetLastError:=True)> _
    Private Shared Function UnhookWindowsHookEx(ByVal idHook As Integer) As Integer
    End Function

    Private Function MouseHookProc(ByVal nCode As Integer, ByVal wParam As Integer, ByVal lParam As IntPtr) As Integer
        If nCode < 0 Then
            Return CallNextHookEx(MouseHookID, nCode, wParam, lParam)
        End If
        Dim MouseData As MouseHookStruct = Marshal.PtrToStructure(lParam, GetType(MouseHookStruct))
        Select Case wParam
            Case MouseMessages.WM_LeftButtonUp
                RaiseEvent MouseLeftButtonClick(Nothing, New MouseEventArgs(MouseButtons.Left, 1, MouseData.pt.x, MouseData.pt.y, 0))
            Case MouseMessages.WM_RightButtonUp
                RaiseEvent MouseRightButtonClick(Nothing, New MouseEventArgs(MouseButtons.Right, 1, MouseData.pt.x, MouseData.pt.y, 0))
        End Select
        Return CallNextHookEx(MouseHookID, nCode, wParam, lParam)
    End Function
End Class

Private Sub MouseDetector_MouseLeftButtonClick(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles MouseDetector.MouseLeftButtonClick
        'MessageBox.Show("left")
End Sub

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM