Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Comment: Edited by sciSpider Java v3.0

...

  • Wiki Markup
    According to the Java Language Specification \[[JLS 05|AA. Java References#JLS 05]\] Section 12.6.2 ""Finalizer Invocations are Not Ordered"":

    Wiki Markup
    The Java programming language imposes no ordering on {{finalize}} method calls. Finalizers \[of different objects\] may be called in any order, or even concurrently.

    This can be a problem as slow running finalizers tend to block others in the queue.

...

Code Block
bgColor#FFcccc
class BaseClass {
  protected void finalize() throws Throwable {
    System.out.println(""Superclass finalize!"");
    doLogic();
  }

  public void doLogic() throws Throwable {
    System.out.println(""This is super-class!"");
  }
}

class SubClass extends BaseClass {
  private Date d; // mutable instance field

  protected SubClass() {
    d = new Date();
  }

  protected void finalize() throws Throwable {
    System.out.println(""Subclass finalize!"");
    try {
      //  cleanup resources 
      d = null;				
    } finally {
      super.finalize();  // Call BaseClass's finalizer
    }
  }
	
  public void doLogic() throws Throwable{
    // any resource allocations made here will persist 

    // inconsistent object state
    System.out.println(""This is sub-class! The date object is: "" + d);  // 'd' is already null
  }
}

public class BadUse {
  public static void main(String[] args) {
    try {
      BaseClass bc = new SubClass();
      // Artificially simulate finalization (do not do this)
      System.runFinalizersOnExit(true); 
    } catch (Throwable t) { 
      // Handle error 
    }  		
  }
}

...

Code Block
bgColor#ccccff
class BaseClass {
  protected void finalize() throws Throwable {
    System.out.println(""superclass finalize!"");
    // Eliminate the call to the overridden doLogic().
  }
  ...
}

...

Wiki Markup
Alternatively, a more expensive solution is to declare an anonymous class so that the {{finalize()}} method is guaranteed to run for the superclass. This solution is applicable to {{public}} non-final classes. ""The finalizer guardian object forces {{super.finalize}} to be called if a subclass overrides {{finalize()}} and does not explicitly call {{super.finalize}}"". \[[JLS 05|AA. Java References#JLS 05]\] 

...

Search for vulnerabilities resulting from the violation of this rule on the CERT website.

References

Wiki Markup
\[[JLS 05|AA. Java References#JLS 05]\] Section 12.6, Finalization of Class Instances
\[[API 06|AA. Java References#API 06]\] [finalize()|http://java.sun.com/j2se/1.4.2/docs/api/java/lang/Object.html#finalize()]
\[[Bloch 08|AA. Java References#Bloch 08]\] Item 7, Avoid finalizers 
\[[Darwin 04|AA. Java References#Darwin 04]\] Section 9.5, The Finalize Method
\[[Flanagan 05|AA. Java References#Flanagan 05]\] Section 3.3, Destroying and Finalizing Objects
\[[Coomes 07|AA. Java References#Coomes 07]\] "Sneaky""Sneaky" Memory Retention
\[[Boehm 05|AA. Java References#Boehm 05]\] 
\[[MITRE 09|AA. Java References#MITRE 09]\] [CWE ID 586|http://cwe.mitre.org/data/definitions/586.html] ""Explicit Call to Finalize()"", [CWE ID 583|http://cwe.mitre.org/data/definitions/583.html] ""finalize() Method Declared Public"", [CWE ID 568|http://cwe.mitre.org/data/definitions/568.html] ""finalize() Method Without super.finalize()""

...

OBJ01-J. Understand how a superclass can affect a subclass            08. Object Orientation (OBJ)            OBJ03-J. Be aware that a final reference may not always refer to immutable data