compilaon - taumaon/teaching/2014-2015/...compilaon * **0368/3133**2014/15a lecture*8*...

152
Compila(on 03683133 2014/15a Lecture 8 IR for Procedure calls + Op(miza(ons Noam Rinetzky 1

Upload: others

Post on 01-Oct-2020

5 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Compila(on      0368-­‐3133    2014/15a  

Lecture  8  

IR  for  Procedure  calls  +  Op(miza(ons  Noam  Rinetzky  

1

Page 2: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Front-­‐End  

Back-­‐End  

✓ ✓ ✓

Where  we  are  

2

Executable

code

exe

Source

text

txt Lexical Analysis

Sem. Analysis

Process text input

characters Syntax Analysis tokens AST

Intermediate code

generation

Annotated  AST  +  Symbol  Table  

Intermediate code

optimization

IR Code generation IR

Target code optimization

Symbolic  Instruc(ons  

SI Machine code generation

Write executable

output

MI

Lexical Analysis

Syntax Analysis

Page 3: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

3

Intermediate  Representa(on  

Page 4: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

1  Note:  Compile  Time  vs  Run(me  

•  Compile  4me:  Data  structures  used  during  program  compila(on  –  AST,  Symbol  table  

•  Run4me:  Data  structures  used  during  program  execu(on  –  Ac(va(on  record  stack,  memory  management    

•  The  compiler  generates  code  that  allows  the  program  to  interact  with  the  run(me    

4

Page 5: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Code  Genera(on:  IR

•  Transla(ng  from  abstract  syntax  (AST)  to  intermediate  representa(on  (IR)  –  Three-­‐Address  Code  

• …  

5

Source  code  

(program)  

 

Lexical  Analysis  

Syntax  Analysis  

Parsing  

AST   Symbol  Table  etc.  

Inter.  Rep.  (IR)  

Code  Genera(on  

Source  code  

(executable)  

 

Page 6: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Intermediate  representa(on  

6  

•  A  language  that  is  between  the  source  language  and  the  target  language  –  not  specific  to  any  machine  

•  Goal  1:  retarge(ng    compiler  components  for  different  source  languages/target  machines  

•  Goal  2:  machine-­‐independent  op(mizer  •  Narrow  interface:  small  number  of  instruc(on  types  

C++   IR  

Pen(um  

Java  bytecode  

Sparc  Pyhton  

Java  

Page 7: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Three-­‐Address  Code  IR

•  A  popular  form  of  IR  •  High-­‐level  assembly  where  instruc(ons  have  at  most  three  operands

7

Chapter 8

Page 8: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Reminder:  cgen  for  expressions

8

cgen(e1  +  e2)  =  {          Choose  a  new  temporary  t          Let  t1  =  cgen(e1)          Let  t2  =  cgen(e2)          Emit(  t  =  t1  +  t2  )          Return  t  }

Algorithm  by  Ravi  Sethi  and  Jeffrey  D.  Ullman    to  minimizes  number  of  temporaries  

Page 9: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Reminder:  cgen  for  control

9

cgen(if  (e) s1  else  s2)  Let  _t  =  cgen(e)  Let  Ltrue  be  a  new  label  Let  Lfalse  be  a  new  label  Let  Laeer  be  a  new  label  Emit(  IfZ  _t  Goto  Lfalse;  )  cgen(s1)  Emit(  Goto  Laeer;  )  Emit(  Lfalse:  )  cgen(s2)  Emit(  Goto  Laeer;)  Emit(  Laeer:  )  

Page 10: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Code  genera(on    for  procedure  calls  

10

Page 11: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Code  genera(on  for  procedure  calls  

•  Compile  (me  genera(on  of  code  for  procedure  invoca(ons  

•  Ac(va(on  Records  (aka  Stack  Frames)  

11

Page 12: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Suppor(ng  Procedures  

•  Stack:  a  new  compu(ng  environment    –  e.g.,  temporary  memory  for  local  variables  

•  Passing  informa(on  into  the  new  environment  –  Parameters  

•  Transfer  of  control  to/from  procedure  •  Handling  return  values  

12

Page 13: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Calling  Conven(ons  

•  In  general,  compiler  can  use  any  conven(on  to  handle  procedures  

•  In  prac(ce,  CPUs  specify  standards  • Aka  calling  conven(os  

– Allows  for  compiler  interoperability  • Libraries!    

13

Page 14: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Abstract  Register  Machine  (High  Level  View)  

14

Code  

Data  

High  addresses  

Low  addresses  

CPU  

Register  00  

Register  01  

Register  xx  

…  

Register  PC  

Control  

registers  

 (data)  re

gisters  

Gene

ral  purpo

se  

…  

Page 15: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Heap  

Abstract  Register  Machine  (High  Level  View)  

15

Global  Variables  

Stack  

Low  addresses  

CPU   Main  Memory  

Register  00  

Register  01  

Register  xx  

…  

Register  PC  

Control  

registers  

 (data)  re

gisters  

Gene

ral  purpo

se  

…  

Code  

High  addresses  

Register  Stack  

Page 16: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Abstract  Ac(va(on  Record  Stack

16

Stack  frame  for  procedure  

Prock+1(a1,…,aN)

Prock

Prock+2

         

Prock+1

main  

Proc1  

Proc2  

Prock  

Prock+1  

Prock+2  

Stack    grows  this  

way  

Page 17: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Abstract  Stack  Frame

17

Param  NParam  N-­‐1

…Param  1_t0

…_tkx

…y

Parameters  (actual  

arguments)

Locals  and  temporaries

Prock

Prock+2

Stack  frame  for  procedure  

Prock+1(a1,…,aN)

Page 18: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Handling  Procedures  •  Store  local  variables/temporaries  in  a  stack  •  A  func(on  call  instruc(on  pushes  arguments  to  stack  and  jumps  to  the  func(on  label  A  statement  x=f(a1,…,an); looks  like  

 Push a1; … Push an; Call f; Pop x;  //  copy  returned  value  

•  Returning  a  value  is  done  by  pushing  it  to  the  stack  (return x;)  

 Push x; •  Return  control  to  caller  (and  roll  up  stack)                Return; 18

Page 19: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Heap  

Abstract  Register  Machine  

19

Global  Variables  

Stack  

Low  addresses  

CPU   Main  Memory  

Register  00  

Register  01  

Register  xx  

…  

Register  PC  

Control  

registers  

 (data)  re

gisters  

Gene

ral  purpo

se  

…  

Code  

High  addresses  

Page 20: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Heap  

Abstract  Register  Machine  

20

Global  Variables  

Stack  

Low  addresses  

CPU   Main  Memory  

 (data)  re

gisters  

Gene

ral  purpo

se  

Code  

High  addresses  

Register  00  

Register  01  

Register  xx  

…  

Register  PC  

Control  

registers  

…  …  Register  Stack  

Page 21: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Intro:  Func(ons  Example  int SimpleFn(int z) {

int x, y; x = x * y * z; return x;

} void main() { int w; w = SimpleFunction(137);

}

21

_SimpleFn: _t0 = x * y; _t1 = _t0 * z; x = _t1; Push x; Return; main: _t0 = 137; Push _t0; Call _SimpleFn; Pop w;

Page 22: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

What  Can  We  Do  with  Procedures?  

•  Declara(ons  &  Defini(ons  •  Call  &  Return  •  Jumping  out  of  procedures  •  Passing  &  Returning  procedures  as  parameters  

22

Page 23: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Design  Decisions  

•  Scoping  rules  –  Sta(c  scoping  vs.  dynamic  scoping  

•  Caller/callee  conven(ons  –  Parameters  – Who  saves  register  values?  

•  Alloca(ng  space  for  local  variables  

23

Page 24: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Sta(c  (lexical)  Scoping  

24

main  (  )  {  

 int  a  =  0  ;    int  b  =  0  ;    {      int  b  =  1  ;      {        int  a  =  2  ;        prinI  (“%d  %d\n”,  a,  b)      }      {        int  b  =  3  ;        prinI  (“%d  %d\n”,  a,  b)  ;      }      prinI  (“%d  %d\n”,  a,  b)  ;    }    prinI  (“%d  %d\n”,  a,  b)  ;  

}  

B0

B1

B3 B3

B2

Declara4on   Scopes  

a=0   B0,B1,B3  

b=0   B0  

b=1   B1,B2  

a=2   B2  

b=3   B3  

a  name  refers  to  its  (closest)  

enclosing  scope    

known  at  compile  4me  

Page 25: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Dynamic  Scoping  

•  Each  iden(fier  is  associated  with  a  global  stack  of  bindings  

•  When  entering  scope  where  iden(fier  is  declared  –  push  declara(on  on  iden(fier  stack  

•  When  exi(ng  scope  where  iden(fier  is  declared  –  pop  iden(fier  stack  

•  Evalua4ng  the  iden4fier  in  any  context  binds  to  the  current  top  of  stack  

•  Determined  at  run4me  

25

Page 26: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Example  

• What  value  is  returned  from  main?  •  Sta(c  scoping?  •  Dynamic  scoping?  

26

int  x  =  42;      int  f()  {  return  x;  }    int  g()  {  int  x  =  1;  return  f();  }  int  main()  {  return  g();  }    

Page 27: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Why  do  we  care?  

•  We  need  to  generate  code  to  access  variables  

•  Sta(c  scoping  –  Iden(fier  binding  is  known  at  compile  (me  –  “Address”  of  the  variable  is  known  at  compile  (me  –  Assigning  addresses  to  variables  is  part  of  code  genera(on  

–  No  run(me  errors  of  “access  to  undefined  variable”  –  Can  check  types  of  variables  

27

Page 28: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Variable  addresses  for  sta(c  scoping:  first  arempt  

28

int  x  =  42;      int  f()  {  return  x;  }    int  g()  {  int  x  =  1;  return  f();  }  int  main()  {  return  g();  }    

iden4fier   address  

x  (global)   0x42  

x  (inside  g)   0x73  

Page 29: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Variable  addresses  for  sta(c  scoping:  first  arempt  

29

int  a  [11]  ;    void  quicksort(int  m,  int  n)  {      int  i;      if  (n  >  m)  {          i  =  par((on(m,  n);          quicksort  (m,  i-­‐1)  ;          quicksort  (i+1,  n)  ;      }    main()  {  ...    quicksort  (1,  9)  ;  }    

what  is  the  address  of  the  variable  “i”  in  

the  procedure  quicksort?  

Page 30: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Compile-­‐Time  Informa(on  on  Variables  •  Name  •  Type  •  Scope  

–  when  is  it  recognized  •  Dura(on    

–  Un(l  when  does  its  value  exist  •  Size    

–  How  many  bytes  are  required  at  run(me      

•  Address  –  Fixed  –  Rela(ve  –  Dynamic   30

Page 31: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Ac(va(on  Record  (Stack  Frames)  

•  separate  space  for  each  procedure  invoca(on  

•  managed  at  run4me  –  code  for  managing  it  generated  by  the  compiler  

•  desired  proper(es    –  efficient  alloca(on  and  dealloca(on  

•  procedures  are  called  frequently  –  variable  size    

•  different  procedures  may  require  different  memory  sizes  

31

Page 32: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Semi-­‐Abstract  Register  Machine  

32

Global  Variables  

Stack  

Heap  

High  addresses  

Low  addresses  

CPU   Main  Memory  

Register  00  

Register  01  

Register  xx  

…  

Register  PC  

Control  

registers  

 (data)  re

gisters  

Gene

ral  purpo

se  

…  

ebp  

esp  …  re

gisters  

Stack  

Page 33: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

A  Logical  Stack  Frame  (Simplified)

33

Param  NParam  N-­‐1

…Param  1_t0

…_tkx

…y

Parameters  (actual  

arguments)

Locals  and  temporaries

Stack  frame  for  func(on  f(a1,…,aN)

Page 34: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Run(me  Stack  

•  Stack  of  ac(va(on  records  •  Call  =  push  new  ac(va(on  record  •  Return  =  pop  ac(va(on  record  •  Only  one  “ac(ve”  ac(va(on  record  –  top  of  stack  

•  How  do  we  handle  recursion?  

34

Page 35: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Ac(va(on  Record  (frame)  

35

parameter  k  

parameter  1  

lexical  pointer  

return  informa(on  

dynamic  link  

registers  &  misc  

local  variables  temporaries  

next  frame  would  be  here  

…  

administra(ve  part  

high    addresses  

low  addresses  

frame  (base)  pointer  

stack  pointer  

incoming    parameters  

stack    grows    down  

Page 36: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Run(me  Stack  •  SP  –  stack  pointer    

–  top  of  current  frame  •  FP  –  frame  pointer    

–  base  of  current  frame  –  Some(mes  called  BP  

(base  pointer)  –  Usually  points  to  a  “fixed”  offset  

from  the  “start”  of  the  frame  

36

Current frame

Previous frame

SP

FP

stack    grows    down  

Page 37: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Code  Blocks  

•  Programming    language  provide  code  blocks    void  foo()    {      int  x  =  8  ;  y=9;//1          {  int  x  =  y  *  y  ;//2  }          {  int  x  =  y  *  7  ;//3}                            x  =  y  +  1;    }  

37

adminstra4ve  

x1  

y1  

x2  

x3  

…  

Page 38: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

L-­‐Values  of  Local  Variables  

•  The  offset  in  the  stack  is  known  at  compile  (me  

•  L-­‐val(x)  =  FP+offset(x)  •  x  =  5  ⇒  Load_Constant  5,  R3                              Store  R3,  offset(x)(FP)                                    

38

Page 39: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Pen(um  Run(me  Stack  

39

Pen(um  stack  registers  

Pen(um  stack  and  call/ret  instruc(ons  

Register   Usage  

ESP   Stack  pointer  

EBP     Base  pointer  

Instruc4on   Usage  

push,  pusha,…   push  on  run(me  stack  

pop,popa,…   Base  pointer  

call   transfer  control  to  called  rou(ne  

return   transfer  control  back  to  caller  

Page 40: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Accessing  Stack  Variables  

•  Use  offset  from  FP  (%ebp)  –  Remember:  stack  grows                  downwards  

•  Above  FP  =  parameters  •  Below  FP  =  locals  •  Examples  

– %ebp  +  4  =  return  address  – %ebp  +  8  =  first  parameter  – %ebp  –  4    =  first  local  

40

SP  

FP  

Return  address  

Return  address  

Param  n  …  

param1  

Local  1  …  

Local  n  

Previous  fp  

Param  n  …  

param1  FP+8  

FP-­‐4    

Page 41: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Factorial  –  fact(int n)

41

fact: pushl %ebp # save ebp movl %esp,%ebp # ebp=esp pushl %ebx # save ebx movl 8(%ebp),%ebx # ebx = n cmpl $1,%ebx # n = 1 ? jle .lresult # then done leal -1(%ebx),%eax # eax = n-1 pushl %eax # call fact # fact(n-1) imull %ebx,%eax # eax=retv*n jmp .lreturn # .lresult: movl $1,%eax # retv .lreturn: movl -4(%ebp),%ebx # restore ebx movl %ebp,%esp # restore esp popl %ebp # restore ebp

ESP

EBP

Return address

Return address

old %ebx

Previous fp

n EBP+8

EBP-4 old %ebp

old %ebx

(stack in intermediate point)

(disclaimer: real compiler can do better than that)

Page 42: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Call  Sequences  

•  The  processor  does  not  save  the  content  of  registers  on  procedure  calls  

•  So  who  will?    –  Caller  saves  and  restores  registers  –  Callee  saves  and  restores  registers  –  But  can  also  have  both  save/restore  some  registers  

42

Page 43: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Call  Sequences  

43

call

caller

callee

return

caller

Caller  push  code  

Callee  push  code  

(prologue)  

Callee  pop  code  

(epilogue)  

Caller  pop  code  

Push  caller-­‐save  registers  Push  actual  parameters  (in  reverse  order)  

push  return  address  (+  other  admin  info)  Jump  to  call  address  

Push  current  base-­‐pointer  bp  =  sp  

Push  local  variables  Push  callee-­‐save  registers  

Pop  callee-­‐save  registers  Pop  callee  ac(va(on  record  

Pop  old  base-­‐pointer  pop  return  address  Jump  to  address  

Pop  return  value  +  parameters  Pop  caller-­‐save  registers  

 

…  

…  

Page 44: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

“To  Callee-­‐save  or  to  Caller-­‐save?”  

•  Callee-­‐saved  registers  need  only  be  saved  when  callee  modifies  their  value  

•  some  heuris(cs  and  conven(ons  are  followed  

44

Page 45: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Caller-­‐Save  and  Callee-­‐Save  Registers  •  Callee-­‐Save  Registers  

–  Saved  by  the  callee  before  modifica(on  –  Values  are  automa(cally  preserved  across  calls  

•  Caller-­‐Save  Registers    –  Saved  (if  needed)  by  the  caller  before  calls  –  Values  are  not  automa(cally  preserved  across  calls  

•  Usually  the  architecture  defines  caller-­‐save  and  callee-­‐save  registers  

•  Separate  compila(on  •  Interoperability  between  code  produced  by  different  

compilers/languages    •  But  compiler  writers  decide  when  to  use  caller/callee  

registers   45

Page 46: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Callee-­‐Save  Registers  •  Saved  by  the  callee  before  modifica(on  •  Usually  at  procedure  prolog  •  Restored  at  procedure  epilog  •  Hardware  support  may  be  available    •  Values  are  automa(cally  preserved  across  calls  

46

.global _foo

Add_Constant -K, SP //allocate space for foo

Store_Local R5, -14(FP) // save R5

Load_Reg R5, R0; Add_Constant R5, 1

JSR f1 ; JSR g1;

Add_Constant R5, 2; Load_Reg R5, R0

Load_Local -14(FP), R5 // restore R5

Add_Constant K, SP; RTS // deallocate

int  foo(int  a)  {      int  b=a+1;      f1();    g1(b);  

   return(b+2);    }  

Page 47: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Caller-­‐Save  Registers  •  Saved  by  the  caller  before  calls  when  needed  

•  Values  are  not  automa(cally  preserved  across  calls  

47

.global _bar

Add_Constant -K, SP //allocate space for bar

Add_Constant R0, 1

JSR f2

Load_Constant 2, R0 ; JSR g2;

Load_Constant 8, R0 ; JSR g2

Add_Constant K, SP // deallocate space for bar

RTS

void  bar  (int  y)  {      int  x=y+1;    f2(x);    

                 g2(2);                    g2(8);    }  

Page 48: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Parameter  Passing  •  1960s  

–   In  memory    •  No  recursion  is  allowed  

•  1970s  –   In  stack  

•  1980s  –   In  registers  –   First  k  parameters  are  passed  in  registers  (k=4  or  k=6)  –  Where  is  (me  saved?  

48

•   Most  procedures  are  leaf  procedures  •   Interprocedural  register  alloca(on  •   Many  of  the  registers  may  be  dead  before  another  invoca(on  •   Register  windows  are  allocated  in  some  architectures  per  call  (e.g.,  sun  Sparc)  

 

Page 49: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Ac(va(on  Records  &    Language  Design  

49

Page 50: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Compile-­‐Time  Informa(on  on  Variables  •  Name,  type,  size  •  Address  kind    

–  Fixed  (global)  –  Rela(ve  (local)  –  Dynamic  (heap)  

•  Scope  –  when  is  it  recognized  

•  Dura(on    –  Un(l  when  does  its  value  exist  

50

Page 51: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Scoping  

• What  value  is  returned  from  main?  •  Sta(c  scoping?  •  Dynamic  scoping?  

int  x  =  42;      int  f()  {  return  x;  }    int  g()  {  int  x  =  1;  return  f();  }  int  main()  {  return  g();  }    

51

Page 52: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Nested  Procedures  

•  For  example  –  Pascal  •  Any  rou(ne  can  have  sub-­‐rou(nes  •  Any  sub-­‐rou(ne  can  access  anything  that  is  defined  in  its  containing  scope  or  inside  the  sub-­‐rou(ne  itself  –  “non-­‐local”  variables  

52

Page 53: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Example:  Nested  Procedures    program p(){ int x; procedure a(){ int y; procedure b(){ … c() … }; procedure c(){ int z; procedure d(){

y := x + z }; … b() … d() …

} … a() … c() … } a() }  

53

Possible  call  sequence:  p  d  a  d  a  d  c  d  b  d  c  d  d  

what  are  the  addresses  of  variables  “x,”  “y”  and  

“z”  in  procedure  d?  

Page 54: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Nested  Procedures  •  can  call  a  sibling,  ancestor  •  when  “c”  uses  (non-­‐local)  

variables  from  “a”,  which  instance  of  “a”  is  it?  

•  how  do  you  find  the  right  ac(va(on  record  at  run(me?  

54

a

b

P

c c

d

a

Possible  call  sequence:  p  d  a  d  a  d  c  d  b  d  c  d  d  

Page 55: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Nested  Procedures  •  goal:  find  the  closest  rou4ne  in  

the  stack  from  a  given  nes4ng  level    

•  if  we  reached  the  same  rou(ne  in  a  sequence  of  calls  –  rou(ne  of  level  k  uses  variables  of  

the  same  nes(ng  level,  it  uses  its  own  variables  

–  if  it  uses  variables  of  nes(ng  level  j  <  k  then  it  must  be  the  last  rou(ne  called  at  level  j  

•  If  a  procedure  is  last  at  level  j  on  the  stack,  then  it  must  be  ancestor  of  the  current  rou(ne  

55

Possible  call  sequence:  p  d  a  d  a  d  c  d  b  d  c  d  d  

a

b

P

c c

d

a

Page 56: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Nested  Procedures  

•  problem:  a  rou(ne  may  need  to  access  variables  of  another  rou(ne  that  contains  it  sta(cally  

•  solu(on:  lexical  pointer  (a.k.a.  access  link)  in  the  ac(va(on  record  

•  lexical  pointer  points  to  the  last  ac(va(on  record  of  the  nes(ng  level  above  it  –  in  our  example,  lexical  pointer  of  d  points  to  ac(va(on  records  of  c  

•  lexical  pointers  created  at  run(me  •  number  of  links  to  be  traversed  is  known  at  compile  (me  

56

Page 57: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Lexical  Pointers    

57

a

a

c

b

c

d

y

y

z

z

Possible  call  sequence:  p  d  a  d  a  d  c  d  b  d  c  d  d  

a

b

P

c c

d

a

 program p(){ int x; procedure a(){ int y; procedure b(){ c() }; procedure c(){ int z; procedure d(){

y := x + z }; … b() … d() …

} … a() … c() … } a() }  

Page 58: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Lexical  Pointers    

58

a

a

c

b

c

d

y

y

z

z

Possible  call  sequence:  p  d  a  d  a  d  c  d  b  d  c  d  d  

a

b

P

c c

d

a

 program p(){ int x; procedure a(){ int y; procedure b(){ c() }; procedure c(){ int z; procedure d(){

y := x + z }; … b() … d() …

} … a() … c() … } a() }  

invokes  invokes  

Page 59: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Ac(va(on  Records:  Remarks  

59

Page 60: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Non-­‐Local  goto  in  C  syntax  

60

Page 61: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Non-­‐local  gotos  in  C  

•  setjmp  remembers  the  current  loca(on  and  the  stack  frame  

•  longjmp  jumps  to  the  current  loca(on  (popping  many  ac(va(on  records)  

61

Page 62: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Non-­‐Local  Transfer  of  Control  in  C  

62

Page 63: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Stack  Frames  •  Allocate  a  separate  space  for  every  procedure  incarna(on  •  Rela(ve  addresses  •  Provide  a  simple  mean  to  achieve  modularity  •  Supports  separate  code  genera(on  of  procedures  •  Naturally  supports  recursion  •  Efficient  memory  alloca(on  policy  

–  Low  overhead  –  Hardware  support  may  be  available  

•  LIFO  policy  •  Not  a  pure  stack  

–  Non  local  references  –  Updated  using  arithme(c  

63

Page 64: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

The  Frame  Pointer  •  The  caller  

–  the  calling  rou(ne  •  The  callee    

–  the  called  rou(ne  •  caller  responsibili(es:  

–  Calculate  arguments  and  save  in  the  stack  –  Store  lexical  pointer  

•  call  instruc(on:            M[-­‐-­‐SP]  :=  RA          PC  :=  callee  

•  callee  responsibili(es:  –  FP  :=  SP  –  SP  :=  SP  -­‐  frame-­‐size  

•  Why  use  both  SP  and  FP?   64

Page 65: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Variable  Length  Frame  Size  •  C  allows  alloca(ng  objects  of  unbounded  size  in  the  stack    void  p()  {          int  i;          char  *p;          scanf(“%d”,  &i);          p  =  (char  *)  alloca(i*sizeof(int));      }            

•  Some  versions  of  Pascal  allows  conformant  array  value  parameters  

65

Page 66: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Limita(ons  

•  The  compiler  may  be  forced  to  store  a  value  on  a  stack  instead  of  registers  

•  The  stack  may  not  suffice  to  handle  some  language  features  

66

Page 67: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Frame-­‐Resident  Variables  •  A  variable  x  cannot  be  stored  in  register  when:    

–  x  is  passed  by  reference  –   Address  of  x  is  taken  (&x)  –   is  addressed  via  pointer  arithme(c  on  the  stack-­‐frame    

(C  varags)  –  x  is  accessed  from  a  nested  procedure  –   The  value  is  too  big  to  fit  into  a  single  register  –   The  variable  is  an  array  –   The  register  of  x  is  needed  for  other  purposes  –   Too  many  local  variables  

•  An    escape  variable:  –  Passed  by  reference  –  Address  is  taken  –  Addressed  via  pointer  arithme(c  on  the  stack-­‐frame  –  Accessed  from  a  nested  procedure   67

Page 68: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

The  Frames  in  Different  Architectures  

Pen(um   MIPS   Sparc  

InFrame(8)   InFrame(0)   InFrame(68)  

InFrame(12)   InReg(X157)   InReg(X157)    

InFrame(16)   InReg(X158)    

InReg(X158)    

M[sp+0]←fp  fp  ←sp  sp  ←sp-­‐K  

sp  ←sp-­‐K  

M[sp+K+0]  ←r2  

X157  ←r4  

X158  ←r5  

save  %sp,  -­‐K,  %sp  

M[fp+68]←i0  X157←i1  X158←i2     68

g(x,  y,  z)  where  x  escapes  

x  

y  

z  

View  

Change  

Page 69: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Limita(ons  of  Stack  Frames  •  A  local  variable  of  P  cannot  be  stored  in  the  ac(va(on  record  of  P  if  its  

dura(on  exceeds  the  dura(on  of  P  •  Example  1:  Sta(c  variables  in  C  

 (own  variables  in  Algol)  void p(int x) { static int y = 6 ; y += x; }

•  Example  2:  Features  of  the  C  language  int * f() { int x ; return &x ; }

•  Example  3:  Dynamic  alloca(on  int * f() { return (int *) malloc(sizeof(int)); }

69

Page 70: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Compiler  Implementa(on  

•  Hide  machine  dependent  parts  •  Hide  language  dependent  part  •  Use  special  modules  

70

Page 71: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Basic  Compiler  Phases  

71

Source  program  (string)  

.EXE  

lexical  analysis  

syntax  analysis  

seman(c  analysis  

Code  genera(on  

Assembler/Linker  

Tokens  

Abstract  syntax  tree  

Assembly  

Frame  manager  Control  Flow  Graph  

Page 72: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Hidden  in  the  frame  ADT  

• Word  size  •  The  loca(on  of  the  formals  •  Frame  resident  variables  • Machine  instruc(ons  to  implement  “shie-­‐of-­‐view”  (prologue/epilogue)  

•  The  number  of  locals  “allocated”  so  far  •  The  label  in  which  the  machine  code  starts  

72

Page 73: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Ac(va(on  Records:  Summary  

•  compile  (me  memory  management  for  procedure  data  

• works  well  for  data  with  well-­‐scoped  life(me  –  dealloca(on  when  procedure  returns  

73

Page 74: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

IR  Op(miza(on  

74

Page 75: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Front-­‐End  

Back-­‐End  

✓ ✓ ✓

Where  we  are  

75

Executable

code

exe

Source

text

txt Lexical Analysis

Sem. Analysis

Process text input

characters Syntax Analysis tokens AST

Intermediate code

generation

Annotated  AST  +  Symbol  Table  

Intermediate code

optimization

IR Code generation IR

Target code optimization

Symbolic  Instruc(ons  

SI Machine code generation

Write executable

output

MI

Lexical Analysis

Syntax Analysis

Page 76: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

IR  Op(miza(on  

• Making  code  berer  

76

Page 77: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

IR  Op(miza(on  

• Making  code  “berer”  

77

Page 78: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

“Op(mized”  evalua(on  

b  

5   c  

*  

array  access  

+  

a  base   index  

   w=0  

   w=0      w=0  

     w=1          w=0    

   w=1  

   w=1  

_t0  =  cgen(  a+b[5*c]  )  Phase  2:  -­‐  use  weights  to  decide  on  order  of  transla(on  

_t0  

_t0  

_t0  Heavier  sub-­‐tree  

Heavier  sub-­‐tree  

_t0 = _t1 * _t0

_t0 = _t1[_t0]

_t0 = _t1 + _t0

_t0  _t1  

_t1  

_t1  _t0 = c

_t1 = 5

_t1 = b

_t1 = a 78

Page 79: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

But  what  about…  

a  :=  1  +  2;  y  :=  a  +  b;  x  :=  a  +  b    +  8;  z  :=  b  +  a;    a  :=  a  +  1;  w:=  a  +  b;      

79

Page 80: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Overview  of  IR  op(miza(on

•  Formalisms  and  Terminology  –  Control-­‐flow  graphs  –  Basic  blocks  

•  Local  op(miza(ons  –  Speeding  up  small  pieces  of  a  procedure  

•  Global  op(miza(ons  –  Speeding  up  procedure  as  a  whole  

•  The  dataflow  framework  –  Defining  and  implemen(ng  a  wide  class  of  op(miza(ons

80

Page 81: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Program  Analysis

•  In  order  to  op(mize  a  program,  the  compiler  has  to  be  able  to  reason  about  the  proper(es  of  that  program  

•  An  analysis  is  called  sound  if  it  never  asserts  an  incorrect  fact  about  a  program  

•  All  the  analyses  we  will  discuss  in  this  class  are  sound  –  (Why?)

81

Page 82: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Soundnessint x; int y; if (y < 5) x = 137; else x = 42; Print(x);

“At  this  point  in  the  program,  x  holds  some  

integer  value”

82

Page 83: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Soundnessint x; int y; if (y < 5) x = 137; else x = 42; Print(x);

“At  this  point  in  the  program,  x  is  either  137  

or  42”

83

Page 84: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Soundnessint x; int y; if (y < 5) x = 137; else x = 42; Print(x);

“At  this  point  in  the  program,  x  is  137”

84

Page 85: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Soundnessint x; int y; if (y < 5) x = 137; else x = 42; Print(x);

“At  this  point  in  the  program,  x  is  either  137,  

42,  or  271”

85

Page 86: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Seman(cs-­‐preserving  op(miza(ons

•  An  op(miza(on  is  seman(cs-­‐preserving  if  it  does  not  alter  the  seman(cs  of  the  original  program  

•  Examples:  –  Elimina(ng  unnecessary  temporary  variables  –  Compu(ng  values  that  are  known  sta(cally  at  compile-­‐(me  instead  of  run(me  

–  Evalua(ng  constant  expressions  outside  of  a  loop  instead  of  inside  

•  Non-­‐examples:  –  Replacing  bubble  sort  with  quicksort  (why?)  –  The  op(miza(ons  we  will  consider  in  this  class  are  all  seman(cs-­‐preserving

86

Page 87: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

A  formalism  for  IR  op(miza(on

•  Every  phase  of  the  compiler  uses  some  new  abstrac(on:  –  Scanning  uses  regular  expressions  –  Parsing  uses  CFGs  –  Seman(c  analysis  uses  proof  systems  and  symbol  tables  

–  IR  genera(on  uses  ASTs  •  In  op(miza(on,  we  need  a  formalism  that  captures  the  structure  of  a  program  in  a  way  amenable  to  op(miza(on

87

Page 88: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Visualizing  IRmain:

_tmp0 = Call _ReadInteger; a = _tmp0; _tmp1 = Call _ReadInteger; b = _tmp1;

_L0: _tmp2 = 0; _tmp3 = b == _tmp2; _tmp4 = 0; _tmp5 = _tmp3 == _tmp4; IfZ _tmp5 Goto _L1; c = a; a = b; _tmp6 = c % a; b = _tmp6; Goto _L0;

_L1: Push a; Call _PrintInt;

88

Page 89: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Visualizing  IRmain:

_tmp0 = Call _ReadInteger; a = _tmp0; _tmp1 = Call _ReadInteger; b = _tmp1;

_L0: _tmp2 = 0; _tmp3 = b == _tmp2; _tmp4 = 0; _tmp5 = _tmp3 == _tmp4; IfZ _tmp5 Goto _L1; c = a; a = b; _tmp6 = c % a; b = _tmp6; Goto _L0;

_L1: Push a; Call _PrintInt;

89

Page 90: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Visualizing  IRmain:

_tmp0 = Call _ReadInteger; a = _tmp0; _tmp1 = Call _ReadInteger; b = _tmp1;

_L0: _tmp2 = 0; _tmp3 = b == _tmp2; _tmp4 = 0; _tmp5 = _tmp3 == _tmp4; IfZ _tmp5 Goto _L1; c = a; a = b; _tmp6 = c % a; b = _tmp6; Goto _L0;

_L1: Push a; Call _PrintInt;

_tmp0 = Call _ReadInteger; a = _tmp0; _tmp1 = Call _ReadInteger; b = _tmp1;

_tmp2 = 0; _tmp3 = b == _tmp2; _tmp4 = 0; _tmp5 = _tmp3 == _tmp4; IfZ _tmp5 Goto _L1;

c = a; a = b; _tmp6 = c % a; b = _tmp6; Goto _L0;

Push a; Call _PrintInt;

start

end 90

Page 91: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Basic  blocks

•  A  basic  block  is  a  sequence  of  IR  instruc(ons  where  –  There  is  exactly  one  spot  where  control  enters  the  sequence,  which  must  be  at  the  start  of  the  sequence  

–  There  is  exactly  one  spot  where  control  leaves  the  sequence,  which  must  be  at  the  end  of  the  sequence  

•  Informally,  a  sequence  of  instruc(ons  that  always  execute  as  a  group

91

Page 92: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Control-­‐Flow  Graphs

•  A  control-­‐flow  graph  (CFG)  is  a  graph  of  the  basic  blocks  in  a  func(on  

•  The  term  CFG  is  overloaded  –  from  here  on  out,  we'll  mean  “control-­‐flow  graph”  and  not  “context  free  grammar”  

•  Each  edge  from  one  basic  block  to  another  indicates  that  control  can  flow  from  the  end  of  the  first  block  to  the  start  of  the  second  block  

•  There  is  a  dedicated  node  for  the  start  and  end  of  a  func(on

92

Page 93: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Types  of  op(miza(ons

•  An  op(miza(on  is  local  if  it  works  on  just  a  single  basic  block  

•  An  op(miza(on  is  global  if  it  works  on  an  en(re  control-­‐flow  graph  

•  An  op(miza(on  is  interprocedural  if  it  works  across  the  control-­‐flow  graphs  of  mul(ple  func(ons  – We  won't  talk  about  this  in  this  course

93

Page 94: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Basic  blocks  exerciseint main() {

int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

START: _t0 = 137; y = _t0; IfZ x Goto _L0; t1 = y; z = _t1; Goto END:

_L0: _t2 = y; x = _t2;

END:

Divide  the  code  into  basic  blocks94

Page 95: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Control-­‐flow  graph  exerciseSTART:

_t0 = 137; y = _t0; IfZ x Goto _L0; t1 = y; z = _t1; Goto END:

_L0: _t2 = y; x = _t2;

END:

Draw the control-flow graph

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

95

Page 96: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Control-­‐flow  graph  exercise

_t0 = 137; y = _t0; IfZ x Goto _L0;

start  

_t1 = y; z = _t1;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

96

Page 97: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

_t0 = 137; y = _t0; IfZ x Goto _L0;

start  

_t1 = y; z = _t1;

_t2 = y; x = _t2;

end  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

97

Page 98: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

_t0 = 137; y = _t0; IfZ x Goto _L0;

start  

_t1 = y; z = _t1;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

98

Page 99: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

y = 137; IfZ x Goto _L0;

start  

_t1 = y; z = _t1;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

99

Page 100: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

y = 137; IfZ x Goto _L0;

start  

_t1 = y; z = _t1;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

100

Page 101: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

y = 137; IfZ x Goto _L0;

start  

z = y;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

101

Page 102: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

y = 137; IfZ x Goto _L0;

start  

z = y;

_t2 = y; x = _t2;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

102

Page 103: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  op(miza(ons

y = 137; IfZ x Goto _L0;

start  

z = y;

x = y;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

103

Page 104: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Global  op(miza(ons

y = 137; IfZ x Goto _L0;

z = y;

x = y;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

104

start  

Page 105: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Global  op(miza(ons

y = 137; IfZ x Goto _L0;

z = y;

x = y;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

105

start  

Page 106: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Global  op(miza(ons

y = 137; IfZ x Goto _L0;

z = 137;

x = 137;

End  

int main() { int x; int y; int z; y = 137; if (x == 0) z = y;

else x = y;

}

106

start  

Page 107: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Local  Op(miza(ons

107

Page 108: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Op(miza(on  path

IR Control-­‐Flow  Graph

CFG  builder

Program  Analysis

Annotated  CFG

Op(mizing  Transforma(on

Target  Code

Code  Genera(on  

(+op(miza(ons)

done  with  IR  

op6miza6ons

IR  op6miza6ons

108

Page 109: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

109

For  brevity:    Simplified  IR  for  procedure  returns  

Page 110: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

110

Class  Object  {      method  fn(int);  }  

Explaining  the  program  

Page 111: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

111

Size  of  Object  

Object  Class  

Class  Object  {      method  fn(int);  }  

For  simplicity,  ignore    Popping  return  value,    

parameters  etc.  

Explaining  the  program  

Page 112: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

112

Class  Object  {      method  fn(int);  }  

Explaining  the  program  

Page 113: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

113

Class  Object  {      method  fn(int);  }  

Explaining  the  program  

Page 114: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

ExampleObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

114

Points  to  ObjectC  

Start  of  fn

Class  Object  {      method  fn(int);  }  

Explaining  the  program  

Page 115: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  Subexpression  Elimina(on

•  If  we  have  two  variable  assignments  v1  =  a  op  b              …  v2  =  a  op  b              

•  and  the  values  of  v1,  a,  and  b  have  not  changed  between  the  assignments,  rewrite  the  code  as  v1  =  a  op  b  …  v2  =  v1  

•  Eliminates  useless  recalcula(on  •  Paves  the  way  for  later  op(miza(ons

115

Page 116: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  Subexpression  Elimina(on

•  If  we  have  two  variable  assignments  v1  =  a  op  b          [or:    v1  =  a]  …  v2  =  a  op  b          [or:    v2  =  a]    

•  and  the  values  of  v1,  a,  and  b  have  not  changed  between  the  assignments,  rewrite  the  code  as  v1  =  a  op  b          [or:    v1  =  a]    …  v2  =  v1                          

•  Eliminates  useless  recalcula(on  •  Paves  the  way  for  later  op(miza(ons

116

Page 117: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = a + b; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

117

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 118: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = _tmp4; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

118

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 119: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = 4; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = _tmp4; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

119

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 120: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = _tmp4; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

120

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 121: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = _tmp4; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

121

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 122: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Common  subexpression  elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

122

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 123: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on

•  If  we  have  a  variable  assignment  v1  =  v2  then  as  long  as  v1  and  v2  are  not  reassigned,  we  can  rewrite  expressions  of  the  form  a  =  …  v1  …  as  a  =  …  v2  …  provided  that  such  a  rewrite  is  legal  

123

Page 124: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

124

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 125: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = _tmp2; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

125

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 126: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(x); _tmp7 = *(_tmp6); Push _tmp5; Push x; Call _tmp7;

126

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 127: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push _tmp5; Push _tmp1; Call _tmp7;

127

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 128: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = a + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push _tmp5; Push _tmp1; Call _tmp7;

128

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 129: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push _tmp5; Push _tmp1; Call _tmp7;

129

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 130: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push _tmp5; Push _tmp1; Call _tmp7;

130

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 131: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push c; Push _tmp1; Call _tmp7;

131

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 132: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = *(_tmp1); _tmp7 = *(_tmp6); Push c; Push _tmp1; Call _tmp7;

132

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 133: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(_tmp6); Push c; Push _tmp1; Call _tmp7;

133

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Is  this  transforma(on  OK?  What  do  we  need  to  know?  

Page 134: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(_tmp6); Push c; Push _tmp1; Call _tmp7;

134

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 135: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

135

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 136: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp3; _tmp4 = _tmp3 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

136

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 137: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Copy  Propaga(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp0; _tmp4 = _tmp0 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

137

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 138: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Dead  Code  Elimina(on

•  An  assignment  to  a  variable  v  is  called  dead  if  the  value  of  that  assignment  is  never  read  anywhere  

•  Dead  code  elimina(on  removes  dead  assignments  from  IR  

•  Determining  whether  an  assignment  is  dead  depends  on  what  variable  is  being  assigned  to  and  when  it's  being  assigned

138

Page 139: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Dead  Code  Elimina(on_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp0; _tmp4 = _tmp0 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

139

Object x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

Page 140: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Dead  Code  Elimina(onObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; _tmp2 = ObjectC; *(_tmp1) = ObjectC; x = _tmp1; _tmp3 = _tmp0; a = _tmp0; _tmp4 = _tmp0 + b; c = _tmp4; _tmp5 = c; _tmp6 = ObjectC; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

values  never  read

values  never  read

140

Page 141: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Dead  Code  Elimina(onObject x; int a; int b; int c; x = new Object; a = 4; c = a + b; x.fn(a + b);

_tmp0 = 4; Push _tmp0; _tmp1 = Call _Alloc; *(_tmp1) = ObjectC; _tmp4 = _tmp0 + b; c = _tmp4; _tmp7 = *(ObjectC); Push c; Push _tmp1; Call _tmp7;

141

Page 142: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons

•  The  different  op(miza(ons  we've  seen  so  far  all  take  care  of  just  a  small  piece  of  the  op(miza(on  

•  Common  subexpression  elimina(on  eliminates  unnecessary  statements  

•  Copy  propaga(on  helps  iden(fy  dead  code  •  Dead  code  elimina(on  removes  statements  that  are  no  longer  needed  

•  To  get  maximum  effect,  we  may  have  to  apply  these  op(miza(ons  numerous  (mes

142

Page 143: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = a * a; d = b + c; e = b + b;

143

Page 144: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = a * a; d = b + c; e = b + b;

Which  op(miza(on  should  we  apply  here?

144

Page 145: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = b; d = b + c; e = b + b;

Common  sub-­‐expression  elimina(on

Which  op(miza(on  should  we  apply  here?

145

Page 146: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = b; d = b + c; e = b + b;

Which  op(miza(on  should  we  apply  here?

146

Page 147: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = b; d = b + b; e = b + b;

Which  op(miza(on  should  we  apply  here?

Copy propagation

147

Page 148: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = b; d = b + b; e = b + b;

Which  op(miza(on  should  we  apply  here?

148

Page 149: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Applying  local  op(miza(ons  example

b = a * a; c = b; d = b + b; e = d;

Which  op(miza(on  should  we  apply  here?

Common  sub-­‐expression  elimina(on  (again)

149

Page 150: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Other  types  of  local  op(miza(ons

•  Arithme(c  Simplifica(on  –  Replace  “hard”  opera(ons  with  easier  ones  –  e.g.  rewrite  x = 4 * a;  as  x = a << 2;

•  Constant  Folding  –  Evaluate  expressions  at  compile-­‐(me  if  they  have  a  constant  value.  

–  e.g.  rewrite  x = 4 * 5; as  x = 20;

150

Page 151: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

Op(miza(ons  and  analyses

• Most  op(miza(ons  are  only  possible  given  some  analysis  of  the  program's  behavior  

•  In  order  to  implement  an  op(miza(on,  we  will  talk  about  the  corresponding  program  analyses

151

Page 152: Compilaon - TAUmaon/teaching/2014-2015/...Compilaon * **0368/3133**2014/15a Lecture*8* IRfor*Procedure*calls*+Op(mizaons * Noam*Rinetzky* 1

152