Path: blob/master/test/hotspot/jtreg/runtime/InvocationTests/shared/ExecutorGenerator.java
40948 views
/*1* Copyright (c) 2009, 2019, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*22*/2324package shared;2526import static jdk.internal.org.objectweb.asm.ClassWriter.*;27import jdk.internal.org.objectweb.asm.Label;28import jdk.internal.org.objectweb.asm.MethodVisitor;29import jdk.internal.org.objectweb.asm.Opcodes;30import jdk.internal.org.objectweb.asm.ClassWriter;31import static jdk.internal.org.objectweb.asm.Opcodes.*;3233public class ExecutorGenerator {34public static final String className = Utils.getInternalName("Test");35private String caseDescription;36private String staticTargetName;37private String dynamicTargetName;3839private String callerSignature;4041public ExecutorGenerator(String caseDescription,42String staticTargetName,43String dynamicTargetName) {44this.caseDescription = caseDescription;45this.staticTargetName = Utils.getInternalName(staticTargetName);46this.dynamicTargetName = Utils.getInternalName(dynamicTargetName);47callerSignature = String.format("(L%s;)Ljava/lang/String;", this.staticTargetName);48}4950public byte[] generateExecutor(String[] callSites) {51ClassWriter cw = new ClassWriter(COMPUTE_MAXS);5253cw.visit(Utils.version, ACC_PUBLIC | (Utils.isACC_SUPER ? ACC_SUPER : 0), className, null, "java/lang/Object", null);5455// Generate constructor56{57MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);58mv.visitCode();59mv.visitVarInsn(ALOAD, 0);60mv.visitMethodInsn(INVOKESPECIAL, "java/lang/Object", "<init>", "()V");61mv.visitInsn(RETURN);62mv.visitEnd();63mv.visitMaxs(0, 0);64}6566// public static void main(String[] args) {67// new Test().run();68// }69{70MethodVisitor mv = cw.visitMethod(ACC_PUBLIC + ACC_STATIC, "main", "([Ljava/lang/String;)V", null, null);71mv.visitCode();72mv.visitTypeInsn(NEW, className);73mv.visitInsn(DUP);74mv.visitMethodInsn(INVOKESPECIAL, className, "<init>", "()V");75mv.visitMethodInsn(INVOKEVIRTUAL, className, "run", "()V");76mv.visitInsn(RETURN);77mv.visitEnd();78mv.visitMaxs(0, 0);79}8081// private String indent(String result) {82// while (result.length() < 8) {83// result = " "+result;84// }85// return result;86// }87{88MethodVisitor mv = cw.visitMethod(ACC_PRIVATE, "indent", "(Ljava/lang/String;)Ljava/lang/String;", null, null);89mv.visitCode();90Label l0 = new Label();91mv.visitLabel(l0);92mv.visitVarInsn(ALOAD, 1);93mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "length", "()I");94mv.visitIntInsn(BIPUSH, 8);95Label l1 = new Label();96mv.visitJumpInsn(IF_ICMPGE, l1);97mv.visitTypeInsn(NEW, "java/lang/StringBuffer");98mv.visitInsn(DUP);99mv.visitMethodInsn(INVOKESPECIAL, "java/lang/StringBuffer", "<init>", "()V");100mv.visitLdcInsn(" ");101mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuffer", "append", "(Ljava/lang/String;)Ljava/lang/StringBuffer;");102mv.visitVarInsn(ALOAD, 1);103mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuffer", "append", "(Ljava/lang/String;)Ljava/lang/StringBuffer;");104mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/StringBuffer", "toString", "()Ljava/lang/String;");105mv.visitVarInsn(ASTORE, 1);106mv.visitJumpInsn(GOTO, l0);107mv.visitLabel(l1);108mv.visitVarInsn(ALOAD, 1);109mv.visitInsn(ARETURN);110mv.visitEnd();111mv.visitMaxs(0, 0);112}113114//private String abbr(String result) {115// result = result.replaceAll("java.lang.NullPointerException", "NPE");116// result = result.replaceAll("java.lang.IllegalAccessError", "IAE");117// result = result.replaceAll("java.lang.IllegalAccessException", "IAExc");118// result = result.replaceAll("java.lang.NoSuchMethodError", "NSME");119// result = result.replaceAll("java.lang.AbstractMethodError", "AME");120// result = result.replaceAll("java.lang.IncompatibleClassChangeError", "ICCE");121//122// return result;123//}124{125MethodVisitor mv = cw.visitMethod(ACC_PRIVATE, "abbr", "(Ljava/lang/String;)Ljava/lang/String;", null, null);126mv.visitCode();127mv.visitVarInsn(ALOAD, 1);128mv.visitLdcInsn("java.lang.NullPointerException");129mv.visitLdcInsn("NPE");130mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");131mv.visitVarInsn(ASTORE, 1);132mv.visitVarInsn(ALOAD, 1);133mv.visitLdcInsn("java.lang.IllegalAccessError");134mv.visitLdcInsn("IAE");135mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");136mv.visitVarInsn(ASTORE, 1);137mv.visitVarInsn(ALOAD, 1);138mv.visitLdcInsn("java.lang.IllegalAccessException");139mv.visitLdcInsn("IAExc");140mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");141mv.visitVarInsn(ASTORE, 1);142mv.visitVarInsn(ALOAD, 1);143mv.visitLdcInsn("java.lang.NoSuchMethodError");144mv.visitLdcInsn("NSME");145mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");146mv.visitVarInsn(ASTORE, 1);147mv.visitVarInsn(ALOAD, 1);148mv.visitLdcInsn("java.lang.AbstractMethodError");149mv.visitLdcInsn("AME");150mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");151mv.visitVarInsn(ASTORE, 1);152mv.visitVarInsn(ALOAD, 1);153mv.visitLdcInsn("java.lang.IncompatibleClassChangeError");154mv.visitLdcInsn("ICCE");155mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/String", "replaceAll", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;");156mv.visitVarInsn(ASTORE, 1);157mv.visitVarInsn(ALOAD, 1);158mv.visitInsn(ARETURN);159mv.visitEnd();160mv.visitMaxs(0, 0);161}162163// Generate execution method164// public void run() {165// System.out.print("2048| ! a.A PUB ! b.B PP a.C PROT |");166//167// C object = new C();168//169// try {170// System.out.print(indent(A.call(object)));171// } catch (Throwable e) {172// System.out.print(indent(abbr(e.getClass().getName())));173// }174//175// ...176//177// System.out.println();178// }179{180MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "run", "()V", null, null);181mv.visitCode();182183// Generate try/catch blocks184Label[][] tryCatchLabels = new Label[callSites.length][3];185for (int I = 0; I < tryCatchLabels.length; I++) {186Label[] labels = tryCatchLabels[I];187for (int K = 0; K < labels.length; K++) {188labels[K] = new Label();189}190191mv.visitTryCatchBlock(labels[0], labels[1], labels[2], "java/lang/Throwable");192}193194// System.out.print("2048| ! a.A PUB ! b.B PP a.C PROT |");195mv.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");196mv.visitLdcInsn(caseDescription);197mv.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "print", "(Ljava/lang/String;)V");198199// C object = new C();200mv.visitTypeInsn(NEW, dynamicTargetName);201mv.visitInsn(DUP);202mv.visitMethodInsn(INVOKESPECIAL, dynamicTargetName, "<init>", "()V");203mv.visitVarInsn(ASTORE, 1);204205// for (String site: callSites) {206// System.out.print(indent(A.call(object)));207// mv.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");208// mv.visitVarInsn(ALOAD, 0);209// mv.visitVarInsn(ALOAD, 1);210// mv.visitMethodInsn(INVOKESTATIC, AbstractGenerator.getInternalName(site), "call", callerSignature);211// mv.visitMethodInsn(INVOKESPECIAL, className, "indent", "(Ljava/lang/String;)Ljava/lang/String;");212// mv.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "print", "(Ljava/lang/String;)V");213// }214215Label returnLabel = new Label();216for (int I = 0; I < callSites.length; I++) {217String site = callSites[I];218Label[] l = tryCatchLabels[I];219220Label nextBlock = (I+1 < callSites.length ? tryCatchLabels[I+1][0] : returnLabel);221222mv.visitLabel(l[0]);223mv.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");224mv.visitVarInsn(ALOAD, 0);225mv.visitVarInsn(ALOAD, 1);226mv.visitMethodInsn(INVOKESTATIC, Utils.getInternalName(site), "call", callerSignature);227mv.visitMethodInsn(INVOKESPECIAL, className, "indent", "(Ljava/lang/String;)Ljava/lang/String;");228mv.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "print", "(Ljava/lang/String;)V");229mv.visitLabel(l[1]);230mv.visitJumpInsn(GOTO, nextBlock);231mv.visitLabel(l[2]);232mv.visitVarInsn(ASTORE, 2);233mv.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");234mv.visitVarInsn(ALOAD, 0);235mv.visitVarInsn(ALOAD, 0);236mv.visitVarInsn(ALOAD, 2);237mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/Object", "getClass", "()Ljava/lang/Class;");238mv.visitMethodInsn(INVOKEVIRTUAL, "java/lang/Class", "getName", "()Ljava/lang/String;");239mv.visitMethodInsn(INVOKESPECIAL, className, "abbr", "(Ljava/lang/String;)Ljava/lang/String;");240mv.visitMethodInsn(INVOKESPECIAL, className, "indent", "(Ljava/lang/String;)Ljava/lang/String;");241mv.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "print", "(Ljava/lang/String;)V");242}243mv.visitLabel(returnLabel);244245// System.out.println();246mv.visitFieldInsn(GETSTATIC, "java/lang/System", "out", "Ljava/io/PrintStream;");247mv.visitMethodInsn(INVOKEVIRTUAL, "java/io/PrintStream", "println", "()V");248mv.visitInsn(RETURN);249250mv.visitEnd();251mv.visitMaxs(0, 0);252}253254cw.visitEnd();255256return cw.toByteArray();257}258}259260261