I am learning High Level Assembly Language at the moment, and am playing with the stack to better understand everything.
I note that in the following program, I can pop the contents of the stack, without ever having pushed anything onto it 37 times before the program crashes.
ike1: uns32 := 1;
begin test1;
while (ike1 < 38) do
pop(eax);
stdout.put(ike1, nl);
stdout.put("ESP: ", esp, nl);
stdout.put("EAX:", eax, nl, nl);
add(1, ike1);
endwhile;
end test1;
Each time the stack is popped into EAX, and the output of EAX shows random data each time.
I firstly don’t understand how this is possible, as I thought every program was seggregated into its own private memory space?
In any event I am popping data of the stack…what would this be, and would it be affecting any other running programs?
My OS is Windows 7 64 bit.
Before the execution of
main()a bunch of other operations need to be done by the OS to properly setup the environment before control of the execution is handled to your application. So, most of what’s on the stack at this point is garbage left from previous operations.Right before
main()is executed, you can expect to findargcandargvon the stack as well.EDIT:
A comment from a user kinda challenged me to go through the process of debugging an assembly application in gdb and examining the stack to backup a statement I made on the original answer.
So please consider the following assembly code written in nasm:
I compiled this on Mac OS X with:
As you can probably tell by the source code, the start of the application is defined by
mystart, and it doesn’t take any parameters.Now, let’s make this investigation a little more exciting by opening this program in gdb:
After gdb has loaded, it’s important for educational purposes to set a cmd line parameter for this application even though it wasn’t written to accept any.
The application is still not running at this point. We need to set a breakpoint to the beginning of the main function so can inspect the stack to see what’s going on before our application starts executing it’s own code:
Execute the command
runon gdb to start the application and break the execution. Now we can inspect the stack with:outputs:
Yes Sir, this command prints the contents of the stack. It tells gdb to show 20 words in hexadecimal format starting at the address stored by the
$espregister.Let’s see,
$espactually points to0xbffff8cc, ok but examining what’s stored by this memory address reveals another address:0x00002000. To what does it points to???Not a shocker, right?! So let’s take a look at what some of the other addresses of the table are pointing to:
Wow. That’s actually the original application’s name and path stored right there on the stack! Awesome, let’s continue to the next interesting address of the table:
Jackpot! The cmd line argument we passed upon executing our application also got stored in the stack. So as I’ve stated before, among the garbage stored in the stack before your application executes, you can also find cmd line parameters that were used to execute the application even when the
main()function of the application isvoidand doesn’t take any parameters.