CE训练教程进阶,步骤 9: 注入++

目录

一、找出存放四个玩家健康值的地址

二、找出修改数据的代码

三、找出是谁调用了修改指令

四、分析玩家的内存数据

五、注入修改代码

六、C语言代码注入


相对于前面8个步骤,步骤9稍微要难一点,所以单独写。

CE训练教程进阶,步骤 9: 注入++_第1张图片

 步骤9是在步骤7的基础上,继续讲代码注入。但是它涉及到代码的细粒度区分,比如“攻击”时,上面4个玩家用到的都是同一段代码,这就需要通过代码去判断,什么时候是在攻击自己玩家(玩家1,玩家2),什么时候是在攻击敌方玩家。

一、找出存放四个玩家健康值的地址

精确查找,分别找出存放四个玩家健康值数据的地址,并双击添加到地址栏。注意查找时,数值类型要选单浮点,因为健康值为小数。当然,如果不知道数值是什么类型,也可以用"未知的初始值"查找,只是要麻烦一点

CE训练教程进阶,步骤 9: 注入++_第2张图片

二、找出修改数据的代码

在四个玩家的地址上,右键选择“找出是什么改写了这个地址”后,再点击“攻击”该玩家,修改该玩家健康值的指令就会显示出来。

CE训练教程进阶,步骤 9: 注入++_第3张图片

 最后会发现,攻击每个玩家时,调用的都是这条指令:

10002F25D - F3 0F11 43 08  - movss [rbx+08],xmm0

所以,我们不能直接修改这条指令,实现攻击己方玩家时健康值增加,攻击敌方玩家时健康值降低。

当然,我们说的仅仅是在“攻击”时,如果直接修改玩家的健康值,是可以成功的。

三、找出是谁调用了修改指令

我们需要用反汇编的方式,继续往前找,找出是谁调用了修改健康值的指令。

CE训练教程进阶,步骤 9: 注入++_第4张图片

右键选择“找出指令访问的地址”:

CE训练教程进阶,步骤 9: 注入++_第5张图片

 再分别攻击这四个玩家,四个玩家健康值地址就会显示出来。CE训练教程进阶,步骤 9: 注入++_第6张图片

 当然,如果我们只是找这个四个玩家健康值的地址,前面早就找出来了,根本不用这么麻烦。下面的步骤才是关键,那就是分析数据。

四、分析玩家的内存数据

选中四个玩家地址,然后右键选择“打开选中地址的分析数据”:

CE训练教程进阶,步骤 9: 注入++_第7张图片

 上面界面选了后,会弹出一个框,点确定即可。

 CE训练教程进阶,步骤 9: 注入++_第8张图片

 然后给这个数据结构取一个名字:

CE训练教程进阶,步骤 9: 注入++_第9张图片

 然后会弹出一个框,点击“yes”:

 CE训练教程进阶,步骤 9: 注入++_第10张图片

 这个结构的起始大小默认是4096,点击“ok”:

 CE训练教程进阶,步骤 9: 注入++_第11张图片

 然后这个数据分析的界面就出现了:

CE训练教程进阶,步骤 9: 注入++_第12张图片

 上面这个界面,分别显示了4个玩家对应的内存数据,我们最开始就已经知道,Dave和Eric是一队,而HAL和KITT是另一个队的。通过上面的数据会发现,只有蓝色框框出的那行,比较符合这个规则。

那么这个界面的作用是什么?

1.找出区分队伍的数据地址偏移量,即+0014;

2.找出各玩家健康值的偏移量,即+0008。

五、注入修改代码

回到汇编界面,点击“自动汇编”:

CE训练教程进阶,步骤 9: 注入++_第13张图片

先选择“CT表框架代码”:

 CE训练教程进阶,步骤 9: 注入++_第14张图片

 再选择“代码注入”,并填写地址:

CE训练教程进阶,步骤 9: 注入++_第15张图片

 然后会生成一段模板代码,需要稍微改下:

[ENABLE]
//code from here to '[DISABLE]' will be used to enable the cheat
alloc(newmem,2048,"Tutorial-x86_64.exe"+2F25D) 
label(returnhere)
label(originalcode)
label(exit)

newmem:
  cmp [rbx+14],1//第1队玩家
  je team1
  cmp [rbx+14],2//第2队玩家
  je team2

team1:
  movss xmm0,[rbx+08]// [rbx+08]就是原健康值的地址,即攻击第1队玩家时健康值不变
  jmp originalcode

team2:
  movss xmm0,[value2]// 第2队敌方玩家的健康值为0
  jmp originalcode

