• Welcome to Dark Bit Factory & Gravity.
 

Making your exe smaller

Started by saida, October 04, 2006

Previous topic - Next topic

0 Members and 0 Guests are viewing this topic.

saida

Normaly, you will create a data segment for your data, and a code segment for your code. This is however not the best way to go, if you are aiming for a really small exe.
If you are going to include a lib made in asm into your c project, you will get two data "sections". This drasticly increases the size of the final exe.
Look at the following code:

.data
szMyString db "param1",0 ;7 bytes
.code
push offset szMyString ; 5 bytes
call myFunctionWithOneParameterPushed ; 5 bytes


(total of 7+5+5 = 17 bytes)
This is indeed a nice and structured way to program, but...

instead, look at this code:

.code
call _ff ; 5 bytes
szMyString db "param1",0 ;7 bytes
_ff:
call myFunctionWithOneParameterPushed ; 5 bytes


(also 17 bytes, but we got rid of the data section)
When we call the label _ff, the processor automaticly pushes the return value to the stack. And guess what, that return value is the address to our string!
So this has eliminated the use of a data segment... or has it?
There is still one more problem to solve: how do we write to the "read-and-execute-only" code segment?
We could use the win api to unprotect the code segment in runtime - but that would be useless because of the extra bytes needed to do so.
Instead, you can link the masm code with:
\masm32\bin\Link /SUBSYSTEM:WINDOWS "myProgram.obj" /section:.text,RWE /MERGE:.rdata=.data /MERGE:.data=.text

If you want to use code that write to the code segment in a c-program, you will have to link your c program so it makes the code segment (.text) writable - dont forget that.
If your compiler fails to do this, just use PEExplorer or something like that to make your exe's code segment writable.

I hope this help someone out there, struggeling with huge mysterial overheads between his c-code, and asm code.
Sorry if something is unclear, i had to much coffee. ::)

Jim

Since in flat model, all the segments, cs, ss, ds are all pointing at the same memory, isn't it simply possible to write code into ds:address and then execute it via cs:address?  Or am I missing something?

Jim
Challenge Trophies Won:

saida

I dont think you have execute priveleges in ds. (only RW)
But i guess you could as well make that area RWE if you wanted to.
The main point here is to get rid of the overhead created, when you have two datasections (one from the asm obj, and one from the main c-program)
This is the only way me and auld got rid of it so far. Its weird, because i really do understand why we couldnt just merge our two data sections..

Jim

I don't mean execute from ds, I mean write your self modifying code or whatever into ds, but then jump to it in cs - it's at the same offset.

If both the data sections are in dgroup the linker should fix that for you and only have one dsection in the exe.  If not, find out what the C compiler is calling the data section and use an identical section name in your asm.  Or am I confused again - it happens :D

Jim
Challenge Trophies Won:

Shockwave

Knowing you Jim, you're probably right!
Shockwave ^ Codigos
Challenge Trophies Won:

saida

Probably - because im totaly lost ;)

Rbz

That is a great trick indeed    O0
Challenge Trophies Won: