Java Code Examples for org.objectweb.asm.commons.GeneratorAdapter#invokeVirtual()

The following examples show how to use org.objectweb.asm.commons.GeneratorAdapter#invokeVirtual() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: AsmDeltaSpikeProxyClassGenerator.java    From deltaspike with Apache License 2.0 6 votes vote down vote up
/**
 * Generates:
 * <pre>
 * Method method =
 *      method.getDeclaringClass().getMethod("methodName", new Class[] { args... });
 * </pre>
 * @param mg
 * @param method
 * @param methodType
 */
private static void loadCurrentMethod(GeneratorAdapter mg, java.lang.reflect.Method method, Type methodType)
{
    mg.push(Type.getType(method.getDeclaringClass()));
    mg.push(method.getName());

    // create the Class[]
    mg.push(methodType.getArgumentTypes().length);
    mg.newArray(TYPE_CLASS);

    // push parameters into array
    for (int i = 0; i < methodType.getArgumentTypes().length; i++)
    {
        // keep copy of array on stack
        mg.dup();

        // push index onto stack
        mg.push(i);
        mg.push(methodType.getArgumentTypes()[i]);
        mg.arrayStore(TYPE_CLASS);
    }

    // invoke getMethod() with the method name and the array of types
    mg.invokeVirtual(TYPE_CLASS, Method.getMethod("java.lang.reflect.Method getDeclaredMethod(String, Class[])"));
}
 
Example 2
Source File: StringSwitch.java    From Stark with Apache License 2.0 6 votes vote down vote up
/**
 * Emit code for a string if-else block.
 *
 *     if (s.equals("collided_method1")) {
 *         visit(s);
 *     } else if (s.equals("collided_method2")) {
 *         visit(s);
 *     }
 *
 * In the most common case of just one string, this degenerates to:
 *
 *      visit(s)
 *
 */
private void visitx(GeneratorAdapter mv, List<String> strings) {
    if (strings.size() == 1) {
        visitCase(strings.get(0));
        return;
    }
    for (String string : strings) {
        Label label = new Label();
        visitString();
        mv.visitLdcInsn(string);
        mv.invokeVirtual(STRING_TYPE, Method.getMethod("boolean equals(Object)"));
        mv.visitJumpInsn(Opcodes.IFEQ, label);
        visitCase(string);
        mv.visitLabel(label);
    }

    visitDefault();
}
 
Example 3
Source File: IntSwitch.java    From Aceso with Apache License 2.0 6 votes vote down vote up
private void visitx(GeneratorAdapter mv, List<String> strings) {
    if (strings.size() == 1) {
        visitCase(strings.get(0));
        return;
    }
    for (String string : strings) {
        Label label = new Label();
        visitString();
        mv.visitLdcInsn(string);
        mv.invokeVirtual(STRING_TYPE, Method.getMethod("boolean equals(Object)"));
        mv.visitJumpInsn(Opcodes.IFEQ, label);
        visitCase(string);
        mv.visitLabel(label);
    }

    visitDefault();
}
 
Example 4
Source File: StringSwitch.java    From AnoleFix with MIT License 6 votes vote down vote up
/**
 * Emit code for a string if-else block.
 *
 *     if (s.equals("collided_method1")) {
 *         visit(s);
 *     } else if (s.equals("collided_method2")) {
 *         visit(s);
 *     }
 *
 * In the most common case of just one string, this degenerates to:
 *
 *      visit(s)
 *
 */
private void visitx(GeneratorAdapter mv, List<String> strings) {
    if (strings.size() == 1) {
        visitCase(strings.get(0));
        return;
    }
    for (int i = 0; i < strings.size(); ++i) {
        String string = strings.get(i);
        Label label = new Label();
        visitString();
        mv.visitLdcInsn(string);
        mv.invokeVirtual(STRING_TYPE, Method.getMethod("boolean equals(Object)"));
        mv.visitJumpInsn(Opcodes.IFEQ, label);
        visitCase(string);
        mv.visitLabel(label);
    }

    visitDefault();
}
 
