三国群英2吧 关注:43,925贴子:999,187

【修改】修复华斩倒飞问题

只看楼主收藏回复

一楼


IP属地:智利1楼2021-07-14 14:41回复
    UE打开EXE,修改:
    从:
    21A5F: 0F AF 45 10 99
    21A70: 0F AF 45 10 99
    21A81: 0F AF 45 10 99
    改为:
    21A5F: F7 6D 10 90 90
    21A70: F7 6D 10 90 90
    21A81: F7 6D 10 90 90


    IP属地:智利2楼2021-07-14 14:42
    回复
      原理:
      华斩的飞行轨迹实际上有两种:当武将之间的距离大于或等于1200px=12.5格时,飞行轨迹是一个参数方程
      x = x0 + (x1 - x0) * t/T
      y = y0 + rsin(t/T*π)
      其中T为总用时,t为参数,r是一个常数,第2、3道剑气的r为200,第4、5道剑气的r为400. 这种情况下,剑气从我将出发,一开一合后飞向敌将,永远不会倒飞。
      另一种情况下,当武将之间的距离小于12.5格时,剑气会从武将的左右两侧产生,其中第2、3道剑气离武将200px,第4、5道剑气离武将400px;剑气以匀速直线飞向敌将。
      这种情况下多数并不会倒飞。然而,因为系统函数ApproachObjectTowards()(即SYSCALL 0x19)的实现有问题,有的情况下,剑气的速度会反向。这是因为该函数按如下公式计算x方向的速度:
      v_x = v * dx / sqrt(dx^2 + dy^2)
      其中dx、dy为剑气和目标武将之间的x、y坐标差。
      我们知道,在EXE中,坐标是以高16位为整数部分,低16位为小数部分的;当dx=1200时,内存中实际储存的是1200 << 16 = 0x 4B0 0000. 而速度v固定为30. 因此
      v * dx = 30 * 0x4B0 0000 = 0x8CA0 0000 > 0x7FFF FFFF = 2147483647 = 2^31 - 1
      发生了数值越界。
      这样,两个正数相乘,就会得到一个负数,导致速度的方向反了,引起华斩倒飞。
      因此,华斩倒飞是很容易复现的:只需要保证双方武将之间的距离刚好在12格时(准确地说是11.375-12.5格之间),打出华斩,则必定倒飞。


      IP属地:智利4楼2021-07-14 14:58
      回复
        修改方法:
        x86汇编允许乘法的结果用两个32位寄存器储存;当乘数之一在eax中时,使用单操作数(而非双操作数)版本的imul指令,即可使得结果被储存在EDX:EAX中。
        IMUL SRC
        (EDX,EAX)←(EAX)*(SRC)
        同时,除法指令idiv也是使用EDX:EAX来储存被除数的:
        IDIV SRC
        (EAX) ← (EDX,EAX) / (SRC)
        (EDX) ← (EDX,EAX) % (SRC)
        因此我们只需要把原来代码中的
        mov eax, [ebp-18]
        imul eax, [ebp+10]
        cdq
        idiv [ebp-14]
        改为
        mov eax, [ebp-18]
        imul [ebp+10]
        idiv [ebp-14]
        即可解决越界问题。此时,imul得到的结果,会被扩充至EDX:EAX,合计64位,不会发生越界,也不需要使用cdq扩充到EDX里,直接接上下面的idiv指令即可。
        实际修改时,把imul eax, [ebp+10]; cdq这两条指令改成imul [ebp+10]即可,剩下的用nop填充。
        对于y和z方向上的速度,也依样画葫芦照此修改。
        这样就解决了越界问题,华斩也就不会倒飞了。


        IP属地:智利5楼2021-07-14 15:05
        回复
          以上


          IP属地:智利6楼2021-07-14 15:06
          回复
            高啊


            7楼2021-07-14 21:26
            回复
              我有个不成熟的推测:
              我们将12.5格以外称为散-聚型华斩;以内称为聚拢型华斩
              可能华斩原来只有一种聚拢型华斩。然而奥汀的测试员原地R了一通后发现会倒飞,程序员没办法补了一个散-聚型华斩。然而他们当时并没想到是1092px以上会越界,于是加了一个分支判断,蒙了一个1200px并且补了一个散-聚型华斩。然后测试员当然是测不出来十二格倒飞的


              IP属地:美国8楼2021-07-14 21:34
              收起回复
                不明觉厉


                IP属地:广东9楼2021-07-15 20:35
                收起回复
                  好像很牛逼的样子


                  IP属地:广东来自Android客户端10楼2021-07-15 21:00
                  回复
                    远帆太强了


                    来自Android客户端11楼2021-07-16 23:10
                    回复


                      IP属地:广东12楼2021-07-17 14:56
                      回复
                        我看不懂,但我大受震撼。


                        星座王
                        点亮12星座印记,去领取
                        活动截止:2100-01-01
                        去徽章馆》
                        IP属地:陕西来自iPhone客户端13楼2022-01-08 17:55
                        收起回复
                          666666


                          IP属地:河北来自Android客户端14楼2022-01-08 23:22
                          回复
                            可以啊


                            IP属地:山东来自Android客户端15楼2022-01-21 07:43
                            回复
                              UE打开搜不到,可能打开的是陈沐版?


                              IP属地:辽宁17楼2023-03-17 21:56
                              回复