Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-5002069

Swing automatically consumes 40 Kb of memory as font strings

XMLWordPrintable

    • 2d
    • b03
    • x86
    • linux
    • Verified

      Name: jl125535 Date: 02/24/2004


      FULL PRODUCT VERSION :
      java version "1.5.0-beta"
      Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0-beta-b32c)
      Java HotSpot(TM) Client VM (build 1.5.0-beta-b32c, mixed mode)

      java version "1.4.2_03"
      Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_03-b02)
      Java HotSpot(TM) Client VM (build 1.4.2_03-b02, mixed mode)


      ADDITIONAL OS VERSION INFORMATION :
      Linux ghoul 2.6.2-1-k7 #1 Sat Feb 7 17:02:15 EST 2004 i686 GNU/Linux
      Debian/unstable.

      A DESCRIPTION OF THE PROBLEM :
      When swing (and maybe awt) is used, a lot of strings in memory are font names.

      For a big application this is not a big problem (~40kB data is not very
      much). For a small application that does not do any drawing, storing this
      information is quite unneccessary and makes the memory usage bigger than
      needed.


      STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
      Create a small program that opens a single jframe will cause high memory usage.
      Source for such a program is in this bug report.

      Run that program in a debugger that can inspect the strings that are used. I use jmp, it is available from http://www.khelekore.org/jmp/

      Start the profiling session:
      java -Xrunjmp:nomethods,nomonitors,noobjects JFrameTest

      Call garbage collect (using the jvmpi to force collection) .
      Enable object profiling
      Bring up a window with all strings and check what strings there are in memory.
      Dump strings to file for more inspection later on.


      EXPECTED VERSUS ACTUAL BEHAVIOR :
      EXPECTED -
      Lower memory usage. Why are font names kept around when they are unused and available on request from the window system. Most of the fonts will never be used so why keep the names?

      ACTUAL -
      High memory usage.

      In the files with all strings that could not be garbage collected there are lots of strings on the format: "/home/robo/pkg/java/j2sdk1.5.0-beta/jre/lib/fonts/LucidaSansRegular.ttf " and
      "-b&h-lucidatypewriter-medium-r-normal-sans-*-%d-*-*-m-*-iso8859-1". Some of the strings exists several times (_note_: not String objects, but distinct char[]).

      There are also a lot of minor variations in the font names:
      "LucidaSansDemiOblique.ttf -b&h-lucidasans-bold-i-normal-sans-0-0-0-0-p-0-iso8859-1" and
      "LucidaSansDemiOblique.ttf -b&h-lucidasans-bold-i-normal-sans-0-0-0-0-p-0-iso8859-2" differ only in the last character.

      For 1.4.2_03, Top reports the memory usage as this:
       1449 robo 25 0 212m 16m 44m S 0.0 3.3 0:00.31
      java

      /proc/1449/status gives this (and some more:
      FDSize: 256
      Groups: 1000 24 29 44
      VmSize: 218084 kB
      VmLck: 0 kB
      VmRSS: 16788 kB
      VmData: 172420 kB
      VmStk: 44 kB
      VmExe: 24 kB
      VmLib: 11460 kB
      Threads: 12


      For 1.5.0-beta, Top reports this:
      1511 robo 16 0 254m 18m 66m S 0.0 3.6 0:00.17 java

      and /proc/1551/status give this:
      Groups: 1000 24 29 44
      VmSize: 260236 kB
      VmLck: 0 kB
      VmRSS: 18864 kB
      VmData: 190020 kB
      VmStk: 2036 kB
      VmExe: 56 kB
      VmLib: 8380 kB
      Threads: 12

      1.5-beta seems to use slightly more memory.

      When profiling there are no big differences between 1.4.2 and 1.5-beta,
      1.5-beta starts up with a little less used heap. The discussion from
      now on is based on 1.5, but 1.4 seems to use about the same resources
      for fonts.

      Jvmpi reports that 1.5-beta uses ~1781740 bytes of memory at startup
      it keeps fluctuating due to the fact that sun.awt.X11.XToolkit calls
      dispatchEvent (sun.awt.X11.XAnyEvent) and allocates a few objects
      continously (every few seconds).

      Forcing garbage collection with the jvmpi-function brings the java heap
      down to 373344 bytes.

      In the heap there are 618 java.lang.String objects and 551 char[]
      The String occupies 14832 bytes and the char[] 87808 bytes (27%
      of the java heap).

      If I have counted correctly there are 268 char[] that hold font
      names (I may have missed a few). I guess that the number depends
      on the available fonts on the system so it could vary quite much.

      Both of these char[] have many characters, according to gnumeric it seems
      to be 28188 bytes used for the char[].

      There are 2 types of string, file names for true type fonts
      /home/robo/pkg/java/j2sdk1.5.0-beta/jre/lib/fonts/LucidaTypewriterBoldOblique.ttf
      and font names.
      -b&h-lucidatypewriter-medium-i-normal-sans-*-%d-*-*-m-*-iso8859-1

      I can send you a full list of the char[] data if you want to.

      I have not had the time to trace the Strings very much, Most are held my
      HashMap$Entry, Hashtable$Entry or Object[]. 40 Strings seems to be keept
      by sun.font.CompositeFont, 12 by sun.font.FontManager$FontRegistrationInfo.


      REPRODUCIBILITY :
      This bug can be reproduced always.

      ---------- BEGIN SOURCE ----------
      import javax.swing.*;

      public class JFrameTest {
          public static void main (String[] args) {
      JFrame jf = new JFrame ();
      jf.setDefaultCloseOperation (JFrame.EXIT_ON_CLOSE);
      jf.setSize (300, 300);
      jf.setVisible (true);
          }
      }

      ---------- END SOURCE ----------
      (Incident Review ID: 239765)
      ======================================================================

            prr Philip Race
            jleesunw Jon Lee (Inactive)
            Votes:
            0 Vote for this issue
            Watchers:
            0 Start watching this issue

              Created:
              Updated:
              Resolved:
              Imported:
              Indexed: