Presentation is loading. Please wait.

Presentation is loading. Please wait.

Carnegie Mellon 1 Introduction to x86 Assembly or “What does my laptop actually do?” Ymir Vigfusson Some slides gracefully borrowed from

Similar presentations


Presentation on theme: "Carnegie Mellon 1 Introduction to x86 Assembly or “What does my laptop actually do?” Ymir Vigfusson Some slides gracefully borrowed from"— Presentation transcript:

1 Carnegie Mellon 1 Introduction to x86 Assembly or “What does my laptop actually do?” Ymir Vigfusson Some slides gracefully borrowed from 18-213@CMU

2 Carnegie Mellon 2 So what is assembly really?

3 Carnegie Mellon 3 Why study assembly? triton$

4 Carnegie Mellon 4 One reason: Reverse engineering People who figure out what viruses do today $$$ !

5 Carnegie Mellon 5 Motivation: The Turing Machine! http://www.youtube.com/watch?v=cYw2ewoO6c4

6 Carnegie Mellon 6 Intel x86 Processors: Overview X86-64 / EM64t X86-32/IA32 X86-16 8086 286 386 486 Pentium Pentium MMX Pentium III Pentium 4 Pentium 4E Pentium 4F Core 2 Duo Core i7 IA: often redefined as latest Intel architecture time ArchitecturesProcessors MMX SSE SSE2 SSE3 SSE4

7 Carnegie Mellon 7 Intel x86 Evolution: Milestones NameDateTransistorsMHz 8086197829K5-10  First 16-bit processor. Basis for IBM PC & DOS  1MB address space 3861985275K16-33  First 32 bit processor, referred to as IA32  Added “flat addressing”  Capable of running Unix  32-bit Linux/gcc uses no instructions introduced in later models Pentium 4F2004125M2800-3800  First 64-bit processor, referred to as x86-64 Core i72008731M2667-3333  Our shark machines

8 Carnegie Mellon 8 Intel x86 Processors Machine Evolution  38619850.3M  Pentium19933.1M  Pentium/MMX19974.5M  PentiumPro19956.5M  Pentium III19998.2M  Pentium 4200142M  Core 2 Duo2006291M  Core i72008731M Added Features  Instructions to support multimedia operations  Parallel operations on 1, 2, and 4-byte data, both integer & FP  Instructions to enable more efficient conditional operations Linux/GCC Evolution  Two major steps: 1) support 32-bit 386. 2) support 64-bit x86-64

9 Carnegie Mellon 9 What is this? (gdb) disass checksum Dump of assembler code for function checksum: 0x08048400 : push %ebp 0x08048401 : xor %edx,%edx 0x08048403 : mov %esp,%ebp 0x08048405 : xor %eax,%eax 0x08048407 : push %esi 0x08048408 : mov 0x8(%ebp),%esi 0x0804840b : push %ebx 0x0804840c : mov 0xc(%ebp),%ebx 0x0804840f : test %ebx,%ebx 0x08048411 : jle 0x8048425 0x08048413 : nop 0x08048414 : lea 0x0(%esi,%eiz,1),%esi 0x08048418 : movsbl (%esi,%edx,1),%ecx 0x0804841c : add $0x1,%edx 0x0804841f : xor %ecx,%eax 0x08048421 : cmp %ebx,%edx 0x08048423 : jne 0x8048418 0x08048425 : pop %ebx 0x08048426 : pop %esi 0x08048427 : pop %ebp 0x08048428 : ret End of assembler dump.

10 Carnegie Mellon 10 CPU Assembly Programmer’s View Programmer-Visible State  PC: Program counter  Address of next instruction  Called “EIP” (IA32) or “RIP” (x86-64)  Register file  Heavily used program data  Condition codes  Store status information about most recent arithmetic operation  Used for conditional branching PC Registers Memory Code Data Stack Addresses Data Instructions Condition Codes  Memory  Byte addressable array  Code and user data  Stack to support procedures

11 Carnegie Mellon 11 text binary Compiler ( gcc -S ) Assembler ( gcc or as ) Linker ( gcc or ld ) C program ( p1.c p2.c ) Asm program ( p1.s p2.s ) Object program ( p1.o p2.o ) Executable program ( p ) Static libraries (.a ) Turning C into Object Code  Code in files p1.c p2.c  Compile with command: gcc –O1 p1.c p2.c -o p  Use basic optimizations ( -O1 )  Put resulting binary in file p

12 Carnegie Mellon 12 Compiling Into Assembly C Code int sum(int x, int y) { int t = x+y; return t; } Generated IA32 Assembly sum: pushl %ebp movl %esp,%ebp movl 12(%ebp),%eax addl 8(%ebp),%eax popl %ebp ret Obtain with command /usr/local/bin/gcc –O1 –m32 -S code.c Produces file code.s Some compilers use instruction “ leave ”

13 Carnegie Mellon 13 Assembly Characteristics: Data Types “Integer” data of 1, 2, or 4 bytes  Data values  Addresses (untyped pointers) Floating point data of 4, 8, or 10 bytes No aggregate types such as arrays or structures  Just contiguously allocated bytes in memory

14 Carnegie Mellon 14 Assembly Characteristics: Operations Perform arithmetic function on register or memory data Transfer data between memory and register  Load data from memory into register  Store register data into memory Transfer control  Unconditional jumps to/from procedures  Conditional branches

15 Carnegie Mellon 15 Code for sum 0x401040 : 0x55 0x89 0xe5 0x8b 0x45 0x0c 0x03 0x45 0x08 0x5d 0xc3 Object Code Assembler  Translates.s into.o  Binary encoding of each instruction  Nearly-complete image of executable code  Missing linkages between code in different files Linker  Resolves references between files  Combines with static run-time libraries  E.g., code for malloc, printf  Some libraries are dynamically linked  Linking occurs when program begins execution Total of 11 bytes Each instruction 1, 2, or 3 bytes Starts at address 0x401040

16 Carnegie Mellon 16 Machine Instruction Example C Code  Add two signed integers Assembly  Add 2 4-byte integers  “Long” words in GCC parlance  Same instruction whether signed or unsigned  Operands: x :Register %eax y :MemoryM[ %ebp+8] t :Register %eax –Return function value in %eax Object Code  3-byte instruction  Stored at address 0x80483ca int t = x+y; addl 8(%ebp),%eax 0x80483ca: 03 45 08 Similar to expression: x += y More precisely: int eax; int *ebp; eax += ebp[2]

17 Carnegie Mellon 17 Disassembled Disassembling Object Code Disassembler objdump -d p  Useful tool for examining object code  Analyzes bit pattern of series of instructions  Produces approximate rendition of assembly code  Can be run on either complete executable or.o file 080483c4 : 80483c4: 55 push %ebp 80483c5: 89 e5 mov %esp,%ebp 80483c7: 8b 45 0c mov 0xc(%ebp),%eax 80483ca: 03 45 08 add 0x8(%ebp),%eax 80483cd: 5d pop %ebp 80483ce: c3 ret

18 Carnegie Mellon 18 Disassembled Dump of assembler code for function sum: 0x080483c4 : push %ebp 0x080483c5 : mov %esp,%ebp 0x080483c7 : mov 0xc(%ebp),%eax 0x080483ca : add 0x8(%ebp),%eax 0x080483cd : pop %ebp 0x080483ce : ret Alternate Disassembly Within gdb Debugger gdb p disassemble sum  Disassemble procedure x/11xb sum  Examine the 11 bytes starting at sum Object 0x401040: 0x55 0x89 0xe5 0x8b 0x45 0x0c 0x03 0x45 0x08 0x5d 0xc3

19 Carnegie Mellon 19 What Can be Disassembled? Anything that can be interpreted as executable code Disassembler examines bytes and reconstructs assembly source % objdump -d WINWORD.EXE WINWORD.EXE: file format pei-i386 No symbols in "WINWORD.EXE". Disassembly of section.text: 30001000 : 30001000: 55 push %ebp 30001001: 8b ec mov %esp,%ebp 30001003: 6a ff push $0xffffffff 30001005: 68 90 10 00 30 push $0x30001090 3000100a: 68 91 dc 4c 30 push $0x304cdc91

20 Carnegie Mellon 20 Registers, operands, move operation

21 Carnegie Mellon 21 Integer Registers (IA32) %eax %ecx %edx %ebx %esi %edi %esp %ebp %ax %cx %dx %bx %si %di %sp %bp %ah %ch %dh %bh %al %cl %dl %bl 16-bit virtual registers (backwards compatibility) general purpose accumulate counter data base source index destination index stack pointer base pointer Origin (mostly obsolete)

22 Carnegie Mellon 22 Moving Data: IA32 Moving Data movl Source, Dest: Operand Types  Immediate: Constant integer data  Example: $0x400, $-533  Like C constant, but prefixed with ‘$’  Encoded with 1, 2, or 4 bytes  Register: One of 8 integer registers  Example: %eax, %edx  But %esp and %ebp reserved for special use  Others have special uses for particular instructions  Memory: 4 consecutive bytes of memory at address given by register  Simplest example: (%eax)  Various other “address modes” %eax %ecx %edx %ebx %esi %edi %esp %ebp

23 Carnegie Mellon 23 movl Operand Combinations Cannot do memory-memory transfer with a single instruction movl Imm Reg Mem Reg Mem Reg Mem Reg SourceDestC Analog movl $0x4,%eaxtemp = 0x4; movl $-147,(%eax)*p = -147; movl %eax,%edxtemp2 = temp1; movl %eax,(%edx)*p = temp; movl (%eax),%edxtemp = *p; Src,Dest

24 Carnegie Mellon 24 Simple Memory Addressing Modes Normal(R)Mem[Reg[R]]  Register R specifies memory address movl (%ecx),%eax DisplacementD(R)Mem[Reg[R]+D]  Register R specifies start of memory region  Constant displacement D specifies offset movl 8(%ebp),%edx

25 Carnegie Mellon 25 Using Simple Addressing Modes void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } Body Set Up Finish swap: pushl %ebp movl %esp,%ebp pushl %ebx movl 8(%ebp), %edx movl 12(%ebp), %ecx movl (%edx), %ebx movl (%ecx), %eax movl %eax, (%edx) movl %ebx, (%ecx) popl %ebx popl %ebp ret

26 Carnegie Mellon 26 Using Simple Addressing Modes void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } swap: pushl %ebp movl %esp,%ebp pushl %ebx movl8(%ebp), %edx movl12(%ebp), %ecx movl(%edx), %ebx movl(%ecx), %eax movl%eax, (%edx) movl%ebx, (%ecx) popl%ebx popl%ebp ret Body Set Up Finish

27 Carnegie Mellon 27 Understanding Swap void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } Stack (in memory) RegisterValue %edxxp %ecxyp %ebxt0 %eaxt1 yp xp Rtn adr Old % ebp %ebp 0 4 8 12 Offset Old % ebx -4 %esp movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

28 Carnegie Mellon 28 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 123 456 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp0x104 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

29 Carnegie Mellon 29 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 123 456 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 0x124 0x104 0x120 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

30 Carnegie Mellon 30 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 123 456 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 0x120 0x104 0x124 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

31 Carnegie Mellon 31 456 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 123 456 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 0x124 0x120 123 0x104 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

32 Carnegie Mellon 32 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 123 456 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 456 0x124 0x120 0x104 123 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

33 Carnegie Mellon 33 456 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 456 0x124 0x120 123 0x104 123 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

34 Carnegie Mellon 34 Understanding Swap 0x120 0x124 Rtn adr %ebp 0 4 8 12 Offset -4 456 123 Address 0x124 0x120 0x11c 0x118 0x114 0x110 0x10c 0x108 0x104 0x100 yp xp %eax %edx %ecx %ebx %esi %edi %esp %ebp 456 0x124 0x120 0x104 123 movl8(%ebp), %edx# edx = xp movl12(%ebp), %ecx# ecx = yp movl(%edx), %ebx# ebx = *xp (t0) movl(%ecx), %eax# eax = *yp (t1) movl%eax, (%edx)# *xp = t1 movl%ebx, (%ecx)# *yp = t0

35 Carnegie Mellon 35 Complete Memory Addressing Modes Most General Form D(Rb,Ri,S)Mem[Reg[Rb]+S*Reg[Ri]+ D]  D: Constant “displacement” 1, 2, or 4 bytes  Rb: Base register: Any of 8 integer registers  Ri:Index register: Any, except for %esp  Unlikely you’d use %ebp, either  S: Scale: 1, 2, 4, or 8 (why these numbers?) Special Cases (Rb,Ri)Mem[Reg[Rb]+Reg[Ri]] D(Rb,Ri)Mem[Reg[Rb]+Reg[Ri]+D] (Rb,Ri,S)Mem[Reg[Rb]+S*Reg[Ri]]

36 Carnegie Mellon 36 So far! History of Intel processors and architectures  Evolutionary design leads to many quirks and artifacts C, assembly, machine code  Compiler must transform statements, expressions, procedures into low-level instruction sequences Assembly Basics: Registers, operands, move  The x86 move instructions cover wide range of data movement forms

37 Carnegie Mellon 37 Complete addressing mode and address computation (leal)

38 Carnegie Mellon 38 Data Representations: IA32 + x86-64 Sizes of C Objects (in Bytes)  C Data TypeGeneric 32-bitIntel IA32x86-64  unsigned444  int444  long int448  char111  short222  float444  double888  long double810/1216  char *448 –Or any other pointer

39 Carnegie Mellon 39 Complete Memory Addressing Modes Most General Form D(Rb,Ri,S)Mem[Reg[Rb]+S*Reg[Ri]+ D]  D: Constant “displacement” 1, 2, or 4 bytes  Rb: Base register: Any of 8 integer registers  Ri:Index register: Any, except for %esp  Unlikely you’d use %ebp, either  S: Scale: 1, 2, 4, or 8 (why these numbers?) Special Cases (Rb,Ri)Mem[Reg[Rb]+Reg[Ri]] D(Rb,Ri)Mem[Reg[Rb]+Reg[Ri]+D] (Rb,Ri,S)Mem[Reg[Rb]+S*Reg[Ri]]

40 Carnegie Mellon 40 Address Computation Examples ExpressionAddress ComputationAddress 0x8(%edx)0xf000 + 0x80xf008 (%edx,%ecx)0xf000 + 0x1000xf100 (%edx,%ecx,4)0xf000 + 4*0x1000xf400 0x80(,%edx,2)2*0xf000 + 0x800x1e080 %edx0x7000 %ecx0x0200 ExpressionAddress ComputationAddress 0x8(%edx) (%edx,%ecx) (%edx,%ecx,4) 0x80(,%edx,2)

41 Carnegie Mellon 41 Address Computation Instruction leal Src,Dest  Src is address mode expression  Set Dest to address denoted by expression Uses  Computing addresses without a memory reference  E.g., translation of p = &x[i];  Computing arithmetic expressions of the form x + k*y  k = 1, 2, 4, or 8 Example int mul12(int x) { return x*12; } int mul12(int x) { return x*12; } leal (%eax,%eax,2), %eax ;t <- x+x*2 sall $2, %eax ;return t<<2 leal (%eax,%eax,2), %eax ;t <- x+x*2 sall $2, %eax ;return t<<2 Converted to ASM by compiler:

42 Carnegie Mellon 42 Arithmetic operations

43 Carnegie Mellon 43 Some Arithmetic Operations Two Operand Instructions: FormatComputation addl Src,DestDest = Dest + Src subl Src,DestDest = Dest  Src imull Src,DestDest = Dest * Src sall Src,DestDest = Dest << SrcAlso called shll sarl Src,DestDest = Dest >> SrcArithmetic shrl Src,DestDest = Dest >> SrcLogical xorl Src,DestDest = Dest ^ Src andl Src,DestDest = Dest & Src orl Src,DestDest = Dest | Src Watch out for argument order! No distinction between signed and unsigned int (why?)

44 Carnegie Mellon 44 Some Arithmetic Operations One Operand Instructions incl DestDest = Dest + 1 decl DestDest = Dest  1 negl DestDest =  Dest notl DestDest = ~Dest See the chapter from CSAPP for more instructions

45 Carnegie Mellon 45 Arithmetic Expression Example int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } arith: pushl%ebp movl%esp, %ebp movl8(%ebp), %ecx movl12(%ebp), %edx leal(%edx,%edx,2), %eax sall$4, %eax leal4(%ecx,%eax), %eax addl%ecx, %edx addl16(%ebp), %edx imull%edx, %eax popl%ebp ret Body Set Up Finish

46 Carnegie Mellon 46 16z 12y 8x 4Rtn Addr 0Old %ebp Understanding arith movl8(%ebp), %ecx movl12(%ebp), %edx leal(%edx,%edx,2), %eax sall$4, %eax leal4(%ecx,%eax), %eax addl%ecx, %edx addl16(%ebp), %edx imull%edx, %eax %ebp Offset int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; }

47 Carnegie Mellon 47 16z 12y 8x 4Rtn Addr 0Old %ebp Understanding arith %ebp Offset Stack int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } movl8(%ebp), %ecx# ecx = x movl12(%ebp), %edx# edx = y leal(%edx,%edx,2), %eax# eax = y*3 sall$4, %eax# eax *= 16 (t4) leal4(%ecx,%eax), %eax# eax = t4 +x+4 (t5) addl%ecx, %edx# edx = x+y (t1) addl16(%ebp), %edx# edx += z (t2) imull%edx, %eax# eax = t2 * t5 (rval)

48 Carnegie Mellon 48 Observations about arith  Instructions in different order from C code  Some expressions require multiple instructions  Some instructions cover multiple expressions  Get exact same code when compile:  (x+y+z)*(x+4+48*y) movl8(%ebp), %ecx# ecx = x movl12(%ebp), %edx# edx = y leal(%edx,%edx,2), %eax# eax = y*3 sall$4, %eax# eax *= 16 (t4) leal4(%ecx,%eax), %eax# eax = t4 +x+4 (t5) addl%ecx, %edx# edx = x+y (t1) addl16(%ebp), %edx# edx += z (t2) imull%edx, %eax# eax = t2 * t5 (rval) int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; } int arith(int x, int y, int z) { int t1 = x+y; int t2 = z+t1; int t3 = x+4; int t4 = y * 48; int t5 = t3 + t4; int rval = t2 * t5; return rval; }

49 Carnegie Mellon 49 Another Example int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } logical: pushl %ebp movl %esp,%ebp movl 12(%ebp),%eax xorl 8(%ebp),%eax sarl $17,%eax andl $8185,%eax popl %ebp ret Body Set Up Finish movl 12(%ebp),%eax# eax = y xorl 8(%ebp),%eax# eax = x^y (t1) sarl $17,%eax# eax = t1>>17 (t2) andl $8185,%eax# eax = t2 & mask (rval)

50 Carnegie Mellon 50 Another Example int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } logical: pushl %ebp movl %esp,%ebp movl 12(%ebp),%eax xorl 8(%ebp),%eax sarl $17,%eax andl $8185,%eax popl %ebp ret Body Set Up Finish movl 12(%ebp),%eax# eax = y xorl 8(%ebp),%eax# eax = x^y (t1) sarl $17,%eax# eax = t1>>17 (t2) andl $8185,%eax# eax = t2 & mask (rval)

51 Carnegie Mellon 51 Another Example int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } logical: pushl %ebp movl %esp,%ebp movl 12(%ebp),%eax xorl 8(%ebp),%eax sarl $17,%eax andl $8185,%eax popl %ebp ret Body Set Up Finish movl 12(%ebp),%eax# eax = y xorl 8(%ebp),%eax# eax = x^y (t1) sarl $17,%eax# eax = t1>>17 (t2) andl $8185,%eax# eax = t2 & mask (rval)

52 Carnegie Mellon 52 Another Example int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } int logical(int x, int y) { int t1 = x^y; int t2 = t1 >> 17; int mask = (1<<13) - 7; int rval = t2 & mask; return rval; } logical: pushl %ebp movl %esp,%ebp movl 12(%ebp),%eax xorl 8(%ebp),%eax sarl $17,%eax andl $8185,%eax popl %ebp ret Body Set Up Finish movl 12(%ebp),%eax# eax = y xorl 8(%ebp),%eax# eax = x^y (t1) sarl $17,%eax# eax = t1>>17 (t2) andl $8185,%eax# eax = t2 & mask (rval) 2 13 = 8192, 2 13 – 7 = 8185

53 53 Control: Conditon codes

54 54 Processor State (IA32, Partial) Information about currently executing program  Temporary data ( %eax, … )  Location of runtime stack ( %ebp, %esp )  Location of current code control point ( %eip, … )  Status of recent tests ( CF, ZF, SF, OF ) %eip General purpose registers Current stack top Current stack frame Instruction pointer CFZFSFOF Condition codes %eax %ecx %edx %ebx %esi %edi %esp %ebp

55 55 Condition Codes (Implicit Setting) Single bit registers  CF Carry Flag (for unsigned)SF Sign Flag (for signed)  ZF Zero FlagOF Overflow Flag (for signed) Implicitly set (think of it as side effect) by arithmetic operations Example: addl/addq Src,Dest ↔ t = a+b CF set if carry out from most significant bit (unsigned overflow) ZF set if t == 0 SF set if t < 0 (as signed) OF set if two’s-complement (signed) overflow (a>0 && b>0 && t =0) Not set by lea instruction

56 56 Condition Codes (Explicit Setting: Compare) Explicit Setting by Compare Instruction  cmpl Src2, Src1  cmpl b,a like computing a-b without setting destination  CF set if carry out from most significant bit (used for unsigned comparisons)  ZF set if a == b  SF set if (a-b) < 0 (as signed)  OF set if two’s-complement (signed) overflow (a>0 && b 0 && (a-b)>0)

57 57 Condition Codes (Explicit Setting: Test) Explicit Setting by Test instruction  testl Src2, Src1 testl b,a like computing a&b without setting destination  Sets condition codes based on value of Src1 & Src2  Useful to have one of the operands be a mask  ZF set when a&b == 0  SF set when a&b < 0

58 58 Reading Condition Codes SetX Instructions  Set single byte based on combinations of condition codes SetXConditionDescription seteZF Equal / Zero setne~ZF Not Equal / Not Zero setsSF Negative setns~SF Nonnegative setg~(SF^OF)&~ZF Greater (Signed) setge~(SF^OF) Greater or Equal (Signed) setl(SF^OF) Less (Signed) setle(SF^OF)|ZF Less or Equal (Signed) seta~CF&~ZF Above (unsigned) setbCF Below (unsigned)

59 59 movl 12(%ebp),%eax# eax = y cmpl %eax,8(%ebp)# Compare x : y setg %al# al = x > y movzbl %al,%eax# Zero rest of %eax Reading Condition Codes (Cont.) SetX Instructions:  Set single byte based on combination of condition codes One of 8 addressable byte registers  Does not alter remaining 3 bytes  Typically use movzbl to finish job int gt (int x, int y) { return x > y; } int gt (int x, int y) { return x > y; } Body %eax%ah%al %ecx%ch%cl %edx%dh%dl %ebx%bh%bl %esi %edi %esp %ebp

60 60 Conditional branches and moves

61 61 Carnegie Mellon Jumping jX Instructions  Jump to different part of code depending on condition codes jXConditionDescription jmp1 Unconditional jeZF Equal / Zero jne~ZF Not Equal / Not Zero jsSF Negative jns~SF Nonnegative jg~(SF^OF)&~ZF Greater (Signed) jge~(SF^OF) Greater or Equal (Signed) jl(SF^OF) Less (Signed) jle(SF^OF)|ZF Less or Equal (Signed) ja~CF&~ZF Above (unsigned) jbCF Below (unsigned)

62 62 Carnegie Mellon Conditional Branch Example int absdiff(int x, int y) { int result; if (x > y) { result = x-y; } else { result = y-x; } return result; } int absdiff(int x, int y) { int result; if (x > y) { result = x-y; } else { result = y-x; } return result; } absdiff: pushl %ebp movl %esp, %ebp movl 8(%ebp), %edx movl 12(%ebp), %eax cmpl %eax, %edx jle.L6 subl %eax, %edx movl %edx, %eax jmp.L7.L6: subl %edx, %eax.L7: popl %ebp ret Body1 Setup Finish Body2b Body2a

63 63 Carnegie Mellon Conditional Branch Example (Cont.) int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } C allows “goto” as means of transferring control  Closer to machine-level programming style Generally considered bad coding style absdiff: pushl %ebp movl %esp, %ebp movl 8(%ebp), %edx movl 12(%ebp), %eax cmpl %eax, %edx jle.L6 subl %eax, %edx movl %edx, %eax jmp.L7.L6: subl %edx, %eax.L7: popl %ebp ret Body1 Setup Finish Body2b Body2a

64 64 Carnegie Mellon Conditional Branch Example (Cont.) int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } absdiff: pushl %ebp movl %esp, %ebp movl 8(%ebp), %edx movl 12(%ebp), %eax cmpl %eax, %edx jle.L6 subl %eax, %edx movl %edx, %eax jmp.L7.L6: subl %edx, %eax.L7: popl %ebp ret Body1 Setup Finish Body2b Body2a

65 65 Carnegie Mellon Conditional Branch Example (Cont.) int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } absdiff: pushl %ebp movl %esp, %ebp movl 8(%ebp), %edx movl 12(%ebp), %eax cmpl %eax, %edx jle.L6 subl %eax, %edx movl %edx, %eax jmp.L7.L6: subl %edx, %eax.L7: popl %ebp ret Body1 Setup Finish Body2b Body2a

66 66 Carnegie Mellon Conditional Branch Example (Cont.) int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } int goto_ad(int x, int y) { int result; if (x <= y) goto Else; result = x-y; goto Exit; Else: result = y-x; Exit: return result; } absdiff: pushl %ebp movl %esp, %ebp movl 8(%ebp), %edx movl 12(%ebp), %eax cmpl %eax, %edx jle.L6 subl %eax, %edx movl %edx, %eax jmp.L7.L6: subl %edx, %eax.L7: popl %ebp ret Body1 Setup Finish Body2b Body2a

67 67 Carnegie Mellon Loops

68 68 Carnegie Mellon C Code int pcount_do(unsigned x) { int result = 0; do { result += x & 0x1; x >>= 1; } while (x); return result; } int pcount_do(unsigned x) { int result = 0; do { result += x & 0x1; x >>= 1; } while (x); return result; } Goto Version int pcount_do(unsigned x) { int result = 0; loop: result += x & 0x1; x >>= 1; if (x) goto loop; return result; } int pcount_do(unsigned x) { int result = 0; loop: result += x & 0x1; x >>= 1; if (x) goto loop; return result; } “Do-While” Loop Example Count number of 1’s in argument x (“popcount”) Use conditional branch to either continue looping or to exit loop

69 69 Carnegie Mellon Goto Version “Do-While” Loop Compilation Registers: %edxx %ecxresult movl$0, %ecx# result = 0.L2:# loop: movl%edx, %eax andl$1, %eax# t = x & 1 addl%eax, %ecx# result += t shrl%edx# x >>= 1 jne.L2# If !0, goto loop int pcount_do(unsigned x) { int result = 0; loop: result += x & 0x1; x >>= 1; if (x) goto loop; return result; } int pcount_do(unsigned x) { int result = 0; loop: result += x & 0x1; x >>= 1; if (x) goto loop; return result; }

70 70 Carnegie Mellon C Code do Body while ( Test ); do Body while ( Test ); Goto Version loop: Body if ( Test ) goto loop loop: Body if ( Test ) goto loop General “Do-While” Translation Body: Test returns integer  = 0 interpreted as false  ≠ 0 interpreted as true { Statement 1 ; Statement 2 ; … Statement n ; }

71 71 Carnegie Mellon C CodeGoto Version “While” Loop Example Is this code equivalent to the do-while version?  Must jump out of loop if test fails int pcount_while(unsigned x) { int result = 0; while (x) { result += x & 0x1; x >>= 1; } return result; } int pcount_while(unsigned x) { int result = 0; while (x) { result += x & 0x1; x >>= 1; } return result; } int pcount_do(unsigned x) { int result = 0; if (!x) goto done; loop: result += x & 0x1; x >>= 1; if (x) goto loop; done: return result; } int pcount_do(unsigned x) { int result = 0; if (!x) goto done; loop: result += x & 0x1; x >>= 1; if (x) goto loop; done: return result; }

72 72 Carnegie Mellon While version while ( Test ) Body while ( Test ) Body Do-While Version if (! Test ) goto done; do Body while( Test ); done: if (! Test ) goto done; do Body while( Test ); done: General “While” Translation Goto Version if (! Test ) goto done; loop: Body if ( Test ) goto loop; done: if (! Test ) goto done; loop: Body if ( Test ) goto loop; done:

73 73 Carnegie Mellon C Code “For” Loop Example Is this code equivalent to other versions? #define WSIZE 8*sizeof(int) int pcount_for(unsigned x) { int i; int result = 0; for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } return result; } #define WSIZE 8*sizeof(int) int pcount_for(unsigned x) { int i; int result = 0; for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } return result; }

74 74 Carnegie Mellon “For” Loop Form for ( Init ; Test ; Update ) Body General Form for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } i = 0 i < WSIZE i++ { unsigned mask = 1 << i; result += (x & mask) != 0; } { unsigned mask = 1 << i; result += (x & mask) != 0; } Init Test Update Body

75 75 Carnegie Mellon “For” Loop  While Loop for ( Init ; Test ; Update ) Body For Version Init ; while ( Test ) { Body Update ; } While Version

76 76 Carnegie Mellon “For” Loop  …  Goto for ( Init ; Test ; Update ) Body For Version Init ; while ( Test ) { Body Update ; } While Version Init ; if (! Test ) goto done; do Body Update while( Test ); done: Init ; if (! Test ) goto done; do Body Update while( Test ); done: Init ; if (! Test ) goto done; loop: Body Update if ( Test ) goto loop; done: Init ; if (! Test ) goto done; loop: Body Update if ( Test ) goto loop; done:

77 77 Carnegie Mellon C Code “For” Loop Conversion Example Initial test can be optimized away #define WSIZE 8*sizeof(int) int pcount_for(unsigned x) { int i; int result = 0; for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } return result; } #define WSIZE 8*sizeof(int) int pcount_for(unsigned x) { int i; int result = 0; for (i = 0; i < WSIZE; i++) { unsigned mask = 1 << i; result += (x & mask) != 0; } return result; } Goto Version int pcount_for_gt(unsigned x) { int i; int result = 0; i = 0; if (!(i < WSIZE)) goto done; loop: { unsigned mask = 1 << i; result += (x & mask) != 0; } i++; if (i < WSIZE) goto loop; done: return result; } int pcount_for_gt(unsigned x) { int i; int result = 0; i = 0; if (!(i < WSIZE)) goto done; loop: { unsigned mask = 1 << i; result += (x & mask) != 0; } i++; if (i < WSIZE) goto loop; done: return result; } Init ! Test Body Update Test

78 78 Carnegie Mellon Summary So far  Complete addressing mode, address computation ( leal )  Arithmetic operations  Control: Condition codes  Conditional branches & conditional moves  Loops Coming up!  Switch statements  Stack  Call / return  Procedure call discipline

79 79 Carnegie Mellon Today Switch statements IA 32 Procedures  Stack Structure  Calling Conventions  Illustrations of Recursion & Pointers

80 80 Carnegie Mellon IA32 Stack Region of memory managed with stack discipline Grows toward lower addresses Register %esp contains lowest stack address  address of “top” element Stack Pointer: %esp Stack Grows Down Increasing Addresses Stack “Top” Stack “Bottom”

81 81 Carnegie Mellon IA32 Stack: Push pushl Src  Fetch operand at Src  Decrement %esp by 4  Write operand at address given by %esp -4 Stack Grows Down Increasing Addresses Stack “Bottom” Stack Pointer: %esp Stack “Top”

82 82 Stack Pointer: %esp Stack Grows Down Increasing Addresses Stack “Top” Stack “Bottom” Carnegie Mellon IA32 Stack: Pop +4

83 83 Carnegie Mellon Procedure Control Flow Use stack to support procedure call and return Procedure call: call label  Push return address on stack  Jump to label Return address:  Address of the next instruction right after call  Example from disassembly 804854e:e8 3d 06 00 00 call 8048b90 8048553:50 pushl %eax  Return address = 0x8048553 Procedure return: ret  Pop address from stack  Jump to address

84 84 0x8048553 0x104 Carnegie Mellon %esp %eip %esp %eip 0x8048b90 0x108 0x10c 0x110 0x104 0x804854e 123 Procedure Call Example 0x108 0x10c 0x110 123 0x108 call 8048b90 804854e:e8 3d 06 00 00 call 8048b90 8048553:50 pushl %eax 804854e:e8 3d 06 00 00 call 8048b90 8048553:50 pushl %eax %eip: program counter

85 85 Carnegie Mellon %esp %eip 0x104 %esp %eip 0x8048591 0x104 0x108 0x10c 0x110 0x8048553 123 Procedure Return Example 0x108 0x10c 0x110 123 ret 8048591:c3 ret 0x108 0x8048553 %eip: program counter

86 86 Carnegie Mellon Stack-Based Languages Languages that support recursion  e.g., C, Pascal, Java  Code must be “Reentrant”  Multiple simultaneous instantiations of single procedure  Need some place to store state of each instantiation  Arguments  Local variables  Return pointer Stack discipline  State for given procedure needed for limited time  From when called to when return  Callee returns before caller does Stack allocated in Frames  state for single procedure instantiation

87 87 Carnegie Mellon Call Chain Example yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); } yoo who amI Example Call Chain amI Procedure amI() is recursive

88 88 Carnegie Mellon Frame Pointer: %ebp Stack Frames Contents  Local variables  Return information  Temporary space Management  Space allocated when enter procedure  “Set-up” code  Deallocated when return  “Finish” code Stack Pointer: %esp Stack “Top” Previous Frame Frame for proc

89 89 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo yoo(…) { who(); } yoo(…) { who(); }

90 90 yoo(…) { who(); } yoo(…) { who(); } Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who who(…) { amI(); amI(); } who(…) { amI(); amI(); }

91 91 yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI amI(…) { amI(); } amI(…) { amI(); }

92 92 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); }

93 93 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); }

94 94 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); } amI(…) { amI(); }

95 95 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); }

96 96 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); }

97 97 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who amI yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); } amI(…) { amI(); } amI(…) { amI(); }

98 98 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo who yoo(…) { who(); } yoo(…) { who(); } who(…) { amI(); amI(); } who(…) { amI(); amI(); }

99 99 Carnegie Mellon Example yoo who amI yoo %ebp %esp Stack yoo yoo(…) { who(); } yoo(…) { who(); }

100 100 Carnegie Mellon IA32/Linux Stack Frame Current Stack Frame (“Top” to Bottom)  “Argument build:” Parameters for function about to call  Local variables If can’t keep in registers  Saved register context  Old frame pointer Caller Stack Frame  Return address  Pushed by call instruction  Arguments for this call Return Addr Saved Registers + Local Variables Argument Build Old %ebp Arguments Caller Frame Frame pointer %ebp Stack pointer %esp

101 101 Carnegie Mellon Revisiting swap void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } int course1 = 15213; int course2 = 18243; void call_swap() { swap(&course1, &course2); } int course1 = 15213; int course2 = 18243; void call_swap() { swap(&course1, &course2); } call_swap: subl$8, %esp movl$course2, 4(%esp) movl$course1, (%esp) callswap call_swap: subl$8, %esp movl$course2, 4(%esp) movl$course1, (%esp) callswap &course2 &course1 Rtn adr %esp Resulting Stack Calling swap from call_swap %esp subl call

102 102 Carnegie Mellon Revisiting swap void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } void swap(int *xp, int *yp) { int t0 = *xp; int t1 = *yp; *xp = t1; *yp = t0; } swap: pushl%ebp movl%esp, %ebp pushl%ebx movl8(%ebp), %edx movl12(%ebp), %ecx movl(%edx), %ebx movl(%ecx), %eax movl%eax, (%edx) movl%ebx, (%ecx) popl%ebx popl%ebp ret Body Set Up Finish

103 103 Carnegie Mellon swap Setup #1 swap: pushl %ebp movl %esp,%ebp pushl %ebx Resulting Stack &course2 &course1 Rtn adr %esp Entering Stack %ebp yp xp Rtn adr Old %ebp %ebp %esp

104 104 Carnegie Mellon swap Setup #2 swap: pushl %ebp movl %esp,%ebp pushl %ebx Resulting Stack &course2 &course1 Rtn adr %esp Entering Stack %ebp yp xp Rtn adr Old %ebp %ebp %esp

105 105 Carnegie Mellon swap Setup #3 swap: pushl %ebp movl %esp,%ebp pushl %ebx Resulting Stack &course2 &course1 Rtn adr %esp Entering Stack %ebp yp xp Rtn adr Old %ebp %ebp %esp Old %ebx

106 106 Carnegie Mellon swap Body movl 8(%ebp),%edx # get xp movl 12(%ebp),%ecx # get yp... Resulting Stack &course2 &course1 Rtn adr %esp Entering Stack %ebp yp xp Rtn adr Old %ebp %ebp %esp Old %ebx Offset relative to %ebp 12 8 4

107 107 Carnegie Mellon swap Finish Stack Before Finish popl%ebx popl%ebp yp xp Rtn adr Old %ebp %ebp %esp Old %ebx Resulting Stack yp xp Rtn adr %ebp %esp Observation  Saved and restored register %ebx  Not so for %eax, %ecx, %edx

108 108 Carnegie Mellon Disassembled swap 08048384 : 8048384:55 push %ebp 8048385:89 e5 mov %esp,%ebp 8048387:53 push %ebx 8048388:8b 55 08 mov 0x8(%ebp),%edx 804838b:8b 4d 0c mov 0xc(%ebp),%ecx 804838e:8b 1a mov (%edx),%ebx 8048390:8b 01 mov (%ecx),%eax 8048392:89 02 mov %eax,(%edx) 8048394:89 19 mov %ebx,(%ecx) 8048396:5b pop %ebx 8048397:5d pop %ebp 8048398:c3 ret 80483b4:movl $0x8049658,0x4(%esp)# Copy &course2 80483bc:movl $0x8049654,(%esp)# Copy &course1 80483c3:call 8048384 # Call swap 80483c8:leave # Prepare to return 80483c9:ret # Return Calling Code

109 109 Carnegie Mellon IA32/Linux+Windows Register Usage %eax, %edx, %ecx  Caller saves prior to call if values are used later %eax  also used to return integer value %ebx, %esi, %edi  Callee saves if wants to use them %esp, %ebp  special form of callee save  Restored to original values upon exit from procedure %eax %edx %ecx %ebx %esi %edi %esp %ebp Caller-Save Temporaries Callee-Save Temporaries Special

110 110 Carnegie Mellon So far IA 32 Procedures  Stack Structure  Calling Conventions  Illustrations of Recursion & Pointers