Example 5
Source File: ByteCodeUtils.java    From Aceso with Apache License 2.0 5 votes vote down vote up
/**
 * Generates unboxing bytecode for the passed type. An {@link Object} is expected to be on the
 * stack when these bytecodes are inserted.
 *
 * ASM takes a short cut when dealing with short/byte types and convert them into int rather
 * than short/byte types. This is not an issue on the jvm nor Android's ART but it is an issue
 * on Dalvik.
 *
 * @param mv the {@link GeneratorAdapter} generating a method implementation.
 * @param type the expected un-boxed type.
 */
public static void unbox(GeneratorAdapter mv, Type type) {
    if (type.equals(Type.SHORT_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, SHORT_VALUE);
    } else if (type.equals(Type.BYTE_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, BYTE_VALUE);
    } else {
        mv.unbox(type);
    }
}
 
Example 6
Source File: ByteCodeUtils.java    From AnoleFix with MIT License 5 votes vote down vote up
/**
 * Generates unboxing bytecode for the passed type. An {@link Object} is expected to be on the
 * stack when these bytecodes are inserted.
 *
 * ASM takes a short cut when dealing with short/byte types and convert them into int rather
 * than short/byte types. This is not an issue on the jvm nor Android's ART but it is an issue
 * on Dalvik.
 *
 * @param mv the {@link GeneratorAdapter} generating a method implementation.
 * @param type the expected un-boxed type.
 */
public static void unbox(GeneratorAdapter mv, Type type) {
    if (type.equals(Type.SHORT_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, SHORT_VALUE);
    } else if (type.equals(Type.BYTE_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, BYTE_VALUE);
    } else {
        mv.unbox(type);
    }
}
 
Example 7
Source File: ByteCodeUtils.java    From Stark with Apache License 2.0 5 votes vote down vote up
/**
 * Generates unboxing bytecode for the passed type. An {@link Object} is expected to be on the
 * stack when these bytecodes are inserted.
 *
 * ASM takes a short cut when dealing with short/byte types and convert them into int rather
 * than short/byte types. This is not an issue on the jvm nor Android's ART but it is an issue
 * on Dalvik.
 *
 * @param mv the {@link GeneratorAdapter} generating a method implementation.
 * @param type the expected un-boxed type.
 */
public static void unbox(GeneratorAdapter mv, Type type) {
    if (type.equals(Type.SHORT_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, SHORT_VALUE);
    } else if (type.equals(Type.BYTE_TYPE)) {
        mv.checkCast(NUMBER_TYPE);
        mv.invokeVirtual(NUMBER_TYPE, BYTE_VALUE);
    } else {
        mv.unbox(type);
    }
}
 
Example 8
Source File: TestThreadExecutionGenerator.java    From lin-check with GNU Lesser General Public License v3.0 5 votes vote down vote up
private static void storeExceptionResultFromThrowable(GeneratorAdapter mv, int resLocal, int iLocal) {
    int eLocal = mv.newLocal(THROWABLE_TYPE);
    mv.storeLocal(eLocal);
    mv.loadLocal(resLocal);
    mv.loadLocal(iLocal);
    mv.loadLocal(eLocal);
    mv.invokeVirtual(OBJECT_TYPE, OBJECT_GET_CLASS);
    mv.invokeStatic(RESULT_TYPE, RESULT_CREATE_EXCEPTION_RESULT);
    mv.arrayStore(RESULT_TYPE);
}
 
