Phase 14 of 20 · Topic 14.3

GC Root Tracing & Reachability States

1Concept

Java uses Root-Set Tracing to determine object liveness. An object is alive if it can be reached via a reference chain starting from a GC Root. GC Roots include: 1. Local variables in active thread stack frames; 2. Static class variables; 3. JNI native handles; 4. Active Thread objects.

2Architecture Diagram

[ GC Root: Thread Stack Local ]
       |
       v
  [ Object A ] ---> [ Object B ]  (Reachable: Survived GC!)

  [ Object C ] ---> [ Object D ]  (Unreachable from any GC Root: Cleaned up!)

3Code Example

Core Java
public class GcRootTracingDemo {
    static class CacheEntry {
        String key;
        CacheEntry(String key) { this.key = key; }
    }

    // Static field: Acts as a permanent GC Root until class unloaded!
    private static CacheEntry permanentRoot = new CacheEntry("PERMANENT_KEY");

    public static void main(String[] args) {
        // Local variable: GC Root while main() method frame is active
        CacheEntry localRoot = new CacheEntry("LOCAL_KEY");

        System.out.println("Permanent GC Root: " + permanentRoot.key);
        System.out.println("Local Stack GC Root: " + localRoot.key);

        localRoot = null; // Severed! Object becomes eligible for garbage collection
        System.out.println("Local object dereferenced and eligible for GC reclamation.");
    }
}

4Expected Output

Permanent GC Root: PERMANENT_KEY
Local Stack GC Root: LOCAL_KEY
Local object dereferenced and eligible for GC reclamation.

5Key Takeaways

  • Static collections (e.g. `static List<T>`) are common sources of memory leaks because they remain rooted forever.
  • WeakReference allows objects to be reclaimed even if referenced.
  • Live objects are promoted from Eden to Survivor, and eventually to Tenured Old Gen after reaching aging threshold.