Top Banner
Heap liveness and its usage in automatic memory management Ran Shaham Elliot Kolodner Mooly Sagiv •ISMM’02 •Unpublishe d http:// www.cs.tau.ac.il/~ransh/ T V L A i n s i d e
74

Heap liveness and its usage in automatic memory management

Jan 23, 2016

Download

Documents

gates

Heap liveness and its usage in automatic memory management. ISMM’02 Unpublished. Ran Shaham Elliot Kolodner Mooly Sagiv. TVLA inside. http://www.cs.tau.ac.il/~ransh/. Motivation. An object could be collected once it is no longer needed - PowerPoint PPT Presentation
Welcome message from author
This document is posted to help you gain knowledge. Please leave a comment to let me know what you think about it! Share it to your friends and learn new things together.
Transcript
Page 1: Heap liveness  and its usage in  automatic memory management

Heap liveness and its usage in

automatic memory management

Ran Shaham

Elliot Kolodner

Mooly Sagiv

•ISMM’02

•Unpublished

http://www.cs.tau.ac.il/~ransh/

TV

LA inside

Page 2: Heap liveness  and its usage in  automatic memory management

Motivation• An object could be collected once it is no longer

needed– Yet, run-time garbage collectors (RTGCs) are

typically based on reachability• Profiling tools can detect when objects are

needed• The compiler can:

– Statically identify a subset of unneeded objects – Issue a free instruction (compile-time Garbage

Collection)– Issue a warning when a potentially needed object is

reclaimed– Inform run-time garbage collector that a reference to

an object is not further used

Page 3: Heap liveness  and its usage in  automatic memory management

A Pathological C Program

a = malloc(…) ;

b = a;

free (a);

c = malloc (…);

if (b == c) printf(“unexpected equality”);

Page 4: Heap liveness  and its usage in  automatic memory management

Inefficient Java Classpublic Class Stack { private Object stack[]; private int top; public Stack(int len) { stack = new Object[len]; top = 0; } public synchronized Object pop() { top= top-1; return stack[top]; } public synchronized void push(Object o) { stack[top]=o; top= top+1; } public synchronized void print() { for (int i=0; i<top; i++) { System.out.println(stack[i]); } }}

GC does not reclaim the memory stack[top+1]

Page 5: Heap liveness  and its usage in  automatic memory management

Needed Location

pp’

l is neededa reference to l is used

l is allocated

Page 6: Heap liveness  and its usage in  automatic memory management

Needed Reference Expression

pp’

e is needed a reference to l is used

e references l

e is not needed free(e) is valid

l is allocated

Page 7: Heap liveness  and its usage in  automatic memory management

A Pathological C Program

a = malloc(…) ;

b = a;

free (a);

c = malloc (…);

if (b == c) printf(“unexpected equality”);

a is needed

Page 8: Heap liveness  and its usage in  automatic memory management

Location Liveness

pp’

l is live

l is not assigned

l is used

Page 9: Heap liveness  and its usage in  automatic memory management

Reference Expression Liveness

pp’

e is live

e denotes a location l

l is not assigned

l is used

Generalizes liveness of program variables when l is &x

Page 10: Heap liveness  and its usage in  automatic memory management

Inefficient Java Classpublic Class Stack { private Object stack[]; private int top; public Stack(int len) { stack = new Object[len]; top = 0; } public synchronized Object pop() { top= top-1; return stack[top]; } public synchronized void push(Object o) { stack[top]=o; top= top+1; } public synchronized void print() { for (int i=0; i<top; i++) { System.out.println(stack[i]); } }}

stack[top+1] is not live

Page 11: Heap liveness  and its usage in  automatic memory management

Typical GC Limits

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

Page 12: Heap liveness  and its usage in  automatic memory management

Typical GC Limits

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

Page 13: Heap liveness  and its usage in  automatic memory management

Typical GC Limits

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

Page 14: Heap liveness  and its usage in  automatic memory management

Liveness Analysis Aids GC

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

root.right is live, root.left is dead

Page 15: Heap liveness  and its usage in  automatic memory management

Liveness Analysis Aids GC

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

root.right is live, root.left is dead

Page 16: Heap liveness  and its usage in  automatic memory management

Liveness Analysis Aids GC

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

root.right is live, root.left is dead

