Cheat Engine Forum Index Cheat Engine
The Official Site of Cheat Engine
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 


[Bug] cheatengine suddenly replaces bytes after injecting
Goto page Previous  1, 2, 3  Next
 
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine
View previous topic :: View next topic  
Author Message
mgr.inz.Player
I post too much
Reputation: 218

Joined: 07 Nov 2008
Posts: 4438
Location: W kraju nad Wisla. UTC+01:00

PostPosted: Mon Jun 20, 2016 4:29 pm    Post subject: Reply with quote

This one?
Code:
if autoAssemble([[alloc(newmem,1024,7ff670daf4ee)
label(justtesting)
registersymbol(justtesting)
newmem:
justtesting:]])

then
  print( 'justtesting =',string.format('%x',getAddress("justtesting")) )
end

_________________
Back to top
View user's profile Send private message MSN Messenger
NoMoreBSoD
Advanced Cheater
Reputation: 3

Joined: 03 Sep 2013
Posts: 85

PostPosted: Mon Jun 20, 2016 4:31 pm    Post subject: Reply with quote

The last one gives me :
Code:

justtesting = 26651870000
justtesting = 26651880000
justtesting = 26651890000


I did it 3 times just to test it out.
Back to top
View user's profile Send private message
mgr.inz.Player
I post too much
Reputation: 218

Joined: 07 Nov 2008
Posts: 4438
Location: W kraju nad Wisla. UTC+01:00

PostPosted: Mon Jun 20, 2016 4:45 pm    Post subject: Reply with quote

Interesting. Maybe it is win10 thing.

Try this script for two different games. Witcher3 and something else (e.g. Middle-earth: Shadow of Mordor).


Code:
if autoAssemble([[
alloc(newmem1,1024,0010000000)
label(justtesting1)
registersymbol(justtesting1)
alloc(newmem2,1024,0100000000)
label(justtesting2)
registersymbol(justtesting2)
alloc(newmem3,1024,0200000000)
label(justtesting3)
registersymbol(justtesting3)
alloc(newmem4,1024,0300000000)
label(justtesting4)
registersymbol(justtesting4)

newmem1:
justtesting1:
newmem2:
justtesting2:
newmem3:
justtesting3:
newmem4:
justtesting4:
]])

then
  print( 'justtesting1 =',string.format('%016x',getAddress("justtesting1")) )
  print( 'justtesting2 =',string.format('%016x',getAddress("justtesting2")) )
  print( 'justtesting3 =',string.format('%016x',getAddress("justtesting3")) )
  print( 'justtesting4 =',string.format('%016x',getAddress("justtesting4")) )
end

_________________
Back to top
View user's profile Send private message MSN Messenger
DarkIceCore
Expert Cheater
Reputation: 0

Joined: 10 Jun 2012
Posts: 102
Location: Moscow

PostPosted: Mon Jun 20, 2016 4:57 pm    Post subject: Reply with quote

mgr.inz.Player wrote:
Interesting. Maybe it is win10 thing.

Try this script for two different games. Witcher3 and something else (e.g. Middle-earth: Shadow of Mordor).


Win 7 x64

"Man O'war Corsair" , mono features,

Code:

justtesting1 = 000000000fee0000
justtesting2 = 0000000100000000
justtesting3 = 0000000200000000
justtesting4 = 0000000300000000
Back to top
View user's profile Send private message
NoMoreBSoD
Advanced Cheater
Reputation: 3

Joined: 03 Sep 2013
Posts: 85

PostPosted: Mon Jun 20, 2016 5:02 pm    Post subject: Reply with quote

Here are the results :

Code:
Witcher 3
justtesting1 = 0000000010000000
justtesting2 = 0000000100000000
justtesting3 = 0000000200000000
justtesting4 = 0000000300000000

Batman : Arkham Knight
justtesting1 = 000000001b960000
justtesting2 = 000000001c810000
justtesting3 = 000000001c820000
justtesting4 = 000000001c830000


Star Wars : KOTOR 2
(1st time)
justtesting1 = 0000000007960000
justtesting2 = 000000000a060000
justtesting3 = 000000000a070000
justtesting4 = 000000000a080000
(2nd time with restarting CE and KOTOR)
justtesting1 = 000000000ffd0000
justtesting2 = 000000000cd40000
justtesting3 = 000000000cd50000
justtesting4 = 000000000cd60000

Final Fantasy XIII
justtesting1 = 000000000f0d0000
justtesting2 = 000000000f0f0000
justtesting3 = 000000000f100000
justtesting4 = 000000000f110000


