丸子de爸爸 发表于 2019-10-23 16:05

植物大战僵尸修改器(四)超级攻击

本帖最后由 丸子de爸爸 于 2019-11-1 20:13 编辑

# 前言

发现帖子被微信公众号推送了,个人还是挺开心的,这样可以有更多的兄弟可以了解编程这个行业。

微信上有人回复说我之前的流程图不合格。我想回答的是,任何的图的最终目的都是为了更好的让人看懂,而不是体现高端标准的存在。当然也可能我的图确实有问题,哈~好多年不画了是真的。我的帖子也是一样,我的概念解释,可能没有体现那么专业,更多的是希望大家能够简单的理解,等有兴趣了,可以自己尝试去深入理解,都是没问题的。(但是我确实是程序员哈,咳咳,还是持证的)

所以在此申明一下,我会尽量呈现我自己经验的东西,大家也千万不要完全以我的概念为标准答案,鼓励大家怀着质疑的心态学习,谁都会错不是么。如果大家有发现有什么地方有问题,也欢迎指出错误。请指出来,共同学习嘛。而不是,哎呀你这个不行这种,谢谢。

讲了很多体外话,来讲下这个系列的计划吧,本来是准备这一篇就直接做修改器了。但是突然觉得,好像CE里面还有一个数据的观察可以讲,可能也对新手朋友有一些思路上的帮助,同时再给AA脚本来一次补课,于是延长一期。下期就是最后一篇了,会讲到通过易语言和AA引擎怎么来制作一个自己的修改器,当然内容好像不少,可能也会有上下集,但是会尽量比较近的时间发出来,谢谢大家。

欢迎文明转载,请注明出处丸子de爸爸

本文所有技术资料仅供研究,不鼓励任何盗版商用行为

请大家支持正版,支持正版!支持正版!!!

