invoke strlen, OFFSET string

invoke crc, OFFSET string, eax


crc algo based from pnglib.
Posted on 2002-07-16 15:38:18 by stryker

i coded a small program to demonstrate 1 way to use crc32 to protect pe files...

there's 'signer' app, that open user-definited file; calculate crc32 from PE header onwards, till the end; and save it at PE header - 4

the selftest.exe app open itself in disk, check its crc32 against this precomputed value, and return 0/1

it can be fooled by incountable ways...

Posted on 2002-07-16 17:18:32 by ancev
Thank you, Stryker.

I've coded small ex. that shows CRC of string Win32ASM.

Here's the main code:

k db "Win32ASM", 0
l db 200 dup(?)
szHexFormat db "%lX",0
caption db "test", 0
hWnd dd 0

invoke lstrlen, offset k
invoke CRC32_Compute, offset k, eax
invoke wsprintf, offset l, offset szHexFormat, eax
invoke MessageBox, hWnd, offset l, offset caption, MB_OK
invoke PostQuitMessage, 0

end main

When I compile and run I get only empty message box :confused: ... but when I load it into Ollydbg (set breakpoint, trace and run...) the CRC value is shown! I don't understand this :(.

Posted on 2002-07-16 17:56:20 by stealthFIGHTER
I don't know why? but here's the a test program, I just did. CRC32 Algo by Nexo from the PNGLib library.

I did some changes, so the algo looks nice. It was a real mess.


probably the formatting used in wsprintf...
Posted on 2002-07-16 19:34:40 by stryker
If I can give you a quite obvious advice (I do so because other people here, beginners, may read too, and I've seen a problem in this regard many times) the best thing to do would be to make many check routines.. not just one. Cracking 10 of them is harder than cracking 1 of them. What about 1000? You (cr?cker) have to find them anyway, and remove them all. 1000 take some serious time. But one must not use the same code for all 1000, otherwise a simple pattern matching will find and remove all of them in one shot. Here having your own compiler helps a lot, I reckon.
Also, crypting your EXE (with your own crypter, not a standard/known one) and making use of self-modifying code to generate these check routines sure helps..
CRC-32 has been cracked anyway, so one should find a more secure algorithm (what about making your own? unknown algorithms are harder to cr?ck.. ), otherwise storing the checksum in a single DWORD becomes then the weak point..

Thanks for the advices. ;)
In fact, I know CRC-32 is a very classic way to protect executables... I usually don't use it "as it", I "encode" it, with a more or less lame sheme to not let it appear clearly... or use less popular/known algorithms like Adler.
The CRC-32 (or alikes) can be used in software protection, but also to check if a file has a good integrity (which can be not only destroyed by hackers, but aborted or erroned downloads or uploads... even if it is censed to be done dynamically and automatically by the network card, ie... or worse, virii).

This way, I have a protection, not much, but not only it prevents the file integrity (important on the project where I used it), but also from "lamers" and inexperienced crackers...
As would say f0dder, if the program has to be cracked, it will be someday... and on the project where I used this technique, I think it is harder to cr*ck it than recoding it for a good programmer... and good cr*ckers are *usually* good programmers)... and another problem was the size was limited and I couldn't code many protections (the Bazik's idea to put MD5 sum in the dos stub message sounds good ^^).
Posted on 2002-07-17 02:08:33 by JCP
Salut Readiosys, I should add something to my previous post.


There's an inherent problem, though, which will be difficult to solve with standard tools.

Even if you don't use a known CRC algo, the cracker can reverse engineer one single of your 1000 check routines, and thus deduce from the algorithm an "acceptable" checksum value and store it in the PE.. fooling the other 999 checkpoints.
So what will really work is to store the checksums 1000 times, i.e. in each of the check routines, as (obfuscated) immediate values. Then it will be *really* necessary (for any cr?cker) to cr?ck them all, one by one (assuming you don't make all of them identical, making them prone to a easy pattern matching attack).

It's clear that you'll have to insert these 1000 immediate values (making sure they aren't all the same, otherwise finding them will be very easy.. you can add to them their current address, for example, or use a more sophisticated method) after you've assembled your program, and this thing is not trivial, at least with the usual tools.

One thing you could make is to disseminate in your asm source code one-line statements like "PROTECT", possibly not in your hyperoptimized gfx innerloops. :D
Then write an utility that gets in input your source file + PROTECT statements, and "compiles" them.. giving in output a pure asm sourcecode (a compiler, ain't it ;) ).
Then you assemble it, and produce a PE. The assembler outputs on a separate file the list of memory locations corresponding to the immediate value used by each protection statement. A final utility calculates the "CRC" and patches all of these immediate values I just mentioned.

Here the advantage of having your own assembler/compiler is clear: you can extend it with functionality like the above, i.e. output the precise memory location that will need to be patched.. and state which kind of patching will it need (i.e. how to crypt that value).

It's true that standard assemblers are uncapable of such flexibility, but short of writing your own assembler/compiler, you could modify FASM sourcecode, for example, to extend any special functionality you require.

This is just one example of what I meant every time I stressed that having your own development tools is extremely useful and important, let away productive.
Posted on 2002-07-17 08:24:43 by Maverick
Hi all,
i want to add a CRC self check to my software. But i really don't know where i should add this CRC check in my source code (in ASM). Can someone make a small source code as an example for me? I use the CRC check source code of Thomas.
All supports will be appreciated.
Posted on 2006-05-13 01:30:56 by rongchaua