使用 Intel PIN 修改寄存器
Modifying registers with Intel PIN
我想破坏所有加载指令 - 本质上,我想找到所有加载指令,并且在加载完成后我想修改存储从内存中读取的值的寄存器中的值。
为此,我检测了所有指令,当我找到加载时,我插入对某个函数的调用,该函数将在加载后破坏写入寄存器。我使用 PIN_REGISTER*
.
传入需要修改的寄存器(即包含从内存加载的数据的寄存器)
假设我知道加载的数据类型(即 int、float 等),我可以根据数据类型 (See this) 访问 PIN_REGISTER
联合。但是,正如您在 link 中看到的那样,PIN_REGISTER
存储一个 数组 值 - 即它不存储一个有符号整数,而是存储 MAX_DWORDS_PER_PIN_REG 有符号整数。
从内存中加载的值是否总是存储在索引 0 处?例如,如果我将一个 32 位有符号整数从内存加载到一个寄存器中,我是否总是可以假设它将存储在 s_dword[0]
?例如,如果我写入 8 位 AH/BH/CH/DH registers 怎么办?由于这些对应于 32 位寄存器的“中间”位,我假设数据 not 位于数组中的索引 0?
找出加载数据存储在数组中哪个索引的最简单方法是什么?
If for instance, I load a 32 bit signed int from memory into a register, can I always assume that it would be stored at s_dword[0]?
是的。
如果您处于长模式并且具有例如 RAX 寄存器,则您有两个 DWORD:较低的低位 32 位(s_dword
中的索引 0)和较高的最重要的 32 位(索引s_dword
).
中的 1 个
What if for instance I write to the 8 bit AH/BH/CH/DH registers? Since these correspond to "middle" bits of 32 bit registers, I assume the data would not be at index 0 in the array?
注:AH
是rAX[8:16]
(rAX是RAX或EAX),不是真的在'middle'.
这实际上取决于您访问的是哪个工会成员。如果我们继续使用 s_dword
成员(或 dword
),那么 AH
仍然在 32 位或 64 位寄存器的“最低”DWORD(索引 0)中。它'同时在最低WORD(16位数量)的高位部分(最高8位)。
// DWORD (32-bit quantity)
auto ah = pinreg->dword[0] >> 8;
auto al = pinreg->dword[0] & 0xff;
// still the same for word (16-bit quantity)
auto ah = pinreg->word[0] >> 8;
auto al = pinreg->word[0] & 0xff;
// not the same for byte (8-bit quantity)
auto ah = pinreg->byte[1];
auto al = pinreg->byte[0];
What's the easiest way for me to figure out which index in the array the loaded data is stored at?
很难说,我很自然地知道它在哪个索引处。只要知道联盟中各种面额的大小,就很简单了:
byte
: 8 位
word
: 16 位
dword
: 32 位
qword
: 64 位
这是一张不同尺寸的草图:
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | byte
+---+---+---+---+---+---+---+---+
+-------+-------+-------+-------+
| 3 | 2 | 1 | 0 | word
+-------+-------+-------+-------+
+---------------+---------------+
| 1 | 0 | dword
+---------------+---------------+
+-------------------------------+
| 0 | qword
+-------------------------------+
^ ^
MSB LSB
AL和AH也一样(可以看到AH是byte[1]
,AL是byte[0]
都在word[0]
,dword[0]
和qword[0]
):
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | AH| AL| byte
+---+---+---+---+---+---+---+---+
+-------+-------+-------+-------+
| 3 | 2 | 1 | 0 | word
+-------+-------+-------+-------+
+---------------+---------------+
| 1 | 0 | dword
+---------------+---------------+
+-------------------------------+
| 0 | qword
+-------------------------------+
^ ^
MSB LSB
我想破坏所有加载指令 - 本质上,我想找到所有加载指令,并且在加载完成后我想修改存储从内存中读取的值的寄存器中的值。
为此,我检测了所有指令,当我找到加载时,我插入对某个函数的调用,该函数将在加载后破坏写入寄存器。我使用 PIN_REGISTER*
.
假设我知道加载的数据类型(即 int、float 等),我可以根据数据类型 (See this) 访问 PIN_REGISTER
联合。但是,正如您在 link 中看到的那样,PIN_REGISTER
存储一个 数组 值 - 即它不存储一个有符号整数,而是存储 MAX_DWORDS_PER_PIN_REG 有符号整数。
从内存中加载的值是否总是存储在索引 0 处?例如,如果我将一个 32 位有符号整数从内存加载到一个寄存器中,我是否总是可以假设它将存储在 s_dword[0]
?例如,如果我写入 8 位 AH/BH/CH/DH registers 怎么办?由于这些对应于 32 位寄存器的“中间”位,我假设数据 not 位于数组中的索引 0?
找出加载数据存储在数组中哪个索引的最简单方法是什么?
If for instance, I load a 32 bit signed int from memory into a register, can I always assume that it would be stored at s_dword[0]?
是的。
如果您处于长模式并且具有例如 RAX 寄存器,则您有两个 DWORD:较低的低位 32 位(s_dword
中的索引 0)和较高的最重要的 32 位(索引s_dword
).
What if for instance I write to the 8 bit AH/BH/CH/DH registers? Since these correspond to "middle" bits of 32 bit registers, I assume the data would not be at index 0 in the array?
注:AH
是rAX[8:16]
(rAX是RAX或EAX),不是真的在'middle'.
这实际上取决于您访问的是哪个工会成员。如果我们继续使用 s_dword
成员(或 dword
),那么 AH
仍然在 32 位或 64 位寄存器的“最低”DWORD(索引 0)中。它'同时在最低WORD(16位数量)的高位部分(最高8位)。
// DWORD (32-bit quantity)
auto ah = pinreg->dword[0] >> 8;
auto al = pinreg->dword[0] & 0xff;
// still the same for word (16-bit quantity)
auto ah = pinreg->word[0] >> 8;
auto al = pinreg->word[0] & 0xff;
// not the same for byte (8-bit quantity)
auto ah = pinreg->byte[1];
auto al = pinreg->byte[0];
What's the easiest way for me to figure out which index in the array the loaded data is stored at?
很难说,我很自然地知道它在哪个索引处。只要知道联盟中各种面额的大小,就很简单了:
byte
: 8 位word
: 16 位dword
: 32 位qword
: 64 位
这是一张不同尺寸的草图:
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | byte
+---+---+---+---+---+---+---+---+
+-------+-------+-------+-------+
| 3 | 2 | 1 | 0 | word
+-------+-------+-------+-------+
+---------------+---------------+
| 1 | 0 | dword
+---------------+---------------+
+-------------------------------+
| 0 | qword
+-------------------------------+
^ ^
MSB LSB
AL和AH也一样(可以看到AH是byte[1]
,AL是byte[0]
都在word[0]
,dword[0]
和qword[0]
):
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | AH| AL| byte
+---+---+---+---+---+---+---+---+
+-------+-------+-------+-------+
| 3 | 2 | 1 | 0 | word
+-------+-------+-------+-------+
+---------------+---------------+
| 1 | 0 | dword
+---------------+---------------+
+-------------------------------+
| 0 | qword
+-------------------------------+
^ ^
MSB LSB