Composing Dataflow Analyses and Transformations Sorin Lerner University
- Slides: 58
Composing Dataflow Analyses and Transformations Sorin Lerner (University of Washington) David Grove (IBM T. J. Watson) Craig Chambers (University of Washington)
Phase ordering problem • • Optimizations can interact in mutually beneficial ways, and no order exploits all of these interactions. Classic example: constant propagation and unreachable code elimination. true x : = 11; if (x == 11) { Do. Something(); } else { Do. Something. Else(); x : = x + 1; } y : = x; // value of y? const prop followed x : = 11; by unreachable Do. Something(); code elimination y : = x; // value of y? const prop again x : = 11; Do. Something(); y : = 11;
One known solution: Iterate individual analyses until the results don’t change • Compiler is slow. • In the presence of loops in the source program, might not yield best possible results. x : = 11; do { if (x == 11) { Do. Something(); } else { Do. Something. Else(); x : = x + 1; } } while (. . . ) y : = x; // value of y?
Another known solution: hand written super-analysis Monolithic Super-Analysis Lose modularity: – difficult to write, reuse, and extend such analyses Examples: – conditional constant propagation [Wegman and Zadeck 91] – class analysis, splitting and inlining [Chambers and Ungar 90] – const prop and pointer analysis [Pioli and Hind 99]
Ideally. . . • . . . we want to: • We present a framework that achieves this. – Write analyses modularly – Exploit mutually beneficial interactions – Have a fast compiler Composition Framework
The key to modular composition • Traditionally, optimizations are defined in two parts: 1. A dataflow analysis. 2. Rules for transforming the program representation after the analysis is solved. • The key insight is to merge these two parts: – Dataflow functions return either a dataflow value OR a replacement graph with which to replace the current statement.
Roadmap • • Several small examples that show flow functions work One large example that shows how modular analyses are automatically composed together Overview of theory behind the framework Experimental validation
Flow function returning a dataflow value y : = 5
Flow function returning a dataflow value [. . . ] y : = 5 PROPAGATE [. . . , y → 5]
Flow function returning a replacement graph y : = x+2
Flow function returning a replacement graph Step 1: Initialize input edges with dataflow information Replacement graph [x → 3] y : = x+2 REPLACE y : = 5
Flow function returning a replacement graph Step 2: Perform recursive dataflow analysis on the replacement graph Step 1: Initialize input edges with dataflow information [x → 3] y : = x+2 [x → 3] y : = 5 [x → 3, y → 5] PROPAGATE
Flow function returning a replacement graph Step 2: Perform recursive dataflow analysis on the replacement graph Step 1: Initialize input edges with dataflow information [x → 3] y : = x+2 y : = 5 [x → 3, y → 5] Step 3: Propagate dataflow information from output edges. PROPAGATE
Flow function returning a replacement graph Replacement graphs: [x → 3] y : = x+2 [x → 3, y → 5] – used to compute outgoing dataflow information for the current statement. – a convenient way of specifying what might otherwise be a complicated flow function.
Flow function returning a replacement graph Soundness requirement: [x → 3] y : = x+2 [x → 3, y → 5] – Replacement graph must have the same concrete semantics as the original statement, but only on concrete inputs that are consistent with the current dataflow facts.
Flow function returning a replacement graph Let’s assume we’ve reached a fixed point. [x → 3] y : = x+2 [x → 3, y → 5]
Flow function returning a replacement graph Let’s assume we’ve reached a fixed point. [x → 3] y : = x+2 [x → 3, y → 5] y : = 5
Flow function returning a replacement graph Let’s assume we’ve reached a fixed point. [x → 3] y : = 5 [x → 3, y → 5] Replacement graphs: – used to transform the program once a fixed point has been reached.
Iterative analysis example Now, let’s assume we haven’t reached a fixed point. [x → 3] [x → T] y : = x+2 [x → 3, y → 5]
Iterative analysis example Now, let’s assume we haven’t reached a fixed point. [x → 3] [x → T] y : = x+2 PROPAGATE [x → 3, y → 5] [x → T, y → T]
Branch folding example if (x == 11) F T
Branch folding example [x → 11] if (x == 11) F T REPLACE
Branch folding example [x → 11] if (x == 11) F T [x → 11]
Branch folding example [x → 11] if (x == 11) F T [x → 11]
Composing several analyses Constant Propagation Class Analysis Inlining Unreachable code elimination x : = new C; do { b : = x instanceof C; if (b) { x : = x. foo(); } else { x : = new D; } } while (. . . ) class A { A foo() { return new A; } }; class C extends A { A foo() { return self; } }; class D extends A { };
x : = new C merge b : = x instanceof C if (b) F T x : = new D x : = x. foo() merge while(…)
x : = new C PROPAGATE [x → T] merge b : = x instanceof C if (b) F T x : = new D x : = x. foo() merge while(…) PROPAGATE [x → {C}] T T
x : = new C PROPAGATE ([x → T], T, →T){C}] [x [x →→ T] {C}], [x merge b : = x instanceof C if (b) F T x : = new D x : = x. foo() merge while(…) T T
x : = new C ([x → T], [x → {C}], T, T) merge PROPAGATE ([x → T], [x → {C}], T, T) b : = x instanceof C if (b) F T x : = new D x : = x. foo() merge while(…)
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C [x → T, PROPAGATE b → T] if (b) F T x : = new D x : = x. foo() merge while(…)
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C [x → T, REP b → T] T x : = new D x : = x. foo() merge while(…) E b : = true if (b) F LAC
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T], [x → {C}], T, T) b : = true if (b) F ([x → T, T x : = new D x : = x. foo() merge while(…) PROPAGATE b → true], [x → {C}, b → {Bool}], T, T)
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T], [x → {C}], T, T) b : = true if (b) F ([x → T, T x : = new D x : = x. foo() merge while(…) b → true], [x → {C}, b → {Bool}], T, T)
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) F T x : = new D x : = x. foo() merge while(…) • Replacement graph is analyzed by composed analysis. • When one analysis chooses a replacement graph, other analyses see it immediately. • Analyses communicate implicitly through graph transformations
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) F REPLACE T x : = new D x : = x. foo() merge while(…) σ
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) F T x : = new D x : = x. foo() merge while(…) σ
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) σ σ if (b) F ( T x : = new D x : = x. foo() merge while(…) , , , ) σ
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) σ σ if (b) F ( T x : = new D x : = x. foo() merge while(…) , , , ) σ
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ([x → T, [x → {C}, b → {Bool}], T, T) x : = x. foo() merge while(…) b → true],
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ([x → T, b → true], [x → {C}, b → {Bool}], T, T) x : = x. foo() REPLACE merge while(…)
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ( , , ([x → T, [x → {C}, b → {Bool}], T, T) x : = x. foo() , ) merge while(…) b → true],
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) x : = C: : foo(x) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ( , , ([x → T, [x → {C}, b → {Bool}], T, T) x : = x. foo() , ) merge while(…) b → true], σ REPLACE
x : = new C ([x → T], [x → {C}], T, T) class C extends A { A foo() { return self; } } merge σ ([x → T], [x → {C}], T, T) x : = C: : foo(x) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) ( , , , ) F T x : = new D ( , , ([x → T, b → true], [x → {C}, b → {Bool}], T, T) σ REPLACE if (b) x : = x. foo() , ) merge while(…) x : = x
x : = new C ([x → T], [x → {C}], T, T) merge σ ([x → T], [x → {C}], T, T) x : = C: : foo(x) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ( , , ([x → T, b → true], [x → {C}, b → {Bool}], T, T) σ x : = x. foo() σ , ) merge while(…) PROPAGATE x : = x σ
x : = new C ([x → T], [x → {C}], T, T) merge ([x → T], [x → {C}], T, T) b : = x instanceof C ([x → T, b → true], [x → {C}, b → {Bool}], T, T) if (b) ( , , , ) F T x : = new D ( , , ([x → T, b → true], [x → {C}, b → {Bool}], T, T) x : = x. foo() ([x → T, , ) b → true], [x → {C}, b → {Bool}], T, T) merge PROPAGATE ([x → T, b → true], [x → {C}, b → {Bool}], T , T) while(…)
x : = new C merge b : = x instanceof C b : = true if (b) F T x : = new D x : = x. foo() merge while(…) x : = x
x : = new C; do { b : = x instanceof C; if (b) { x : = x. foo(); } else { x : = new D; } } while (. . . ) merge b : = true x : = x merge while(…) x : = new C; do { b : = true; x : = x; } while (. . . )
• • • Analyses are defined modularly and separately. Combining them achieves the results of a monolithic analysis. If the analyses were run separately in any order any number of times, no optimizations could be performed. x : = new C; do { b : = x instanceof C; if (b) { x : = x. foo(); } else { x : = new D; } } while (. . . ) x : = new C; do { b : = true; x : = x; } while (. . . )
Theoretical foundation • • Definition: used abstract interpretation to define precisely how the framework composes analyses. Soundness theorem: if the individual analyses are sound, the composed analysis is sound. Termination theorem: composed analyses are guaranteed to terminate, under reasonable conditions. Precision theorem: if the composed flow function is monotonic, the composed analysis is guaranteed to produce results as precise as running the individual analyses in sequence, any number of times, in any order.
Experimental validation • Implemented and used our framework in the Vortex and Whirlwind compilers for 5+ years. – composed: class analysis, splitting, inlining, const prop, CSE, removal of redundant loads and stores, symbolic assertion prop • Compiled a range of big programs in Vortex. • Our framework vs. iteration: • Our framework vs. monolithic super-analysis: – largest benchmark: Vortex compiler with ~60, 000 lines – compiles at least 5 times faster – same precision – compiles at most 20% slower
Conclusions • • • We developed and implemented a new approach for defining dataflow analyses. Our approach allows analyses to be written modularly: – easier to write and reuse analyses. Our approach allows analyses to be automatically combined into a monolithic analysis.
- Critical thinking example in nursing
- Data flow modeling in verilog
- Naiad dataflow
- Dataflow
- Arbicor
- Semicolon adder
- Molecular ecological network analyses
- What is rhetorical analysis
- Geicp
- Partial fraction solution
- Composing skill
- Composing the message in business communication
- Sorin mitran
- Sorin cismas
- Sorin peste
- Labcecil
- Sorin mitrea
- Primordial prevention
- Nqfhe
- Sorin constantin
- Dan sorin duke
- Sorin dragomir
- Notre dame sorin society
- Simbolul nucului
- Sorin adam matei
- Lerner index formula
- Umich
- Lerner index of monopoly power
- Lerner index of monopoly power
- J curve economics
- Lerner index
- Apa itu indeks lerner
- Lerners index
- Welfare effects of monopoly
- Social cost of monopoly
- Marshall lerner koşulu
- Indice de lerner formule
- Marshall lerner koşulu
- Delia lerner frases
- Shirley lerner
- Lerner diagram
- Marshall lerner koşulu nedir
- 沈榮麟
- Non-rigid transformations
- Jordan peterson personality and its transformations
- 7 parent functions
- Lexical problems examples
- 2-7 parent functions and transformations answer key
- Transformations of linear and absolute value functions
- Partner of sine and cosine
- Normal sin graph
- 7-2 similarity and transformations
- 2-7 parent functions and transformations
- Geometry topic 1 review
- Energy transformation running
- Energy transformations and conservation
- 100 examples of energy transformation
- Economic transformations commerce and consequence
- Week 1: congruence transformations