0
|
1 /*
|
|
2 * Copyright 2004-2005 Sun Microsystems, Inc. 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.
|
|
8 *
|
|
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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
|
|
20 * CA 95054 USA or visit www.sun.com if you need additional information or
|
|
21 * have any questions.
|
|
22 *
|
|
23 */
|
|
24
|
|
25 package sun.jvm.hotspot.ui.tree;
|
|
26
|
|
27 import java.util.*;
|
|
28 import sun.jvm.hotspot.oops.FieldIdentifier;
|
|
29 import sun.jvm.hotspot.oops.Oop;
|
|
30 import sun.jvm.hotspot.oops.UnknownOopException;
|
|
31 import sun.jvm.hotspot.debugger.*;
|
|
32 import sun.jvm.hotspot.runtime.*;
|
|
33 import sun.jvm.hotspot.types.*;
|
|
34 import sun.jvm.hotspot.utilities.CStringUtilities;
|
|
35
|
|
36 /** Encapsulates an arbitrary type value in a tree handled by SimpleTreeModel */
|
|
37
|
|
38 public class CTypeTreeNodeAdapter extends FieldTreeNodeAdapter {
|
|
39 final private Address addr;
|
|
40 final private Type type;
|
|
41 private CTypeFieldIdentifier[] fields = null;
|
|
42
|
|
43 private void collectFields(Type type, ArrayList list, boolean statics, boolean recurse) {
|
|
44 Type supertype = type.getSuperclass();
|
|
45 if (supertype != null && recurse) {
|
|
46 collectFields(supertype, list, statics, recurse);
|
|
47 }
|
|
48 Iterator i = type.getFields();
|
|
49 while (i.hasNext()) {
|
|
50 Field f = (Field) i.next();
|
|
51 if (f.isStatic() == statics) {
|
|
52 list.add(new CTypeFieldIdentifier(type, f));
|
|
53 }
|
|
54 }
|
|
55 }
|
|
56
|
|
57
|
|
58 private CTypeFieldIdentifier[] getFields() {
|
|
59 if (fields == null) {
|
|
60 ArrayList f = new ArrayList();
|
|
61 collectFields(type, f, false, true);
|
|
62 fields = (CTypeFieldIdentifier[]) f.toArray(new CTypeFieldIdentifier[0]);
|
|
63 }
|
|
64 return fields;
|
|
65 }
|
|
66
|
|
67 static class CTypeFieldIdentifier extends FieldIdentifier {
|
|
68 final private Field field;
|
|
69 final private Type holder;
|
|
70
|
|
71 CTypeFieldIdentifier(Type t, Field f) {
|
|
72 holder = t;
|
|
73 field = f;
|
|
74 }
|
|
75
|
|
76 public Field getField() {
|
|
77 return field;
|
|
78 }
|
|
79
|
|
80 public String getName() {
|
|
81 return field.getType().getName() + " " + holder.getName() + "::" + field.getName();
|
|
82 }
|
|
83 }
|
|
84
|
|
85
|
|
86 public CTypeTreeNodeAdapter(Address a, Type t, FieldIdentifier id) {
|
|
87 this(a, t, id, false);
|
|
88 }
|
|
89
|
|
90 public CTypeTreeNodeAdapter(Address a, Type t, FieldIdentifier id, boolean treeTableMode) {
|
|
91 super(id, treeTableMode);
|
|
92 type = t;
|
|
93 addr = a;
|
|
94 }
|
|
95
|
|
96 public CTypeTreeNodeAdapter(Type t) {
|
|
97 super(null, false);
|
|
98 type = t;
|
|
99 addr = null;
|
|
100 ArrayList statics = new ArrayList();
|
|
101 collectFields(type, statics, true, false);
|
|
102 fields = (CTypeFieldIdentifier[])statics.toArray(new CTypeFieldIdentifier[0]);
|
|
103 }
|
|
104
|
|
105 public CTypeTreeNodeAdapter(Iterator types) {
|
|
106 super(null, false);
|
|
107 addr = null;
|
|
108 type = null;
|
|
109 ArrayList statics = new ArrayList();
|
|
110 while (types.hasNext()) {
|
|
111 collectFields((Type)types.next(), statics, true, false);
|
|
112 }
|
|
113 fields = (CTypeFieldIdentifier[])statics.toArray(new CTypeFieldIdentifier[0]);
|
|
114 }
|
|
115
|
|
116 public int getChildCount() {
|
|
117 return getFields().length;
|
|
118 }
|
|
119
|
|
120 public SimpleTreeNode getChild(int index) {
|
|
121 CTypeFieldIdentifier cf = getFields()[index];
|
|
122 Field f = cf.getField();
|
|
123 Type t = f.getType();
|
|
124 try {
|
|
125 if (t.isOopType()) {
|
|
126 OopHandle handle;
|
|
127 if (f.isStatic()) {
|
|
128 handle = f.getOopHandle();
|
|
129 } else {
|
|
130 handle = f.getOopHandle(addr);
|
|
131 }
|
|
132 try {
|
|
133 Oop oop = VM.getVM().getObjectHeap().newOop(handle);
|
|
134 return new OopTreeNodeAdapter(oop, cf, getTreeTableMode());
|
|
135 } catch (AddressException e) {
|
|
136 return new BadOopTreeNodeAdapter(handle,
|
|
137 new CTypeFieldIdentifier(type, f),
|
|
138 getTreeTableMode());
|
|
139 } catch (UnknownOopException e) {
|
|
140 return new BadOopTreeNodeAdapter(handle,
|
|
141 new CTypeFieldIdentifier(type, f),
|
|
142 getTreeTableMode());
|
|
143 }
|
|
144 } else if (t.isCIntegerType()) {
|
|
145 long value = 0;
|
|
146 if (f.isStatic()) {
|
|
147 value = f.getCInteger((CIntegerType)t);
|
|
148 } else {
|
|
149 value = f.getCInteger(addr, (CIntegerType)t);
|
|
150 }
|
|
151 return new LongTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
152 } else if (t.isJavaPrimitiveType()) {
|
|
153 boolean isStatic = f.isStatic();
|
|
154 if (f instanceof JByteField) {
|
|
155 long value = isStatic? f.getJByte() : f.getJByte(addr);
|
|
156 return new LongTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
157 } else if (f instanceof JShortField) {
|
|
158 long value = isStatic? f.getJShort() : f.getJShort(addr);
|
|
159 return new LongTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
160 } else if (f instanceof JIntField) {
|
|
161 long value = isStatic? f.getJInt() : f.getJInt(addr);
|
|
162 return new LongTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
163 } else if (f instanceof JLongField) {
|
|
164 long value = isStatic? f.getJLong() : f.getJLong(addr);
|
|
165 return new LongTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
166 } else if (f instanceof JCharField) {
|
|
167 char value = isStatic? f.getJChar() : f.getJChar(addr);
|
|
168 return new CharTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
169 } else if (f instanceof JBooleanField) {
|
|
170 boolean value = isStatic? f.getJBoolean() : f.getJBoolean(addr);
|
|
171 return new BooleanTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
172 } else if (f instanceof JFloatField) {
|
|
173 float value = isStatic? f.getJFloat() : f.getJFloat(addr);
|
|
174 return new DoubleTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
175 } else if (f instanceof JDoubleField) {
|
|
176 double value = isStatic? f.getJDouble() : f.getJDouble(addr);
|
|
177 return new DoubleTreeNodeAdapter(value, cf, getTreeTableMode());
|
|
178 } else {
|
|
179 throw new RuntimeException("unhandled type: " + t.getName());
|
|
180 }
|
|
181 } else if (t.isPointerType()) {
|
|
182 Address ptr;
|
|
183 if (f.isStatic()) {
|
|
184 ptr = f.getAddress();
|
|
185 } else {
|
|
186 ptr = f.getAddress(addr);
|
|
187 }
|
|
188
|
|
189 if (t.isCStringType()) {
|
|
190 return new CStringTreeNodeAdapter(CStringUtilities.getString(ptr), cf);
|
|
191 }
|
|
192
|
|
193 return new CTypeTreeNodeAdapter(ptr, ((PointerType) t).getTargetType(), cf, getTreeTableMode());
|
|
194 } else {
|
|
195 if (f.isStatic()) {
|
|
196 return new CTypeTreeNodeAdapter(f.getStaticFieldAddress(), f.getType(),
|
|
197 cf, getTreeTableMode());
|
|
198 } else {
|
|
199 return new CTypeTreeNodeAdapter(addr.addOffsetTo(f.getOffset()), f.getType(),
|
|
200 cf, getTreeTableMode());
|
|
201 }
|
|
202 }
|
|
203 } catch (AddressException e) {
|
|
204 return new BadAddressTreeNodeAdapter(e.getAddress(),
|
|
205 new CTypeFieldIdentifier(type, f),
|
|
206 getTreeTableMode());
|
|
207 }
|
|
208 }
|
|
209
|
|
210 public boolean isLeaf() {
|
|
211 return getFields().length == 0;
|
|
212 }
|
|
213
|
|
214 public int getIndexOfChild(SimpleTreeNode child) {
|
|
215 CTypeFieldIdentifier id = (CTypeFieldIdentifier)((FieldTreeNodeAdapter) child).getID();
|
|
216 CTypeFieldIdentifier[] f = getFields();
|
|
217 for (int i = 0; i < f.length; i++) {
|
|
218 if (id == f[i]) {
|
|
219 return i;
|
|
220 }
|
|
221 }
|
|
222 return -1;
|
|
223 }
|
|
224
|
|
225 public String getValue() {
|
|
226 if (type != null) {
|
|
227 return type.getName() + " @ " + addr;
|
|
228 } else {
|
|
229 return "<statics>";
|
|
230 }
|
|
231 }
|
|
232 }
|