assembly - 使用 MOV 和 JMP 的汇编替代方案
问题描述
目前我有这段代码可以使用 MOV 和 JMP 将我的函数地址放入内存中。我的问题是我可以使用 MOV 或 JMP 的替代品吗?这可以用 LEA 来完成吗?如果可以,怎么做?谢谢!
BYTE orig[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; // 12 bytes being replaced
BYTE code[] = { 0x48, 0xB8 }; //MOV RAX
BYTE code_end[] = { 0xFF, 0xE0 }; // JMP RAX
RtlSecureZeroMemory(&orig, sizeof(orig));
memcpy((PVOID)((ULONG_PTR)orig), &code, sizeof(code));
uintptr_t hook_address = reinterpret_cast<uintptr_t>(kernel_function_address);
memcpy((PVOID)((ULONG_PTR)orig + sizeof(code)), &hook_address, sizeof(void*));
memcpy((PVOID)((ULONG_PTR)orig + sizeof(code) + sizeof(void*)), code_end, sizeof(code_end));
解决方案
是的,它可以用LEA
. 因为我假设这是在 Windows 操作系统上,所以同一用户模式进程模块中的地址永远不会超过 32 位偏移量。(无论如何,您都不应尝试修改内核内存,否则会产生严重后果)。这意味着使用的 32 位偏移量LEA
就足够了。为此,首先选择一个寄存器,为简单起见,让我们选择RCX
. 然后像这样引用跳转目标:
LEA RCX, MY_JUMP_TARGET
这将有效地为您提供比 10 字节 mov 更短的组件并节省空间。在此之后,只需跳转:
JMP RCX
. 那替代品JMP
呢?您可以使用如下CALL
指令:
CALL RCX
事实上,您实际上可以将整个事情简化为单个CALL
or JMP
,因为这些指令不仅支持通用寄存器作为操作数,还支持直接偏移:
CALL MY_JUMP_TARGET
或者
JMP MY_JUMP_TARGET
(请注意:使用CALL
指令会将返回地址压入堆栈,因此您需要将其与 . 匹配RET
。)
PS。我不会提供您可以粘贴的可复制粘贴解决方案,这不是 Stack Overflow 的工作方式。
推荐阅读
- node.js - 带有 Angular 5 应用程序的 Azure 部署选项无法在持续集成中编译和构建
- javascript - 如何比较数组中的连续日期/时间项并根据特定时间进行过滤
- sql - 如何创建将在聊天中返回单个消息的过程
- c - 带字符的免费结构数组**
- r - 在 R 中有条件地使用滞后值
- d3.js - Leaflet.js 上的自定义坐标和轴范围
- javascript - jQuery插件 - 初始化后更新元素
- java - 将不同的两个图像添加到 Firebase 实时数据库
- reactjs - 如何使用 reactjs 动态生成一对输入字段
- node.js - 为什么我从运行指向 Angular 应用程序的 /dist 文件夹的节点服务器得到一个空白页面?