1 /*
   2  * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 
  27 /*
  28  * The Original Code is HAT. The Initial Developer of the
  29  * Original Code is Bill Foote, with contributions from others
  30  * at JavaSoft/Sun.
  31  */
  32 
  33 package com.sun.tools.hat.internal.server;
  34 
  35 import com.sun.tools.hat.internal.model.*;
  36 import java.util.*;
  37 
  38 /**
  39  * References by type summary
  40  *
  41  */
  42 public class RefsByTypeQuery extends QueryHandler {
  43     public void run() {
  44         JavaClass clazz = snapshot.findClass(query);
  45         if (clazz == null) {
  46             error("class not found: " + query);
  47         } else {
  48             Map<JavaClass, Long> referrersStat = new HashMap<JavaClass, Long>();
  49             final Map<JavaClass, Long> refereesStat = new HashMap<JavaClass, Long>();
  50             Enumeration instances = clazz.getInstances(false);
  51             while (instances.hasMoreElements()) {
  52                 JavaHeapObject instance = (JavaHeapObject) instances.nextElement();
  53                 if (instance.getId() == -1) {
  54                     continue;
  55                 }
  56                 Enumeration e = instance.getReferers();
  57                 while (e.hasMoreElements()) {
  58                     JavaHeapObject ref = (JavaHeapObject) e.nextElement();
  59                     JavaClass cl = ref.getClazz();
  60                     if (cl == null) {
  61                          System.out.println("null class for " + ref);
  62                          continue;
  63                     }
  64                     Long count = referrersStat.get(cl);
  65                     if (count == null) {
  66                         count = new Long(1);
  67                     } else {
  68                         count = new Long(count.longValue() + 1);
  69                     }
  70                     referrersStat.put(cl, count);
  71                 }
  72                 instance.visitReferencedObjects(
  73                     new AbstractJavaHeapObjectVisitor() {
  74                         public void visit(JavaHeapObject obj) {
  75                             JavaClass cl = obj.getClazz();
  76                             Long count = refereesStat.get(cl);
  77                             if (count == null) {
  78                                 count = new Long(1);
  79                             } else {
  80                                 count = new Long(count.longValue() + 1);
  81                             }
  82                             refereesStat.put(cl, count);
  83                         }
  84                     }
  85                 );
  86             } // for each instance
  87 
  88             startHtml("References by Type");
  89             out.println("<p align='center'>");
  90             printClass(clazz);
  91             if (clazz.getId() != -1) {
  92                 println("[" + clazz.getIdString() + "]");
  93             }
  94             out.println("</p>");
  95 
  96             if (referrersStat.size() != 0) {
  97                 out.println("<h3 align='center'>Referrers by Type</h3>");
  98                 print(referrersStat);
  99             }
 100 
 101             if (refereesStat.size() != 0) {
 102                 out.println("<h3 align='center'>Referees by Type</h3>");
 103                 print(refereesStat);
 104             }
 105 
 106             endHtml();
 107         }  // clazz != null
 108     } // run
 109 
 110     private void print(final Map<JavaClass, Long> map) {
 111         out.println("<table border='1' align='center'>");
 112         Set<JavaClass> keys = map.keySet();
 113         JavaClass[] classes = new JavaClass[keys.size()];
 114         keys.toArray(classes);
 115         Arrays.sort(classes, new Comparator<JavaClass>() {
 116             public int compare(JavaClass first, JavaClass second) {
 117                 Long count1 = map.get(first);
 118                 Long count2 = map.get(second);
 119                 return count2.compareTo(count1);
 120             }
 121         });
 122 
 123         out.println("<tr><th>Class</th><th>Count</th></tr>");
 124         for (int i = 0; i < classes.length; i++) {
 125             JavaClass clazz = classes[i];
 126             out.println("<tr><td>");
 127             out.print("<a href='/refsByType/");
 128             print(clazz.getIdString());
 129             out.print("'>");
 130             print(clazz.getName());
 131             out.println("</a>");
 132             out.println("</td><td>");
 133             out.println(map.get(clazz));
 134             out.println("</td></tr>");
 135         }
 136         out.println("</table>");
 137     }
 138 }