0

我正在编写一个 MSN Plus 脚本,实际上是 javascript。
对于与 Windows 的互操作,有一个名为Interop.
使用它的静态函数Call,可以调用指定 dll 中的指定函数,最多 12 个参数。
我的目标是编写一个从 PID 中获取进程名称的脚本。
我做的一切都是正确的,但它仍然不起作用。

函数 GetProcNameFromPID(pid)  
{
    var hnd = Interop.Call("kernel32", "CreateToolhelp32Snapshot", 2, 0);
    var handle = Interop.Call("kernel32", "GetCurrentProcess");
    var StructP = Interop.Allocate(4+4+4+4+4+4+4+4+4+260);//*为ProcessEntry32结构分配空间*
    var hnd_ptr = Interop.Allocate(4);
    var ress = Interop.Call("kernel32", "WriteProcessMemory", 句柄, StructP, StructP.size.DataPtr, 4, hnd_ptr);
    Debug.Trace(ReadInt(hnd_ptr, 0));
    var res = Interop.Call("kernel32", "Process32FirstW", hnd, StructP.DataPtr);
    如果(!res)
    {
        Debug.Trace("FAAAAIIIILLLLL / " + Interop.Call("kernel32", "GetLastError") + " / " + ress);
    }
    别的
    {
        做
        {
            变量位置 = 0;
            ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            var owpid = ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            var parpid = ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            ReadInt(StructP, pos);
            var name = ReadString(pos, 50);
            如果(pid == owpid)
                返回名称;
            StructP = Interop.Allocate(4+4+4+4+4+4+4+8+4+50);
            Interop.Call("kernel32", "WriteProcessMemory", 句柄, StructP.DataPtr, StructP.size.DataPtr, 4, null);
        }
            while(Interop.Call("kernel32", "Process32NextW", hnd, StructP.DataPtr) == true)
    }
}
函数 ReadInt(缓冲区,位置)
{
变量 res = 0;
    for(var i = 0; i >> 24;  
    var b2 = 地址 >> 24;  
    var b3 = 地址 >> 24;  
    var b4 = 地址 >> 24;  
    返回 b4 + b3*256 + b2*256*256 + b1*256*256*256;  
}  

Process32FirstW函数始终成功,但结构为空。
WriteProcessMemory功能也成功了。但写入的字节数始终为 0。

4

1 回答 1

1

我没有机器来测试东西,但你的第一个问题是你似乎没有将正确的参数传递给WriteProcessMemory

BOOL WINAPI WriteProcessMemory(
  __in   HANDLE hProcess,
  __in   LPVOID lpBaseAddress,
  __in   LPCVOID lpBuffer,
  __in   SIZE_T nSize,
  __out  SIZE_T *lpNumberOfBytesWritten
);

你路过...

handle => hProcess,
StructP => lpBaseAddress, // ???
StructP.size.DataPtr => lpBuffer, // ???
4 => nSize,
hnd_ptr => lpNumberOfBytesWritten

让我们从WriteProcessMemory 的概述开始:它应该在当前进程中获取一大块数据,由lpBuffer 指向,长度为nSize 个字节。它将该数据复制到由 hProcess 指示的进程的内存空间中,并将该数据放在该目标进程中的地址 lpBaseAddress 中。

我在您的代码中看到的问题是:

  1. lpBaseAddress应该是您正在写入的另一个进程中的地址。由于您handle指向当前流程,我什至不知道您为什么要调用此函数。您可以只使用StructP.WriteWORD(Offset, Data)将数据写入您的结构。但我现在假设你这样做是为了最起码的演示目的——看看你是否可以开始WriteProcessMemory()工作。

  2. 我认为这甚至不是有效的代码。 StructP.size存在,但它是一个 int,而不是一个 object。它没有 DataPtr 成员。 StructP.DataPtr也存在。其实StructP.DataPtr就是StructP根据帮助文件指定发送的内容。那么,作为最低限度的测试,您是否再次尝试结构直接写回结构?如果是这样,两个指针都应该是StructP

之后,我不知道ReadInt()您使用的功能来自哪里。在我看来,Databloc 有几个用于读取值的成员函数,但你可以这样称呼它们:hnd_ptr.ReadWORD(0)

我对调用后结构为空并不感到惊讶Process32FirstW(),因为它会检查dwSize结构成员的值。由于您没有成功写入它,我希望该值通常为 0,因此不会写入任何数据。

我从来没有摆弄过 Messger Plus,所以你不得不原谅我被很多东西弄糊涂了。让我知道这是否有用。

于 2010-10-26T01:55:30.030 回答