Held Wednesday, December 4, 2002
Today we continue our study of optimization with an extended example.
- I now have one parser in hand. Can I expect the others soon?
- Upcoming schedule:
- Friday: Final distributed; More optimization
- Monday: Nathan presents on type inference
- Wednesday: Garbage collection
- Friday: Wrapup
- Due dates:
- Parser: Monday, 9 December 2002 (final deadline)
- Translator: Friday, 20 December 2002
- Final: Friday, 20 December 2002
- I will also assign a short essay on your project experience.
I expect you to take it much more seriously than you took the
- Improvement, reviewed
- Loop optimization
- An example
- We typically want to spend the most effort where it will make
the most difference.
- The typical observation is that 10% of the code does 90% of the
- At the source level, we can profile the code to figure out
where most of the work goes on and then carefully recode
- At the intermediate level, we can identify loops and
- How do we identify loops? By looking at the flow graph.
- What optimizations are available?
- Code movement: If we can get statements out of loops,
we're much better off.
- Induction variables and reduction in strength not all
operations are the same (for example, multiplication may take more
time than addition). At times, we can trade one for the other
by observing when two variables change in lockstep.
- Consider the following sample code
add t1, $1, t1
mul t1, $4, t2
- We call t1 and t2 induction variables because they
change in relation to the loop and because a proof of the
loop's termination will typically involve inducation on
one of these variables
- Some simple analysis tells us that at every step of the
loop, t1 is incremented by 1 which means that t2 is
incremented by 4.
- If t1 is never used again, we can replace the code with
- Even if t1 is used again, the add is still cheaper than
- Let's look at a slightly longer program and consider how
to optimize it.
- Consider the code fragment
for i := 1 to n do
for j := 1 to n do
B[j,i] := A[i,j]
- Assumptions for translation:
- Integers take four bytes
- Each dimension of the array is indexed from 1..n.
- The array is stored in row-major order. That is, if n is 3,
we have the following elements in sequence A[1,1], A[1,2],
A[1,3], A[2,1], A[2,2], A[2,3], A[3,1], A[3,2], A[3,3].
- Given those assumptions, and knowledge that the representation of
A begins at some position (which we'll also call A), where if A[x,y]?
- base of A + offset n*4*(x-1) + 4*(y-1)
- The code will look something like the following
MOV $1, i
JEQ i, n -> END_OUTER
MOV $1 -> j
JEQ j, n -> END_INNER
ISUB i, $1 -> t1
IMUL t1, $4 -> t2
IMUL t2, n -> t3
ISUB j, $1 -> t4
IMUL t4, $4 -> t5
IADD t3, t5 -> t6
MOV offset(A,t6) -> t7
ISUB j, $1 -> t8
IMUL t8, $4 -> t9
IMUL t9, n -> t10
ISUB i, $1 -> t11
IMUL t11, $4 -> t12
IADD t10, t12 -> t13
IMOV t7 -> offset(B,t13)
IADD j, $1 -> j
IADD i, $1 -> i
- We'll start by breaking the code into basic blocks.
- We'll continue by identifying and eliminating common
- We'll continue by propagating copies.
- We'll conclude by identifying induction variables and
reducing the strength of some operations.
Thursday, 29 August 2002
- First version, based somewhat on outlines from