< prev index next >

src/jdk.hotspot.agent/share/classes/sun/jvm/hotspot/utilities/ObjectReader.java

Print this page




   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 package sun.jvm.hotspot.utilities;
  26 
  27 import java.lang.reflect.Modifier;
  28 import java.util.*;

  29 import sun.jvm.hotspot.debugger.*;
  30 import sun.jvm.hotspot.oops.*;
  31 import sun.jvm.hotspot.runtime.*;
  32 import sun.jvm.hotspot.utilities.*;
  33 
  34 /**
  35  * ObjectReader can "deserialize" objects from debuggee.
  36  *
  37  * Class Loading:
  38  *
  39  * ObjectReader loads classes using the given class loader. If no
  40  * class loader is supplied, it uses a ProcImageClassLoader, which
  41  * loads classes from debuggee core or process.
  42 
  43  * Object creation:
  44  *
  45  * This class uses no-arg constructor to construct objects. But if
  46  * there is no no-arg constructor in a given class, then it tries to
  47  * use other constructors with 'default' values - null for object
  48  * types, 0, 0.0, false etc. for primitives.  If this process fails to


 187       Object value = null;
 188       Oop next = null;
 189       try {
 190          key = readObject(keyField.getValue(oop));
 191          value = readObject(valueField.getValue(oop));
 192          next =  (Oop)nextField.getValue(oop);
 193          // For Properties, should use setProperty(k, v). Since it only runs in SA
 194          // using put(k, v) should be OK.
 195          p.put(key, value);
 196          if (next != null) {
 197             setHashtableEntry(p, next);
 198          }
 199       } catch (ClassNotFoundException ce) {
 200          if( DEBUG) {
 201             debugPrintln("Class not found " + ce);
 202             debugPrintStackTrace(ce);
 203          }
 204       }
 205    }
 206 
 207    protected Object getHashtable(Instance oop, boolean isProperties) {















 208       InstanceKlass k = (InstanceKlass)oop.getKlass();
 209       OopField tableField = (OopField)k.findField("table", "[Ljava/util/Hashtable$Entry;");
 210       if (tableField == null) {
 211          debugPrintln("Could not find field of [Ljava/util/Hashtable$Entry;");
 212          return null;
 213       }
 214       java.util.Hashtable table = (isProperties) ? new java.util.Properties()
 215                                                  : new java.util.Hashtable();
 216       ObjArray kvs = (ObjArray)tableField.getValue(oop);
 217       long size = kvs.getLength();
 218       debugPrintln("Hashtable$Entry Size = " + size);
 219       for (long i=0; i<size; i++) {
 220          Oop entry = kvs.getObjAt(i);
 221          if (entry != null && entry.isInstance()) {
 222             setHashtableEntry(table, entry);
 223          }
 224       }
 225       return table;
 226    }
 227 

































 228    public Object readInstance(Instance oop) throws ClassNotFoundException {
 229       Object result = getFromObjTable(oop);
 230       if (result == null) {
 231          InstanceKlass kls = (InstanceKlass) oop.getKlass();
 232          // Handle java.lang.String instances differently. As part of JSR-133, fields of immutable
 233          // classes have been made final. The algorithm below will not be able to read Strings from
 234          // debuggee (can't use reflection to set final fields). But, need to read Strings is very
 235          // important.
 236          // Same for Hashtable, key and hash are final, could not be set in the algorithm too.
 237          // FIXME: need a framework to handle many other special cases.
 238          if (kls.getName().equals(javaLangString())) {
 239             return OopUtilities.stringOopToString(oop);
 240          }
 241 
 242          if (kls.getName().equals(javaUtilHashtable())) {
 243             return getHashtable(oop, false);
 244          }
 245 
 246          if (kls.getName().equals(javaUtilProperties())) {
 247             return getHashtable(oop, true);
 248          }
 249 
 250          Class clz = readClass(kls);
 251          try {
 252             result = clz.newInstance();
 253          } catch (Exception ex) {
 254             // no-arg constructor failed to create object. Let us try
 255             // to call constructors one-by-one with default arguments
 256             // (null for objects, 0/0.0 etc. for primitives) till we
 257             // succeed or fail on all constructors.
 258 
 259             java.lang.reflect.Constructor[] ctrs = clz.getDeclaredConstructors();
 260             for (int n = 0; n < ctrs.length; n++) {
 261                java.lang.reflect.Constructor c = ctrs[n];
 262                Class[] paramTypes = c.getParameterTypes();
 263                Object[] params = new Object[paramTypes.length];
 264                for (int i = 0; i < params.length; i++) {
 265                   if (paramTypes[i].isPrimitive()) {
 266                      params[i] = getDefaultPrimitiveValue(paramTypes[i]);
 267                   }




   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 package sun.jvm.hotspot.utilities;
  26 
  27 import java.lang.reflect.Modifier;
  28 import java.util.*;
  29 import java.util.stream.*;
  30 import sun.jvm.hotspot.debugger.*;
  31 import sun.jvm.hotspot.oops.*;
  32 import sun.jvm.hotspot.runtime.*;
  33 import sun.jvm.hotspot.utilities.*;
  34 
  35 /**
  36  * ObjectReader can "deserialize" objects from debuggee.
  37  *
  38  * Class Loading:
  39  *
  40  * ObjectReader loads classes using the given class loader. If no
  41  * class loader is supplied, it uses a ProcImageClassLoader, which
  42  * loads classes from debuggee core or process.
  43 
  44  * Object creation:
  45  *
  46  * This class uses no-arg constructor to construct objects. But if
  47  * there is no no-arg constructor in a given class, then it tries to
  48  * use other constructors with 'default' values - null for object
  49  * types, 0, 0.0, false etc. for primitives.  If this process fails to


 188       Object value = null;
 189       Oop next = null;
 190       try {
 191          key = readObject(keyField.getValue(oop));
 192          value = readObject(valueField.getValue(oop));
 193          next =  (Oop)nextField.getValue(oop);
 194          // For Properties, should use setProperty(k, v). Since it only runs in SA
 195          // using put(k, v) should be OK.
 196          p.put(key, value);
 197          if (next != null) {
 198             setHashtableEntry(p, next);
 199          }
 200       } catch (ClassNotFoundException ce) {
 201          if( DEBUG) {
 202             debugPrintln("Class not found " + ce);
 203             debugPrintStackTrace(ce);
 204          }
 205       }
 206    }
 207 
 208    private void setPropertiesEntry(java.util.Properties p, Oop oop) {
 209       InstanceKlass ik = (InstanceKlass)oop.getKlass();
 210       OopField keyField = (OopField)ik.findField("key", "Ljava/lang/Object;");
 211       OopField valueField = (OopField)ik.findField("val", "Ljava/lang/Object;");
 212 
 213       try {
 214          p.setProperty((String)readObject(keyField.getValue(oop)),
 215                        (String)readObject(valueField.getValue(oop)));
 216       } catch (ClassNotFoundException ce) {
 217          if (DEBUG) {
 218             debugPrintStackTrace(ce);
 219          }
 220       }
 221    }
 222 
 223    protected Object getHashtable(Instance oop) {
 224       InstanceKlass k = (InstanceKlass)oop.getKlass();
 225       OopField tableField = (OopField)k.findField("table", "[Ljava/util/Hashtable$Entry;");
 226       if (tableField == null) {
 227          debugPrintln("Could not find field of [Ljava/util/Hashtable$Entry;");
 228          return null;
 229       }
 230       java.util.Hashtable table = new java.util.Hashtable();

 231       ObjArray kvs = (ObjArray)tableField.getValue(oop);
 232       long size = kvs.getLength();
 233       debugPrintln("Hashtable$Entry Size = " + size);
 234       for (long i=0; i<size; i++) {
 235          Oop entry = kvs.getObjAt(i);
 236          if (entry != null && entry.isInstance()) {
 237             setHashtableEntry(table, entry);
 238          }
 239       }
 240       return table;
 241    }
 242 
 243    private Properties getProperties(Instance oop) {
 244       InstanceKlass k = (InstanceKlass)oop.getKlass();
 245       OopField mapField = (OopField)k.findField("map", "Ljava/util/concurrent/ConcurrentHashMap;");
 246       if (mapField == null) {
 247          debugPrintln("Could not find field of Ljava/util/concurrent/ConcurrentHashMap");
 248          return null;
 249       }
 250 
 251       Instance mapObj = (Instance)mapField.getValue(oop);
 252       if (mapObj == null) {
 253          debugPrintln("Could not get map field from java.util.Properties");
 254          return null;
 255       }
 256 
 257       InstanceKlass mk = (InstanceKlass)mapObj.getKlass();
 258       OopField tableField = (OopField)mk.findField("table", "[Ljava/util/concurrent/ConcurrentHashMap$Node;");
 259       if (tableField == null) {
 260          debugPrintln("Could not find field of [Ljava/util/concurrent/ConcurrentHashMap$Node");
 261          return null;
 262       }
 263 
 264       java.util.Properties props = new java.util.Properties();
 265       ObjArray kvs = (ObjArray)tableField.getValue(mapObj);
 266       long size = kvs.getLength();
 267       debugPrintln("ConcurrentHashMap$Node Size = " + size);
 268       LongStream.range(0, size)
 269                 .mapToObj(kvs::getObjAt)
 270                 .filter(o -> o != null)
 271                 .forEach(o -> setPropertiesEntry(props, o));
 272 
 273       return props;
 274    }
 275 
 276    public Object readInstance(Instance oop) throws ClassNotFoundException {
 277       Object result = getFromObjTable(oop);
 278       if (result == null) {
 279          InstanceKlass kls = (InstanceKlass) oop.getKlass();
 280          // Handle java.lang.String instances differently. As part of JSR-133, fields of immutable
 281          // classes have been made final. The algorithm below will not be able to read Strings from
 282          // debuggee (can't use reflection to set final fields). But, need to read Strings is very
 283          // important.
 284          // Same for Hashtable, key and hash are final, could not be set in the algorithm too.
 285          // FIXME: need a framework to handle many other special cases.
 286          if (kls.getName().equals(javaLangString())) {
 287             return OopUtilities.stringOopToString(oop);
 288          }
 289 
 290          if (kls.getName().equals(javaUtilHashtable())) {
 291             return getHashtable(oop);
 292          }
 293 
 294          if (kls.getName().equals(javaUtilProperties())) {
 295             return getProperties(oop);
 296          }
 297 
 298          Class clz = readClass(kls);
 299          try {
 300             result = clz.newInstance();
 301          } catch (Exception ex) {
 302             // no-arg constructor failed to create object. Let us try
 303             // to call constructors one-by-one with default arguments
 304             // (null for objects, 0/0.0 etc. for primitives) till we
 305             // succeed or fail on all constructors.
 306 
 307             java.lang.reflect.Constructor[] ctrs = clz.getDeclaredConstructors();
 308             for (int n = 0; n < ctrs.length; n++) {
 309                java.lang.reflect.Constructor c = ctrs[n];
 310                Class[] paramTypes = c.getParameterTypes();
 311                Object[] params = new Object[paramTypes.length];
 312                for (int i = 0; i < params.length; i++) {
 313                   if (paramTypes[i].isPrimitive()) {
 314                      params[i] = getDefaultPrimitiveValue(paramTypes[i]);
 315                   }


< prev index next >