Du kannst nicht mehr als 25 Themen auswählen Themen müssen mit entweder einem Buchstaben oder einer Ziffer beginnen. Sie können Bindestriche („-“) enthalten und bis zu 35 Zeichen lang sein.

StackMapTest.java 26KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800
  1. package javassist.bytecode;
  2. import java.util.Iterator;
  3. import java.util.List;
  4. import java.util.regex.Pattern;
  5. import java.util.regex.Matcher;
  6. import java.io.ByteArrayOutputStream;
  7. import java.io.IOException;
  8. import java.io.PrintStream;
  9. import java.lang.reflect.Method;
  10. import javassist.ClassPool;
  11. import javassist.CodeConverter;
  12. import javassist.CtClass;
  13. import javassist.CtMethod;
  14. import javassist.CtNewMethod;
  15. import javassist.JvstTest;
  16. import javassist.Loader;
  17. import javassist.bytecode.stackmap.MapMaker;
  18. import javassist.bytecode.stackmap.TypeData;
  19. import junit.framework.TestCase;
  20. public class StackMapTest extends TestCase {
  21. public static final String PATH = JvstTest.PATH;
  22. private ClassPool loader, dloader;
  23. private Loader cloader;
  24. public StackMapTest(String name) { super(name); }
  25. protected void setUp() throws Exception {
  26. loader = ClassPool.getDefault();
  27. dloader = new ClassPool(null);
  28. dloader.appendSystemPath();
  29. dloader.insertClassPath(".");
  30. cloader = new Loader(dloader);
  31. }
  32. protected Object make(String name) throws Exception {
  33. return cloader.loadClass(name).newInstance();
  34. }
  35. protected int invoke(Object target, String method) throws Exception {
  36. Method m = target.getClass().getMethod(method, new Class[0]);
  37. Object res = m.invoke(target, new Object[0]);
  38. return ((Integer)res).intValue();
  39. }
  40. protected static void rebuildStackMaps(CtClass cc) throws BadBytecode, IOException {
  41. ClassPool cp = cc.getClassPool();
  42. Iterator it = cc.getClassFile().getMethods().iterator();
  43. while (it.hasNext()) {
  44. MethodInfo minfo = (MethodInfo)it.next();
  45. rebuildStackMap(cc, cp, minfo);
  46. }
  47. }
  48. protected static void rebuildStackMap(CtClass cc, ClassPool cp, MethodInfo minfo) throws BadBytecode, IOException {
  49. CodeAttribute ca = minfo.getCodeAttribute();
  50. if (ca != null) {
  51. StackMapTable smt = (StackMapTable)ca.getAttribute(StackMapTable.tag);
  52. if (smt != null) {
  53. String data = readSmt(smt);
  54. StackMapTable smt2 = MapMaker.make(cp, minfo);
  55. String data2 = readSmt(smt2);
  56. try {
  57. assertEquals(cc.getName() + ":" + minfo.getName() + ":" + minfo.getDescriptor(),
  58. data, data2);
  59. }
  60. catch (junit.framework.ComparisonFailure e) {
  61. System.out.println("*** " + cc.getName() + ":" + minfo.getName() + ":" + minfo.getDescriptor());
  62. smt.println(System.out);
  63. System.out.println("---");
  64. smt2.println(System.out);
  65. }
  66. }
  67. }
  68. }
  69. protected static void rebuildStackMaps2(CtClass cc) throws BadBytecode {
  70. ClassPool cp = cc.getClassPool();
  71. Iterator it = cc.getClassFile().getMethods().iterator();
  72. while (it.hasNext()) {
  73. MethodInfo minfo = (MethodInfo)it.next();
  74. minfo.rebuildStackMap(cp);
  75. }
  76. }
  77. protected static String readSmt(StackMapTable smt) throws BadBytecode, IOException {
  78. if (smt == null)
  79. return "";
  80. ByteArrayOutputStream out = new ByteArrayOutputStream();
  81. PrintStream pout = new PrintStream(out);
  82. smt.println(pout);
  83. pout.close();
  84. return out.toString();
  85. }
  86. public static void main(String[] args) throws Exception {
  87. if (args.length == 2 && args[0].equals("-c")) {
  88. CtClass cc = ClassPool.getDefault().get(args[0].replace('/', '.'));
  89. rebuildStackMaps(cc);
  90. }
  91. else {
  92. for (int i = 0; i < args.length; i++) {
  93. CtClass cc = ClassPool.getDefault().get(getClassName(args[i]));
  94. System.out.println(cc.getName());
  95. rebuildStackMaps2(cc);
  96. cc.writeFile("rebuild");
  97. }
  98. }
  99. }
  100. public static String getClassName(String fileName) {
  101. Matcher m = Pattern.compile("(.*)\\.class").matcher(fileName);
  102. if (m.matches())
  103. return m.group(1).replace('/', '.');
  104. else
  105. return fileName;
  106. }
  107. public void testCommonSuper() throws Exception {
  108. CtClass type = loader.get("javassist.CtClassType[]");
  109. CtClass base = loader.get("javassist.CtClass[]");
  110. CtClass array = loader.get("javassist.CtArray[]");
  111. CtClass array2 = loader.get("javassist.CtArray[][]");
  112. CtClass str = loader.get("java.lang.String[]");
  113. CtClass strObj = loader.get("java.lang.String");
  114. CtClass obj = loader.get("java.lang.Object[]");
  115. CtClass objObj = loader.get("java.lang.Object");
  116. assertEquals(base, TypeData.commonSuperClassEx(type, base));
  117. assertEquals(base, TypeData.commonSuperClassEx(base, type));
  118. assertEquals(base, TypeData.commonSuperClassEx(array, type));
  119. assertEquals(obj, TypeData.commonSuperClassEx(base, str));
  120. assertEquals(objObj, TypeData.commonSuperClassEx(strObj, str));
  121. assertEquals(obj, TypeData.commonSuperClassEx(array, array2));
  122. assertEquals(obj, TypeData.commonSuperClassEx(base, array2));
  123. }
  124. public void testRebuild() throws Exception {
  125. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T1");
  126. rebuildStackMaps2(cc);
  127. //Class c = cc.toClass();
  128. //Object t1 = c.newInstance();
  129. cc.writeFile();
  130. Object t1 = make(cc.getName());
  131. assertEquals(3, invoke(t1, "test"));
  132. }
  133. public static interface Intf {
  134. int foo();
  135. }
  136. public static class C1 implements Intf {
  137. public int foo() { return 0; }
  138. }
  139. public static class C2 implements Intf {
  140. public int foo() { return 3; }
  141. }
  142. public static class T1 {
  143. public int test() {
  144. return foo(-1);
  145. }
  146. public int foo(int i) {
  147. Intf obj;
  148. if (i > 0)
  149. obj = new C1();
  150. else
  151. obj = new C2();
  152. return obj.foo();
  153. }
  154. }
  155. public void testRebuild2() throws Exception {
  156. CtClass cc = loader.get("javassist.bytecode.StackMapTest$C3");
  157. rebuildStackMaps2(cc);
  158. cc.writeFile();
  159. Object t1 = make(cc.getName());
  160. assertEquals(7, invoke(t1, "test"));
  161. }
  162. public static class C3 {
  163. int value;
  164. public C3(int i) {
  165. value = i;
  166. }
  167. public C3(boolean b) {
  168. this(b ? 7 : 10);
  169. }
  170. public C3() { this(true); }
  171. public int test() { return value; }
  172. }
  173. public void testRebuild3() throws Exception {
  174. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T3");
  175. rebuildStackMaps2(cc);
  176. cc.writeFile();
  177. Object t1 = make(cc.getName());
  178. assertEquals(1100, invoke(t1, "test"));
  179. }
  180. public static interface Intf2 {
  181. int bar();
  182. }
  183. public static class D1 extends C1 implements Intf2 {
  184. public int bar() { return 10; }
  185. }
  186. public static class D2 extends C1 implements Intf2 {
  187. public int bar() { return 100; }
  188. }
  189. public static class T3 {
  190. public int bar(Intf2 i) { return 1000; }
  191. public int test() {
  192. return foo(-1);
  193. }
  194. public int foo(int i) {
  195. Intf2 obj;
  196. if (i > 0)
  197. obj = new D1();
  198. else
  199. obj = new D2();
  200. System.out.println(obj.toString());
  201. return obj.bar() + bar(obj);
  202. }
  203. }
  204. public void testRebuildArray() throws Exception {
  205. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T4");
  206. rebuildStackMaps2(cc);
  207. cc.writeFile();
  208. Object t1 = make(cc.getName());
  209. assertEquals(30, invoke(t1, "test"));
  210. }
  211. public static class T4 {
  212. public int test() {
  213. return foo(3) + foo2(3) + foo3(3) + foo4(3);
  214. }
  215. public int foo(int i) {
  216. C1[] a;
  217. if (i > 0)
  218. a = new D1[1];
  219. else
  220. a = new D2[1];
  221. if (i > 0)
  222. a[0] = new D1();
  223. else
  224. a[0] = new D2();
  225. return a[0].foo();
  226. }
  227. public int foo2(int i) {
  228. Intf2[] a;
  229. if (i > 0)
  230. a = new D1[1];
  231. else
  232. a = new D2[1];
  233. if (i > 0)
  234. a[0] = new D1();
  235. else
  236. a[0] = new D2();
  237. return a[0].bar();
  238. }
  239. public int foo3(int i) {
  240. Intf2[] a = null;
  241. if (i > 0)
  242. a = new D1[1];
  243. a[0] = new D1();
  244. return a[0].bar();
  245. }
  246. public int foo4(int i) {
  247. Intf2[] a = new Intf2[1];
  248. if (i > 0)
  249. a[0] = new D1();
  250. return a[0].bar();
  251. }
  252. }
  253. public void testRebuildConstructor() throws Exception {
  254. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T5");
  255. rebuildStackMaps2(cc);
  256. cc.writeFile();
  257. Object t1 = make(cc.getName());
  258. assertEquals(123, invoke(t1, "test"));
  259. }
  260. public static class T5 {
  261. int count;
  262. public T5() { count = 0; }
  263. public T5(int k) {
  264. if (k > 0) count = 10;
  265. else count = 100;
  266. count++;
  267. }
  268. public T5(double d) {
  269. this(d > 0.0 ? 1 : -1);
  270. if (d > 1.0) count += 10;
  271. else count += 100;
  272. count++;
  273. }
  274. public int test() {
  275. return new T5(3).count + new T5(1.0).count;
  276. }
  277. }
  278. public void testRebuildConstructor2() throws Exception {
  279. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T6");
  280. rebuildStackMaps2(cc);
  281. cc.writeFile();
  282. Object t1 = make(cc.getName());
  283. assertEquals(101, invoke(t1, "test2"));
  284. }
  285. public static class T6 {
  286. public int test2() {
  287. T5 t0 = new T5();
  288. T5 t = new T5(t0.count > 0 ? (new T5(t0.count > 0 ? 1 : -1).count) : -1);
  289. if (t0.count > 0)
  290. t.count += 1000;
  291. return t.count;
  292. }
  293. }
  294. public void testSwitchCase() throws Exception {
  295. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T7");
  296. // CodeConverter conv = new CodeConverter();
  297. // conv.replaceNew(cc, cc, "make2");
  298. // cc.instrument(conv);
  299. StringBuffer sbuf = new StringBuffer("String s;");
  300. for (int i = 0; i < 130; i++)
  301. sbuf.append("s =\"" + i + "\";");
  302. cc.getDeclaredMethod("foo").insertBefore(sbuf.toString());
  303. cc.getDeclaredMethod("test2").setBody(loader.get("javassist.bytecode.StackMapTest$T8").getDeclaredMethod("test2"), null);
  304. //rebuildStackMaps2(cc);
  305. cc.writeFile();
  306. Object t1 = make(cc.getName());
  307. assertEquals(110, invoke(t1, "test"));
  308. }
  309. public static class T7 {
  310. int value = 1;
  311. T7 t7;
  312. public static T7 make2() { return null; }
  313. public int foo() { return 1; }
  314. public int test() { return test2(10); }
  315. public int test2(int k) { return k; }
  316. }
  317. public static class T8 {
  318. public int test2(int k) {
  319. String s = "abc";
  320. T7 t = k > 0 ? new T7() : new T7();
  321. switch (k) {
  322. case 0:
  323. t = new T7();
  324. k += t.value;
  325. break;
  326. case 10:
  327. k += 100;
  328. break;
  329. }
  330. return k;
  331. }
  332. }
  333. public void testSwitchCase2() throws Exception {
  334. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T7b");
  335. StringBuffer sbuf = new StringBuffer("String s;");
  336. for (int i = 0; i < 130; i++)
  337. sbuf.append("s =\"" + i + "\";");
  338. cc.getDeclaredMethod("foo").insertBefore(sbuf.toString());
  339. cc.getDeclaredMethod("test2").setBody(loader.get("javassist.bytecode.StackMapTest$T8b").getDeclaredMethod("test2"), null);
  340. rebuildStackMaps2(cc);
  341. cc.writeFile();
  342. Object t1 = make(cc.getName());
  343. assertEquals(110, invoke(t1, "test"));
  344. }
  345. public static class T7b {
  346. int value = 1;
  347. T7b t7;
  348. public static T7b make2() { return null; }
  349. public int foo() { return 1; }
  350. public int test() { return test2(10); }
  351. public int test2(int k) { return k; }
  352. }
  353. public static class T8b {
  354. public int test2(int k) {
  355. String s = "abc";
  356. T7b t = k > 0 ? new T7b() : new T7b();
  357. switch (k) {
  358. case 0:
  359. t = new T7b();
  360. k += t.value;
  361. break;
  362. case 10:
  363. k += 100;
  364. break;
  365. }
  366. return k;
  367. }
  368. }
  369. public void testSwitchCase3() throws Exception {
  370. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T7c");
  371. StringBuffer sbuf = new StringBuffer("String s;");
  372. for (int i = 0; i < 130; i++)
  373. sbuf.append("s =\"" + i + "\";");
  374. cc.getDeclaredMethod("foo").insertBefore(sbuf.toString());
  375. cc.getDeclaredMethod("test2").setBody(loader.get("javassist.bytecode.StackMapTest$T8c").getDeclaredMethod("test2"), null);
  376. cc.writeFile();
  377. Object t1 = make(cc.getName());
  378. assertEquals(100, invoke(t1, "test"));
  379. }
  380. public static class T7c {
  381. int value = 1;
  382. T7b t7;
  383. public static T7b make2() { return null; }
  384. public static void print(String s) {}
  385. public int foo() { return 1; }
  386. public int test() { return test2(10); }
  387. public int test2(int k) { return 0; }
  388. }
  389. public static class T8c {
  390. public int test2(int k) {
  391. int jj = 50;
  392. if (k > 0)
  393. k += "fooo".length();
  394. int j = 50;
  395. loop: for (int i = 0; i < 10; i++) {
  396. int jjj = 1;
  397. switch (i) {
  398. case 0:
  399. k++;
  400. { int poi = 0; }
  401. break;
  402. case 9:
  403. break loop;
  404. case 7:
  405. k += jjj;
  406. break;
  407. }
  408. }
  409. return j + jj;
  410. }
  411. }
  412. public void testSwitchCase4() throws Exception {
  413. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T8e");
  414. StringBuffer sbuf = new StringBuffer("String s;");
  415. for (int i = 0; i < 130; i++)
  416. sbuf.append("s =\"" + i + "\";");
  417. cc.getDeclaredMethod("foo").insertBefore(sbuf.toString());
  418. CtClass orig = loader.get("javassist.bytecode.StackMapTest$T8d");
  419. CtMethod origM = orig.getDeclaredMethod("test2");
  420. writeLdcw(origM);
  421. cc.getDeclaredMethod("test2").setBody(origM, null);
  422. orig.writeFile();
  423. cc.writeFile();
  424. Object t1 = make(cc.getName());
  425. assertEquals(100, invoke(t1, "test"));
  426. }
  427. private void writeLdcw(CtMethod method) {
  428. CodeAttribute ca = method.getMethodInfo().getCodeAttribute();
  429. int index = ca.getConstPool().addStringInfo("ldcw");
  430. CodeIterator ci = ca.iterator();
  431. ci.writeByte(Opcode.LDC_W, 14);
  432. ci.write16bit(index, 15);
  433. ci.writeByte(Opcode.LDC_W, 43);
  434. ci.write16bit(index, 44);
  435. }
  436. public static class T8e {
  437. static T8dd helper() { return new T8dd(); }
  438. int integer() { return 9; }
  439. boolean integer2(String s) { return true; }
  440. static void print(String s) {}
  441. private void print2(String s) {}
  442. private Object func(String s) { return null; }
  443. I8d func2(String s) { return null; }
  444. static String ldcw() { return "k"; }
  445. static boolean debug = false;
  446. void log(String p1,String p2,String p3,Long p4, Object p5, Object p6) {}
  447. public int foo() { return 1; }
  448. public int test() {
  449. try {
  450. return test2("", 10) ? 1 : 0;
  451. } catch (Exception e) {}
  452. return 100;
  453. }
  454. public boolean test2(String s, int k) throws Exception { return false; }
  455. }
  456. public static interface I8d {
  457. String foo(String s, int i);
  458. }
  459. public static class T8dd {
  460. java.util.List foo(String s) { return new java.util.ArrayList(); }
  461. }
  462. public static class T8d {
  463. static T8dd helper() { return new T8dd(); }
  464. int integer() { return 9; }
  465. boolean integer2(String s) { return true; }
  466. static void print(String s) {}
  467. private void print2(String s) {}
  468. private Object func(String s) { return null; }
  469. I8d func2(String s) { return null; }
  470. static String ldcw() { return "k"; }
  471. static boolean debug = false;
  472. void log(String p1,String p2,String p3,Long p4, Object p5, Object p6) {}
  473. public boolean test2(String s, int i) throws Exception {
  474. String k = null;
  475. Object k2 = null;
  476. boolean v5 = true;
  477. if (!debug)
  478. print(ldcw());
  479. Object k3 = this.func(s);
  480. if (k3 == null)
  481. throw new Exception(new StringBuilder().append(ldcw()).append(s).append(",").toString());
  482. String v7 = k3.toString();
  483. k2 = this.func2(v7);
  484. if (k2 != null) { // 82:
  485. if (k2 instanceof I8d) {
  486. I8d k5 = (I8d)k2;
  487. k = k5.foo(s, i);
  488. }
  489. }
  490. java.util.List list = helper().foo(v7); // local 8
  491. for (int v9 = 0; v9 < list.size(); v9++) {
  492. boolean v10 = true;
  493. T8d v11 = (T8d)list.get(v9);
  494. switch (v11.integer()) {
  495. case 1:
  496. break;
  497. case 2:
  498. v10 = this.integer2(s);
  499. v5 &= v10;
  500. break;
  501. default :
  502. throw new Exception(new StringBuilder().append("ldc 189").append(v11.integer()).append("ldc 169").toString());
  503. }
  504. }
  505. if (v5) // 246:
  506. this.print2(s);
  507. if (v5)
  508. this.log(ldcw(), v7, s, Long.valueOf(new Integer(i).longValue()), k, null);
  509. else // 290:
  510. this.log(ldcw(), v7, s, Long.valueOf(new Integer(i).longValue()), k, null);
  511. return v5;
  512. }
  513. }
  514. public void testInnerClass() throws Exception {
  515. CtClass cc = loader.get("javassist.bytecode.StackMapTest$T9");
  516. CtClass par = loader.get("javassist.bytecode.StackMapTest$T9$Parent");
  517. CtClass in = loader.get("javassist.bytecode.StackMapTest$T9$In");
  518. rebuildStackMaps2(cc);
  519. rebuildStackMaps2(par);
  520. rebuildStackMaps2(in);
  521. cc.writeFile();
  522. in.writeFile();
  523. par.writeFile();
  524. Object t1 = make(cc.getName());
  525. assertEquals(19, invoke(t1, "test"));
  526. }
  527. public static class T9 {
  528. class Parent {
  529. int f;
  530. Parent(int i) { f = i; }
  531. }
  532. class In extends Parent {
  533. int value;
  534. public In(int i) {
  535. super(i > 0 ? 10 : 20);
  536. value = i;
  537. }
  538. }
  539. public int test() {
  540. In in = new In(9);
  541. return in.value + in.f;
  542. }
  543. }
  544. public void testConstructor3() throws Exception {
  545. CtClass cc = loader.get("javassist.bytecode.StackMapTest$C4");
  546. MethodInfo mi = cc.getDeclaredMethod("foo").getMethodInfo();
  547. mi.rebuildStackMapForME(loader);
  548. CodeIterator ci = mi.getCodeAttribute().iterator();
  549. ci.insertGap(0, 7);
  550. cc.writeFile();
  551. Object t1 = make(cc.getName());
  552. assertEquals(6, invoke(t1, "test"));
  553. }
  554. public static class C4 {
  555. public int test() { return foo(3); }
  556. public int foo(int i) {
  557. String s = new String(i > 0 ? "pos" : "negative");
  558. System.out.println("2nd stage");
  559. int len = 0;
  560. if (i > 0) {
  561. String t = new String(i > 0 ? "pos" : "negative");
  562. len = t.length();
  563. }
  564. return s.length() + len;
  565. }
  566. }
  567. public void testJIRA175() throws Exception {
  568. CtClass cc = loader.get("javassist.bytecode.StackMapTest$C5");
  569. cc.getDeclaredMethod("setter").instrument(new javassist.expr.ExprEditor() {
  570. @Override
  571. public void edit(javassist.expr.FieldAccess f) throws javassist.CannotCompileException {
  572. if (!f.where().getMethodInfo().isMethod())
  573. return;
  574. f.replace("{ $_ = $proceed($$); if (false) return $_;}");
  575. }
  576. });
  577. cc.writeFile();
  578. Object t1 = make(cc.getName());
  579. assertEquals(3, invoke(t1, "test"));
  580. }
  581. public static class C5 {
  582. String value;
  583. int ivalue;
  584. public int test() {
  585. setter("foo");
  586. return value.length();
  587. }
  588. public void setter(String s) {
  589. value = s;
  590. ivalue = s.length();
  591. }
  592. }
  593. public void testJIRA175b() throws Exception {
  594. CtClass cc = loader.get("javassist.bytecode.StackMapTest$C6");
  595. try {
  596. cc.getDeclaredMethod("setter").instrument(new javassist.expr.ExprEditor() {
  597. public void edit(javassist.expr.FieldAccess f) throws javassist.CannotCompileException {
  598. if (!f.where().getMethodInfo().isMethod())
  599. return;
  600. f.replace("{ $_ = $proceed($$); return $_;}");
  601. }
  602. });
  603. fail("deadcode detection");
  604. }
  605. catch (javassist.CannotCompileException e) {}
  606. }
  607. public static class C6 {
  608. String value;
  609. int ivalue;
  610. public int test() {
  611. setter("foo");
  612. return value.length();
  613. }
  614. public void setter(String s) {
  615. value = s;
  616. ivalue = s.length();
  617. }
  618. }
  619. public void testForHibernate() throws Exception {
  620. ClassFile cf = loader.makeClass("javassist.bytecode.StackMapTestHibTest").getClassFile();
  621. ConstPool cp = cf.getConstPool();
  622. MethodInfo mi = new MethodInfo(cp, "foo", "()V");
  623. Bytecode code = new Bytecode(cp, 0, 0);
  624. code.add(Opcode.RETURN);
  625. CodeAttribute ca = code.toCodeAttribute();
  626. mi.addAttribute(ca);
  627. cf.addMethod(mi);
  628. int pc = 111;
  629. int throwableType_index = cp.addClassInfo(Throwable.class.getName());
  630. StackMapTable.Writer writer = new StackMapTable.Writer(32);
  631. int[] localTags = { StackMapTable.OBJECT, StackMapTable.OBJECT, StackMapTable.OBJECT, StackMapTable.INTEGER };
  632. int[] localData = { cp.getThisClassInfo(), cp.addClassInfo("java/lang/Object"),
  633. cp.addClassInfo("[Ljava/lang/Object;"), 0};
  634. int[] stackTags = { StackMapTable.OBJECT };
  635. int[] stackData = { throwableType_index };
  636. writer.fullFrame(pc, localTags, localData, stackTags, stackData);
  637. ca.setAttribute(writer.toStackMapTable(cp));
  638. cf.write(new java.io.DataOutputStream(new java.io.FileOutputStream("./test-hibernate.class")));
  639. }
  640. public void testCommonSuperclass() throws Exception {
  641. CtClass obj = loader.get("java.lang.Object");
  642. CtClass objarray = loader.get("java.lang.Object[]");
  643. CtClass one = loader.get("byte[]");
  644. CtClass two = loader.get("byte[][]");
  645. assertEquals("java.lang.Object", TypeData.commonSuperClassEx(one, two).getName());
  646. assertTrue(one.subtypeOf(obj));
  647. assertTrue(two.subtypeOf(obj));
  648. assertFalse(one.subtypeOf(objarray));
  649. assertTrue(two.subtypeOf(objarray));
  650. one = loader.get("int[][]");
  651. two = loader.get("java.lang.Object[]");
  652. assertEquals("java.lang.Object[]", TypeData.commonSuperClassEx(one, two).getName());
  653. assertTrue(one.subtypeOf(objarray));
  654. assertTrue(two.subtypeOf(objarray));
  655. one = loader.get("int[]");
  656. two = loader.get("java.lang.String");
  657. assertEquals("java.lang.Object", TypeData.commonSuperClassEx(one, two).getName());
  658. assertTrue(one.subtypeOf(obj));
  659. assertTrue(two.subtypeOf(obj));
  660. assertFalse(one.subtypeOf(objarray));
  661. assertFalse(two.subtypeOf(objarray));
  662. one = loader.get("int[]");
  663. two = loader.get("int[]");
  664. assertEquals("int[]", TypeData.commonSuperClassEx(one, two).getName());
  665. assertTrue(one.subtypeOf(obj));
  666. assertFalse(one.subtypeOf(objarray));
  667. one = loader.get("int[]");
  668. two = loader.get("java.lang.String[]");
  669. assertEquals("java.lang.Object", TypeData.commonSuperClassEx(one, two).getName());
  670. assertTrue(one.subtypeOf(obj));
  671. assertTrue(two.subtypeOf(obj));
  672. assertFalse(one.subtypeOf(objarray));
  673. assertTrue(two.subtypeOf(objarray));
  674. one = loader.get("java.lang.String[]");
  675. two = loader.get("java.lang.Class[]");
  676. assertEquals("java.lang.Object[]", TypeData.commonSuperClassEx(one, two).getName());
  677. assertTrue(one.subtypeOf(objarray));
  678. assertTrue(two.subtypeOf(objarray));
  679. }
  680. public void tstCtClassType() throws Exception {
  681. ClassPool cp = ClassPool.getDefault();
  682. CtClass cc = cp.get("javassist.CtClassType");
  683. MethodInfo minfo = getMethodInfo(cc.getClassFile(), "getFields", "(Ljava/util/ArrayList;Ljavassist/CtClass;)V");
  684. rebuildStackMap(cc, cp, minfo);
  685. }
  686. MethodInfo getMethodInfo(ClassFile cf, String name, String desc) {
  687. List list = cf.getMethods();
  688. Iterator it = list.iterator();
  689. while (it.hasNext()) {
  690. MethodInfo mi = (MethodInfo)it.next();
  691. if (mi.getName().equals(name) && mi.getDescriptor().equals(desc))
  692. return mi;
  693. }
  694. return null;
  695. }
  696. }