111 111 Carnegie Mellon %esp Creating and Initializing Local Variable int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } Variable localx must be stored on stack  Because: Need to create pointer to it Compute pointer as -4(%ebp) First part of add3 x Rtn adr Old %ebp %ebp 0 4 8 -4 localx = x Unused -12 -8 -16 add3: pushl%ebp movl%esp, %ebp subl$24, %esp# Alloc. 24 bytes movl8(%ebp), %eax movl%eax, -4(%ebp)# Set localx to x add3: pushl%ebp movl%esp, %ebp subl$24, %esp# Alloc. 24 bytes movl8(%ebp), %eax movl%eax, -4(%ebp)# Set localx to x -20 -24

112 112 Carnegie Mellon %esp Creating Pointer as Argument int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } Use leal instruction to compute address of localx Middle part of add3 x Rtn adr Old %ebp %ebp 0 4 8 -4 localx Unused -12 -8 -16 movl$3, 4(%esp)# 2 nd arg = 3 leal-4(%ebp), %eax# &localx movl%eax, (%esp) # 1 st arg = &localx callincrk movl$3, 4(%esp)# 2 nd arg = 3 leal-4(%ebp), %eax# &localx movl%eax, (%esp) # 1 st arg = &localx callincrk -20 -24 3 %esp+4

113 113 Carnegie Mellon %esp Retrieving local variable int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } int add3(int x) { int localx = x; incrk(&localx, 3); return localx; } Retrieve localx from stack as return value Final part of add3 x Rtn adr Old %ebp %ebp 0 4 8 -4 localx Unused -12 -8 -16 movl-4(%ebp), %eax # Return val= localx leave ret movl-4(%ebp), %eax # Return val= localx leave ret -20 -24

114 114 Carnegie Mellon IA32/Linux+Windows Register Usage %eax, %edx, %ecx  Caller saves prior to call if values are used later %eax  also used to return integer value %ebx, %esi, %edi  Callee saves if wants to use them %esp, %ebp  special form of callee save  Restored to original values upon exit from procedure %eax %edx %ecx %ebx %esi %edi %esp %ebp Caller-Save Temporaries Callee-Save Temporaries Special

115 115 Carnegie Mellon Today Switch statements IA 32 Procedures  Stack Structure  Calling Conventions  Illustrations of Recursion & Pointers

116 Carnegie Mellon 116 Basic Data Types Integral  Stored & operated on in general (integer) registers  Signed vs. unsigned depends on instructions used IntelASMBytesC byte b 1[ unsigned ] char word w 2[ unsigned ] short double word l 4[ unsigned ] int quad word q 8[ unsigned ] long int (x86-64) Floating Point  Stored & operated on in floating point registers IntelASMBytesC Single s 4 float Double l 8 double Extended t 10/12/16 long double

117 Carnegie Mellon 117 Array Allocation Basic Principle T A[ L ];  Array of data type T and length L  Contiguously allocated region of L * sizeof( T ) bytes char string[12]; xx + 12 int val[5]; x x + 4x + 8x + 12x + 16x + 20 double a[3]; x + 24 x x + 8x + 16 char *p[3]; x x + 8x + 16 x + 24 x x + 4x + 8x + 12 IA32 x86-64

118 Carnegie Mellon 118 Array Access Basic Principle T A[ L ];  Array of data type T and length L  Identifier A can be used as a pointer to array element 0: Type T* ReferenceTypeValue val[4]int 3 valint * x val+1int * x + 4 &val[2]int * x + 8 val[5]int ?? *(val+1)int 5 val + i int * x + 4 i int val[5]; 15213 x x + 4x + 8x + 12x + 16x + 20

119 Carnegie Mellon 119 Array Example Declaration “ zip_dig cmu ” equivalent to “ int cmu[5] ” Example arrays were allocated in successive 20 byte blocks  Not guaranteed to happen in general #define ZLEN 5 typedef int zip_dig[ZLEN]; zip_dig cmu = { 1, 5, 2, 1, 3 }; zip_dig mit = { 0, 2, 1, 3, 9 }; zip_dig ucb = { 9, 4, 7, 2, 0 }; zip_dig cmu; 15213 16 2024283236 zip_dig mit; 02139 36 4044485256 zip_dig ucb; 94720 56 6064687276

120 Carnegie Mellon 120 Array Accessing Example Register %edx contains starting address of array Register %eax contains array index Desired digit at 4*%eax + %edx Use memory reference (%edx,%eax,4) int get_digit (zip_dig z, int dig) { return z[dig]; } # %edx = z # %eax = dig movl (%edx,%eax,4),%eax # z[dig] IA32 zip_dig cmu; 15213 16 2024283236

121 Carnegie Mellon 121 # edx = z movl$0, %eax# %eax = i.L4:# loop: addl$1, (%edx,%eax,4)# z[i]++ addl$1, %eax# i++ cmpl$5, %eax# i:5 jne.L4# if !=, goto loop Array Loop Example (IA32) void zincr(zip_dig z) { int i; for (i = 0; i < ZLEN; i++) z[i]++; }

122 Carnegie Mellon 122 Pointer Loop Example (IA32) void zincr_p(zip_dig z) { int *zend = z+ZLEN; do { (*z)++; z++; } while (z != zend); } void zincr_v(zip_dig z) { void *vz = z; int i = 0; do { (*((int *) (vz+i)))++; i += ISIZE; } while (i != ISIZE*ZLEN); } # edx = z = vz movl$0, %eax# i = 0.L8:# loop: addl$1, (%edx,%eax)# Increment vz+i addl$4, %eax# i += 4 cmpl$20, %eax# Compare i:20 jne.L8# if !=, goto loop


Download ppt "Carnegie Mellon 1 Introduction to x86 Assembly or “What does my laptop actually do?” Ymir Vigfusson Some slides gracefully borrowed from"

Similar presentations


Ads by Google