Witcher 3 again just to be sure, after restarting CE and the game
justtesting1 = 0000000010000000
justtesting2 = 0000000100000000
justtesting3 = 0000000200000000
justtesting4 = 0000000300000000


Weirdly, Witcher is the only one which produced the addresses you put in assembly.
Back to top
View user's profile Send private message
mgr.inz.Player
I post too much
Reputation: 218

Joined: 07 Nov 2008
Posts: 4438
Location: W kraju nad Wisla. UTC+01:00

PostPosted: Mon Jun 20, 2016 5:12 pm    Post subject: Reply with quote

Quote:
Code:
Witcher 3
justtesting1 = 0000000010000000
justtesting2 = 0000000100000000
justtesting3 = 0000000200000000
justtesting4 = 0000000300000000

It is a good result. It tells us that internal FindFreeBlockForRegion function can find free blocks near preferred region on your machine. It just can not find it for witcher3.exe+9AF4EE. You are forced to use "14 byte jump" plus nops. Or code cave.





"Weirdly, Witcher is the only one which produced the addresses you put in assembly"
because Final Fantasy XIII is a 32bit application.

_________________
Back to top
View user's profile Send private message MSN Messenger
NoMoreBSoD
Advanced Cheater
Reputation: 3

Joined: 03 Sep 2013
Posts: 85

PostPosted: Mon Jun 20, 2016 7:19 pm    Post subject: Reply with quote

mgr.inz.Player wrote:
It is a good result. It tells us that internal FindFreeBlockForRegion function can find free blocks near preferred region on your machine. It just can not find it for witcher3.exe+9AF4EE. You are forced to use "14 byte jump" plus nops. Or code cave.





"Weirdly, Witcher is the only one which produced the addresses you put in assembly"
because Final Fantasy XIII is a 32bit application.

So I reinstalled Shadow of Mordor just to test out CE on another 64 bits game and the results are :
Code:
justtesting1 = 0000000014320000
justtesting2 = 0000000100000000
justtesting3 = 0000000200000000
justtesting4 = 0000000300000000


How do I do a 14 bytes jump?
I did read a lot about code caves before I started using CE, but I haven't used them in years. I think those 2 threads will help me solve the problem at hand ( link1, link2).

If I understand correctly, I have to scan for a code cave far away, manually code the jump to and back from while using nops to make sure the code doesn't crash during execution.

Regarding the original problem, it seems like it's caused because CE doesn't look far away enough and/or can't not encode 14 byte jumps
Back to top
View user's profile Send private message
ParkourPenguin
I post too much
Reputation: 140

Joined: 06 Jul 2014
Posts: 4297

PostPosted: Mon Jun 20, 2016 9:50 pm    Post subject: This post has 1 review(s) Reply with quote

In a 32-bit process, you can use the near jump (5 bytes) no problem regardless of where the memory is allocated because every address is within 2GB of every other address in a 4GB address space.

In a 64-bit process, however, the virtual address space is much greater than 4GB, so you won't always be able to use the near jump. That's what the third parameter to alloc is for: the computer will try to allocate that memory within 2GB of that address.

In order to jump to a memory location further than 2GB away, you'll need to store the address you want to go to in some r/m64 and use that instead. The 14 byte jump in this case refers to storing the address you want to jump to just after the jmp instruction. This subsequently overrides any instructions in the way and forms all the "garbage" disassembly you see. 6 byte jmp + 8 bytes for the address = 14 bytes overridden.

Thus, when doing a code injection using a 14-byte jump, the only noticeable difference to you is that you'll need to override nearly 3x more instructions. Using the OP as an example, here's how you'd explicitly use a 14-byte jmp:
Code:
[ENABLE]
aobscanmodule(aob_highlight,witcher3.exe,48 8B 39 8B 41 08 45 33 E4 48 8D 0C 80 4C 8B F2) // should be unique
alloc(newmem,$1000,"witcher3.exe"+9AF4EE)
alloc(pointer_highlight,8)

label(return)

registersymbol(pointer_highlight)
registersymbol(aob_highlight)

newmem:
  mov [pointer_highlight],rcx
  mov rdi,[rcx]
  mov eax,[rcx+08]
  xor r12d,r12d
  lea rcx,[rax+rax*4]
  mov r14,rdx
  jmp return

aob_highlight:
  db FF 25 00 00 00 00
  dq newmem
  nop
  nop
return:

[DISABLE]
aob_highlight:
  db 48 8B 39 8B 41 08 45 33 E4 48 8D 0C 80 4C 8B F2

