LeakChecker: Practical Static Memory Leak Detection for Managed Languages

432 views

Published on

Static detection of memory leaks in a managed language such as Java is
attractive because it does not rely on any leak-triggering inputs,
allowing compile-time tools to find leaks before software is
released. A long-standing issue that prevents practical static memory
leak detection for Java is that it can be very expensive to statically
determine object liveness in large applications. We present a novel
(and the first practical) static leak detection technique that
bypasses this problem by considering a common leak pattern. In many
cases severe leaks occur in loops where, in each iteration, some
objects created by the iteration are unnecessarily referenced by
objects external to the loop. These unnecessary references are never
used in later loop iterations. Based on this insight, we shift our
focus from computing liveness, which is very difficult to achieve
precisely and efficiently for large programs, to the easier goal of
identifying objects that flow out of a loop but never flow back in.
We formalize this analysis using a type and effect system and present
its key properties. The analysis was implemented in a tool called
LeakChecker and used to detect leaks in eight real-world programs,
such as Eclipse, Derby, and log4j. LeakChecker not only identified
known leaks, but also discovered new ones whose causes were
unknown beforehand, while exhibiting a false positive rate suitable
for practical use.

Published in: Technology
0 Comments
1 Like
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
432
On SlideShare
0
From Embeds
0
Number of Embeds
7
Actions
Shares
0
Downloads
4
Comments
0
Likes
1
Embeds 0
No embeds

No notes for slide

