【问题标题】:MemorySharp setting offset to an address not workingMemorySharp 设置偏移到地址不起作用
【发布时间】:2013-09-22 16:45:50
【问题描述】:

好的,我正在使用MemorySharp 库来读/写游戏的内存。我的问题是当我尝试将偏移量添加到基指针地址时,Visual Studio 在运行时抛出错误。这是基本代码

using (var m = new MemorySharp(ApplicationFinder.FromProcessName("Cube").First()))
{
    IntPtr healthPtr = GetBaseAddress("Cube") + 0x0036B1C8;
    int[] offsets = {0x39c, 0x16c};

foreach(var offset in offsets)
{
    healthPtr = m[healthPtr + offset].Read<IntPtr>(); //I'm getting the error on this line
}

var healthLocation = m[m[healthPtr].Read<IntPtr>()];
float health = healthLocation.Read<float>();
MessageBox.Show(health.ToString());
}

这是我的 GetBaseAddress 方法

internal static IntPtr GetBaseAddress(string ProcessName)
{
    try
    {
        Process[] L2Process = Process.GetProcessesByName(ProcessName);
        return L2Process[0].MainModule.BaseAddress;
    }
    catch { return IntPtr.Zero; }
}

但是当我运行这个 Visual Studios 时会抛出这个错误

“'System.ArgumentOutOfRangeException' 类型的未处理异常发生在 MemorySharp.dll 附加信息:相对地址不能大于 主模块大小。”

而且它指向这行代码healthPtr = m[healthPtr + offset].Read&lt;IntPtr&gt;(); 不太确定我在这里做错了什么。

编辑
这是我的更新代码,但仍然无法正常工作

using (var m = new MemorySharp(ApplicationFinder.FromProcessName("Cube").First()))
{
    var healthPtr = new IntPtr(0x0036B1C8);
    int[] offsets = { 0x39c, 0x16c };
    healthPtr = m[healthPtr].Read<IntPtr>();

    foreach (var offset in offsets)
    {
        healthPtr = m[healthPtr + offset, false].Read<IntPtr>(); // false is here to avoid rebasing
    }

    float Health = m[healthPtr, false].Read<float>(); // false is here to avoid rebasing
    MessageBox.Show(Health.ToString());
}

找到编辑答案
我必须将最终指针读取为我想要的类型。所以只有 2 个指针,我读取第一个指针,然后在最后一个读取指针,就像这样

using (var m = new MemorySharp(ApplicationFinder.FromProcessName("Cube").First()))
{
    var healthPtr = new IntPtr(0x0036B1C8);
    int[] offsets = { 0x39C, 0x16C };
    healthPtr = m[healthPtr].Read<IntPtr>();

    healthPtr = m[healthPtr + offsets[0], false].Read<IntPtr>(); // false is here to avoid rebasing

    float Health = m[healthPtr + offsets[1],false].Read<float>();
    MessageBox.Show(Health.ToString());
}

【问题讨论】:

    标签: c# visual-studio pointers memory-address memory-editing


    【解决方案1】:

    首先,使用MemorySharp 对象的索引器已经将指针变基到进程的主模块的基地址。所以,你不需要使用你的函数GetBaseAddress,你可以像这样声明你的指针/偏移量:

    var healthPtr = new IntPtr(0x0036B1C8);
    int[] offsets = { 0x39c, 0x16c };
    

    现在读取指针的值

    healthPtr = m[healthPtr].Read<IntPtr>(); // The pointer is automatically rebased
    

    使用偏移量浏览指针链

    foreach (var offset in offsets)
    {
        healthPtr = m[healthPtr + offset, false].Read<IntPtr>(); // false is here to avoid rebasing
    }
    

    注意第二个参数设置为false。它声明地址不能重新定位到进程的主模块。

    此外,在第一次读取后使用偏移量也很重要,否则声明偏移量而不是直接将值添加到地址的目的是什么。 :)

    我认为设置 var healthLocation 的行是不需要的,它将读取未知的内存地址。你确定要这样做吗?

    这个错误:

    “'System.ArgumentOutOfRangeException' 类型的未处理异常 发生在 MemorySharp.dll 附加信息:相对 地址不能大于主模块大小。”

    如果您没有将第二个参数设置为 false(如上所述),则 MemorySharp 已经将指针变基(rebase)。

    让我知道这是否适合你。

    【讨论】:

    • 好的,现在它通过了循环,但是现在当我尝试读取浮点数时,它会抛出与以前相同的错误,我编辑了我的问题以显示我当前的代码
    • 和之前一样,设置第二个参数为false(不需要rebase指针)float Health = m[healthPtr, false].Read&lt;float&gt;();。
    • 好的,在将第二个参数设置为 false 并再次尝试后,我得到“MemorySharp.dll 中出现“System.ComponentModel.Win32Exception”类型的未处理异常附加信息:无法读取 4 字节( s) 从 0x3F800000 开始。”现在我真的很困惑哈哈,以为那会是最后一个错误,是的,它发生在同一行
    • 检查所有指针级别是否正确,并使用CheatEngine之类的工具检查0x3F800000位置是否有东西。
    • 好的所以我发现了问题但不知道如何解决它,我将地址内容添加到作弊引擎中以跟踪地址,并使用 Visual Studio 中的消息框来传递更改的地址。在它添加 0x39C 并指向正确的地址 (16ECD168) 之后,当它添加 0x16C 时它应该转到 (16ECD2D4) 但它转到 (3F800000) 时,它在将 16C 添加到指针时搞砸了。为什么会这样?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-04-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-05-04
    • 2012-09-26
    • 1970-01-01
    相关资源
    最近更新 更多