JDK-6579224 : (coll) toString() on self-referential Checked collections causes stack overflow
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.util:collections
  • Affected Version: 7
  • Priority: P4
  • Status: Closed
  • Resolution: Won't Fix
  • OS: generic
  • CPU: generic
  • Submitted: 2007-07-11
  • Updated: 2012-10-08
  • Resolved: 2011-01-13
Related Reports
Relates :  
Relates :  
Description
Description:
   As per bug 4421469, toString() method was throwing StackOverFlowError with self-referential collections and was fixed. Now trying out a similar scenario with Collections.checkedMap and Collections.checkedList also ends up with StackOverFlowError. This should be fixed to maintain the consistency .Please find the testcase below:

<code>

import java.util.Collections;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;


public class SelfReferencetoString {
    
    public static void main( String[] args ) {
        
        try{
            // Map<String,Map> map1 = new HashMap<String,Map>();  //  Uncomment this and comment the next line-This will work,Already fixed
            Map<String,Map> map1 = Collections.checkedMap(new Hashtable<String,Map>(),String.class,Map.class);
            map1.put("first",map1);
            System.out.println("My Hashtable "+map1);
            System.out.println("TestCase1 Passed!");
        } catch(StackOverflowError ste){
            //  ste.printStackTrace();
            System.out.println("TestCase1 Failed with StackOverflowError!!!!");
        }
        
        
        try{
            // List<List> listOfLists = new LinkedList<List>();//  Uncomment this and comment the next line-This will work,Already fixed
            List<List> listOfLists = Collections.checkedList(new LinkedList<List>(),List.class);
            listOfLists.add(listOfLists);
            System.out.println("My LinkedList "+ listOfLists);
            System.out.println("TestCase2 Passed!");
        } catch(StackOverflowError ste){
            //  ste.printStackTrace();
            System.out.println("TestCase2 Failed with StackOverflowError!!!!");
        }
        
    }           
}


</code>
<output>
	TestCase1 Failed with StackOverflowError!!!!
	TestCase2 Failed with StackOverflowError!!!!

</output>

Tried in :
<version>
bash-3.00$ java -version
java version "1.7.0-ea"
Java(TM) SE Runtime Environment (build 1.7.0-ea-b14)
Java HotSpot(TM) Client VM (build 1.7.0-ea-b14, mixed mode)

bash-3.00$ uname -a
SunOS hrajan 5.10 Generic sun4u sparc SUNW,Sun-Blade-100
</version>

Comments
EVALUATION This is a general case of self-referential collections. The past decision (4421469) has been to not try to address the general problem.
13-01-2011

EVALUATION In the general case, defining recursive data structures will cause infinite loops in toString and similar methods. It is possible, but difficult and expensive to prevent all such infinite loops - all potentially recursive methods would have to keep track of objects seen along the way. Probably we will not be able to fix this in the general case. Some fixes for very special cases might make sense. As Josh said in the original CR, ----- The general problem (comparison, hashing and printing of self-referential collections) is not solvable, but this special case is. I think that it would be worthwhile for the toString method in AbstactMap and AbstractSet to look for simple self-reference, substitute the string "(this collection)" or "(this map)" for the recursive invocation. To reiterate, this would not solve the general problem! But it would catch the simplest possible case of self-reference, and could aid substanbtially in debugging. ------ Probably we should close as Will Not Fix.
11-07-2007