所以我有一个非常基本的cs文件,它是一个.dll文件。
我正在使用Process Hacker手动注入我的NotePad进程.. 此时它应该执行它并运行MessageBox正确吗? (纠正我,如果我错了那个)
起初我认为我的喷油器有问题,但似乎是dll。 (随意通过下面的注射器检查) (这是我第一次尝试创建一个dll文件)
我是否需要以某种方式制作Dll钩子,或者它是否真的很简单?
DLL。
using System;
using System.Windows.Forms;
namespace SomeName
{
public class Class1
{
public static void Main()
{
MessageBox.Show("Lets try this");
}
}
}
注射器
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace FormDLLInjection
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
[DllImport("kernel32")]
public static extern IntPtr CreateRemoteThread(
IntPtr hProcess,
IntPtr lpThreadAttributes,
uint dwStackSize,
UIntPtr lpStartAddress, // raw Pointer into remote process
IntPtr lpParameter,
uint dwCreationFlags,
out IntPtr lpThreadId
);
[DllImport("kernel32.dll")]
public static extern IntPtr OpenProcess(
UInt32 dwDesiredAccess,
Int32 bInheritHandle,
Int32 dwProcessId
);
[DllImport("kernel32.dll")]
public static extern Int32 CloseHandle(
IntPtr hObject
);
[DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
static extern bool VirtualFreeEx(
IntPtr hProcess,
IntPtr lpAddress,
UIntPtr dwSize,
uint dwFreeType
);
[DllImport("kernel32.dll", CharSet = CharSet.Ansi, ExactSpelling = true)]
public static extern UIntPtr GetProcAddress(
IntPtr hModule,
string procName
);
[DllImport("kernel32.dll", SetLastError = true, ExactSpelling = true)]
static extern IntPtr VirtualAllocEx(
IntPtr hProcess,
IntPtr lpAddress,
uint dwSize,
uint flAllocationType,
uint flProtect
);
[DllImport("kernel32.dll")]
static extern bool WriteProcessMemory(
IntPtr hProcess,
IntPtr lpBaseAddress,
string lpBuffer,
UIntPtr nSize,
out IntPtr lpNumberOfBytesWritten
);
[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr GetModuleHandle(
string lpModuleName
);
[DllImport("kernel32", SetLastError = true, ExactSpelling = true)]
internal static extern Int32 WaitForSingleObject(
IntPtr handle,
Int32 milliseconds
);
public Int32 GetProcessId(String proc)
{
Process[] ProcList;
ProcList = Process.GetProcessesByName(proc);
return ProcList[0].Id;
}
public void InjectDLL(IntPtr hProcess, String strDLLName)
{
IntPtr bytesout;
// Length of string containing the DLL file name +1 byte padding
Int32 LenWrite = strDLLName.Length + 1;
// Allocate memory within the virtual address space of the target process
IntPtr AllocMem = (IntPtr)VirtualAllocEx(hProcess, (IntPtr)null, (uint)LenWrite, 0x1000, 0x40); //allocation pour WriteProcessMemory
// Write DLL file name to allocated memory in target process
WriteProcessMemory(hProcess, AllocMem, strDLLName, (UIntPtr)LenWrite, out bytesout);
// Function pointer "Injector"
UIntPtr Injector = (UIntPtr)GetProcAddress(GetModuleHandle("kernel32.dll"), "LoadLibraryA");
if (Injector == null)
{
MessageBox.Show(" Injector Error! \n ");
// return failed
return;
}
// Create thread in target process, and store handle in hThread
IntPtr hThread = (IntPtr)CreateRemoteThread(hProcess, (IntPtr)null, 0, Injector, AllocMem, 0, out bytesout);
// Make sure thread handle is valid
if (hThread == null)
{
//incorrect thread handle ... return failed
MessageBox.Show(" hThread [ 1 ] Error! \n ");
return;
}
// Time-out is 10 seconds...
int Result = WaitForSingleObject(hThread, 10 * 1000);
// Check whether thread timed out...
if (Result == 0x00000080L || Result == 0x00000102L || Result == 0xFFFFFFFF)
{
/* Thread timed out... */
MessageBox.Show(" hThread [ 2 ] Error! \n ");
// Make sure thread handle is valid before closing... prevents crashes.
if (hThread != null)
{
//Close thread in target process
CloseHandle(hThread);
}
return;
}
// Sleep thread for 1 second
Thread.Sleep(1000);
// Clear up allocated space ( Allocmem )
VirtualFreeEx(hProcess, AllocMem, (UIntPtr)0, 0x8000);
// Make sure thread handle is valid before closing... prevents crashes.
if (hThread != null)
{
//Close thread in target process
CloseHandle(hThread);
}
// return succeeded
return;
}
private void injectBtn_Click(object sender, EventArgs e)
{
String strDLLName = @"DllPath"; // here you put the dll you want, only the path.
String strProcessName = "notepad"; //here you will put the process name without ".exe"
Int32 ProcID = GetProcessId(strProcessName);
if (ProcID >= 0)
{
IntPtr hProcess = (IntPtr)OpenProcess(0x1F0FFF, 1, ProcID);
if (hProcess == null)
{
MessageBox.Show("OpenProcess() Failed!");
return;
}
else
InjectDLL(hProcess, strDLLName);
}
}
}
}
答案 0 :(得分:1)
遗憾的是,您无法将.NET程序集注入到本身没有首先加载CLR的本机进程中。当您尝试从本机进程加载托管DLL时,.NET不会神奇地做到这一点。后者的唯一例外是托管代码是作为COM对象公开的。为什么我的类文件在内存中启动时不执行?
现在你的代码实际上可能导致记事本尝试加载你的.dll,但是由于缺少DllMain
(Windows希望它在此时成为本机DLL)将失败。
作为 cdkMoose' 的后续评论,即使您将其DllMain
称为“{1}},评论也是默认Main
或DllMain
存在于托管程序集EXPORTS
表中,因为它没有。有additional steps用于手动公开托管方法,使其显示为本机进程可识别的EXPORT
条目。
让我们假设NotePad之前的prepared a CLR environment与SQL Server完全相同。它看起来像这样:
HRESULT hr;
ICLRMetaHost *pMetaHost = NULL;
ICLRRuntimeInfo *pRuntimeInfo = NULL;
ICLRRuntimeHost *pClrRuntimeHost = NULL;
// build runtime
hr = CLRCreateInstance(CLSID_CLRMetaHost, IID_PPV_ARGS(&pMetaHost));
hr = pMetaHost->GetRuntime(L"v4.0.30319", IID_PPV_ARGS(&pRuntimeInfo));
hr = pRuntimeInfo->GetInterface(CLSID_CLRRuntimeHost,
IID_PPV_ARGS(&pClrRuntimeHost));
// start runtime
hr = pClrRuntimeHost->Start();
然后在这种情况下,NotePad或SQL不会将LoadLibraryA
用于您的程序集,而是:
// execute managed assembly
DWORD pReturnValue;
hr = pClrRuntimeHost->ExecuteInDefaultAppDomain(
L"T:\\FrameworkInjection\\_build\\debug\\anycpu\\InjectExample.exe",
L"InjectExample.Program",
L"EntryPoint",
L"hello .net runtime",
&pReturnValue);
...假设您的.NET程序集正在公开static int EntryPoint(String pwzArgument)
。
所以关注:
Main
或DllMain
......我们不必担心因为:
static
方法EXPORTS
表LoadLibrary
)