| 1 15 16 package javassist.bytecode; 17 18 import java.io.DataInputStream ; 19 import java.io.DataOutputStream ; 20 import java.io.ByteArrayOutputStream ; 21 import java.io.PrintWriter ; 22 import java.io.IOException ; 23 import java.util.Map ; 24 import java.util.HashMap ; 25 import javassist.CtClass; 26 27 30 public final class ConstPool { 31 LongVector items; 32 int numOfItems; 33 HashMap classes; 34 HashMap strings; 35 int thisClassInfo; 36 37 40 public static final int CONST_Class = ClassInfo.tag; 41 42 45 public static final int CONST_Fieldref = FieldrefInfo.tag; 46 47 50 public static final int CONST_Methodref = MethodrefInfo.tag; 51 52 55 public static final int CONST_InterfaceMethodref 56 = InterfaceMethodrefInfo.tag; 57 58 61 public static final int CONST_String = StringInfo.tag; 62 63 66 public static final int CONST_Integer = IntegerInfo.tag; 67 68 71 public static final int CONST_Float = FloatInfo.tag; 72 73 76 public static final int CONST_Long = LongInfo.tag; 77 78 81 public static final int CONST_Double = DoubleInfo.tag; 82 83 86 public static final int CONST_NameAndType = NameAndTypeInfo.tag; 87 88 91 public static final int CONST_Utf8 = Utf8Info.tag; 92 93 96 public static final CtClass THIS = null; 97 98 104 public ConstPool(String thisclass) { 105 items = new LongVector(); 106 numOfItems = 0; 107 addItem(null); classes = new HashMap (); 109 strings = new HashMap (); 110 thisClassInfo = addClassInfo(thisclass); 111 } 112 113 118 public ConstPool(DataInputStream in) throws IOException { 119 classes = new HashMap (); 120 strings = new HashMap (); 121 thisClassInfo = 0; 122 124 read(in); 125 } 126 127 void prune() { 128 classes = new HashMap (); 129 strings = new HashMap (); 130 } 131 132 135 public String getClassName() { 136 return getClassInfo(thisClassInfo); 137 } 138 139 143 public int getThisClassInfo() { 144 return thisClassInfo; 145 } 146 147 void setThisClassInfo(int i) { 148 thisClassInfo = i; 149 } 150 151 ConstInfo getItem(int n) { 152 return (ConstInfo)items.elementAt(n); 153 } 154 155 159 public int getTag(int index) { 160 return getItem(index).getTag(); 161 } 162 163 170 public String getClassInfo(int index) { 171 ClassInfo c = (ClassInfo)getItem(index); 172 if (c == null) 173 return null; 174 else 175 return Descriptor.toJavaName(getUtf8Info(c.name)); 176 } 177 178 183 public int getNameAndTypeName(int index) { 184 NameAndTypeInfo ntinfo = (NameAndTypeInfo)getItem(index); 185 return ntinfo.memberName; 186 } 187 188 193 public int getNameAndTypeDescriptor(int index) { 194 NameAndTypeInfo ntinfo = (NameAndTypeInfo)getItem(index); 195 return ntinfo.typeDescriptor; 196 } 197 198 203 public int getFieldrefClass(int index) { 204 FieldrefInfo finfo = (FieldrefInfo)getItem(index); 205 return finfo.classIndex; 206 } 207 208 215 public String getFieldrefClassName(int index) { 216 FieldrefInfo f = (FieldrefInfo)getItem(index); 217 if (f == null) 218 return null; 219 else 220 return getClassInfo(f.classIndex); 221 } 222 223 228 public int getFieldrefNameAndType(int index) { 229 FieldrefInfo finfo = (FieldrefInfo)getItem(index); 230 return finfo.nameAndTypeIndex; 231 } 232 233 241 public String getFieldrefName(int index) { 242 FieldrefInfo f = (FieldrefInfo)getItem(index); 243 if (f == null) 244 return null; 245 else { 246 NameAndTypeInfo n = (NameAndTypeInfo)getItem(f.nameAndTypeIndex); 247 if(n == null) 248 return null; 249 else 250 return getUtf8Info(n.memberName); 251 } 252 } 253 254 262 public String getFieldrefType(int index) { 263 FieldrefInfo f = (FieldrefInfo)getItem(index); 264 if (f == null) 265 return null; 266 else { 267 NameAndTypeInfo n = (NameAndTypeInfo) getItem(f.nameAndTypeIndex); 268 if(n == null) 269 return null; 270 else 271 return getUtf8Info(n.typeDescriptor); 272 } 273 } 274 275 280 public int getMethodrefClass(int index) { 281 MethodrefInfo minfo = (MethodrefInfo)getItem(index); 282 return minfo.classIndex; 283 } 284 285 292 public String getMethodrefClassName(int index) { 293 MethodrefInfo minfo = (MethodrefInfo)getItem(index); 294 if (minfo == null) 295 return null; 296 else 297 return getClassInfo(minfo.classIndex); 298 } 299 300 305 public int getMethodrefNameAndType(int index) { 306 MethodrefInfo minfo = (MethodrefInfo)getItem(index); 307 return minfo.nameAndTypeIndex; 308 } 309 310 318 public String getMethodrefName(int index) { 319 MethodrefInfo minfo = (MethodrefInfo)getItem(index); 320 if (minfo == null) 321 return null; 322 else { 323 NameAndTypeInfo n 324 = (NameAndTypeInfo)getItem(minfo.nameAndTypeIndex); 325 if(n == null) 326 return null; 327 else 328 return getUtf8Info(n.memberName); 329 } 330 } 331 332 340 public String getMethodrefType(int index) { 341 MethodrefInfo minfo = (MethodrefInfo)getItem(index); 342 if (minfo == null) 343 return null; 344 else { 345 NameAndTypeInfo n 346 = (NameAndTypeInfo)getItem(minfo.nameAndTypeIndex); 347 if(n == null) 348 return null; 349 else 350 return getUtf8Info(n.typeDescriptor); 351 } 352 } 353 354 359 public int getInterfaceMethodrefClass(int index) { 360 InterfaceMethodrefInfo minfo 361 = (InterfaceMethodrefInfo)getItem(index); 362 return minfo.classIndex; 363 } 364 365 372 public String getInterfaceMethodrefClassName(int index) { 373 InterfaceMethodrefInfo minfo 374 = (InterfaceMethodrefInfo)getItem(index); 375 return getClassInfo(minfo.classIndex); 376 } 377 378 383 public int getInterfaceMethodrefNameAndType(int index) { 384 InterfaceMethodrefInfo minfo 385 = (InterfaceMethodrefInfo)getItem(index); 386 return minfo.nameAndTypeIndex; 387 } 388 389 398 public String getInterfaceMethodrefName(int index) { 399 InterfaceMethodrefInfo minfo 400 = (InterfaceMethodrefInfo)getItem(index); 401 if (minfo == null) 402 return null; 403 else { 404 NameAndTypeInfo n 405 = (NameAndTypeInfo)getItem(minfo.nameAndTypeIndex); 406 if(n == null) 407 return null; 408 else 409 return getUtf8Info(n.memberName); 410 } 411 } 412 413 422 public String getInterfaceMethodrefType(int index) { 423 InterfaceMethodrefInfo minfo 424 = (InterfaceMethodrefInfo)getItem(index); 425 if (minfo == null) 426 return null; 427 else { 428 NameAndTypeInfo n 429 = (NameAndTypeInfo)getItem(minfo.nameAndTypeIndex); 430 if(n == null) 431 return null; 432 else 433 return getUtf8Info(n.typeDescriptor); 434 } 435 } 436 445 public Object getLdcValue(int index) { 446 ConstInfo constInfo = this.getItem(index); 447 Object value = null; 448 if (constInfo instanceof StringInfo) 449 value = this.getStringInfo(index); 450 else if (constInfo instanceof FloatInfo) 451 value = new Float (getFloatInfo(index)); 452 else if (constInfo instanceof IntegerInfo) 453 value = new Integer (getIntegerInfo(index)); 454 else if (constInfo instanceof LongInfo) 455 value = new Long (getLongInfo(index)); 456 else if (constInfo instanceof DoubleInfo) 457 value = new Double (getDoubleInfo(index)); 458 else 459 value = null; 460 461 return value; 462 } 463 464 470 public int getIntegerInfo(int index) { 471 IntegerInfo i = (IntegerInfo)getItem(index); 472 return i.value; 473 } 474 475 481 public float getFloatInfo(int index) { 482 FloatInfo i = (FloatInfo)getItem(index); 483 return i.value; 484 } 485 486 492 public long getLongInfo(int index) { 493 LongInfo i = (LongInfo)getItem(index); 494 return i.value; 495 } 496 497 503 public double getDoubleInfo(int index) { 504 DoubleInfo i = (DoubleInfo)getItem(index); 505 return i.value; 506 } 507 508 514 public String getStringInfo(int index) { 515 StringInfo si = (StringInfo)getItem(index); 516 return getUtf8Info(si.string); 517 } 518 519 525 public String getUtf8Info(int index) { 526 Utf8Info utf = (Utf8Info)getItem(index); 527 return utf.string; 528 } 529 530 540 public int isConstructor(String classname, int index) { 541 return isMember(classname, MethodInfo.nameInit, index); 542 } 543 544 560 public int isMember(String classname, String membername, int index) { 561 MemberrefInfo minfo = (MemberrefInfo)getItem(index); 562 if (getClassInfo(minfo.classIndex).equals(classname)) { 563 NameAndTypeInfo ntinfo 564 = (NameAndTypeInfo)getItem(minfo.nameAndTypeIndex); 565 if (getUtf8Info(ntinfo.memberName).equals(membername)) 566 return ntinfo.typeDescriptor; 567 } 568 569 return 0; } 571 572 private int addItem(ConstInfo info) { 573 items.addElement(info); 574 return numOfItems++; 575 } 576 577 588 public int copy(int n, ConstPool dest, Map classnames) { 589 if (n == 0) 590 return 0; 591 592 ConstInfo info = getItem(n); 593 return info.copy(this, dest, classnames); 594 } 595 596 int addConstInfoPadding() { 597 return addItem(new ConstInfoPadding()); 598 } 599 600 608 public int addClassInfo(CtClass c) { 609 if (c == THIS) 610 return thisClassInfo; 611 else if (!c.isArray()) 612 return addClassInfo(c.getName()); 613 else { 614 619 return addClassInfo(Descriptor.toJvmName(c)); 620 } 621 } 622 623 633 public int addClassInfo(String qname) { 634 ClassInfo info = (ClassInfo)classes.get(qname); 635 if (info != null) 636 return info.index; 637 else { 638 int utf8 = addUtf8Info(Descriptor.toJvmName(qname)); 639 info = new ClassInfo(utf8, numOfItems); 640 classes.put(qname, info); 641 return addItem(info); 642 } 643 } 644 645 654 public int addNameAndTypeInfo(String name, String type) { 655 return addNameAndTypeInfo(addUtf8Info(name), addUtf8Info(type)); 656 } 657 658 665 public int addNameAndTypeInfo(int name, int type) { 666 return addItem(new NameAndTypeInfo(name, type)); 667 } 668 669 682 public int addFieldrefInfo(int classInfo, String name, String type) { 683 int nt = addNameAndTypeInfo(name, type); 684 return addFieldrefInfo(classInfo, nt); 685 } 686 687 694 public int addFieldrefInfo(int classInfo, int nameAndTypeInfo) { 695 return addItem(new FieldrefInfo(classInfo, nameAndTypeInfo)); 696 } 697 698 711 public int addMethodrefInfo(int classInfo, String name, String type) { 712 int nt = addNameAndTypeInfo(name, type); 713 return addMethodrefInfo(classInfo, nt); 714 } 715 716 723 public int addMethodrefInfo(int classInfo, int nameAndTypeInfo) { 724 return addItem(new MethodrefInfo(classInfo, nameAndTypeInfo)); 725 } 726 727 741 public int addInterfaceMethodrefInfo(int classInfo, String name, 742 String type) { 743 int nt = addNameAndTypeInfo(name, type); 744 return addInterfaceMethodrefInfo(classInfo, nt); 745 } 746 747 755 public int addInterfaceMethodrefInfo(int classInfo, 756 int nameAndTypeInfo) { 757 return addItem(new InterfaceMethodrefInfo(classInfo, 758 nameAndTypeInfo)); 759 } 760 761 770 public int addStringInfo(String str) { 771 return addItem(new StringInfo(addUtf8Info(str))); 772 } 773 774 780 public int addIntegerInfo(int i) { 781 return addItem(new IntegerInfo(i)); 782 } 783 784 790 public int addFloatInfo(float f) { 791 return addItem(new FloatInfo(f)); 792 } 793 794 800 public int addLongInfo(long l) { 801 int i = addItem(new LongInfo(l)); 802 addItem(new ConstInfoPadding()); 803 return i; 804 } 805 806 812 public int addDoubleInfo(double d) { 813 int i = addItem(new DoubleInfo(d)); 814 addItem(new ConstInfoPadding()); 815 return i; 816 } 817 818 829 public int addUtf8Info(String utf8) { 830 Utf8Info info = (Utf8Info)strings.get(utf8); 831 if (info != null) 832 return info.index; 833 else { 834 info = new Utf8Info(utf8, numOfItems); 835 strings.put(utf8, info); 836 return addItem(info); 837 } 838 } 839 840 846 public void renameClass(String oldName, String newName) { 847 LongVector v = items; 848 int size = numOfItems; 849 for (int i = 1; i < size; ++i) 850 ((ConstInfo)v.elementAt(i)).renameClass(this, oldName, newName); 851 } 852 853 859 public void renameClass(Map classnames) { 860 LongVector v = items; 861 int size = numOfItems; 862 for (int i = 1; i < size; ++i) 863 ((ConstInfo)v.elementAt(i)).renameClass(this, classnames); 864 } 865 866 private void read(DataInputStream in) throws IOException { 867 int n = in.readUnsignedShort(); 868 869 int size = (n / LongVector.SIZE + 1) * LongVector.SIZE; 870 items = new LongVector(size); 871 numOfItems = 0; 872 addItem(null); 874 while (--n > 0) { int tag = readOne(in); 876 if ((tag == LongInfo.tag) || (tag == DoubleInfo.tag)) { 877 addItem(new ConstInfoPadding()); 878 --n; 879 } 880 } 881 } 882 883 private int readOne(DataInputStream in) throws IOException { 884 ConstInfo info; 885 int tag = in.readUnsignedByte(); 886 switch (tag) { 887 case Utf8Info.tag : info = new Utf8Info(in, numOfItems); 889 strings.put(((Utf8Info)info).string, info); 890 break; 891 case IntegerInfo.tag : info = new IntegerInfo(in); 893 break; 894 case FloatInfo.tag : info = new FloatInfo(in); 896 break; 897 case LongInfo.tag : info = new LongInfo(in); 899 break; 900 case DoubleInfo.tag : info = new DoubleInfo(in); 902 break; 903 case ClassInfo.tag : info = new ClassInfo(in, numOfItems); 905 break; 907 case StringInfo.tag : info = new StringInfo(in); 909 break; 910 case FieldrefInfo.tag : info = new FieldrefInfo(in); 912 break; 913 case MethodrefInfo.tag : info = new MethodrefInfo(in); 915 break; 916 case InterfaceMethodrefInfo.tag : info = new InterfaceMethodrefInfo(in); 918 break; 919 case NameAndTypeInfo.tag : info = new NameAndTypeInfo(in); 921 break; 922 default : 923 throw new IOException ("invalid constant type: " + tag); 924 } 925 926 addItem(info); 927 return tag; 928 } 929 930 933 public void write(DataOutputStream out) throws IOException { 934 out.writeShort(numOfItems); 935 LongVector v = items; 936 int size = numOfItems; 937 for (int i = 1; i < size; ++i) 938 ((ConstInfo)v.elementAt(i)).write(out); 939 } 940 941 944 public void print() { 945 print(new PrintWriter (System.out, true)); 946 } 947 948 951 public void print(PrintWriter out) { 952 int size = numOfItems; 953 for (int i = 1; i < size; ++i) { 954 out.print(i); 955 out.print(" "); 956 ((ConstInfo)items.elementAt(i)).print(out); 957 } 958
|