Example 9
Source File: TestThreadExecutionGenerator.java    From lin-check with GNU Lesser General Public License v3.0 4 votes vote down vote up
private static void generateRun(ClassVisitor cv, Type testType, int iThread, List<Actor> actors, List<Object> objArgs, boolean waitsEnabled) {
    int access = ACC_PUBLIC;
    Method m = new Method("call", RESULT_ARRAY_TYPE, NO_ARGS);
    GeneratorAdapter mv = new GeneratorAdapter(access, m,
        // Try-catch blocks sorting is required
        new TryCatchBlockSorter(cv.visitMethod(access, m.getName(), m.getDescriptor(), null, null),
            access, m.getName(), m.getDescriptor(), null, null)
    );
    mv.visitCode();
    // Create Result[] array and store it to a local variable
    int resLocal = createResultArray(mv, actors.size());
    // Call runner's onStart(iThread) method
    mv.loadThis();
    mv.getField(TEST_THREAD_EXECUTION_TYPE, "runner", RUNNER_TYPE);
    mv.push(iThread);
    mv.invokeVirtual(RUNNER_TYPE, RUNNER_ON_START_METHOD);
    // Number of current operation (starts with 0)
    int iLocal = mv.newLocal(Type.INT_TYPE);
    mv.push(0);
    mv.storeLocal(iLocal);
    // Invoke actors
    for (int i = 0; i < actors.size(); i++) {
        Actor actor = actors.get(i);
        // Add busy-wait before operation execution (for non-first operations only)
        if (waitsEnabled && i > 0) {
            mv.loadThis();
            mv.getField(TEST_THREAD_EXECUTION_TYPE, "waits", INT_ARRAY_TYPE);
            mv.push(i - 1);
            mv.arrayLoad(Type.INT_TYPE);
            mv.invokeStatic(UTILS_TYPE, UTILS_CONSUME_CPU);
        }
        // Start of try-catch block for exceptions which this actor should handle
        Label start, end = null, handler = null, handlerEnd = null;
        if (actor.handlesExceptions()) {
            start = mv.newLabel();
            end = mv.newLabel();
            handler = mv.newLabel();
            handlerEnd = mv.newLabel();
            for (Class<? extends Throwable> ec : actor.handledExceptions)
                mv.visitTryCatchBlock(start, end, handler, Type.getType(ec).getInternalName());
            mv.visitLabel(start);
        }
        // Load result array and index to store the current result
        mv.loadLocal(resLocal);
        mv.push(i);
        // Load test instance
        mv.loadThis();
        mv.getField(TEST_THREAD_EXECUTION_TYPE, "testInstance", OBJECT_TYPE);
        mv.checkCast(testType);
        // Load arguments for operation
        for (int j = 0; j < actor.arguments.length; j++) {
            pushArgumentOnStack(mv, objArgs, actor.arguments[j], actor.method.getParameterTypes()[j]);
        }
        // Invoke operation
        Method actorMethod = Method.getMethod(actor.method);
        mv.invokeVirtual(testType, actorMethod);
        // Create result
        mv.box(actorMethod.getReturnType()); // box if needed
        if (actor.method.getReturnType() == void.class) {
            mv.pop();
            mv.invokeStatic(RESULT_TYPE, RESULT_CREATE_VOID_RESULT);
        } else {
            mv.invokeStatic(RESULT_TYPE, RESULT_CREATE_VALUE_RESULT);
        }
        // Store result to array
        mv.arrayStore(RESULT_TYPE);
        // End of try-catch block
        if (actor.handlesExceptions()) {
            mv.visitLabel(end);
            mv.goTo(handlerEnd);
            mv.visitLabel(handler);
            storeExceptionResultFromThrowable(mv, resLocal, iLocal);
            mv.visitLabel(handlerEnd);
        }
        // Increment number of current operation
        mv.iinc(iLocal, 1);
    }
    // Call runner's onFinish(iThread) method
    mv.loadThis();
    mv.getField(TEST_THREAD_EXECUTION_TYPE, "runner", RUNNER_TYPE);
    mv.push(iThread);
    mv.invokeVirtual(RUNNER_TYPE, RUNNER_ON_FINISH_METHOD);
    // Return results
    mv.loadThis();
    mv.loadLocal(resLocal);
    mv.returnValue();
    mv.visitMaxs(1, 1);
    mv.visitEnd();
}
 
