1 11 package org.eclipse.jdi.internal; 12 13 14 import java.io.ByteArrayOutputStream ; 15 import java.io.DataInputStream ; 16 import java.io.DataOutputStream ; 17 import java.io.IOException ; 18 import java.util.ArrayList ; 19 import java.util.Iterator ; 20 import java.util.List ; 21 22 import org.eclipse.jdi.internal.jdwp.JdwpClassID; 23 import org.eclipse.jdi.internal.jdwp.JdwpClassObjectID; 24 import org.eclipse.jdi.internal.jdwp.JdwpCommandPacket; 25 import org.eclipse.jdi.internal.jdwp.JdwpID; 26 import org.eclipse.jdi.internal.jdwp.JdwpReplyPacket; 27 28 import com.sun.jdi.ClassNotLoadedException; 29 import com.sun.jdi.ClassNotPreparedException; 30 import com.sun.jdi.ClassType; 31 import com.sun.jdi.Field; 32 import com.sun.jdi.IncompatibleThreadStateException; 33 import com.sun.jdi.InvalidTypeException; 34 import com.sun.jdi.InvocationException; 35 import com.sun.jdi.Method; 36 import com.sun.jdi.ObjectReference; 37 import com.sun.jdi.ThreadReference; 38 import com.sun.jdi.Value; 39 40 46 public class ClassTypeImpl extends ReferenceTypeImpl implements ClassType { 47 48 49 public static final byte typeTag = JdwpID.TYPE_TAG_CLASS; 50 51 52 private ClassTypeImpl fSuperclass = null; 53 54 57 public ClassTypeImpl(VirtualMachineImpl vmImpl, JdwpClassID classID) { 58 super("ClassType", vmImpl, classID); } 60 61 64 public ClassTypeImpl(VirtualMachineImpl vmImpl, JdwpClassID classID, String signature, String genericSignature) { 65 super("ClassType", vmImpl, classID, signature, genericSignature); } 67 68 71 public byte typeTag() { 72 return typeTag; 73 } 74 75 78 public Value createNullValue() { 79 return new ClassObjectReferenceImpl(virtualMachineImpl(), new JdwpClassObjectID(virtualMachineImpl())); 80 } 81 82 85 public void flushStoredJdwpResults() { 86 super.flushStoredJdwpResults(); 87 88 Iterator itr = virtualMachineImpl().allCachedRefTypes(); 90 while (itr.hasNext()) { 91 ReferenceTypeImpl refType = (ReferenceTypeImpl)itr.next(); 92 if (refType instanceof ClassTypeImpl) { 93 ClassTypeImpl classType = (ClassTypeImpl)refType; 94 if (classType.fSuperclass != null && classType.fSuperclass.equals(this)) { 95 classType.flushStoredJdwpResults(); 96 } 97 } 98 } 99 100 fSuperclass = null; 101 } 102 103 106 private int optionsToJdwpOptions(int options) { 107 int jdwpOptions = 0; 108 if ((options & INVOKE_SINGLE_THREADED) != 0) 109 jdwpOptions |= MethodImpl.INVOKE_SINGLE_THREADED_JDWP; 110 return jdwpOptions; 111 } 112 113 116 public Method concreteMethodByName(String name, String signature) { 117 121 122 Iterator methods = methods().iterator(); 123 MethodImpl method; 124 while (methods.hasNext()) { 125 method = (MethodImpl)methods.next(); 126 if (method.name().equals(name) && method.signature().equals(signature)) { 127 if (method.isAbstract()) { 128 return null; 129 } 130 return method; 131 } 132 } 133 134 if (superclass() != null) { 135 return superclass().concreteMethodByName(name, signature); 136 } 137 138 return null; 139 } 140 141 145 public Value invokeMethod(ThreadReference thread, Method method, List arguments, int options) throws InvalidTypeException, ClassNotLoadedException, IncompatibleThreadStateException, InvocationException { 146 checkVM(thread); 147 checkVM(method); 148 ThreadReferenceImpl threadImpl = (ThreadReferenceImpl)thread; 149 MethodImpl methodImpl = (MethodImpl)method; 150 151 if (!visibleMethods().contains(method)) 153 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Class_does_not_contain_given_method_1); 154 if (method.argumentTypeNames().size() != arguments.size()) 155 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Number_of_arguments_doesn__t_match_2); 156 if (method.isConstructor() || method.isStaticInitializer()) 157 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Method_is_constructor_or_intitializer_3); 158 159 List checkedArguments= ValueImpl.checkValues(arguments, method.argumentTypes(), virtualMachineImpl()); 161 162 initJdwpRequest(); 163 try { 164 ByteArrayOutputStream outBytes = new ByteArrayOutputStream (); 165 DataOutputStream outData = new DataOutputStream (outBytes); 166 write(this, outData); 167 threadImpl.write(this, outData); 168 methodImpl.write(this, outData); 169 170 writeInt(checkedArguments.size(), "size", outData); Iterator iter = checkedArguments.iterator(); 172 while(iter.hasNext()) { 173 ValueImpl elt = (ValueImpl)iter.next(); 174 if (elt != null) { 175 elt.writeWithTag(this, outData); 176 } else { 177 ValueImpl.writeNullWithTag(this, outData); 178 } 179 } 180 181 writeInt(optionsToJdwpOptions(options),"options", MethodImpl.getInvokeOptions(), outData); 183 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.CT_INVOKE_METHOD, outBytes); 184 switch (replyPacket.errorCode()) { 185 case JdwpReplyPacket.INVALID_METHODID: 186 throw new IllegalArgumentException (); 187 case JdwpReplyPacket.TYPE_MISMATCH: 188 throw new InvalidTypeException(); 189 case JdwpReplyPacket.INVALID_CLASS: 190 throw new ClassNotLoadedException(name()); 191 case JdwpReplyPacket.INVALID_THREAD: 192 throw new IncompatibleThreadStateException(); 193 case JdwpReplyPacket.THREAD_NOT_SUSPENDED: 194 throw new IncompatibleThreadStateException(); 195 } 196 defaultReplyErrorHandler(replyPacket.errorCode()); 197 DataInputStream replyData = replyPacket.dataInStream(); 198 ValueImpl value = ValueImpl.readWithTag(this, replyData); 199 ObjectReferenceImpl exception = ObjectReferenceImpl.readObjectRefWithTag(this, replyData); 200 if (exception != null) 201 throw new InvocationException(exception); 202 return value; 203 } catch (IOException e) { 204 defaultIOExceptionHandler(e); 205 return null; 206 } finally { 207 handledJdwpRequest(); 208 } 209 } 210 211 215 public ObjectReference newInstance(ThreadReference thread, Method method, List arguments, int options) throws InvalidTypeException, ClassNotLoadedException, IncompatibleThreadStateException, InvocationException { 216 checkVM(thread); 217 checkVM(method); 218 ThreadReferenceImpl threadImpl = (ThreadReferenceImpl)thread; 219 MethodImpl methodImpl = (MethodImpl)method; 220 221 if (!methods().contains(method)) 223 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Class_does_not_contain_given_method_4); 224 if (method.argumentTypeNames().size() != arguments.size()) 225 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Number_of_arguments_doesn__t_match_5); 226 if (!method.isConstructor()) 227 throw new IllegalArgumentException (JDIMessages.ClassTypeImpl_Method_is_not_a_constructor_6); 228 229 List checkedArguments= ValueImpl.checkValues(arguments, method.argumentTypes(), virtualMachineImpl()); 230 231 initJdwpRequest(); 232 try { 233 ByteArrayOutputStream outBytes = new ByteArrayOutputStream (); 234 DataOutputStream outData = new DataOutputStream (outBytes); 235 write(this, outData); 236 threadImpl.write(this, outData); 237 methodImpl.write(this, outData); 238 239 writeInt(checkedArguments.size(), "size", outData); Iterator iter = checkedArguments.iterator(); 241 while(iter.hasNext()) { 242 ValueImpl elt = (ValueImpl)iter.next(); 243 if (elt != null) { 244 checkVM(elt); 245 elt.writeWithTag(this, outData); 246 } else { 247 ValueImpl.writeNullWithTag(this, outData); 248 } 249 } 250 251 writeInt(optionsToJdwpOptions(options),"options", MethodImpl.getInvokeOptions(), outData); 253 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.CT_NEW_INSTANCE, outBytes); 254 switch (replyPacket.errorCode()) { 255 case JdwpReplyPacket.INVALID_METHODID: 256 throw new IllegalArgumentException (); 257 case JdwpReplyPacket.TYPE_MISMATCH: 258 throw new InvalidTypeException(); 259 case JdwpReplyPacket.INVALID_CLASS: 260 throw new ClassNotLoadedException(name()); 261 case JdwpReplyPacket.INVALID_THREAD: 262 throw new IncompatibleThreadStateException(); 263 case JdwpReplyPacket.THREAD_NOT_SUSPENDED: 264 throw new IncompatibleThreadStateException(); 265 } 266 defaultReplyErrorHandler(replyPacket.errorCode()); 267 DataInputStream replyData = replyPacket.dataInStream(); 268 ObjectReferenceImpl object = ObjectReferenceImpl.readObjectRefWithTag(this, replyData); 269 ObjectReferenceImpl exception = ObjectReferenceImpl.readObjectRefWithTag(this, replyData); 270 if (exception != null) 271 throw new InvocationException(exception); 272 return object; 273 } catch (IOException e) { 274 defaultIOExceptionHandler(e); 275 return null; 276 } finally { 277 handledJdwpRequest(); 278 } 279 } 280 281 284 public void setValue(Field field, Value value) throws InvalidTypeException, ClassNotLoadedException { 285 initJdwpRequest(); 287 try { 288 ByteArrayOutputStream outBytes = new ByteArrayOutputStream (); 289 DataOutputStream outData = new DataOutputStream (outBytes); 290 write(this, outData); 291 writeInt(1, "size", outData); checkVM(field); 293 ((FieldImpl)field).write(this, outData); 294 295 ValueImpl checkedValue= ValueImpl.checkValue(value, field.type(), virtualMachineImpl()); 297 298 if (checkedValue != null) { 299 checkedValue.write(this, outData); 300 } else { 301 ValueImpl.writeNull(this, outData); 302 } 303 304 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.CT_SET_VALUES, outBytes); 305 switch (replyPacket.errorCode()) { 306 case JdwpReplyPacket.TYPE_MISMATCH: 307 throw new InvalidTypeException(); 308 case JdwpReplyPacket.INVALID_CLASS: 309 throw new ClassNotLoadedException(name()); 310 } 311 defaultReplyErrorHandler(replyPacket.errorCode()); 312 } catch (IOException e) { 313 defaultIOExceptionHandler(e); 314 } finally { 315 handledJdwpRequest(); 316 } 317 } 318 319 322 public List subclasses() { 323 List subclasses = new ArrayList (); 325 Iterator itr = virtualMachineImpl().allRefTypes(); 326 while (itr.hasNext()) { 327 try { 328 ReferenceTypeImpl refType = (ReferenceTypeImpl)itr.next(); 329 if (refType instanceof ClassTypeImpl) { 330 ClassTypeImpl classType = (ClassTypeImpl)refType; 331 if (classType.superclass() != null && classType.superclass().equals(this)) { 332 subclasses.add(classType); 333 } 334 } 335 } catch (ClassNotPreparedException e) { 336 continue; 337 } 338 } 339 return subclasses; 340 } 341 342 345 public ClassType superclass() { 346 if (fSuperclass != null) 347 return fSuperclass; 348 349 initJdwpRequest(); 350 try { 351 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.CT_SUPERCLASS, this); 352 defaultReplyErrorHandler(replyPacket.errorCode()); 353 DataInputStream replyData = replyPacket.dataInStream(); 354 fSuperclass = ClassTypeImpl.read(this, replyData); 355 return fSuperclass; 356 } catch (IOException e) { 357 defaultIOExceptionHandler(e); 358 return null; 359 } finally { 360 handledJdwpRequest(); 361 } 362 } 363 364 367 public static ClassTypeImpl read(MirrorImpl target, DataInputStream in) throws IOException { 368 VirtualMachineImpl vmImpl = target.virtualMachineImpl(); 369 JdwpClassID ID = new JdwpClassID(vmImpl); 370 ID.read(in); 371 if (target.fVerboseWriter != null) 372 target.fVerboseWriter.println("classType", ID.value()); 374 if (ID.isNull()) 375 return null; 376 377 ClassTypeImpl mirror = (ClassTypeImpl)vmImpl.getCachedMirror(ID); 378 if (mirror == null) { 379 mirror = new ClassTypeImpl(vmImpl, ID); 380 vmImpl.addCachedMirror(mirror); 381 } 382 return mirror; 383 } 384 385 388 public static ClassTypeImpl readWithSignature(MirrorImpl target, boolean withGenericSignature, DataInputStream in) throws IOException { 389 VirtualMachineImpl vmImpl = target.virtualMachineImpl(); 390 JdwpClassID ID = new JdwpClassID(vmImpl); 391 ID.read(in); 392 if (target.fVerboseWriter != null) 393 target.fVerboseWriter.println("classType", ID.value()); 395 String signature = target.readString("signature", in); String genericSignature= null; 397 if (withGenericSignature) { 398 genericSignature= target.readString("generic signature", in); } 400 if (ID.isNull()) 401 return null; 402 403 ClassTypeImpl mirror = (ClassTypeImpl)vmImpl.getCachedMirror(ID); 404 if (mirror == null) { 405 mirror = new ClassTypeImpl(vmImpl, ID); 406 vmImpl.addCachedMirror(mirror); 407 } 408 mirror.setSignature(signature); 409 mirror.setGenericSignature(genericSignature); 410 return mirror; 411 } 412 413 public boolean isEnum() { 414 if (virtualMachineImpl().isJdwpVersionGreaterOrEqual(1, 5)) { 415 ClassType superClass = superclass(); 417 return superClass != null && "<E:Ljava/lang/Enum<TE;>;>Ljava/lang/Object;Ljava/lang/Comparable<TE;>;Ljava/io/Serializable;".equals(superClass.genericSignature()); } 419 return false; 421 } 422 423 } 424 | Popular Tags |