value2:
  dd (float)0

originalcode:
movss [rbx+08],xmm0

exit:
jmp returnhere

"Tutorial-x86_64.exe"+2F25D:
jmp newmem
returnhere:
 
[DISABLE]
//code from here till the end of the code will be used to disable the cheat
dealloc(newmem)
"Tutorial-x86_64.exe"+2F25D:
movss [rbx+08],xmm0
//Alt: db F3 0F 11 43 08

 上面代码看起很多,实际只有中间那段是手写的,作用就是:

如果玩家是1队的,健康值不变;如果玩家是2队的,健康值设为0。

保存脚本,然后选择“文件”菜单中的“分配到当前CT表”:

CE训练教程进阶,步骤 9: 注入++_第16张图片

回到CE主界面,激活自动汇编脚本:

CE训练教程进阶,步骤 9: 注入++_第17张图片

 然后点击Tutorial-x86_64.exe的步骤9界面,点击“重新启动游戏并自动执行”,然后随便“攻击”一个玩家,就可以激活“下一步”按钮了。

六、注入C语言代码

直接修改汇编代码,需要对汇编指令相当熟悉才可以,而且逻辑稍微复杂一点,修改起来会相当繁琐。比较幸运的是,在CE中,居然可以直接使用C语言的代码来编写。

下面我用C语言来实现一个功能,那就是:

攻击己方玩家时,健康值减少10;而攻击敌方玩家时,健康值减少100。

[ENABLE]
//code from here to '[DISABLE]' will be used to enable the cheat
alloc(newmem,2048,"Tutorial-x86_64.exe"+2F25D) 
label(returnhere)

{$c}
// {$c} 表示c语言代码块,可以定义我们需要调用的函数。
void SetHP(void* hpBase)
{
   if(*(int*)(hpBase+0x14)!=1){
     *(float*)(hpBase+0x8)=*(float*)(hpBase+0x8)-100; //攻击敌方玩家,健康值减少100。
   }else{
     *(float*)(hpBase+0x8)=*(float*)(hpBase+0x8)-10; //攻击己方玩家,健康值减少10。
   }
}
{$asm}//c代码块结束

newmem:
// 注意这是里用的是ccode,hpBase代表参数名,rbx代表参数值
{$ccode hpBase=rbx}
  SetHP(hpBase);
{$asm}
  jmp returnhere

"Tutorial-x86_64.exe"+2F25D:
jmp newmem
returnhere:
 
[DISABLE]
//code from here till the end of the code will be used to disable the cheat
dealloc(newmem)
"Tutorial-x86_64.exe"+2F25D:
movss [rbx+08],xmm0

上面代码总体来说,比汇编代码要容易读一些,也精简了不少,实现效果如下:

CE训练教程进阶,步骤 9: 注入++_第18张图片

最后再说一点,关于movss指令:

MOVSS,Move scalar single precision floating-point value between XMM registers or between an XMM register and memory.

存放float类型的数据大多是xmm寄存器,而movss指令(SSE指令集之一)则用来移动单精度float类型的数据。

七、注入lua代码

除了可以内嵌C语言的代码外,还可以支持lua代码内嵌,把上面的C语言版本改成lua后,代码如下:

[ENABLE]
//code from here to '[DISABLE]' will be used to enable the cheat
alloc(newmem,2048,"Tutorial-x86_64.exe"+2F25D) 
label(returnhere)

{$lua}//我在win7 64位上面,不加下面这段代码,就不能运行luacode
if not getAddressSafe('luaclient-x86_64.dll') then
  assert(injectDLL('luaclient-x86_64.dll'))
end
{$asm}

newmem:
//hpBase代表参数名,rbx代表参数值
{$luacode hpBase=rbx}
  if readInteger(hpBase+0x14)==1
  then
    writeFloat(hpBase+0x8,readFloat(hpBase+0x8)-10.0)
  else
    writeFloat(hpBase+0x8,0)
  end

{$asm}//这里必须要顶格写,不然会报错
  jmp returnhere

"Tutorial-x86_64.exe"+2F25D:
jmp newmem
returnhere:
 
[DISABLE]
//code from here till the end of the code will be used to disable the cheat
dealloc(newmem)
"Tutorial-x86_64.exe"+2F25D:
movss [rbx+08],xmm0

 lua语法更加简洁一些,但是在我的电脑(win7 64位)上,需要手动注入luaclient.dll,不然不能运行。

参考文章:

Cheat Engine

Cheat Engine Tutorial Guide (x64) - Cheat Engine

Cheat Engine

你可能感兴趣的:(CE,游戏程序)