[上集传送门](https://www.52pojie.cn/thread-1037811-1-1.html)

# 工具

CheatEngine6.7

植物大战僵尸本体

PS:(我使用的是年度版,可以直接解锁所有物品,不然你就自己打到后面去吧)

# 本次基础概念

**内存,一切皆内存,我们操作的全部都是内存。**

所有地址相关的概念,都可以理解为坐标,用来给我们做标记的而已。

如果实在搞不明白,你想想指南针为啥指向北边,为啥叫南北,只是定义,只是公认

PS:上面这一段是重复了,但是我觉得还是有必要多重复一下,看多了,大家就印象深刻一点。

## AA脚本的保存

每次CE修改完,写了AA脚本之后,可以保存为CT文件,下次运行游戏的时候,直接打开,就可以直接使用。

## 对象

编程的一种概念,简单理解成对事物的个体化表现。(实在不想说啥抽象啥之类的,很绕口,哈~)

比如说,我们都知道猫,就可以把猫看成一个对象。如果猫是一个对象,那它就可以变得具体化,比如红色的毛呀,多少岁呀,也可以有名字呀,爱吃鱼呀,会跑会跳。

所以对象就会包含两个基本元素:属性和方法。具体区分,可以用动名词分析法,动词就是方法;名词就是属性。如跑,跳,吃就是方法;红色,黑眼睛就是属性。想了解的,可以进一步去查查,动名词分析法或者对象。

# 实现步骤

植物超级攻击可以分为2种模式:

1. 修改植物攻击CD
2. 特殊超级攻击(这个我是不知道怎么形容,这个是因为特殊原因造成的,并不是啥逻辑)

## 修改植物攻击CD

### CE查找CD地址

首先老规矩,打开CE和游戏本体,开始游戏。并用CE附加进程。(选植物的时候可以选个玉米投手,后面有用)



用前两次找的阳光指针或者基址,改个阳光数量。

然后等一个僵尸出现,等僵尸出现,在那一排种下一个单发射手(其他都行,看你自己),然后切换到CE。



这时候我们可以理一下攻击CD的流程。和之前植物种植CD是一样的。

每攻击一下,跑CD,CD结束,再攻击。(CD是先赋值最大值,再减少到0。尝试出来的)



回到CE,扫描类型设置为“未知的初始值”,首次扫描。



在CE中开启变速精灵,将速度降低,点击应用。

这是为了我们可以在一次攻击中,多次搜索CD。防止僵尸被太快的打死。



回到游戏,看植物发射了一颗子弹。切换到CE,搜索“减少的数值”,点击“再次扫描”。

如果植物又发射了一颗新的子弹,需要搜索“增加的数值”。因为攻击CD是一个循环,见流程图。

具体为啥,第二篇CD里面有详解了,不多说。



多次搜索,最终可以精确到一个值,当然其实你经验好,也不用筛选到最后一个,有可疑的可以先测试。

将整个值改到0,发现植物马上又发射了一颗子弹,所以他就是攻击的CD了。



右键选择“找出是什么访问了这个地址”。

因为理论上,循环的减少CD,一直改写。减少完之后,需要判断是否CD完成,这个判断就是访问。

所以我们这里选择访问。



回到游戏,CE立刻多了很多纪录。

但是出现了个问题,可以发现,最后两条纪录虽然是比较的,但是都不是0。

之前我们是修改到0,然后植物重新发出了子弹。所以正常应该是和0比较,但是这里没有。

说明,这个CD,不是很准确,或者是不由这个CD来控制,或者是有特殊的方法判断。

那没办法,我们从第一个,是减少值CD,从修改入手分析逻辑。



从红框往下dec开始,分析每条代码含义(其实我就是前面几条看到了,才决定一直往下分析的)

- 就是攻击CD,CD = CD -1
- 将CD存到eax寄存器中
- 将edi存到栈里
- 检查eax是否为0,也就是判断CD是不是为0
- 之前CD>0就跳转,所以下面的代码,就是CD=0的时候执行的逻辑
- 栈里存一个15常量
- 调用一个方法,啥方法先不管
- ecx赋值一个值,
- ecx = ecx-CD
- eax赋值为一个不是CD的值,
- esp+4,esp栈顶指针,一般简单可以先不管。
- 将ecx赋值到CD。这里就可以发现可疑了。

之前有一个ecx = ecx-CD,然后ecx又赋值给了原本存放CD的位置。

所以判断,ecx,也就是,是CD的最大值。



### AA脚本实现

根据上面的分析,只需要直接把最大值改为50,就可以实现增加输出的速度。

(至于为啥是50,应该是和动画有关,改为低一点的,会有子弹打不出来)

选中 movecx,这一行,选“工具”,自动汇编。



先选“CT表框架代码”,再选“代码注入”。PS:选AOB注入可以解决多版本兼容问题。



AA脚本运行逻辑是:

先从具体代码行数开始执行"PlantsVsZombies.exe"+6DC21:

通过jmp到指定标签,默认是newmem,执行完新的代码之后,再向下接着执行。

打开的时候,执行enable里面的逻辑;关闭的时候,执行disable里面的逻辑。

但是我们只需要修改mov ecx,,改为mov ecx ,0x32就行。

PS:注入原理是,在你选择的代码处将原来的代码修改为jmp,跳转到自己开辟的一块新位置,然后按你的逻辑执行汇编。其中会根据你选择的代码字节码的长度和jmp进行对比,对代码进行调整。所以有时候我们会看到originalcode里面就是一行代码,有时候是两行,是因为每次都在原处改为jmp,必须和源代码的长度是符合的。(jmp好像是5长度,这样如果修改注入的位置只有3,就不会够长度,于是就会把下面两行代码都放到新方法里,在原代码处用nop补位。新手有个概念就行,这些都是系统会做的,慢慢就会明白了)

```assembly
                     //激活脚本时的逻辑
//code from here to '' will be used to enable the cheat
alloc(newmem,2048)             //申明一个新代码空间newmem
label(returnhere)                        //申明标签returnhere
label(originalcode)            //申明标签originalcode
label(exit)                  //申明标签exit

newmem:                        //一般自己的代码就写在这里,但是你也可以直接修改下面的代码,但是需要注意保证原始执行逻辑
originalcode:               //原本的代码,修改时需要注意。内容由jmp和代码差生的字节码差导致。
mov ecx,0x32                  //这里要改为32,就是十进制的50
sub ecx,eax

exit:
jmp returnhere

"PlantsVsZombies.exe"+6DC21:
jmp newmem
returnhere:

                   //关闭脚本时的逻辑
//code from here till the end of the code will be used to disable the cheat
dealloc(newmem)
"PlantsVsZombies.exe"+6DC21:
mov ecx,
sub ecx,eax
//Alt: db 8B 4E 5C 29 C1
```

修改完成后,点击“分配到当前的CT表”。就可以在CE中搜索结果栏看见脚本。



点击脚本最前面的方框就可以启动脚本,再点一次就是取消。

启动后,发现植物的攻击频率明显提升。(但是缺点是双发子弹数也变成单发一样了)



## 超级攻击

这个攻击是我当时在尝试修改攻击间隔的时候发现的,也正是因为这个,我觉得有必要新增这一篇帖子。

### CE查找超级攻击地址

无论这种语言是面向对象的还是面相过程的,在某种程度上都可以理解为有对象的存在,只是看是不是显性的。(好像有点远,讲多了也麻烦,大家当是我个人的意见吧,可以自己去查查,面向对象,面向过程。)

他们会把一个对象相关的值,放在相近的内存区域里。其实如果仔细一点我们从之前的分析就可以看出来。

见下图,红框内每一句分析,在上面都有,不记得的往上翻翻。

这里的esi分别和什么有关,esi+58是CD,esi+5C是最大值,esi+24暂时不知道(其实这是植物的种类)。

这说明在植物攻击CD倒计时结束进入的这一块逻辑里,esi对应的是当前植物对象在内存中的的首地址。



在游戏里,把其他植物都铲了,防止干扰你观察数据。

在有僵尸的那一栏,种下一个玉米。(其实种啥都行,玉米方便观察)

回到CE,在push 0F那打断点,其实上面打断点也行,但是为了方便后面调试。

(这里进入断点的,就是开炮的时候,只要在jg下面就行,不同版本的也没关系)

回到游戏,等待断点触发,查看到ESI的值为“28CC5618”,每个人不一样,纪录你自己的。



右键左下角内存区域的任何一项,选择“转到地址”,填写我们刚才的ESI值,点确定。



自己调整下内存区域的显示大小,边框拉一下,拉大一点。

ctrl+B,去掉所有的断点。按F9使程序恢复运行,然后在CE中,变速精灵保证是减速到0.25(这都是方便观察)

可以发现,在红框位置的有一个数值,在CD跑完了之后(自己转到地址是可以加偏移的,可以确定哪个值是CD)

这个红框内的值开始进行了一个倒计时,并最终停留在了1上。


然而为1的时候,游戏里的画面是酱紫的。

玉米保持一个投掷的姿势,等玉米恢复到了填弹状态,该数值才重新变为0。

PS:是的,我重开了游戏,之前开变速精灵的时候崩了...



所以我们是不是可以推测,之前我们那个攻击CD之所以没有0,是因为我们认为的攻击CD只是代表填弹的间隔。

填弹完毕,然后再由这个真正的攻击CD来控制,进行一个攻击动画的倒计时。

等到1的时候,丢出弹药,然后再次填充。

所以我们先在这个地址上右键,然后选择“把地址添加到列表”

你么如果懒,不想自己观察,可以告诉你们偏移就是ESI+90的那个位置。



在CE里,右键刚添加的地址,选择“什么访问了地址”。

老原因,因为在攻击的时候需要判断,是否到一个临界值,所以只是访问而不是改写。



又是一堆纪录,不过好像直接找到了我们想要的东西,是不是有一个与01的比较了,就是他了。

和我们的分析也一样,判断到了1,则释放子弹,为啥不是0。因为0的时候是空闲状态。

所以选中cmp 01那一行,显示反汇编。



接下来都不需要断点了,cmp下面一行是jne,不等于才跳转。

也就是,不等于1的时候,就直接跳走,等于1才执行下面的逻辑。

那我们只需要让他一直执行1的逻辑,就可以实现一直攻击了。(是他执行多少次,就攻击多少次)



选中jne那一行,自动汇编,参考上面的AA。只需要把originalcode中的内容去掉就可以了,因为我们不需要执行任何代码。只是要把跳转去掉就行了。



添加到表中之后,打开脚本,攻击开始狂暴了。

这里其实子弹的个数,就是你真正的攻击CD的数量。因为他只在倒计时里执行判断,所以没法让它一直开枪。

当然有人可能说,那我直接给它改一下不行么?还真不行,它的循环逻辑比较复杂,我观察了一段时间,感觉没有啥太好的处理方法。不过也有思路,就是去观察对象的数据结构,也就是我为啥能发现这个为1的时候,开始执行真正攻击的原因。

进一步的分析数据结构,对比双重或者四重和单重的区别,加以分析,应该就可以找到每次的子弹数的位置了。

如果能分析出子弹对象的属性,让豌豆射手打出玉米加农炮都是可能的...

有兴趣的可以去分析分析,然后分享一下,我还是偷偷懒吧。



# 总结

想要分享给大家的,不是简单的一个功能,而是一种思路。有时候如果发现找到的结果和自己的想法不太一致,尝试去分析一下对象周边的东西,关联联想是非常重要的,我们之前其他几个功能也有用到类似的方法。不过这一次希望引入对象的概念,使大家能够更加清晰,多谢各位,有问题和意见欢迎回复。

PS:可以留个作业,植物只有看到僵尸才会打子弹,能不能让它不看到僵尸也打子弹,其实很简单,试试吧。

下篇文章真的是本系列最后一篇了,将分享使用易语言和AA引擎制作外挂,敬请期待。

[下一篇](https://www.52pojie.cn/thread-1047244-1-1.html)

丸子de爸爸 发表于 2019-10-23 22:47

本帖最后由 丸子de爸爸 于 2019-10-23 23:09 编辑

wzwdlxf 发表于 2019-10-23 21:49
大牛,玉米投手 黄油攻击的逻辑或机制是怎样的,可以修改为只出现黄油么
{:1_893:}谢谢回复,理论上是可行的。我没尝试过,就不说死了,改天试试再给你准确答案。
他投掷黄油和普通的攻击都是属于攻击动作的调用,理论上只要找到那个分支判断,就可以实现无限黄油攻击。
试过了可行,就按我之前说的做就可以,有图有真相。

newtin 发表于 2019-10-23 17:56

这样还有乐趣可言吗?

丸子de爸爸 发表于 2019-10-26 13:59

Huggo1995 发表于 2019-10-26 03:05
哇,很少在国内看到这么细致的CE教程了,必须支持一下!!!

另外,提两个小建议给楼主:


{:1_893:}谢回复,也谢谢你的建议。
结构分析那些目前还没找到需要演示的,直接介绍估计很多人都会犯困.
以后如果遇到需要使用的,自然会演示。
我的教程更多的是希望分享给大家思考的方式,毕竟看起来都简单,但是怎么让大家愿意看,愿意动手,稍微有点点难。先调动积极性再说:lol

Huggo1995 发表于 2019-10-26 03:05

哇,很少在国内看到这么细致的CE教程了,必须支持一下!!!

另外,提两个小建议给楼主:

1.现在网上看到的教程其实都过于陈旧了,对新手很不友好,但是其实cheatEngine在6.x版本之后有很多新功能对新手十分友好,但是几乎没有教程会提到这些功能.例如 结构分析Utilmap等等,楼主可以给新手示范下这些功能,我觉得更加能带动新手入门.
2.顺便期待下下一期的E语言,希望可以有内部和外部CALL的调用讲解.

再说一次,楼主真的是太棒了!希望楼主以后还能出一些高质量的教学!

丸子de爸爸 发表于 2019-10-30 15:23

wzzjnb2006 发表于 2019-10-29 21:12
什么时候出:使用易语言和AA引擎制作外挂
等的花儿都谢了。

{:1_886:}这么期待,意思是AA脚本和之前各种反汇编全部都弄懂了?
没弄懂的话,单独学会使用制作外挂又有啥用。
如果已经会了前面这些,说明你可以尝试去学习一门编程语言了。
只要随便会一门编程语言,就可以使用AA引擎做了,原理就是使用dll而已。

浪漫网络 发表于 2019-10-23 16:21

收藏了 以后能学习到

HTMason 发表于 2019-10-23 16:33

说实话汇编代码很多都看不懂emmmm

MZ667458 发表于 2019-10-23 16:41

技术大牛,感谢楼主分享

wangliang52880 发表于 2019-10-23 17:19

感谢楼主的分享。

向往的歌 发表于 2019-10-23 17:52

还以为是植物大战僵尸四的游戏呢…………

春夏之交 发表于 2019-10-23 17:53

我也还在玩植物大战僵尸,跟你一比,你才是会玩啊

biubiufish 发表于 2019-10-23 18:00

学习了学习了

233500 发表于 2019-10-23 19:51

本帖最后由 233500 于 2019-10-23 19:53 编辑

大佬,AA脚本 点过自动汇编>模板>CT表框架代码>    然后点代码注入会卡住   是什么情况,哪里出了问题吗?
页: [1] 2 3 4 5 6 7 8 9 10
查看完整版本: 植物大战僵尸修改器(四)超级攻击