dealloc(newmem)
dealloc(pointer_highlight)
unregistersymbol(pointer_highlight)
unregistersymbol(aob_highlight)

CE automatically does this when it goes to assemble the instruction "jmp newmem" if newmem is further than 2GB away. However, something obviously isn't working perfectly right now, so do this in order to avoid any ambiguity.

For more technical information, refer to the Intel Software Developer's Manual Volume 2A section 2.2.1.6 "RIP-relative addressing", as well as the documentation on the JMP instruction within said manual (or any other valid x64 reference of your choice).

_________________
I don't know where I'm going, but I'll figure it out when I get there.
Back to top
View user's profile Send private message
Zanzer
I post too much
Reputation: 126

Joined: 09 Jun 2013
Posts: 3278

PostPosted: Mon Jun 20, 2016 11:03 pm    Post subject: Reply with quote

The original code works fine for me. Windows 10, 64-bit.
No problem with ParkourPenguin's code either.

Depending on the address of pointer_highlight, I've been known to have issues with instructions like:
Code:
mov [pointer_highlight],rcx

In those cases, I use:
Code:
  mov rdi,pointer_highlight
  mov [rdi],rcx
  mov rdi,[rcx]
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 458

Joined: 09 May 2003
Posts: 25291
Location: The netherlands

PostPosted: Tue Jun 21, 2016 2:36 am    Post subject: Reply with quote

Sorry, i overlooked the important part.
You use kernelmode query memory regions.
You can't use a prefered base with that enabled. (Paged out memory will be seen as free memory, and if you try to allocate on existing memory windows will completely ignore the prefered address)

As for not activating without. Make sure you are on a release build of windows 10. Fast ring and especially insider preview builds are bugged. (Virtualquery returns broken results)

Instead of aobscan use the address witcher3.exe+9AF4EE

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping


Last edited by Dark Byte on Tue Jun 21, 2016 3:01 am; edited 1 time in total
Back to top
View user's profile Send private message MSN Messenger
mgr.inz.Player
I post too much
Reputation: 218

Joined: 07 Nov 2008
Posts: 4438
Location: W kraju nad Wisla. UTC+01:00

PostPosted: Tue Jun 21, 2016 2:54 am    Post subject: Reply with quote

@Zanzer, Yes, it is problematic when using two injection points which are inside two different modules. (or more)

Also, ordering is important when you have alloc with third parameter and "normal" alloc.

Code:
alloc(newmem1,$1000,cheatengine-x86_64.exe)
alloc(pointer_highlight,8)
alloc(newmem2,$1000,lua53-64.dll)




Code:
alloc(newmem1,$1000,cheatengine-x86_64.exe)
alloc(newmem2,$1000,lua53-64.dll)
alloc(pointer_highlight,8)




so, if pointer_highlight is not shared between two injection points (and two modules) better provide third parameter for all alloc. Or just use a label.

If it is shared, you can use "mov [pointer_highlight],rcx" in one module, and "mov rdi,pointer_highlight; mov [rdi],rcx" in another.




NoMoreBSoD wrote:
I'm now using windows 10

What "winver" shows?

_________________


Last edited by mgr.inz.Player on Tue Jun 21, 2016 2:56 am; edited 1 time in total
Back to top
View user's profile Send private message MSN Messenger
DarkIceCore
Expert Cheater
Reputation: 0

Joined: 10 Jun 2012
Posts: 102
Location: Moscow

PostPosted: Tue Jun 21, 2016 2:56 am    Post subject: Reply with quote

ParkourPenguin wrote:
In a 32-bit process, you can use the near jump (5 bytes) no problem regardless of where the memory is allocated because every address is within 2GB of every other address in a 4GB address space.

In a 64-bit process, however, the virtual address space is much greater than 4GB, so you won't always be able to use the near jump. That's what the third parameter to alloc is for: the computer will try to allocate that memory within 2GB of that address.

In order to jump to a memory location further than 2GB away, you'll need to store the address you want to go to in some r/m64 and use that instead. The 14 byte jump in this case refers to storing the address you want to jump to just after the jmp instruction. This subsequently overrides any instructions in the way and forms all the "garbage" disassembly you see. 6 byte jmp + 8 bytes for the address = 14 bytes overridden.

Thus, when doing a code injection using a 14-byte jump, the only noticeable difference to you is that you'll need to override nearly 3x more instructions. Using the OP as an example, here's how you'd explicitly use a 14-byte jmp

CE automatically does this when it goes to assemble the instruction "jmp newmem" if newmem is further than 2GB away. However, something obviously isn't working perfectly right now, so do this in order to avoid any ambiguity.