Example 10
Source File: AsmDeltaSpikeProxyClassGenerator.java    From deltaspike with Apache License 2.0 4 votes vote down vote up
private static void defineMethod(ClassWriter cw, java.lang.reflect.Method method, Type proxyType)
{
    Type methodType = Type.getType(method);
    
    ArrayList<Type> exceptionsToCatch = new ArrayList<Type>();
    for (Class<?> exception : method.getExceptionTypes())
    {
        if (!RuntimeException.class.isAssignableFrom(exception))
        {
            exceptionsToCatch.add(Type.getType(exception));
        }
    }
    
    // push the method definition
    int modifiers = (Opcodes.ACC_PUBLIC | Opcodes.ACC_PROTECTED) & method.getModifiers();
    Method asmMethod = Method.getMethod(method);
    GeneratorAdapter mg = new GeneratorAdapter(modifiers,
            asmMethod,
            null,
            getTypes(method.getExceptionTypes()),
            cw);

    // copy annotations
    for (Annotation annotation : method.getDeclaredAnnotations())
    {
        mg.visitAnnotation(Type.getDescriptor(annotation.annotationType()), true).visitEnd();
    }

    mg.visitCode();

    Label tryBlockStart = mg.mark();

    mg.loadThis();
    mg.getField(proxyType, FIELDNAME_INVOCATION_HANDLER, TYPE_DELTA_SPIKE_PROXY_INVOCATION_HANDLER);
    mg.loadThis();
    loadCurrentMethod(mg, method, methodType);
    loadArguments(mg, method, methodType);
    
    mg.invokeVirtual(TYPE_DELTA_SPIKE_PROXY_INVOCATION_HANDLER,
            Method.getMethod("Object invoke(Object, java.lang.reflect.Method, Object[])"));

    // cast the result
    mg.unbox(methodType.getReturnType());

    // build try catch
    Label tryBlockEnd = mg.mark();
    
    // push return
    mg.returnValue();

    // catch runtime exceptions and rethrow it
    Label rethrow = mg.mark();
    mg.visitVarInsn(Opcodes.ASTORE, 1);
    mg.visitVarInsn(Opcodes.ALOAD, 1);
    mg.throwException();
    mg.visitTryCatchBlock(tryBlockStart, tryBlockEnd, rethrow, Type.getInternalName(RuntimeException.class));

    // catch checked exceptions and rethrow it
    boolean throwableCatched = false;
    if (!exceptionsToCatch.isEmpty())
    {
        rethrow = mg.mark();
        mg.visitVarInsn(Opcodes.ASTORE, 1);
        mg.visitVarInsn(Opcodes.ALOAD, 1);
        mg.throwException();

        // catch declared exceptions and rethrow it...
        for (Type exceptionType : exceptionsToCatch)
        {
            if (exceptionType.getClassName().equals(Throwable.class.getName()))
            {
                throwableCatched = true;
            }
            mg.visitTryCatchBlock(tryBlockStart, tryBlockEnd, rethrow, exceptionType.getInternalName());
        }
    }

    // if throwable isn't alreached cachted, catch it and wrap it with an UndeclaredThrowableException and throw it
    if (!throwableCatched)
    {
        Type uteType = Type.getType(UndeclaredThrowableException.class);
        Label wrapAndRethrow = mg.mark();

        mg.visitVarInsn(Opcodes.ASTORE, 1);
        mg.newInstance(uteType);
        mg.dup();
        mg.visitVarInsn(Opcodes.ALOAD, 1);
        mg.invokeConstructor(uteType,
                Method.getMethod("void <init>(java.lang.Throwable)"));
        mg.throwException();

        mg.visitTryCatchBlock(tryBlockStart, tryBlockEnd, wrapAndRethrow, Type.getInternalName(Throwable.class));
    }

    // finish the method
    mg.endMethod();
    mg.visitMaxs(12, 12);
    mg.visitEnd();
}
 
Example 11
Source File: Utils.java    From datakernel with Apache License 2.0 4 votes vote down vote up
public static void invokeVirtualOrInterface(GeneratorAdapter g, Class<?> owner, Method method) {
	if (owner.isInterface())
		g.invokeInterface(getType(owner), method);
	else
		g.invokeVirtual(getType(owner), method);
}
 
