c - Help deciphering simple Assembly Code -


i learning assembly using gdb & eclipse
here simple c code.

int absdiff(int x, int y) {   if(x < y)     return y-x; else     return x-y; }  int main(void) {   int x = 10;   int y = 15;   absdiff(x,y); return exit_success;   } 

here corresponding assembly instructions main()

          main: 080483bb:   push %ebp  #push old frame pointer onto stack 080483bc:   mov %esp,%ebp #move frame pointer down, position of stack pointer 080483be:   sub $0x18,%esp  # ??? 25         int x = 10;     080483c1:   movl $0xa,-0x4(%ebp) #move "x(10)" 4 address below frame pointer (why not push?) 26         int y = 15; 080483c8:   movl $0xf,-0x8(%ebp) #move "y(15)" 8 address below frame pointer (why not push?) 28         absdiff(x,y); 080483cf:   mov -0x8(%ebp),%eax # -0x8(%ebp) == 15 = y, , move %eax 080483d2:   mov %eax,0x4(%esp) # point on, confused 080483d6:   mov -0x4(%ebp),%eax  080483d9:   mov %eax,(%esp) 080483dc:   call 0x8048394 <absdiff> 31         return exit_success; 080483e1:   mov $0x0,%eax 32        } 

basically, asking me make sense of assembly code, , why doing things in particular order. point stuck, shown in assembly comments. !

first bears saying assembly in at&t syntax version of x86_32, , order of arguments operations reversed intel syntax (used masm, yasm, , many other assemblers , debuggers).

080483bb:   push %ebp  #push old frame pointer onto stack 080483bc:   mov %esp,%ebp #move frame pointer down, position of stack pointer 080483be:   sub $0x18,%esp  # ??? 

this enters stack frame. frame area of memory between stack pointer (esp) , base pointer (ebp). area intended used local variables have live on stack. note: stack frames don't have implemented in way, , gcc has optimization switch -fomit-frame-pointer away except when alloca or variable sized arrays used, because implemented changing stack pointer arbitrary values. not using ebp frame pointer allows used general purpose register (more general purpose registers good).

using base pointer makes several things simpler calculate compilers , debuggers, since variables located relative base not change while in function, can index them relative stack pointer , same results, though stack pointer tend change around same location may require different index @ different times.

in code 0x18 (or 24) bytes being reserved on stack local use.

this code far called function prologue (not confused programming language "prolog").

25         int x = 10;     080483c1:   movl $0xa,-0x4(%ebp) #move "x(10)" 4 address below frame pointer (why not push?) 

this line moves constant 10 (0xa) location within current stack frame relative base pointer. because base pointer below top of stack , since stack grows downward in ram index negative rather positive. if indexed relative stack pointer different index used, positive.

you correct value have been pushed rather copied this. suspect done way because have not compiled optimizations turned on. default gcc (which assume using based on use of gdb) not optimize much, , code default "copy constant location in stack frame" code. may not case, 1 possible explanation.

26         int y = 15; 080483c8:   movl $0xf,-0x8(%ebp) #move "y(15)" 8 address below frame pointer (why not push?) 

similar previous line of code. these 2 lines of code put 10 , 15 local variables. on stack (rather in registers) because unoptimized code.

28         absdiff(x,y); 

gdb printing meant source code line being executed, not function being executed (yet).

080483cf:   mov -0x8(%ebp),%eax # -0x8(%ebp) == 15 = y, , move %eax 

in preparation calling function values being passed arguments need retrieved storage locations (even though placed @ locations , values known because of no optimization thing)

080483d2:   mov %eax,0x4(%esp) # point on, confused 

this second part of move stack of 1 of local variables' value can use argument function. can't (usually) move 1 memory address on x86, have move through register (eax in case).

080483d6:   mov -0x4(%ebp),%eax  080483d9:   mov %eax,(%esp) 

these 2 lines same thing except other variable. note since variable being moved top of stack no offset being used in second instruction.

080483dc:   call 0x8048394 <absdiff> 

this pushed return address top of stack , jumps address of absdiff.

you didn't include code absdiff, did not step through that.

31         return exit_success; 080483e1:   mov $0x0,%eax 

c programs return 0 upon success, exit_success defined 0 someone. integer return values put in eax, , code called main function use value argument when calling exit function.

32        } 

this end. reason gdb stopped here there things happen clean up. in c++ common see destructor local class instances being called here, in c see function epilogue. compliment function prologue, , consists of returning stack pointer , base pointer values at. done similar math on them, done leave instruction. there enter instruction can used prologue, gcc doesn't (i don't know why). if had continued view disassembly here have seen epilogue code , ret instruction.

something may interested in ability tell gcc produce assembly files. if do:

gcc -s source_file.c 

a file named source_file.s produced assembly code in it.

if do:

 gcc -s -o source_file.c 

then same thing happen, basic optimizations done. make reading assembly code easier since code not have many odd instructions seem have been done better way (like moving constant values stack, register, location on stack , never using push instruction).

you regular optimization flags gcc are:

-o0         default -- none -o1         few optimizations -o          same -o1 -o2         lot of optimizations -o3         bunch more, of may take long time and/or make code lot bigger -os         optimize size -- similar -o2, not quite 

if trying debug c programs want least optimizations possible since things happen in order written in code , variables won't disappear.

you should have @ gcc man page:

man gcc 

Comments

Popular posts from this blog

android - Spacing between the stars of a rating bar? -

html - Instapaper-like algorithm -

c# - How to execute a particular part of code asynchronously in a class -