Page 17: Heap liveness  and its usage in  automatic memory management

Liveness Analysis Aids GC

class Node { Node left, right; int data;}

class C { void main(…) { Node root = createTree(); processTree(root.right); }}

root

root.right is live, root.left is dead

Page 18: Heap liveness  and its usage in  automatic memory management

Typical GC Limits

Program

Variables

a

b

c

d

e

f

Page 19: Heap liveness  and its usage in  automatic memory management

Outline

• Dynamic liveness measurements– Complete location liveness– Assign-null interface

• Static analysis algorithms– (Exact) assign null (improve GC)– (Exact) free (CTGC)

Page 20: Heap liveness  and its usage in  automatic memory management

Dynamic Liveness Measurements

• Estimating the potential of static analysis– Find upper bounds on expected savings

• Can be used in as an assistant tool

• Liveness information kinds– Stack reference liveness– Global reference liveness– Heap reference liveness

Page 21: Heap liveness  and its usage in  automatic memory management

Main Results

• Dynamic measurements for 10 benchmarks

• Shallow information Small Potential– local variables 2%– global variables 5%– local + global 9%

• Deep information Larger Potential– heap liveness 39% complete location liveness

15% assign-null interface

Page 22: Heap liveness  and its usage in  automatic memory management

Dynamic measurements

– Implemented via an instrumented JVM

• Complete location liveness measurements– Single-run algorithm

• Assign-null liveness interface – Determines the liveness of expressions– Assign null to dead reference expressions– Requires two runs of the program

Page 23: Heap liveness  and its usage in  automatic memory management

Complete Liveness Measurements

• An Observation

The last use of the references to an object determines the time an object could be collected assuming liveness information

Page 24: Heap liveness  and its usage in  automatic memory management

Heap Liveness Example IStack

y

z

gStatic

x

f

f2

f 1

f

fHeapL= t

use z.f

f

HeapL

= t

Page 25: Heap liveness  and its usage in  automatic memory management

Heap Liveness Example IStack

y

z

gStatic

x

f

f2

f 1

f

fHeapL= t+2

use y.f2

f

HeapL= t

= t+2

Page 26: Heap liveness  and its usage in  automatic memory management

Heap Liveness Example IIStack

y

z

gStatic

x

f

f2

f 1

f

f

StackR = t’’

f

StackR = Directly stack reachable

(computed during GC)

Collection time = max(t’, t’’)

Collection time(obj) = max(HeapL(obj), StackR(obj), StaticR(obj), OtherR(obj))

= t’’

HeapL= t’

Page 27: Heap liveness  and its usage in  automatic memory management

Complete Liveness Summary

• Mutator– Tracks the last use of references to an object

• Collector– Propagation needed for stack/static liveness– Propagates reachability information– Propagates path liveness

• Object Collection/Program Termination– Maximum of liveness/reachability properties of an object– Depends on liveness scheme (heap liveness etc.)

Page 28: Heap liveness  and its usage in  automatic memory management

Experimental Results

• Instrumented Sun’s classic JVM (1.2)

• 10 benchmarks (5 SPECjvm)

• Time is measured bytes allocated by the mutator so far in program

• Total space savings (integral)

• Maximum heap size savings (footprint)

Page 29: Heap liveness  and its usage in  automatic memory management

Analyzer - Complete Liv eness

0

0.5

1

1.5

2

2.5

3

3.5

0 50 100 150 200 250 300

allocation time (MB)

siz

e (

MB

) heap liveness

stack+staticliveness

w /out liveness

Page 30: Heap liveness  and its usage in  automatic memory management

Potential Savings – Total Space

0

0.1

0.2

0.3

0.4

0.5

0.6

0.7

0.8

jess

raytr

ace

db

javac

jack

analy

zer

juru

eule

r

mc

tvla

average

heap+stack+static liveness heap liveness

stack+static liveness static liveness

stack liveness

Page 31: Heap liveness  and its usage in  automatic memory management

Restricted GC Interface

• GC Interface– Should be simple/effective/efficient – Feasible heap liveness representation

• Assign null to dead heap references– Simple– Effective?

• Partially answered by our experiments

– Efficient?• Will be answered by static analysis

Page 32: Heap liveness  and its usage in  automatic memory management

Null Assignable Program Points

• Normalized statements (Java Bytecode)– Manipulate at most one heap reference