Example 12
Source File: ExpressionCmp.java    From datakernel with Apache License 2.0 4 votes vote down vote up
@Override
public Type load(Context ctx) {
	GeneratorAdapter g = ctx.getGeneratorAdapter();
	Label labelTrue = new Label();
	Label labelExit = new Label();

	Type leftType = left.load(ctx);
	Type rightType = right.load(ctx);
	checkArgument(Objects.equals(leftType, rightType), "Types of compared values should match");

	if (isPrimitiveType(leftType)) {
		g.ifCmp(leftType, operation.opCode, labelTrue);
	} else {
		if (operation == EQ || operation == NE) {
			g.invokeVirtual(leftType, new Method("equals", BOOLEAN_TYPE, new Type[]{Type.getType(Object.class)}));
			g.push(operation == EQ);
			g.ifCmp(BOOLEAN_TYPE, GeneratorAdapter.EQ, labelTrue);
		} else {
			g.invokeVirtual(leftType, new Method("compareTo", INT_TYPE, new Type[]{Type.getType(Object.class)}));
			if (operation == LT) {
				g.ifZCmp(GeneratorAdapter.LT, labelTrue);
			} else if (operation == GT) {
				g.ifZCmp(GeneratorAdapter.GT, labelTrue);
			} else if (operation == LE) {
				g.ifZCmp(GeneratorAdapter.LE, labelTrue);
			} else if (operation == GE) {
				g.ifZCmp(GeneratorAdapter.GE, labelTrue);
			}
		}
	}

	g.push(false);
	g.goTo(labelExit);

	g.mark(labelTrue);
	g.push(true);

	g.mark(labelExit);

	return BOOLEAN_TYPE;
}
 
Example 13
Source File: ExpressionToString.java    From datakernel with Apache License 2.0 4 votes vote down vote up
@Override
public Type load(Context ctx) {
	GeneratorAdapter g = ctx.getGeneratorAdapter();

	g.newInstance(getType(StringBuilder.class));
	g.dup();
	g.invokeConstructor(getType(StringBuilder.class), getMethod("void <init> ()"));

	boolean first = true;

	for (Object key : arguments.keySet()) {
		String str = first ? begin : separator;
		first = false;
		if (key instanceof String) {
			str += key;
		}
		if (!str.isEmpty()) {
			g.dup();
			g.push(str);
			g.invokeVirtual(getType(StringBuilder.class), getMethod("StringBuilder append(String)"));
			g.pop();
		}

		g.dup();
		Expression expression = arguments.get(key);
		Type type = expression.load(ctx);
		if (isPrimitiveType(type)) {
			g.invokeStatic(wrap(type), new Method("toString", getType(String.class), new Type[]{type}));
		} else {
			Label nullLabel = new Label();
			Label afterToString = new Label();
			g.dup();
			g.ifNull(nullLabel);
			g.invokeVirtual(type, getMethod("String toString()"));
			g.goTo(afterToString);
			g.mark(nullLabel);
			g.pop();
			g.push("null");
			g.mark(afterToString);
		}
		g.invokeVirtual(getType(StringBuilder.class), getMethod("StringBuilder append(String)"));
		g.pop();
	}

	if (!end.isEmpty()) {
		g.dup();
		g.push(end);
		g.invokeVirtual(getType(StringBuilder.class), getMethod("StringBuilder append(String)"));
		g.pop();
	}

	g.invokeVirtual(getType(StringBuilder.class), getMethod("String toString()"));
	return getType(String.class);
}
 