LeakChecker: Practical Static Memory Leak Detection for Managed Languages

  1. 1. LeakChecker:  Prac,cal  Sta,c  Memory  Leak   Detec,on  for  Managed  Languages   Dacong  (Tony)  Yan1,  Guoqing  Xu2,  Shengqian  Yang1,  Atanas  Rountev1     1  Ohio  State  University   2  University  of  California,  Irvine     PRESTO:  Program  Analyses  and  So5ware  Tools  Research  Group,  Ohio  State  University  
  2. 2. Memory  Leaks  in  Managed  Languages   •  Languages  such  as  Java  sMll  have  memory  leaks:   unnecessary  references  keep  unused  objects  alive   •  StaMc  leak  detecMon   –  Widely  used  for  unmanaged  languages  such  as  C   –  Cannot  be  applied  to  managed  languages:  no  explicit  memory   deallocaMon   •  General  definiMon  of  leaks   –  Precision:  difficult  to  compute  object  liveness  precisely   –  Performance:  limited  scalability  for  large  programs   •  Our  approach   –  Shi5  the  focus,  and  idenMfy  common  leak  paVerns   2  
  3. 3. Proposed  Leak  DetecMon  for  Java   •  ObservaMon:  leaks  are  o5en  related  to  frequently   occurring  events  (e.g.,  loop  iteraMons)   •  SoluMon:  focus  on  a  user-­‐specified  event  loop   •  ObservaMon:  a  leaking  object  is  o5en   –  created  by  one  loop  iteraMon   –  escapes  this  iteraMon   –  never  used  in  later  iteraMons   •  SoluMon:  interprocedural  tracking  of   3   –  whether  an  object  escapes  to  a  memory  locaMon  outside  of   the  loop   –  whether  an  escaping  object  flows  from  the  outside  locaMon   back  into  a  later  loop  iteraMon  
  4. 4. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! 20 ! } }! An  example  adapted  from  SPECjbb2000   ! 4  
  5. 5. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! 20 ! } }! An  example  adapted  from  SPECjbb2000   ! 5  
  6. 6. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! loop  object   ! void display() {! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 6   } }!
  7. 7. “main”:! outside  object   Example   7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! loop  object   ! void display() {! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 7   } }!
  8. 8. “main”:! outside  object   Example   7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! loop  object   ! void display() {! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 8   } }!
  9. 9. “main”:! outside  object   Example   7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! loop  object   ! void display() {! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 9   } }!
  10. 10. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 10   } }!
  11. 11. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 11   } }!
  12. 12. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 23 void addOrder(Order q) {! 17 this.prev = p;! store16   Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! 20 ! 12   } }!
  13. 13. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 23 void addOrder(Order q) {! 17 this.prev = p;! store16   Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! Order4! store16   20 Transaction1! ! ! 13   escape   } }!
  14. 14. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! this.orders[...] = q;! store24   24 25 }! 26 }! ! 20 ! 14   } }!
  15. 15. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! this.orders[...] = q;! store24   24 25 }! 26 }! Order4! 15   20 store24     Order[]23! store22     ! Customer?! ! } store?     escape   }! Customer[]10! store9   Transaction1!
  16. 16. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! ! Order4,i! 16   20 store24/orders,  …,  store9/custs     store16/prev   } }! Transaction1! !
  17. 17. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! Order4,i! 17   store24/orders,  …,  store9/custs     20 leaking?   ! } }! Transaction1! !
  18. 18. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! 20 ! Order4,i! 18   store16/prev   } }! Transaction1! ! leaking?  
  19. 19. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! load11   ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! 20 ! Order4,i! 19   store16/prev   } }! Transaction1! ! leaking?  
  20. 20. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! load11   ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! 20 ! Order4,i! 20   store16/prev   } }! Transaction1! ! leaking?   store16  
  21. 21. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! load11   ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! load11/prev   ! Order4,i! 21   20 store16/prev   } }! Transaction1! ! leaking?   store16  
  22. 22. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! load11   ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 26 }! this.orders[...] = q;! }! (i+1)-­‐th  itera,on   load11/prev   ! Order4,i! 22   i-­‐th  itera,on   20 store16/prev   } }! Transaction1! ! leaking?   store16  
  23. 23. Example   “main”:! 7 class Transaction {! 1 Transaction t = new Transaction();! 8 Order prev;! 2 for (int i = 0; i < X; ++i) {! Customer[] custs = new Customer[…]; 9 3 t.display();! 10 4 Order order = new Order(...);! 11 Order r = this.prev;! 5 t.process(order);! 12 … // display r! 13 this.prev = null; // remove! 6 }! void display() {! ! 14 } ! 21 class Customer {! 15 void process(Order p) {! 22 Order[] orders = new Order[…];! 16 this.prev = p;! 23 void addOrder(Order q) {! 17 Customer c = this.custs[…];! 18 c.addOrder(p);! 19 ... // process p! 24 25 this.orders[...] = q;! }! 26 }! store24/orders,  …,  store9/custs     Order4,i! 23   store16/prev   20 leaking   ! } }! Transaction1! ! non-­‐leaking  
  24. 24. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language   reachability  to  match  store/load  and  call/return   24  
  25. 25. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language   reachability  to  match  store/load  and  call/return   25  
  26. 26. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  cstore     ontext-­‐free  language   store     store     store   Order4! Order[]23! Customer?! Customer[]10! Transaction1! reachability  to  match  store/load  and  call/return   24 26   22 ? 9
  27. 27. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language   reachability  to  match  store/load  and  call/return   27  
  28. 28. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language   Transaction1 reachability  to  match  s! tore/load  aOrderall/return   nd  c 4,i-1! 28   load11/prev  
  29. 29. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language   reachability  to  match  store/load  and  call/return   29  
  30. 30. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language  bject   outside  o reachability  to  match  store/load  and  Transaction1! call/return   30  
  31. 31. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language  bject   outside  o reachability  to  match  store/load  and  Transaction1! call/return   Order4,i! 31   i-­‐th  itera,on  
  32. 32. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language  bject   outside  o reachability  to  match  store/load  and  Transaction1! call/return   Order4,i! 32   i-­‐th  itera,on   store16/prev  
  33. 33. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   •  On-­‐demand  analysis  using  context-­‐free  language  bject   (i+1)-­‐th  itera,on   load /prev   outside  o reachability  to  match  store/load  and  Transaction1! call/return   Order4,i! 11 33   i-­‐th  itera,on   store16/prev  
  34. 34. StaMc  Analysis  Outline   •  Object:  pair  of  allocaMon  site  and  calling  context   •  Flows-­‐out  path   –  Loop  object  escaping  to  outside  object   –  Sequence  of  store  statements  for  the  flow   •  Flows-­‐in  path   –  Escaping  object  flows  from  outside  object  into  the  loop   –  Sequence  of  load  statements  causing  the  flow   •  Loop  iteraMon  constraints   –  Flows-­‐in  valid  only  if  the  corresponding  Flows-­‐out  occurs  in   an  earlier  iteraMon   –  Captured  b analysis  u recency  abstracMon   ERA)   •  On-­‐demand  y  extended  sing  context-­‐free  l(anguage   reachability  to  match  store/load  and  call/return   34  
  35. 35. StaMc  Analysis  Outline  (cont.)   •  On-­‐demand  analysis   –  Detect  leaks  only  for  objects  allocated  in  specified  loops   –  Context-­‐free  language  reachability  to  match  relevant  store/ load  and  call/return   •  ConservaMve  handling  of  thread  lifeMme   –  Assume  the  lifeMme  of  each  thread  exceeds  the  loop  lifeMme   –  Capture  objects  leaking  to  long-­‐running  threads   35  
  36. 36. Analysis  ImplementaMon   •  Memory  leak   –  An  object  leaks  if  it  starts  a  flows-­‐out  path,  but  does  not  have   a  matching  flows-­‐in  path   •  ReporMng  leaks   –  Leaking  object,  with  calling  context  of  its  allocaMon   –  Outside  target  object,  with  calling  context  of  its  allocaMon   –  Escape-­‐causing  heap  write  (store)  statement,  with  its  calling   context   •  LeakChecker:  leak  detecMon  tool  built  using  Soot     36  
  37. 37. EvaluaMon   •  8  real-­‐world  Java  programs   –  Enterprise  trading,  so5ware  tools,  databases,  logging   –  3  programs  never  studied  by  exisMng  work   •  EffecMve  for  leak  detecMon?   –  LeakChecker  detected  both  known  and  new  leaks   •  Suitable  for  pracMcal  use?   –  Analysis  running  Mme  (all  <  35  mins)   –  Reasonable  false  posiMve  rate  (avg  <  50%)   •  Case  studies   37   –  Performed  to  understand  quality  of  leak  report   –  For  each  leak  defect,  pinpoint  root  cause  and  fix  the  problem   in  <  2  hours  
  38. 38. Eclipse  Diff   •  Scenario:  compare  two  large  JAR  files   –  runCompare  method  in  compare  plugin! –  An  arMficial  loop  to  invoke  runCompare  mulMple  Mmes   •  Loop  objects   –  Editor:  display  comparison  results   –  HistoryEntry:  represent  list  of  opened  editors,  and  allow   users  to  navigate  them  backward/forward   •  Outside  object   –  History:  managed  by  another  plugin  to  save  HistoryEntry     38   compare  plugin   !!!! Editor! loop  objects   history  plugin   HistoryEntry! History! outside  object  
  39. 39. Conclusions   •  LeakChecker  is  both  effecMve  and  pracMcal   •  Key  insights   –  Capture  common  paVerns  of  leaking  behavior   –  Focus  on  user-­‐specified  event  loops   –  Report  leaks  with  detailed  context  informaMon     39  
  40. 40. Thank    you   40  

×