For more technical information, refer to the Intel Software Developer's Manual Volume 2A section 2.2.1.6 "RIP-relative addressing", as well as the documentation on the JMP instruction within said manual (or any other valid x64 reference of your choice).


Big thnx for sufficient information, now i solved my problems with injects by myself.
Back to top
View user's profile Send private message
NoMoreBSoD
Advanced Cheater
Reputation: 3

Joined: 03 Sep 2013
Posts: 85

PostPosted: Tue Jun 21, 2016 4:49 am    Post subject: Reply with quote

ParkourPenguin wrote:
In a 32-bit process, you can use the near jump (5 bytes) no problem regardless of where the memory is allocated because every address is within 2GB of every other address in a 4GB address space.

In a 64-bit process, however, the virtual address space is much greater than 4GB, so you won't always be able to use the near jump. That's what the third parameter to alloc is for: the computer will try to allocate that memory within 2GB of that address.

In order to jump to a memory location further than 2GB away, you'll need to store the address you want to go to in some r/m64 and use that instead. The 14 byte jump in this case refers to storing the address you want to jump to just after the jmp instruction. This subsequently overrides any instructions in the way and forms all the "garbage" disassembly you see. 6 byte jmp + 8 bytes for the address = 14 bytes overridden.

Thus, when doing a code injection using a 14-byte jump, the only noticeable difference to you is that you'll need to override nearly 3x more instructions. Using the OP as an example, here's how you'd explicitly use a 14-byte jmp:


CE automatically does this when it goes to assemble the instruction "jmp newmem" if newmem is further than 2GB away. However, something obviously isn't working perfectly right now, so do this in order to avoid any ambiguity.

For more technical information, refer to the Intel Software Developer's Manual Volume 2A section 2.2.1.6 "RIP-relative addressing", as well as the documentation on the JMP instruction within said manual (or any other valid x64 reference of your choice).

This is incredibly helpful! You've solved the problem and explained it to me in a way that makes sense! Now I can even manually update the other scripts myself Very Happy

To recap :
A 16 bytes jump isn't shown as such in memory viewer and looks like random garbage. "FF 25 00 00 00 00" is the 6 bytes code that initiates an 8 bytes jump and must be followed by an 8 bytes address. This makes 14 bytes, and my injection point needs to be at least that long without breaking any existing instruction.
I nop the extra bytes (after 14) from those instructions when creating my jump.
"db FF 25 00 00 00 00" means jump to, and "dq newmem" means get the address of newmem.


Dark Byte wrote:
Sorry, i overlooked the important part.
You use kernelmode query memory regions.
You can't use a prefered base with that enabled. (Paged out memory will be seen as free memory, and if you try to allocate on existing memory windows will completely ignore the prefered address)

As for not activating without. Make sure you are on a release build of windows 10. Fast ring and especially insider preview builds are bugged. (Virtualquery returns broken results)

Instead of aobscan use the address witcher3.exe+9AF4EE
So another solution is to skip aobscan on 64 bits game? i'll try this.

mgr.inz.Player wrote:
What "winver" shows?

Here is what I have :


I haven't done any change to windows.



Thanks for helping me everybody, it's really appreciated! I couldn't have solved it myself Very Happy
Back to top
View user's profile Send private message
hhhuut
Grandmaster Cheater
Reputation: 6

Joined: 08 Feb 2015
Posts: 607

PostPosted: Tue Jun 21, 2016 4:51 am    Post subject: Reply with quote

NoMoreBSoD wrote:
So another solution is to skip aobscan on 64 bits game?

No, AOB-Scans within 64bit applications work fine as long as you use the regular windows version of the memoryquery routine, not CE's one ...
Back to top
View user's profile Send private message
NoMoreBSoD
Advanced Cheater
Reputation: 3

Joined: 03 Sep 2013
Posts: 85

PostPosted: Tue Jun 21, 2016 4:53 am    Post subject: Reply with quote

hhhuut wrote:
NoMoreBSoD wrote:
So another solution is to skip aobscan on 64 bits game?

No, AOB-Scans within 64bit applications work fine as long as you use the regular windows version of the memoryquery routine, not CE's one ...
But the regular windows version doesn't return anything at all when I scan for an array or when I do "find what accesses this address".
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine All times are GMT - 6 Hours
Goto page Previous  1, 2, 3  Next
Page 2 of 3

 
Jump to:  
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


Powered by phpBB © 2001, 2005 phpBB Group

CE Wiki   IRC (#CEF)   Twitter
Third party websites