| 1 12 package org.eclipse.jdi.internal; 13 14 15 import java.io.ByteArrayOutputStream ; 16 import java.io.DataInputStream ; 17 import java.io.DataOutputStream ; 18 import java.io.IOException ; 19 import java.lang.reflect.Modifier ; 20 import java.util.ArrayList ; 21 import java.util.Collections ; 22 import java.util.HashMap ; 23 import java.util.HashSet ; 24 import java.util.Hashtable ; 25 import java.util.Iterator ; 26 import java.util.List ; 27 import java.util.Map ; 28 import java.util.Set ; 29 30 import org.eclipse.jdi.internal.jdwp.JdwpCommandPacket; 31 import org.eclipse.jdi.internal.jdwp.JdwpFieldID; 32 import org.eclipse.jdi.internal.jdwp.JdwpID; 33 import org.eclipse.jdi.internal.jdwp.JdwpMethodID; 34 import org.eclipse.jdi.internal.jdwp.JdwpReferenceTypeID; 35 import org.eclipse.jdi.internal.jdwp.JdwpReplyPacket; 36 37 import com.ibm.icu.text.MessageFormat; 38 import com.sun.jdi.AbsentInformationException; 39 import com.sun.jdi.ClassLoaderReference; 40 import com.sun.jdi.ClassNotLoadedException; 41 import com.sun.jdi.ClassNotPreparedException; 42 import com.sun.jdi.ClassObjectReference; 43 import com.sun.jdi.ClassType; 44 import com.sun.jdi.Field; 45 import com.sun.jdi.InternalException; 46 import com.sun.jdi.NativeMethodException; 47 import com.sun.jdi.ObjectCollectedException; 48 import com.sun.jdi.ReferenceType; 49 import com.sun.jdi.VMDisconnectedException; 50 import com.sun.jdi.Value; 51 52 58 public abstract class ReferenceTypeImpl extends TypeImpl implements ReferenceType, org.eclipse.jdi.hcr.ReferenceType { 59 60 61 public static final int JDWP_CLASS_STATUS_VERIFIED = 1; 62 public static final int JDWP_CLASS_STATUS_PREPARED = 2; 63 public static final int JDWP_CLASS_STATUS_INITIALIZED = 4; 64 public static final int JDWP_CLASS_STATUS_ERROR = 8; 65 66 67 private static String [] fgClassStatusStrings = null; 68 69 72 protected static class FileInfo { 73 74 77 protected int fFileId; 78 79 82 protected String fFileName; 83 84 87 protected String fAbsoluteFileName; 88 89 94 private HashMap fLineInfo; 95 96 103 public FileInfo(int fileId, String fileName, String absoluteFileName) { 104 fFileId= fileId; 105 fFileName= fileName; 106 fAbsoluteFileName= absoluteFileName; 107 fLineInfo= new HashMap (); 108 } 109 110 119 public void addLineInfo(int inputLine, int outputStartLine, int outputLineRange) { 120 Integer key= new Integer (inputLine); 121 List outputLines= (List )fLineInfo.get(key); 122 if (outputLines == null) { 123 outputLines= new ArrayList (); 124 fLineInfo.put(key, outputLines); 125 } 126 outputLines.add(new int[] {outputStartLine, outputLineRange}); 127 } 128 129 136 public List getOutputLinesForLine(int lineNumber) { 137 List list= new ArrayList (); 138 List outputLines= (List )fLineInfo.get(new Integer (lineNumber)); 139 if (outputLines != null) { 140 for (Iterator iter = outputLines.iterator(); iter.hasNext();) { 141 int[] info = (int[])iter.next(); 142 int outputLineNumber= info[0]; 143 int length = info[1]; 144 if (length == 0){ 145 length = length + 1; 146 } 147 for (int i= 0; i < length; i++) { 148 list.add(new Integer (outputLineNumber++)); 149 } 150 } 151 } 152 return list; 153 } 154 155 158 public boolean equals(Object object) { 159 if (!(object instanceof FileInfo)) { 160 return false; 161 } 162 return fFileId == ((FileInfo)object).fFileId; 163 } 164 165 } 166 167 170 protected static class Stratum { 171 172 175 private String fId; 176 177 180 private List fFileInfos; 181 182 185 private int fPrimaryFileId; 186 187 191 private HashMap fOutputLineToInputLine; 192 193 197 public Stratum(String id) { 198 fId= id; 199 fFileInfos= new ArrayList (); 200 fOutputLineToInputLine= new HashMap (); 201 fPrimaryFileId= -1; 202 } 203 204 210 public void addFileInfo(int fileId, String fileName) throws AbsentInformationException { 211 addFileInfo(fileId, fileName, null); 212 } 213 214 221 public void addFileInfo(int fileId, String fileName, String absoluteFileName) throws AbsentInformationException { 222 if (fPrimaryFileId == -1) { 223 fPrimaryFileId= fileId; 224 } 225 FileInfo fileInfo= new FileInfo(fileId, fileName, absoluteFileName); 226 if (fFileInfos.contains(fileInfo)) { 227 throw new AbsentInformationException(MessageFormat.format(JDIMessages.ReferenceTypeImpl_28, new String [] {Integer.toString(fileId), fId})); 228 } 229 fFileInfos.add(fileInfo); 230 } 231 232 242 public void addLineInfo(int inputStartLine, int lineFileId, int repeatCount, int outputStartLine, int outputLineIncrement) throws AbsentInformationException { 243 FileInfo fileInfo= null; 244 for (Iterator iter = fFileInfos.iterator(); iter.hasNext();) { 246 FileInfo element = (FileInfo)iter.next(); 247 if (element.fFileId == lineFileId) { 248 fileInfo= element; 249 } 250 } 251 if (fileInfo == null) { 252 throw new AbsentInformationException(MessageFormat.format(JDIMessages.ReferenceTypeImpl_29, new String [] {Integer.toString(lineFileId)})); 253 } 254 for (int i= 0; i < repeatCount; i++, inputStartLine++) { 256 fileInfo.addLineInfo(inputStartLine, outputStartLine, outputLineIncrement); 257 if (outputLineIncrement == 0) { 258 addLineInfoToMap(inputStartLine, lineFileId, outputStartLine); 260 } else { 261 for (int j= 0; j < outputLineIncrement; j++, outputStartLine++) { 262 addLineInfoToMap(inputStartLine, lineFileId, outputStartLine); 263 } 264 } 265 } 266 } 267 268 271 private void addLineInfoToMap(int inputStartLine, int lineFileId, int outputStartLine) { 272 Integer key= new Integer (outputStartLine); 273 List inputLines= (List )fOutputLineToInputLine.get(key); 274 if (inputLines == null) { 275 inputLines= new ArrayList (); 276 fOutputLineToInputLine.put(key, inputLines); 277 } 278 inputLines.add(new int[] {lineFileId, inputStartLine}); 279 } 280 281 286 public FileInfo getFileInfo(String sourceName) { 287 for (Iterator iter = fFileInfos.iterator(); iter.hasNext();) { 288 FileInfo fileInfo = (FileInfo)iter.next(); 289 if (fileInfo.fFileName.equals(sourceName)) { 290 return fileInfo; 291 } 292 } 293 return null; 294 } 295 296 300 public List getInputLineInfos(int outputLineNumber) { 301 return (List )fOutputLineToInputLine.get(new Integer (outputLineNumber)); 302 } 303 304 } 305 306 307 308 309 private JdwpReferenceTypeID fReferenceTypeID; 310 311 312 protected List fInterfaces = null; 313 private List fMethods = null; 314 private Hashtable fMethodTable= null; 315 private List fFields = null; 316 private List fAllMethods = null; 317 private List fVisibleMethods = null; 318 private List fAllFields = null; 319 private List fVisibleFields = null; 320 private List fAllInterfaces = null; 321 private Map fStratumAllLineLocations = null; 322 private String fSourceName = null; 323 private int fModifierBits = -1; 324 private ClassLoaderReferenceImpl fClassLoader = null; 325 private ClassObjectReferenceImpl fClassObject = null; 326 327 private String fGenericSignature; private boolean fGenericSignatureKnown; 330 private boolean fGotClassFileVersion = false; private int fClassFileVersion; private boolean fIsHCREligible; private boolean fIsVersionKnown; 335 private boolean fSourceDebugExtensionAvailable= true; 337 340 private String fDefaultStratumId; 342 347 private Map fStrata; 349 352 private String fSmap; 354 357 protected ReferenceTypeImpl(String description, VirtualMachineImpl vmImpl, JdwpReferenceTypeID referenceTypeID) { 358 super(description, vmImpl); 359 fReferenceTypeID = referenceTypeID; 360 } 361 362 365 protected ReferenceTypeImpl(String description, VirtualMachineImpl vmImpl, JdwpReferenceTypeID referenceTypeID, String signature, String genericSignature) { 366 super(description, vmImpl); 367 fReferenceTypeID = referenceTypeID; 368 setSignature(signature); 369 setGenericSignature(genericSignature); 370 } 371 372 375 public abstract byte typeTag(); 376 377 380 public void flushStoredJdwpResults() { 381 Iterator iter; 382 383 if (fMethods != null) { 385 iter = fMethods.iterator(); 386 while (iter.hasNext()) { 387 MethodImpl method = (MethodImpl)iter.next(); 388 method.flushStoredJdwpResults(); 389 } 390 fMethods = null; 391 fMethodTable= null; 392 } 393 394 if (fFields != null) { 396 iter = fFields.iterator(); 397 while (iter.hasNext()) { 398 FieldImpl field = (FieldImpl)iter.next(); 399 field.flushStoredJdwpResults(); 400 } 401 fFields = null; 402 } 403 404 fInterfaces = null; 405 fAllMethods = null; 406 fVisibleMethods = null; 407 fAllFields = null; 408 fVisibleFields = null; 409 fAllInterfaces = null; 410 fStratumAllLineLocations = null; 411 fSourceName = null; 412 fModifierBits = -1; 413 fClassLoader = null; 414 fClassObject = null; 415 fGotClassFileVersion = false; 416 fGenericSignature= null; 418 fGenericSignatureKnown= false; 419 420 fSourceDebugExtensionAvailable= true; 422 fDefaultStratumId= null; 423 fStrata= null; 424 fSmap= null; 425 426 fSignature = null; 428 fSourceName = null; 429 } 430 431 434 public List allInterfaces() { 435 if (fAllInterfaces != null) { 436 return fAllInterfaces; 437 } 438 439 444 HashSet allInterfacesSet = new HashSet (interfaces()); 447 448 Iterator interfaces = interfaces().iterator(); 450 InterfaceTypeImpl inter; 451 while (interfaces.hasNext()) { 452 inter = (InterfaceTypeImpl)interfaces.next(); 453 allInterfacesSet.addAll(inter.allInterfaces()); 454 } 455 456 if (this instanceof ClassType) { 458 ClassType superclass = ((ClassType)this).superclass(); 459 if (superclass != null) { 460 allInterfacesSet.addAll(superclass.allInterfaces()); 461 } 462 } 463 464 fAllInterfaces = new ArrayList (allInterfacesSet); 465 return fAllInterfaces; 466 } 467 468 471 public JdwpReferenceTypeID getRefTypeID() { 472 return fReferenceTypeID; 473 } 474 475 478 public int modifiers() { 479 if (fModifierBits != -1) 480 return fModifierBits; 481 482 initJdwpRequest(); 483 try { 484 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.RT_MODIFIERS, this); 485 defaultReplyErrorHandler(replyPacket.errorCode()); 486 DataInputStream replyData = replyPacket.dataInStream(); 487 fModifierBits = readInt("modifiers", AccessibleImpl.getModifierStrings(), replyData); return fModifierBits; 489 } catch (IOException e) { 490 defaultIOExceptionHandler(e); 491 return 0; 492 } finally { 493 handledJdwpRequest(); 494 } 495 } 496 497 500 private void addVisibleMethods(List inheritedMethods, Set nameAndSignatures, List resultMethods) { 501 Iterator iter = inheritedMethods.iterator(); 502 MethodImpl inheritedMethod; 503 while (iter.hasNext()) { 504 inheritedMethod = (MethodImpl)iter.next(); 505 if (!nameAndSignatures.contains(inheritedMethod.name() + inheritedMethod.signature())) { 506 resultMethods.add(inheritedMethod); 507 } 508 } 509 } 510 511 514 public List visibleMethods() { 515 if (fVisibleMethods != null) 516 return fVisibleMethods; 517 518 523 Set namesAndSignatures = new HashSet (); 525 List visibleMethods= new ArrayList (); 526 527 for (Iterator iter= methods().iterator(); iter.hasNext();) { 529 MethodImpl method= (MethodImpl) iter.next(); 530 namesAndSignatures.add(method.name() + method.signature()); 531 visibleMethods.add(method); 532 } 533 534 Iterator interfaces = interfaces().iterator(); 536 InterfaceTypeImpl inter; 537 while (interfaces.hasNext()) { 538 inter = (InterfaceTypeImpl)interfaces.next(); 539 addVisibleMethods(inter.visibleMethods(), namesAndSignatures, visibleMethods); 540 } 541 542 if (this instanceof ClassType) { 544 ClassType superclass = ((ClassType)this).superclass(); 545 if (superclass != null) 546 addVisibleMethods(superclass.visibleMethods(), namesAndSignatures, visibleMethods); 547 } 548 549 fVisibleMethods= visibleMethods; 550 return fVisibleMethods; 551 } 552 553 556 public List allMethods() { 557 if (fAllMethods != null) 558 return fAllMethods; 559 560 565 HashSet resultSet = new HashSet (); 567 568 resultSet.addAll(methods()); 570 571 Iterator interfaces = interfaces().iterator(); 573 InterfaceTypeImpl inter; 574 while (interfaces.hasNext()) { 575 inter = (InterfaceTypeImpl)interfaces.next(); 576 resultSet.addAll(inter.allMethods()); 577 } 578 579 if (this instanceof ClassType) { 581 ClassType superclass = ((ClassType)this).superclass(); 582 if (superclass != null) 583 resultSet.addAll(superclass.allMethods()); 584 } 585 586 fAllMethods = new ArrayList (resultSet); 587 return fAllMethods; 588 } 589 590 593 public List interfaces() { 594 if (fInterfaces != null) { 595 return fInterfaces; 596 } 597 598 initJdwpRequest(); 599 try { 600 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.RT_INTERFACES, this); 601 switch (replyPacket.errorCode()) { 602 case JdwpReplyPacket.NOT_FOUND: 603 return Collections.EMPTY_LIST; 606 default: 607 defaultReplyErrorHandler(replyPacket.errorCode()); 608 } 609 DataInputStream replyData = replyPacket.dataInStream(); 610 List elements = new ArrayList (); 611 int nrOfElements = readInt("elements", replyData); for (int i = 0; i < nrOfElements; i++) { 613 InterfaceTypeImpl ref = InterfaceTypeImpl.read(this, replyData); 614 if (ref == null) { 615 continue; 616 } 617 elements.add(ref); 618 } 619 fInterfaces = elements; 620 return elements; 621 } catch (IOException e) { 622 defaultIOExceptionHandler(e); 623 return null; 624 } finally { 625 handledJdwpRequest(); 626 } 627 } 628 629 632 private void addVisibleFields(List newFields, Set names, List resultFields) { 633 Iterator iter = newFields.iterator(); 634 FieldImpl field; 635 while (iter.hasNext()) { 636 field = (FieldImpl)iter.next(); 637 String name = field.name(); 638 if (!names.contains(name)) { 639 resultFields.add(field); 640 names.add(name); 641 } 642 } 643 } 644 645 648 public List visibleFields() { 649 if (fVisibleFields != null) 650 return fVisibleFields; 651 652 657 HashSet fieldNames = new HashSet (); 659 660 List visibleFields = new ArrayList (); 662 addVisibleFields(fields(), fieldNames, visibleFields); 663 664 Iterator interfaces = interfaces().iterator(); 666 InterfaceTypeImpl inter; 667 while (interfaces.hasNext()) { 668 inter = (InterfaceTypeImpl)interfaces.next(); 669 addVisibleFields(inter.visibleFields(), fieldNames, visibleFields); 670 } 671 672 if (this instanceof ClassType) { 674 ClassType superclass = ((ClassType)this).superclass(); 675 if (superclass != null) 676 addVisibleFields(superclass.visibleFields(), fieldNames, visibleFields); 677 } 678 679 fVisibleFields = visibleFields; 680 return fVisibleFields; 681 } 682 683 686 public List allFields() { 687 if (fAllFields != null) 688 return fAllFields; 689 690 695 HashSet resultSet = new HashSet (); 697 698 resultSet.addAll(fields()); 700 701 Iterator interfaces = interfaces().iterator(); 703 InterfaceTypeImpl inter; 704 while (interfaces.hasNext()) { 705 inter = (InterfaceTypeImpl)interfaces.next(); 706 resultSet.addAll(inter.allFields()); 707 } 708 709 if (this instanceof ClassType) { 711 ClassType superclass = ((ClassType)this).superclass(); 712 if (superclass != null) 713 resultSet.addAll(superclass.allFields()); 714 } 715 716 fAllFields = new ArrayList (resultSet); 717 return fAllFields; 718 } 719 720 723 public ClassLoaderReference classLoader() { 724 if (fClassLoader != null) 725 return fClassLoader; 726 727 initJdwpRequest(); 728 try { 729 JdwpReplyPacket replyPacket = requestVM(JdwpCommandPacket.RT_CLASS_LOADER, this); 730 defaultReplyErrorHandler(replyPacket.errorCode()); 731 DataInputStream replyData = replyPacket.dataInStream(); 732 fClassLoader = ClassLoaderReferenceImpl.read(this, replyData); 733 return fClassLoader; 734 } catch (IOException e) { 735 defaultIOExceptionHandler(e); 736 return null; 737 } finally { 738 handledJdwpRequest(); 739 } 740 } 741 742 745 public ClassObjectReference classObject() { 746 if (fClassObject != null) 747 return fClassObject; 748 749 initJdwpRequest(); 750 &n
|