• x = y.f is null assignable– Could be followed by y.f = null

• Dynamic algorithm – First run

• Determine null assignable program points– Assume all program points are null assignable– Detect non-null-assignable program points during the run

– Second run• Assign null in null assignable program points

Page 33: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

x

n

pd d

n

pd d

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 34: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

x

n

pd d

n

pd d

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

y

Page 35: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

yt

[pt2]

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 36: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

yt

[pt2]

[pt3]

d1

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 37: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

yt

[pt2]

[pt3]

d1

[pt4]

d2

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 38: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

y t

[pt2]

[pt3]

d1

[pt4]

d2

[pt5][pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 39: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

t y

[pt2]

[pt3]

d1

[pt4]

d2

[pt5]

[pt2]

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 40: Heap liveness  and its usage in  automatic memory management

[pt4]

Doubly-Linked List Example – First Run

n

pd d

n

pd d

t y

[pt2]

[pt3]

d1

[pt3]

d2

[pt5]

[pt1]

[pt1]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; // y.d = null process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 41: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example – First Run

n

pd d

n

pd d

[pt2]

[pt3]

d2

[pt3]

d1

[pt5]

[pt3]

[pt1]

[pt3]

// processing list elements in pairspt1: y = x.n; // x.n = null; x = null; while (y != null) { pt2: t = y.p; // y.p = null;pt3: d1 = t.d; // t.d = nullpt4: d2 = y.d; process(d1, d2); pt5: t = y.n; // y.n = null; y = t; }

Page 42: Heap liveness  and its usage in  automatic memory management

Doubly-Linked List Example - Second Run

x

n

pd d

n

pd d

// processing list elements in pairspt1: y = x.n; x.n = null; x = null; while (y != null) { pt2: t = y.p; y.p = null;pt3: d1 = t.d; t.d = nullpt4: d2 = y.d; process(d1, d2); pt5: t = y.n; y.n = null; y = t; }

Page 43: Heap liveness  and its usage in  automatic memory management

n

pd d

n

pd d

ty

// processing list elements in pairspt1: y = x.n; x.n = null; x = null; while (y != null) { pt2: t = y.p; y.p = null;pt3: d1 = t.d; t.d = nullpt4: d2 = y.d; process(d1, d2); pt5: t = y.n; y.n = null; y = t; }

Doubly-Linked List Example - Second Run

d1 d2

Page 44: Heap liveness  and its usage in  automatic memory management

// processing list elements in pairspt1: y = x.n; x.n = null; x = null; while (y != null) { pt2: t = y.p; y.p = null;pt3: d1 = t.d; t.d = nullpt4: d2 = y.d; process(d1, d2); pt5: t = y.n; y.n = null; y = t; }

Doubly-Linked List Example - Second Run

d

n

pd d

ty

d1 d2

Page 45: Heap liveness  and its usage in  automatic memory management

Assign Null - Potential Savings

0%

5%

10%

15%

20%

25%

30%

35%

40%

jes

s

ray

tra

ce

db

jav

ac

jac

k

an

aly

ze

r

juru

eu

ler

mc

tvla

av

era

ge

context=0

context=1

context=2

context=3

• 15% average savings for context = 2– 11% assigning null to instance fields– 10% assigning null to array elements

• Results are valid across runs – Detecting null assignable program points on a second input– Running the program with the first input

– null assignable program points are those detected for both inputs

Page 46: Heap liveness  and its usage in  automatic memory management

Related Work

• On the Usefulness of Liveness for Garbage Collection and Leak Detection [HDH01]– Does not handle heap liveness – Algorithm requires two runs

• First run: record uses and defs• Analyze log backwards for liveness information• Second run: use liveness results

• Garbage Collection and Local Variable Type-Precision and Liveness in Java Virtual Machines [ADM98]– Stack liveness static analysis– Actual trends match our upper bounds

• On the Effectiveness of GC in Java [SKS00]– Drag information

• Slightly larger potential than heap liveness information• Not clear how to automate space savings

• HUP tool (PLDI’01 + M. Pan)

Page 47: Heap liveness  and its usage in  automatic memory management

Dynamic liveness measurements -Conclusion

• Liveness Information has large potential• Assign null savings “achievable” by static analysis• Stack liveness information

– Small potential• Stack+static liveness information

– Medium potential• Heap liveness information

– Is feasible• Recording history on heap is a powerful mechanism

– Larger potential• Depends on static analysis precision• Depends on GC interface

Page 48: Heap liveness  and its usage in  automatic memory management

Static Analysis

• Combine history with shape analysis – a-La- Horwitz, Pfeiffer, and Reps 1989

• Assign null – Assign null to a dead reference expression– GC exploits information

• Free– free an unneeded object

Page 49: Heap liveness  and its usage in  automatic memory management

Assign Null Analysis

– Insert “x.fld = null” after statements in which the expression x.fld becomes dead

– Limitations• Only one reference is assigned null• All the paths to the statement must agree

– Detects last-use– Technically

• llastu[pt,x.fld](v)– The last use of the location denoted by x.fld occurs at pt

• null[pt,x.fld]() – It is safe to insert “x.fld = null” after pt

Page 50: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

nn

null[pt3,y.n]

Page 51: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x,y

nn

null[pt3,y.n]

Page 52: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x,y

nn

null[pt3,y.n]

Page 53: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x,y

n

llastu[pt3,y.n]

nn

t

null[pt3,y.n]

Page 54: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

y,t

null[pt3,y.n]

Page 55: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

y,t

null[pt3,y.n]

Page 56: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

y

llastu[pt3,y.n]

nt null[pt3,y.n]

Page 57: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

y,t null[pt3,y.n]

Page 58: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

y,t null[pt3,y.n]

Page 59: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

llastu[pt3,y.n]

y

n

t

null[pt3,y.n]

Page 60: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

nn

llastu[pt3,y.n]

n

llastu[pt3,y.n]

n

y,tn

null[pt3,y.n]

Page 61: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

nn

llastu[pt3,y.n]

n

llastu[pt3,y.n]

n

y,tn

Page 62: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

llastu[pt3,y.n]

y

n

tn

null[pt3,y.n]

Page 63: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

y,tn

null[pt3,y.n]

Page 64: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

nn

llastu[pt3,y.n]

n

y,tn

null[pt3,y.n]

Page 65: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n]

