 |
Cheat Engine The Official Site of Cheat Engine
|
| View previous topic :: View next topic |
| Author |
Message |
booingthetroll Expert Cheater
Reputation: 0
Joined: 30 Aug 2011 Posts: 114 Location: ::1
|
Posted: Sat Jul 11, 2015 10:30 pm Post subject: How does CE scan so fast? |
|
|
| First I'd like to say that I am NOT trying to make a competitor to CE. I'm trying to write a DLL that'll do a specific task faster (I have to scan for a ridiculous number of values) in the hopes that because it can directly access memory without ReadProcessMemory it'll be faster. but somehow CE absolutely destroys mine in terms of time (scanning for 2 bytes, at least). I don't wanna post my code but it looks pretty good, I'm gonna continue refining it but what the heck? how is this possible? DLL in-process scanning has potential to be faster right? it just seems ridiculous that an external very flexible scanner could be so much faster than a very specific in-memory scanner. |
|
| Back to top |
|
 |
Rudo Advanced Cheater
Reputation: 2
Joined: 27 Jun 2015 Posts: 80
|
Posted: Sun Jul 12, 2015 12:29 am Post subject: |
|
|
| Dark Byte must have put some of his magic in CE ... |
|
| Back to top |
|
 |
Gniarf Grandmaster Cheater Supreme
Reputation: 43
Joined: 12 Mar 2012 Posts: 1285
|
Posted: Sun Jul 12, 2015 12:31 am Post subject: |
|
|
If I don't know what's in your code I cannot tell you what's wrong with it. If you don't want to post it that's fine, but at least try to give it in pseudo code.
Until then the best advice I can give is to check cheat engine's source code, since it is open source.
Trying wild guesses, the other advices I can give are:
-use VirtualQueryEx to check if the region you're scanning is writable, and when it's not writable increase the scan address by the RegionProperties.RegionSize it returns.
-Only scan even addresses if you're looking for 2 byte ints in a program that is not an oldie.
-Then, multithreading... _________________
DO NOT PM me if you want help on making/fixing/using a hack. |
|
| Back to top |
|
 |
Dark Byte Site Admin
Reputation: 471
Joined: 09 May 2003 Posts: 25819 Location: The netherlands
|
Posted: Sun Jul 12, 2015 2:06 am Post subject: |
|
|
* don't write every single address you find to disk the second you find it (ce's bottleneck is more often disk speed than memory speed)
* don't convert memory to a hexadecimal string and then compare strings with eachother(i know this is a stupid tip, but i have seen scanners where they did this...)
* don't print to the console (slow)
* don't scan your dll's memory, nor the memory it dynamically allocates (e.g if your dll has a buffer where it stores the previous value, your scanner will find it and add every already found address to the list again, and then it adds that list, and that list, and that list, and that list, until the end off the buffer)
* don't resize the list of found addresses for every found result. (when full write to disk or only then resize the buffer to be twice as big as before)
* don't touch page_guard memory. Doing so can ruin the stack
* don't call windows api's inside your scanner loop unless it's really necesary (exception/result writing when buffer full is necesary, but not virtualquery or memory alloxation)
.
* not really a speed improvement, but, use a complex exception handler. During the scan memory can be freed. When that happens an exception will be raised and you'll need to handle that else the game will crash. (using isbadreadptr will not work, and is slow anyhow)
You need to handle this exception quickly and efficiently. So don't encapsule only the read in a try/except, but do it for the loop itself.
on exception you can assume the whole page is gone, and probably even more. So call virtualquery again to find the next block
i have played with injected scanners before (5.x had hyperscan, and there's the cetc project which scans a process from kernelmode) but it's speed was about the same as the normal scan with the added headache of filtering out dll related memory and some games don't handle dll injection well. _________________
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 |
|
| Back to top |
|
 |
booingthetroll Expert Cheater
Reputation: 0
Joined: 30 Aug 2011 Posts: 114 Location: ::1
|
Posted: Sun Jul 12, 2015 12:18 pm Post subject: |
|
|
| Code: | void QueryRegions(HANDLE Process, byte* data, int length) {
MEMORY_BASIC_INFORMATION mem;
int ms = sizeof(mem);
unsigned int i, x;
byte *address, *base;
bool match;
for (i = 0; VirtualQueryEx(Process, (void*)i, &mem, ms);) {
if ((mem.AllocationProtect & 238) && !(mem.Protect & 257) && (mem.State & 4096)) {
base = (byte*)mem.BaseAddress;
for (address = base; address < base + mem.RegionSize; address++) {
match = true;
for (x = 0; x < length; x++)
if (address[x] != data[x]) {
match = false;
break;
}
if (match)
file << hex << (int)address << endl; // even without this it's really slow
}
}
if (i>0xFFFFFFFF - mem.RegionSize - 1)
break;
i += mem.RegionSize;
}
} |
That's what I have so far, even with your tips I'm not really sure what changes I can make. I wrote it without much knowledge of memory but yeah I don't scan PAGE_GUARD memory and I'm pretty sure it's not double scanning. I'll add it but the DLL's small enough that I don't think excluding it would make much of a difference
[edit] Thanks for the help but since DLLs seem to pause the game whereas remote accesses don't I'll probably just use CE |
|
| Back to top |
|
 |
STN I post too much
Reputation: 43
Joined: 09 Nov 2005 Posts: 2676
|
Posted: Sun Jul 12, 2015 5:16 pm Post subject: |
|
|
Wow, you are doing this byte by byte!. Of course it will be slow, thats a lot of data.
Here is how i did mine (outside the process in my trainer)
Scan only the module (if applicable) otherwise start from a location i know there is a chance (its pointless to start from 0 because you can never find it such low addresses)
Dump memory using RPM (not the whole, just pieces (1000 bytes or so can't remember))
An algo that i wrote that compares only the first byte, if it matches then i go byte by byte to compare the full signature otherwise quickly jump to the next chunk of data.
Repeat
It was badly coded and still pretty fast. Within the memory inside a dll if you have got a module to start from (i.e the cheat address/memory is not dynamically loaded like how Minecraft does e.g) then, the scanning goes really fast and with educated guesses you can avoid scanning for unnecessary mem regions.
Your scanner's speed depends on your comparison algorithm and how big of a jump you do to the next chunk of bytes (of course without missing the signature in between). Google for examples you can find pretty fast signature scanners using efficient data structure algorithms (Quick search and others i don't remember anymore, was taught in university data structure class).
If you care a lot about speed, write your dll in asm (your flavor of assembler), c++ is fast but asm is faster. _________________
|
|
| 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
|
|