Example 14
Source File: ExpressionComparator.java    From datakernel with Apache License 2.0 4 votes vote down vote up
@Override
public Type load(Context ctx) {
	GeneratorAdapter g = ctx.getGeneratorAdapter();

	Label labelReturn = new Label();

	for (ComparablePair pair : pairs) {
		Type leftPropertyType = pair.left.load(ctx);
		Type rightPropertyType = pair.right.load(ctx);

		checkArgument(leftPropertyType.equals(rightPropertyType), "Types of compared values should match");
		if (isPrimitiveType(leftPropertyType)) {
			g.invokeStatic(wrap(leftPropertyType), new Method("compare", INT_TYPE, new Type[]{leftPropertyType, leftPropertyType}));
			g.dup();
			g.ifZCmp(NE, labelReturn);
			g.pop();
		} else if (!pair.nullable) {
			g.invokeVirtual(leftPropertyType, new Method("compareTo", INT_TYPE, new Type[]{Type.getType(Object.class)}));
			g.dup();
			g.ifZCmp(NE, labelReturn);
			g.pop();
		} else {
			VarLocal varRight = ctx.newLocal(rightPropertyType);
			varRight.store(ctx);

			VarLocal varLeft = ctx.newLocal(leftPropertyType);
			varLeft.store(ctx);

			Label continueLabel = new Label();
			Label nonNulls = new Label();
			Label leftNonNull = new Label();

			varLeft.load(ctx);
			g.ifNonNull(leftNonNull);

			varRight.load(ctx);
			g.ifNull(continueLabel);
			g.push(-1);
			g.returnValue();

			g.mark(leftNonNull);

			varRight.load(ctx);
			g.ifNonNull(nonNulls);
			g.push(1);
			g.returnValue();

			g.mark(nonNulls);

			varLeft.load(ctx);
			varRight.load(ctx);

			g.invokeVirtual(leftPropertyType, new Method("compareTo", INT_TYPE, new Type[]{Type.getType(Object.class)}));
			g.dup();
			g.ifZCmp(NE, labelReturn);
			g.pop();

			g.mark(continueLabel);
		}
	}

	g.push(0);

	g.mark(labelReturn);

	return INT_TYPE;
}
 
Example 15
Source File: ExpressionHash.java    From datakernel with Apache License 2.0 4 votes vote down vote up
@Override
public Type load(Context ctx) {
	GeneratorAdapter g = ctx.getGeneratorAdapter();

	int resultVar = g.newLocal(INT_TYPE);

	boolean firstIteration = true;

	for (Expression argument : arguments) {
		if (firstIteration) {
			g.push(0);
			firstIteration = false;
		} else {
			g.push(31);
			g.loadLocal(resultVar);
			g.math(IMUL, INT_TYPE);
		}

		Type fieldType = argument.load(ctx);

		if (isPrimitiveType(fieldType)) {
			if (fieldType.getSort() == Type.LONG) {
				g.dup2();
				g.push(32);
				g.visitInsn(LUSHR);
				g.visitInsn(LXOR);
				g.visitInsn(L2I);
			}
			if (fieldType.getSort() == Type.FLOAT) {
				g.invokeStatic(getType(Float.class), getMethod("int floatToRawIntBits (float)"));
			}
			if (fieldType.getSort() == Type.DOUBLE) {
				g.invokeStatic(getType(Double.class), getMethod("long doubleToRawLongBits (double)"));
				g.dup2();
				g.push(32);
				g.visitInsn(LUSHR);
				g.visitInsn(LXOR);
				g.visitInsn(L2I);
			}
			g.visitInsn(IADD);
		} else {
			int tmpVar = g.newLocal(fieldType);
			g.storeLocal(tmpVar);
			g.loadLocal(tmpVar);
			Label ifNullLabel = g.newLabel();
			g.ifNull(ifNullLabel);
			g.loadLocal(tmpVar);
			g.invokeVirtual(fieldType, getMethod("int hashCode()"));
			g.visitInsn(IADD);
			g.mark(ifNullLabel);
		}

		g.storeLocal(resultVar);
	}

	if (firstIteration) {
		g.push(0);
	} else {
		g.loadLocal(resultVar);
	}

	return INT_TYPE;
}
 
Example 16
Source File: StringSwitch.java    From AnoleFix with MIT License 4 votes vote down vote up
void visitHashMethod(GeneratorAdapter mv) {
    mv.invokeVirtual(STRING_TYPE, Method.getMethod("int hashCode()"));
}
 
Example 17
Source File: StringSwitch.java    From Stark with Apache License 2.0 4 votes vote down vote up
void visitHashMethod(GeneratorAdapter mv) {
    mv.invokeVirtual(STRING_TYPE, Method.getMethod("int hashCode()"));
}