You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

TransformNew.java 3.1KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192
  1. /*
  2. * Javassist, a Java-bytecode translator toolkit.
  3. * Copyright (C) 1999-2003 Shigeru Chiba. All Rights Reserved.
  4. *
  5. * The contents of this file are subject to the Mozilla Public License Version
  6. * 1.1 (the "License"); you may not use this file except in compliance with
  7. * the License. Alternatively, the contents of this file may be used under
  8. * the terms of the GNU Lesser General Public License Version 2.1 or later.
  9. *
  10. * Software distributed under the License is distributed on an "AS IS" basis,
  11. * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
  12. * for the specific language governing rights and limitations under the
  13. * License.
  14. */
  15. package javassist.convert;
  16. import javassist.bytecode.*;
  17. import javassist.CtClass;
  18. import javassist.CannotCompileException;
  19. final public class TransformNew extends Transformer {
  20. private int nested;
  21. private String classname, trapClass, trapMethod;
  22. public TransformNew(Transformer next,
  23. String classname, String trapClass, String trapMethod) {
  24. super(next);
  25. this.classname = classname;
  26. this.trapClass = trapClass;
  27. this.trapMethod = trapMethod;
  28. }
  29. public void initialize(ConstPool cp, CodeAttribute attr) {
  30. nested = 0;
  31. }
  32. /**
  33. * Replace a sequence of
  34. * NEW classname
  35. * DUP
  36. * ...
  37. * INVOKESPECIAL
  38. * with
  39. * NOP
  40. * NOP
  41. * ...
  42. * INVOKESTATIC trapMethod in trapClass
  43. */
  44. public int transform(CtClass clazz, int pos, CodeIterator iterator,
  45. ConstPool cp) throws CannotCompileException
  46. {
  47. int index;
  48. int c = iterator.byteAt(pos);
  49. if (c == NEW) {
  50. index = iterator.u16bitAt(pos + 1);
  51. if (cp.getClassInfo(index).equals(classname)) {
  52. if (iterator.byteAt(pos + 3) != DUP)
  53. throw new CannotCompileException(
  54. "NEW followed by no DUP was found");
  55. iterator.writeByte(NOP, pos);
  56. iterator.writeByte(NOP, pos + 1);
  57. iterator.writeByte(NOP, pos + 2);
  58. iterator.writeByte(NOP, pos + 3);
  59. ++nested;
  60. }
  61. }
  62. else if (c == INVOKESPECIAL) {
  63. index = iterator.u16bitAt(pos + 1);
  64. int typedesc = cp.isConstructor(classname, index);
  65. if (typedesc != 0 && nested > 0) {
  66. int methodref = computeMethodref(typedesc, cp);
  67. iterator.writeByte(INVOKESTATIC, pos);
  68. iterator.write16bit(methodref, pos + 1);
  69. --nested;
  70. }
  71. }
  72. return pos;
  73. }
  74. private int computeMethodref(int typedesc, ConstPool cp) {
  75. int classIndex = cp.addClassInfo(trapClass);
  76. int mnameIndex = cp.addUtf8Info(trapMethod);
  77. typedesc = cp.addUtf8Info(
  78. Descriptor.changeReturnType(classname,
  79. cp.getUtf8Info(typedesc)));
  80. return cp.addMethodrefInfo(classIndex,
  81. cp.addNameAndTypeInfo(mnameIndex, typedesc));
  82. }
  83. }