|
Cheat Engine The Official Site of Cheat Engine
|
View previous topic :: View next topic |
Author |
Message |
justNOPing How do I cheat? Reputation: 0
Joined: 09 Aug 2022 Posts: 7
|
Posted: Wed Aug 17, 2022 8:40 am Post subject: Help with Teleport Script? |
|
|
Hello. I know there are a bunch of topics related to Teleport hacks on CEF, but I wasn't really able to find that could help me out.
++METHOS example (cant post links) was actually pretty helpful (as well as mgr.inz.Player explanations (cant post links) ), but that's way too advanced and looking at legacy code doesn't give me much
Anyway, I tried making a save/load teleport script for a 2D isometric game but it doesn't work as expected and I got more questions than answers:
1. Both, Y and X coords have 2 constant and reliable instructions, both of them are shared. Which opcode is better to use and why?
(see attachment 1)
2. Is there any difference in using fstp/fld/fadd type opcodes or just regular mov [register]
when making teleport scripts? What would the script look like, if I use FSTP/FLD instead of MOVs?
3. Why do people push and pop random registers before storing the value(judging by code examples)? They seem to be storing coords in an empty register and then loading them, but what if I don't have an empty register to store in?
4. Is it possible to improve the script and make it work this way: teleportsymbol = 1 (save), teleportsymbol = 2 (load)
So far, I've followed SER[G]ANT's Tomb Raider's teleport script and made this:
Code: |
[ENABLE]
aobscanmodule(_loadAOB,Lionheart.exe,8B 86 18 01 00 00 8B 8E 14 01 00 00 50) // should be unique
alloc(newmem,$1000)
label(_loadRet)
label(_loadOrg1)
label(_loadOrg2)
label(coordX)
label(coordY)
label(_save)
label(_load)
label(_saveCoords)
label(_loadCoords)
registersymbol(_saveCoords)
registersymbol(_loadCoords)
registersymbol(_loadAOB)
newmem:
_save:
cmp [_saveCoords],1
jne short _load
push eax
push ecx
mov eax,[esi+00000118]
cmp [esi+24],00
jne _loadOrg1
mov [coordY],eax
mov ecx,[esi+00000114]
cmp [esi+24],00
jne _loadOrg2
mov [coordX],ecx
pop eax
pop ecx
mov [_saveCoords],0
jmp _loadOrg1
_load:
cmp [coordX],0
je short _loadOrg1
push ecx
push eax
mov ecx,[coordX]
cmp [esi+24],00
jne _loadOrg1
mov [esi+00000114],ecx
cmp [esi+24],00
jne _loadOrg2
mov eax,[coordY]
mov [esi+00000118],eax
pop ecx
pop eax
mov [_loadCoords],0
_loadOrg1:
mov eax,[esi+00000118]
_loadOrg2:
mov ecx,[esi+00000114]
jmp _loadRet
coordX:
dd 0
coordY:
dd 0
_saveCoords:
dd 0
_loadCoords:
dd 0
_loadAOB:
jmp _save
nop
_loadRet:
[DISABLE]
_loadAOB:
db 8B 86 18 01 00 00
unregistersymbol(*)
dealloc(*)
{
// ORIGINAL CODE - INJECTION POINT: Lionheart.exe+1AA442
Lionheart.exe+1AA426: 8B CE - mov ecx,esi
Lionheart.exe+1AA428: FF 92 1C 01 00 00 - call dword ptr [edx+0000011C]
Lionheart.exe+1AA42E: 8D 4C 24 28 - lea ecx,[esp+28]
Lionheart.exe+1AA432: E8 79 DE 01 00 - call Lionheart.exe+1C82B0
Lionheart.exe+1AA437: 5F - pop edi
Lionheart.exe+1AA438: 5E - pop esi
Lionheart.exe+1AA439: 32 C0 - xor al,al
Lionheart.exe+1AA43B: 5B - pop ebx
Lionheart.exe+1AA43C: 83 C4 64 - add esp,64
Lionheart.exe+1AA43F: C2 08 00 - ret 0008
// ---------- INJECTING HERE ----------
Lionheart.exe+1AA442: 8B 86 18 01 00 00 - mov eax,[esi+00000118]
// ---------- DONE INJECTING ----------
Lionheart.exe+1AA448: 8B 8E 14 01 00 00 - mov ecx,[esi+00000114]
Lionheart.exe+1AA44E: 50 - push eax
Lionheart.exe+1AA44F: 51 - push ecx
Lionheart.exe+1AA450: 8B CE - mov ecx,esi
Lionheart.exe+1AA452: FF 92 C0 00 00 00 - call dword ptr [edx+000000C0]
Lionheart.exe+1AA458: 5F - pop edi
Lionheart.exe+1AA459: 5E - pop esi
Lionheart.exe+1AA45A: 32 C0 - xor al,al
Lionheart.exe+1AA45C: 5B - pop ebx
Lionheart.exe+1AA45D: 83 C4 64 - add esp,64
}
|
It's really messy and works on an instruction that's only being accessed while moving (and was made before i found a better one). When you make save "1" it just randomly teleports player and all the NPCs to a random location.
Currently I'm stuck with this:
(see attachment 2)
and have absolutely no idea what to do next and how do I make a script
Description: |
|
Filesize: |
120.22 KB |
Viewed: |
2107 Time(s) |
|
Description: |
|
Filesize: |
95.06 KB |
Viewed: |
2107 Time(s) |
|
|
|
Back to top |
|
|
cooleko Grandmaster Cheater Reputation: 11
Joined: 04 May 2016 Posts: 717
|
Posted: Wed Aug 17, 2022 2:15 pm Post subject: |
|
|
Simplify your approach.
Use the instruction that populates on moving to store the base address and use the hotkey/script activation to change the address.
Then you just need to verify that the address is populated on activation and write to it if so.
Personally, I would use the X address to populate EAX since it is first, but there is no difference here.
Set a symbol to a particular address, store EAX there using an AOB that triggers on mov, and then change it when activating the teleport.
If you desire to use this outside of CE, then you need to start tracing EAX to see what populates it until you find the base address. Then you only have to look at a pointer.
|
|
Back to top |
|
|
sbryzl Master Cheater Reputation: 6
Joined: 25 Jul 2016 Posts: 252
|
Posted: Wed Aug 17, 2022 2:21 pm Post subject: Re: Help with Teleport Script? |
|
|
Quote: |
1. Both, Y and X coords have 2 constant and reliable instructions, both of them are shared. Which opcode is better to use and why?
(see attachment 1)
|
If they are both shared instructions use whichever is easier to distinguish the address you are looking for.
Quote: |
2. Is there any difference in using fstp/fld/fadd type opcodes or just regular mov [register]
when making teleport scripts? What would the script look like, if I use FSTP/FLD instead of MOVs?
|
If you use the fpu it allows you to do floating point math. That's the only big difference.
Quote: |
3. Why do people push and pop random registers before storing the value(judging by code examples)? They seem to be storing coords in an empty register and then loading them, but what if I don't have an empty register to store in?
|
The registers are preserved by pushing them on the stack and restored afterward. In this regard note in your script the registers are not restored on most of your conditional jumps. This will cause a crash with certainty.
Quote: |
4. Is it possible to improve the script and make it work this way: teleportsymbol = 1 (save), teleportsymbol = 2 (load)
|
Yes. It looks like _loadCoords was supposed to be used for that but all it does is write 0 to it so it serves no purpose now.
|
|
Back to top |
|
|
++METHOS I post too much Reputation: 92
Joined: 29 Oct 2010 Posts: 4197
|
Posted: Wed Aug 17, 2022 2:32 pm Post subject: |
|
|
If you are wanting to learn, then I would recommend that you study each line of the original script to try to understand what is happening. If there is something that you do not understand, then you can ask about each thing, specifically, and someone can help you. This will benefit you over the long-term.
Once you have a basic understanding, you can compare it to the script that you have written above and try to fix all of the issues.
1. When looking for a viable injection point, the decision will be based on what it is that I am trying to achieve. For example, if I am trying to teleport main character only, then the first thing that I do is look for an instruction that is being accessed constantly, that is exclusive to the main character, just as an example. If the game is using multiple instructions for each coordinate, then I will typically try to use the base coordinate for my injection point because it simplifies things for me since I use custom templates to save time.
2. When starting out, you should try to use mov, if possible, assuming that you are making a basic teleport script. This will just make things easier for you. Once you understand more, you can experiment with other things. It may also depend on the target and how various data types are being handled.
3. Pushing/popping the registers temporarily frees them up to be used for whatever purpose that you need without messing up the original code that is needed for the program to execute properly. Think of it like dumping a bucket of milk into a temporary container, then using that bucket to transfer water. Once done, you can dump the water and collect the milk that you stored in the temporary container, just like you were never there. If you did not store the milk somewhere, you would mix it up with the water and make a mess of things.
4. The script can be improved, but it will need to be fixed first.
|
|
Back to top |
|
|
justNOPing How do I cheat? Reputation: 0
Joined: 09 Aug 2022 Posts: 7
|
Posted: Thu Aug 18, 2022 6:41 am Post subject: Re: Help with Teleport Script? |
|
|
cooleko wrote: |
Personally, I would use the X address to populate EAX since it is first, but there is no difference here.
Set a symbol to a particular address, store EAX there using an AOB that triggers on mov, and then change it when activating the teleport.
|
Hey, thanks for a useful advice! I was basically melted at the time of creating this thread so I didn't even think of that!
sbryzl wrote: |
If you use the fpu it allows you to do floating point math. That's the only big difference.
|
Noted. Thank you so much for replying.
++METHOS wrote: |
3. Pushing/popping the registers temporarily frees them up to be used for whatever purpose that you need without messing up the original code that is needed for the program to execute properly. Think of it like dumping a bucket of milk into a temporary container, then using that bucket to transfer water. Once done, you can dump the water and collect the milk that you stored in the temporary container, just like you were never there. If you did not store the milk somewhere, you would mix it up with the water and make a mess of things.
|
This is top-tier explanation regarding this topic! Definitely will screenshot and then frame it. Thank you so much, ++METHOS!
++METHOS wrote: |
If the game is using multiple instructions for each coordinate, then I will typically try to use the base coordinate for my injection point because it simplifies things for me since I use custom templates to save time.
|
I forgot to ask, how do you use a "base coordinate" if opcode is shared? Do you use a compare or something?
|
|
Back to top |
|
|
++METHOS I post too much Reputation: 92
Joined: 29 Oct 2010 Posts: 4197
|
Posted: Fri Aug 19, 2022 12:06 pm Post subject: Re: Help with Teleport Script? |
|
|
justNOPing wrote: | I forgot to ask, how do you use a "base coordinate" if opcode is shared? Do you use a compare or something? | -When I refer to base coordinate, I simply mean the first coordinate as it is found in the game (e.g. BaseAddress, BaseAddress+4 and BaseAddress+8).
Typically, 3D targets that have 3 axes for objects (XYZ), will store those coordinate values closely together, usually 4 bytes apart. So, your X coordinate may be at address 11111110, and your Y coordinate may be at address 11111114, with Z at 11111118 or similar. So, your base address will be the 11111110, since it is first. You can call this coordinate X, if you want.
The reasoning for this is simply that it makes things easier, more efficient, minimizes errors and reduces confusion etc.. If you are using custom templates, you would have to rewrite parts of them to make them work if you decide to inject at coordinate Y or Z (base+4 or base+8), for example.
In other words, what cooleko wrote.
|
|
Back to top |
|
|
justNOPing How do I cheat? Reputation: 0
Joined: 09 Aug 2022 Posts: 7
|
Posted: Fri Aug 19, 2022 1:38 pm Post subject: Re: Help with Teleport Script? |
|
|
++METHOS wrote: |
-When I refer to base coordinate, I simply mean the first coordinate as it is found in the game (e.g. BaseAddress, BaseAddress+4 and BaseAddress+.
Typically, 3D targets that have 3 axes for objects (XYZ), will store those coordinate values closely together, usually 4 bytes apart. So, your X coordinate may be at address 11111110, and your Y coordinate may be at address 11111114, with Z at 11111118 or similar. So, your base address will be the 11111110, since it is first. You can call this coordinate X, if you want.
The reasoning for this is simply that it makes things easier, more efficient, minimizes errors and reduces confusion etc.. If you are using custom templates, you would have to rewrite parts of them to make them work if you decide to inject at coordinate Y or Z (base+4 or base+, for example.
In other words, what cooleko wrote. |
Thank you once again, ++METHOS! I've managed to fix the script and combine it with cursor coords in-game to make a "teleport to cursor" script. Criticism is welcome
Code: | [ENABLE]
aobscanmodule(AOBTeleport,Lionheart.exe,D8 86 14 01 00 00 D9 9E)
aobscanmodule(_saveAOB,Lionheart.exe,8B 8E 00 01 00 00 89 4C)
alloc(newmem,2048)
label(_loadRet)
label(_saveRet)
label(_loadOrg)
label(coordX)
label(coordY)
label(_save)
label(_load)
label(_loadcoordsBlink)
registersymbol(_loadcoordsBlink)
registersymbol(AOBTeleport)
registersymbol(_saveAOB)
newmem:
_save:
push ebx //Places EBX in stack.
mov ebx,[esi+00000100] //Places ESI value into EBX. ESI+100 Holds the value of cursos X position on map
mov [coordX],ebx //Place value of the EBX into CoordX
mov ebx,[esi+00000104] //Same as above, places Y coord of the mouse position
mov [coordY],ebx
pop ebx //Popping EBX out of stack
mov ecx,[esi+00000100] //Execute the original cursor code
jmp _saveRet
_load:
cmp [_loadcoordsBlink],1 //If _loadcoordsBlink = 1 then save code will be executed instead
jne short _loadOrg //If _loadcoordsBlink is not equal 1, jump to original code instead
cmp [coordX],0 //Prevent from accidental loading X=6,Y=0.
je short _loadOrg //if coordX=0, execute original code
cmp [esi+24],0 //Check if player
jne _loadOrg
push ebx //placing EBX into stack again
mov ebx,[coordX] //Placing saved X coord into EBX
mov [esi+00000114],ebx //Placing the result in EBX, replacing coordinates
mov ebx,[coordY]
mov [esi+00000118],ebx
pop ebx //Popping EBX outta stack
mov [_loadcoordsBlink],0 //Changing _loadcoordsBlink to 0 so it won't load again
_loadOrg: //Original code (Player Coords)
fadd dword ptr [esi+00000114]
jmp _loadRet
coordX:
dd 0
coordY:
dd 0
coordZ:
dd 0
_saveCoords:
dd 0
_loadcoordsBlink:
dd 0
AOBTeleport:
jmp _load //jump straight to load code
nop
_loadRet:
_saveAOB:
jmp _save //jump straight to save code
nop
_saveRet:
[DISABLE]
AOBTeleport:
db D8 86 14 01 00 00
_saveAOB:
db 8B 8E 00 01 00 00
unregistersymbol(*) // unregister all symbols
dealloc(*) //deallocate all the allocated memory regions
|
|
|
Back to top |
|
|
++METHOS I post too much Reputation: 92
Joined: 29 Oct 2010 Posts: 4197
|
Posted: Fri Aug 19, 2022 2:14 pm Post subject: |
|
|
Good job. If you continue to learn, then your only limitation will be your imagination.
Making cheats is not only about making things easy; you can literally reinvent a game and do things that were never supposed to be possible, allowing you to replay games while having a totally new experience.
|
|
Back to top |
|
|
TsTg Master Cheater Reputation: 5
Joined: 12 Dec 2012 Posts: 334 Location: Somewhere....
|
Posted: Sat Aug 20, 2022 4:10 am Post subject: |
|
|
Quote: | 1. Both, Y and X coords have 2 constant and reliable instructions, both of them are shared. Which opcode is better to use and why?
(see attachment 1) |
there is no difference(since both are reliable and you are sure of that) but personally i'd prefer the one on the right, you would want to store the base address (ESI) in case you are doing some other cheats maybe, as well as knowing the offset to the co-ordinates (ESI+114 and ESI+118).
-on the left side, the co-ordinate addresses are directly read from stack address (which later copied to EAX), without the need to add offset (since DC38864 - 114= DC38750), you will notice down after the address is also loaded into the floating-point stack for processing.
Quote: | 2. Is there any difference in using fstp/fld/fadd type opcodes or just regular mov [register]
when making teleport scripts? What would the script look like, if I use FSTP/FLD instead of MOVs? |
if you are just going to update the values without doing calculations, you are fine with using MOV, otherwise you have to use FSTP, FADD etc
Quote: | 3. Why do people push and pop random registers before storing the value(judging by code examples)? They seem to be storing coords in an empty register and then loading them, but what if I don't have an empty register to store in? |
this is used to preserve whatever data already exist in the register (so you dont mess with the game stuff that might lead it into a crash), while at the same time and in a script you need to store something temporarly, so you would use a PUSH EAX for example, use it to move/manipulate data, then finally restore it using POP EAX.
Quote: | 4. Is it possible to improve the script and make it work this way: teleportsymbol = 1 (save), teleportsymbol = 2 (load) |
thats for sure, the latest script you wrote seems good enough.
|
|
Back to top |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum You cannot attach files in this forum You can download files in this forum
|
|