n

llastu[pt3,y.n]

yn

llastu[pt3,y.n]

null[pt3,y.n]

Page 66: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n] llastu[pt3,y.n]

n

null[pt3,y.n]

Page 67: Heap liveness  and its usage in  automatic memory management

Assign Null Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

llastu[pt3,y.n] llastu[pt3,y.n]

n

null[pt3,y.n]

Page 68: Heap liveness  and its usage in  automatic memory management

• Static Reachability Information +Static Liveness Information CT garbage detection

• Issue “free(e)” for unneeded e

Compile-Time Garbage Collection

Page 69: Heap liveness  and its usage in  automatic memory management

Exact Free Analysis

– Insert free(x) at program points when the x becomes unneeded

• Only one location is freed• All the paths to the statement must agree on the

garbage

– History predicates• lastu[pt,x](v)

– the last use of the location pointed-to by x occurs

• unneeded [pt,x]() – “free(x)” is safe after pt

Page 70: Heap liveness  and its usage in  automatic memory management

Exact Free Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

nn

unneeded[pt1,x]

unneeded[pt2,y]

unneeded[pt3,y]

unneeded[pt4,t]

Page 71: Heap liveness  and its usage in  automatic memory management

Exact unneeded Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x,y

nn

unneeded[pt1,x]

unneeded[pt2,y]

unneeded[pt3,y]

unneeded[pt4,t]

lastu[pt1,x]

Page 72: Heap liveness  and its usage in  automatic memory management

Exact Free Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x,y

nn

unneeded[pt2,y]

unneeded[pt3,y]

unneeded[pt4,t]

lastu[pt2,y]

Page 73: Heap liveness  and its usage in  automatic memory management

Exact Free Example // traversing list elements pt1: y = x; pt2: while (y != null) { pt3: t = y.n; pt4: y = t; }

x

n

unneeded[pt3,y]

lastu[pt3,y] lastu[pt3,y]

n

Page 74: Heap liveness  and its usage in  automatic memory management

Preliminary Conclusions

• Heap Liveness is useful

• Can be dynamically computed for large programs

• More data is needed to confirm scalability of static analysis

• Recording local history is a powerful tool– Refines the abstraction