Java Solaris Communities Sun Store Join SDN My Profile Why Join?
 
Bug Database
Bug Detail
Quick Lists
Top 25 Bugs
Top 25 RFE's
Recently Closed Bugs
Printable Page Printable Page


Bug Database
Bug ID: 4257720
Votes 10
Synopsis Swing styled text application using excessive memory
Category java:classes_swing
Reported Against 1.2.2
Release Fixed 1.4(merlin-beta)
State 10-Fix Delivered, bug
Priority: 3-Medium
Related Bugs 4203912
Submit Date 28-JUL-1999
Description
When using the Swing demo application Stylepad (as a reproducable test case) you can observe excessive memory usage, making the application not viable as a release product.  Reproduce by the following:
(NT 4 SP4, JDK 1.2.2 FCS)
i) open task manager
ii) run Stylepad application
 customer ) cut all of alice text out 
iv) copy some 96k text from ie. Notepad
v) paste using menu 

You can see that over 20MB is taken up by this procedure and it is linear upon pasting greater text sizes.

I believe this to be associated with bug : 4203912.
Work Around
N/A
Evaluation
Using OptimizeIt to analyze the memory consumption of models and views
produced by StyledEditorKit (which Stylepad uses) show that about 13%
of the memory consumed is from the model and the other 87% is the view.
Switching to use ZoneView to hold the paragraphs would bring the consumption
for views to a constant amount of something just a little over what the
model consumes (13% in the analysis performed).  Using weak references and
sharing position objects that point to the same location could further reduce
the consumption of the model.  It also looks like there might be a leak in
GapContent.

The StyledEditorKit now uses ZoneView which has been substantially improved
to the point that it is believed to be a reasonable replacement.  The test 
below was used to measure the heap before and after which is not an accurate
measurement (i.e. the acutal consumption would be less), but it does give
an approximation.  

A 1Mb file was used for the test.  

  The kestrel version loaded in 47 sec and reported 42Mb
  The post-fix version loaded in 5.8 sec and reported 12Mb

The test used was:

import java.io.*;
import java.awt.*;

import javax.swing.*;

public class StyleTest {

    public static void main(String[] args) {
	try {
	    // initialize a JEditorPane and prepare to load it using
	    // setText() which will run synchronously.
	    JEditorPane testPane = new JTextPane();
	    JScrollPane scroller = new JScrollPane();
	    JViewport vp = scroller.getViewport();
	    vp.add(testPane);
	    vp.setBackingStoreEnabled(true);

	    JFrame frame = new JFrame();
	    frame.setTitle("JEditorPane test of text/styled");
	    frame.setBackground(Color.lightGray);
	    frame.getContentPane().setLayout(new BorderLayout());
	    frame.getContentPane().add("Center", scroller);
	    frame.pack();
	    frame.setSize(600, 480);
	    frame.show();

	    // String text = readFile();
	    long startingMemoryUse = getUsedMemory();
	    System.err.println("starting test");
	    long startTime = System.currentTimeMillis();
	    
	    FileReader fr = new FileReader("large.txt");
	    testPane.read(fr, null);
	    // testPane.setText(text);

	    long endTime = System.currentTimeMillis();
	    System.err.println("test done");
	    long endingMemoryUse = getUsedMemory();
	    float approxSize = (endingMemoryUse - startingMemoryUse);
	    System.err.println("loaded in: " + (endTime - startTime) + " ms");
	    System.err.println("heap difference: " + approxSize);
	} catch (Throwable e) {
	    e.printStackTrace();
	    System.exit(1);
	} 
	System.exit(0);
    }

    private static String readFile() throws FileNotFoundException {
	System.out.println("creating 1Mb string");
	File f = new File("large.txt");
	FileReader fr = new FileReader(f);
	StringBuffer r = new StringBuffer("");;
        char[] buff = new char[4096];
        int nch;
	try {
	    while ((nch = fr.read(buff, 0, buff.length)) != -1) {
		r.append(buff);
	    }
	} catch(IOException e) {
	    e.printStackTrace();
	    System.exit(1);
	}
	System.out.println("done creating 1Mb string");
	return r.toString();
    }

   private static long getUsedMemory() {
      gc();
      long totalMemory = Runtime.getRuntime().totalMemory();
      gc();
      long freeMemory = Runtime.getRuntime().freeMemory();
      long usedMemory = totalMemory - freeMemory;
      return usedMemory;
   }

   private static void gc() {
      try {
         System.gc();
         Thread.currentThread().sleep(100);
         System.runFinalization();
         Thread.currentThread().sleep(100);
         System.gc();
         Thread.currentThread().sleep(100);      
         System.runFinalization();
         Thread.currentThread().sleep(100);
      } catch (Exception e) {
         e.printStackTrace();
      }

   }

}

  xxxxx@xxxxx   2000-03-17
Comments
  
  Include a link with my name & email   


PLEASE NOTE: JDK6 is formerly known as Project Mustang