Example usage for org.objectweb.asm MethodVisitor visitLocalVariable

List of usage examples for org.objectweb.asm MethodVisitor visitLocalVariable

Introduction

In this page you can find the example usage for org.objectweb.asm MethodVisitor visitLocalVariable.

Prototype

public void visitLocalVariable(final String name, final String descriptor, final String signature,
        final Label start, final Label end, final int index) 

Source Link

Document

Visits a local variable declaration.

Usage

From source file:org.enerj.enhancer.ClassEnhancer.java

License:Open Source License

/**
 * Emits enerj_WriteObject./*from w w w.  j a  v a  2  s.c o  m*/
 *
 * @param someFields a list of the persistent fields for this class (not including
 *  super-class fields).
 */
private void emitWriteObject(ArrayList<Field> someFields) {
    MethodVisitor mv = cv.visitMethod(ACC_PUBLIC, "enerj_WriteObject", sReadWriteObjectMethodSignature, null,
            new String[] { "java/io/IOException" });

    mv.visitCode();
    Label startLabel = new Label();
    mv.visitLabel(startLabel);

    mv.visitVarInsn(ALOAD, 1);
    mv.visitMethodInsn(INVOKEVIRTUAL, sObjectSerializerClassNameSlashed, "getDataOutput",
            "()Ljava/io/DataOutput;");
    mv.visitVarInsn(ASTORE, 2);

    // Invoke enerjPreStore if it exists
    if (mHasPreStore) {
        // Use INVOKESPECIAL here rather than INVOKEVIRTUAL for two reasons:
        // 1) We want to call the method on this object ONLY, NOT an overridden
        // method in a sub-class; 2) the method may be private, in which case
        // INVOKESPECIAL should be used according to the VM Spec.
        // this
        mv.visitVarInsn(ALOAD, 0);
        mv.visitMethodInsn(INVOKESPECIAL, mThisClassNameSlashed, sPreStoreMethodName, sNoArgMethodSignature);
    }

    if (!mIsTopLevelPersistable) {
        // Call super write if not a top-level persistable
        mv.visitVarInsn(ALOAD, 0);
        mv.visitVarInsn(ALOAD, 1);
        mv.visitMethodInsn(INVOKESPECIAL, mSuperClassNameSlashed, "enerj_WriteObject",
                sReadWriteObjectMethodSignature);
    }

    for (Field field : someFields) {
        String fieldName = field.getName();
        String fieldType = field.getDescriptor();

        // This will return null if the type is not a primitive.
        String dataInOutSuffix = MetaData.getPrimitiveDataInOutSuffix(fieldType);
        if (dataInOutSuffix != null) {
            // Write instructions for primitive...
            // DataOutput "stream" - for write method
            mv.visitVarInsn(ALOAD, 2);
            // this - for getfield
            mv.visitVarInsn(ALOAD, 0);
            mv.visitFieldInsn(GETFIELD, mThisClassNameSlashed, fieldName, fieldType);
            // Invoke write method on DataOutput
            char sigChar = fieldType.charAt(0);
            // Special case - byte, short, and char are given as an int parameter.
            if (sigChar == 'B' || sigChar == 'S' || sigChar == 'C') {
                sigChar = 'I';
            }

            mv.visitMethodInsn(INVOKEINTERFACE, sDataOutputClassNameSlashed, "write" + dataInOutSuffix,
                    "(" + sigChar + ")V");
        } else {
            // Write instructions for a SCO or FCO...
            // WriteContext - write method param 1
            mv.visitVarInsn(ALOAD, 1);
            // this - for getfield
            mv.visitVarInsn(ALOAD, 0);
            // getfield value - write method param 2
            mv.visitFieldInsn(GETFIELD, mThisClassNameSlashed, fieldName, fieldType);
            // this - write method param 3
            mv.visitVarInsn(ALOAD, 0);
            // Invoke writeObject method.
            mv.visitMethodInsn(INVOKEVIRTUAL, sObjectSerializerClassNameSlashed, "writeObject",
                    "(Ljava/lang/Object;Lorg/enerj/core/Persistable;)V");
        }
    }

    // Invoke enerjPostStore if it exists
    if (mHasPostStore) {
        // See comments on call to enerjPreStore for reason why INVOKESPECIAL is used.
        mv.visitVarInsn(ALOAD, 0);
        mv.visitMethodInsn(INVOKESPECIAL, mThisClassNameSlashed, sPostStoreMethodName, sNoArgMethodSignature);
    }

    mv.visitInsn(RETURN);

    Label endLabel = new Label();
    mv.visitLabel(endLabel);
    mv.visitLocalVariable("this", mThisClassDescr, null, startLabel, endLabel, 0);
    mv.visitLocalVariable("aContext", sObjectSerializerClassDescr, null, startLabel, endLabel, 1);
    mv.visitLocalVariable("stream", "Ljava/io/DataOutput;", null, startLabel, endLabel, 2);
    mv.visitMaxs(3, 3);
    mv.visitEnd();
}

From source file:org.enerj.enhancer.ClassEnhancer.java

License:Open Source License

/**
 * Emits enerj_ResolveObject./*from ww w.  ja v a2s. co m*/
 *
 * @param someFields a list of the persistent fields for this class (not including
 *  super-class fields).
 */
private void emitResolveObject(ArrayList<Field> someFields) {
    MethodVisitor mv = cv.visitMethod(ACC_PUBLIC, "enerj_ResolveObject", sResolveObjectMethodSignature, null,
            new String[] { "java/io/IOException" });

    mv.visitCode();
    Label startLabel = new Label();
    mv.visitLabel(startLabel);

    if (!mIsTopLevelPersistable) {
        // Call super write if not a top-level persistable
        mv.visitVarInsn(ALOAD, 0);
        mv.visitVarInsn(ALOAD, 1);
        mv.visitVarInsn(ILOAD, 2);
        mv.visitMethodInsn(INVOKESPECIAL, mSuperClassNameSlashed, "enerj_ResolveObject",
                sResolveObjectMethodSignature);
    }

    for (Field field : someFields) {
        String fieldName = field.getName();
        String fieldType = field.getDescriptor();

        // This will return null if the type is not a primitive.
        String dataInOutSuffix = MetaData.getPrimitiveDataInOutSuffix(fieldType);
        // Only need to resolve objects, not primitive types.
        if (dataInOutSuffix == null) {
            // Write instructions for a SCO or FCO...
            // WriteContext - write method param 1
            mv.visitVarInsn(ALOAD, 1);
            // this - for getfield
            mv.visitVarInsn(ALOAD, 0);
            // getfield value - write method param 2
            mv.visitFieldInsn(GETFIELD, mThisClassNameSlashed, fieldName, fieldType);
            // this - write method param 2
            mv.visitVarInsn(ILOAD, 2);
            mv.visitMethodInsn(INVOKEVIRTUAL, sObjectSerializerClassNameSlashed, "resolveObject",
                    "(Ljava/lang/Object;Z)V");
        }
    }

    mv.visitInsn(RETURN);

    Label endLabel = new Label();
    mv.visitLabel(endLabel);
    mv.visitLocalVariable("this", mThisClassDescr, null, startLabel, endLabel, 0);
    mv.visitLocalVariable("aContext", sObjectSerializerClassDescr, null, startLabel, endLabel, 1);
    mv.visitLocalVariable("shouldDisassociate", "Z", null, startLabel, endLabel, 2);
    mv.visitMaxs(3, 3);
    mv.visitEnd();
}

From source file:org.enerj.enhancer.ClassEnhancer.java

License:Open Source License

/**
 * Generate the enerj_Hollow method./*from   w  w w.j av a2  s . c o  m*/
 *
 * @param someFields a list of the persistent fields for this class (not including
 *  super-class fields).
 *
 * @throws EnhancerException in the event of an error.
 */
private void emitHollow(ArrayList<Field> someFields) throws EnhancerException {
    MethodVisitor mv = cv.visitMethod(ACC_PUBLIC, "enerj_Hollow", sNoArgMethodSignature, null, null);

    mv.visitCode();
    Label startLabel = new Label();
    mv.visitLabel(startLabel);

    // Invoke enerjPreHollow if it exists
    if (mHasPreHollow) {
        mv.visitVarInsn(ALOAD, 0);
        mv.visitMethodInsn(INVOKESPECIAL, mThisClassNameSlashed, "enerjPreHollow", sNoArgMethodSignature);
    }

    if (!mIsTopLevelPersistable) {
        // Call super's hollow if not a top-level persistable.
        mv.visitVarInsn(ALOAD, 0);
        mv.visitMethodInsn(INVOKESPECIAL, mSuperClassNameSlashed, "enerj_Hollow", sNoArgMethodSignature);
    }

    for (Field field : someFields) {
        String fieldType = field.getDescriptor();
        // Only null the field if not a primitive type.
        if (!MetaData.isPrimitive(fieldType)) {
            // this
            mv.visitVarInsn(ALOAD, 0);
            // null
            mv.visitInsn(ACONST_NULL);
            // Store the value
            mv.visitFieldInsn(PUTFIELD, mThisClassNameSlashed, field.getName(), fieldType);
        }
    }

    mv.visitVarInsn(ALOAD, 0);
    mv.visitMethodInsn(INVOKESTATIC, sPersistableHelperClassSlashed, "completeHollow",
            sPersistableVoidSignature);
    mv.visitInsn(RETURN);

    Label endLabel = new Label();
    mv.visitLabel(endLabel);

    mv.visitLocalVariable("this", mThisClassDescr, null, startLabel, endLabel, 0);
    mv.visitMaxs(0, 0);
    mv.visitEnd();
}

From source file:org.enerj.enhancer.ClassEnhancer.java

License:Open Source License

/**
 * Emit the special constructor. "&lt;init>(Persister)".
 *///  w w w  .  j av a2 s  .  com
private void emitSpecialConstructor() {
    MethodVisitor mv = cv.visitMethod(ACC_PUBLIC, "<init>", sPersisterConstructorSignature, null, null);

    mv.visitCode();
    Label startLabel = new Label();
    mv.visitLabel(startLabel);
    mv.visitVarInsn(ALOAD, 0);

    String constructorClass = mSuperClassNameSlashed;
    String signature;
    if (mIsTopLevelPersistable) {
        // Super-class is not Persistable, call default constructor
        signature = sNoArgMethodSignature;

        if (mHasNoArgConstructor) {
            // Use this class' no-arg constructor rather than the super-class'.
            // The super-class might not have an exposed no-arg constructor.
            // However, this also causes PersistableHelper.initPersistable to be called since
            // the default constructor was enhanced to do so. This has side-effect,
            // of just marking the object as "new". However, the Persister.getObjectByOID()
            // method clears the "new" flag.
            constructorClass = mThisClassNameSlashed;
        }
    } else {
        mv.visitVarInsn(ALOAD, 1); // aDatabase
        signature = sPersisterConstructorSignature;
    }

    mv.visitMethodInsn(INVOKESPECIAL, constructorClass, "<init>", signature);

    mv.visitInsn(RETURN);
    Label endLabel = new Label();
    mv.visitLabel(endLabel);

    mv.visitLocalVariable("this", mThisClassDescr, null, startLabel, endLabel, 0);
    mv.visitMaxs(0, 0);
    mv.visitEnd();
}

From source file:org.enerj.enhancer.ClassEnhancer.java

License:Open Source License

/**
 * Emits the class Id static variable and a static and non-static getters for it.
 *//*  w ww .  j  a  va  2 s .c o  m*/
private void emitClassId() {
    // Emit static field
    FieldVisitor fv = cv.visitField(ACC_PRIVATE + ACC_STATIC + ACC_TRANSIENT, sClassIdFieldName, "J", null,
            null);
    fv.visitEnd();

    // Emit static getter. We'll use this when we only have a class and not an object.
    MethodVisitor mv = cv.visitMethod(ACC_PUBLIC + ACC_STATIC, "enerj_GetClassIdStatic", "()J", null, null);
    mv.visitCode();
    mv.visitFieldInsn(GETSTATIC, mThisClassNameSlashed, sClassIdFieldName, "J");
    mv.visitInsn(LRETURN);
    mv.visitMaxs(0, 0);
    mv.visitEnd();

    // Emit non-static Persistable interface getter. 
    // We'll use for non-reflective access when we have a Persistable.
    mv = cv.visitMethod(ACC_PUBLIC, "enerj_GetClassId", "()J", null, null);
    mv.visitCode();
    Label startLabel = new Label();
    mv.visitLabel(startLabel);
    mv.visitFieldInsn(GETSTATIC, mThisClassNameSlashed, sClassIdFieldName, "J");
    mv.visitInsn(LRETURN);

    Label endLabel = new Label();
    mv.visitLabel(endLabel);
    mv.visitLocalVariable("this", mThisClassDescr, null, startLabel, endLabel, 0);
    mv.visitMaxs(0, 0);
    mv.visitEnd();
}

From source file:org.fabric3.binding.rs.runtime.bytecode.ProviderGeneratorImpl.java

License:Open Source License

private void writeConstructor(String handlerName, String handlerDescriptor, ClassWriter cw) {
    MethodVisitor mv;
    mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
    mv.visitCode();/*ww  w .j  ava2s  . c om*/
    Label l0 = new Label();
    mv.visitLabel(l0);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitMethodInsn(INVOKESPECIAL, handlerName, "<init>", "()V");
    mv.visitInsn(RETURN);
    Label l1 = new Label();
    mv.visitLabel(l1);
    mv.visitLocalVariable("this", handlerDescriptor, null, l0, l1, 0);
    mv.visitMaxs(1, 1);
    mv.visitEnd();
}

From source file:org.fabric3.implementation.bytecode.proxy.common.ProxyFactoryImpl.java

License:Open Source License

private void writeConstructor(String baseName, String thisDescriptor, ClassWriter cw) {
    MethodVisitor mv;
    mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
    mv.visitCode();//from w  w w. ja v  a2 s. co m
    Label l0 = new Label();
    mv.visitLabel(l0);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitMethodInsn(INVOKESPECIAL, baseName, "<init>", "()V");
    mv.visitInsn(RETURN);
    Label l1 = new Label();
    mv.visitLabel(l1);
    mv.visitLocalVariable("this", thisDescriptor, null, l0, l1, 0);
    mv.visitMaxs(1, 1);
    mv.visitEnd();
}

From source file:org.fabric3.implementation.bytecode.reflection.BytecodeConsumerInvokerFactory.java

License:Open Source License

private void writeTargetInvoke(Method method, String internalTargetName, ClassWriter cw) {
    MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "invoke",
            "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;", null, EXCEPTIONS);
    mv.visitCode();//from ww w.j  a va  2  s.c  om
    Label label1 = new Label();
    mv.visitLabel(label1);
    mv.visitLineNumber(9, label1);
    mv.visitVarInsn(Opcodes.ALOAD, 1);
    mv.visitTypeInsn(Opcodes.CHECKCAST, internalTargetName);

    if (method.getParameterTypes().length == 1) {
        // single argument method, load the parameter passes on to the stack
        Class<?> paramType = method.getParameterTypes()[0];
        mv.visitVarInsn(Opcodes.ALOAD, 2);

        writeParam(paramType, mv);

    } else if (method.getParameterTypes().length > 1) {
        // multi-argument method: cast the parameter to an object array and then load each element on the stack to be passed as params
        mv.visitVarInsn(Opcodes.ALOAD, 2);

        mv.visitTypeInsn(Opcodes.CHECKCAST, "[Ljava/lang/Object;");
        mv.visitTypeInsn(Opcodes.CHECKCAST, "[Ljava/lang/Object;");
        mv.visitVarInsn(Opcodes.ASTORE, 3);

        int pos = 0;
        mv.visitVarInsn(Opcodes.ALOAD, 3);
        for (Class<?> paramType : method.getParameterTypes()) {
            mv.visitInsn(Opcodes.ICONST_0 + pos);
            mv.visitInsn(Opcodes.AALOAD);

            writeParam(paramType, mv);

            if (pos < method.getParameterTypes().length - 1) {
                mv.visitVarInsn(Opcodes.ALOAD, 3);
            }
            pos++;
        }
    }

    // invoke the instance
    String methodName = method.getName();
    String methodDescriptor = Type.getMethodDescriptor(method);

    mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, internalTargetName, methodName, methodDescriptor);

    Class<?> returnType = method.getReturnType();
    writeReturn(returnType, mv);

    Label label2 = new Label();
    mv.visitLabel(label2);
    String descriptor = Type.getDescriptor(ServiceInvoker.class);

    mv.visitLocalVariable("this", descriptor, null, label1, label2, 0);
    mv.visitLocalVariable("instance", "Ljava/lang/Object;", null, label1, label2, 1);
    mv.visitLocalVariable("arg", "Ljava/lang/Object;", null, label1, label2, 2);
    mv.visitMaxs(2, 3);
    mv.visitEnd();
}

From source file:org.fabric3.implementation.bytecode.reflection.BytecodeHelper.java

License:Open Source License

/**
 * Creates a no-args constructor./*from ww  w . j av  a2s.c  om*/
 *
 * @param cw the class writer
 */
public static void writeConstructor(ClassWriter cw, Class<?> superType) {
    String descriptor = Type.getDescriptor(ServiceInvoker.class);

    MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
    mv.visitCode();
    Label label = new Label();
    mv.visitLabel(label);
    mv.visitLineNumber(6, label);
    mv.visitVarInsn(Opcodes.ALOAD, 0);
    mv.visitMethodInsn(Opcodes.INVOKESPECIAL, Type.getInternalName(superType), "<init>", "()V");
    mv.visitInsn(Opcodes.RETURN);
    Label l1 = new Label();
    mv.visitLabel(l1);
    mv.visitLocalVariable("this", descriptor, null, label, l1, 0);
    mv.visitMaxs(1, 1);
    mv.visitEnd();
}

From source file:org.fabric3.monitor.impl.proxy.BytecodeMonitorProxyService.java

License:Open Source License

/**
 * Implements a monitor interface method.
 *
 * @param cw                       the class writer
 * @param index                    the method index
 * @param proxyClassNameInternal   the parameter signature
 * @param writeParametersSignature the parameter types
 *///  w  ww.j av  a 2s  .  c o m
private void generateMethod(ClassWriter cw, Method method, int index, String proxyClassNameInternal,
        String writeParametersSignature) {
    String methodSignature = Type.getMethodDescriptor(method);

    // calculate the position of local variables. Per the JVM spec, pos 0 is reserved for a reference to "this"
    Class<?>[] paramTypes = method.getParameterTypes();
    int numParams = paramTypes.length;

    int offset = calculateParameterSpace(paramTypes);

    // calculate position of local variables
    int varIndexPosition = offset + 1; // pos of the index variable used for looking up the DispatchInfo
    int varCurrentLevelPosition = varIndexPosition + 1;
    int varCurrentMessagePosition = varCurrentLevelPosition + 1;
    int varTimestampPosition = varCurrentMessagePosition + 1;
    int varDispatchInfoPosition = varCurrentMessagePosition + 1; // Note this is the same as varTimestampPos since there is an if

    int varEntryPosition = varTimestampPosition + 2; // Note +2
    int varArgsPosition = varTimestampPosition + 2; // Note +2 and the same as varEntryPosition since there is an if

    int varStartPosition = varEntryPosition + 1;
    int varBufferPosition = varStartPosition + 2;

    MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, method.getName(), methodSignature, null, null);

    mv.visitCode();
    Label l0 = new Label();
    Label l1 = new Label();
    Label l2 = new Label();
    mv.visitTryCatchBlock(l0, l1, l2, null);
    Label l3 = new Label();
    mv.visitTryCatchBlock(l2, l3, l2, null);
    Label l4 = new Label();
    mv.visitLabel(l4);
    mv.visitLineNumber(62, l4);

    // set the index var used to lookup the DispatchInfo. The array of DispatchInfo objects correspond to the ordering of Methods in the proxy interface.
    pushInteger(index, mv);
    mv.visitVarInsn(ISTORE, varIndexPosition);

    Label l5 = new Label();
    mv.visitLabel(l5);
    mv.visitLineNumber(65, l5);

    // lookup the DispatchInfo based on the index for the method
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "infos", "[L" + DISPATCH_INFO + ";");
    mv.visitVarInsn(ILOAD, varIndexPosition);
    mv.visitInsn(AALOAD);
    mv.visitVarInsn(ASTORE, varDispatchInfoPosition);
    Label l11 = new Label();
    mv.visitLabel(l11);
    mv.visitLineNumber(70, l11);
    mv.visitVarInsn(ALOAD, varDispatchInfoPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, DISPATCH_INFO, "getLevel", "()L" + MONITOR_LEVEL + ";");
    mv.visitVarInsn(ASTORE, varCurrentLevelPosition);
    Label l12 = new Label();
    mv.visitLabel(l12);
    mv.visitLineNumber(71, l12);
    mv.visitVarInsn(ALOAD, varDispatchInfoPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, DISPATCH_INFO, "getMessage", "()Ljava/lang/String;");
    mv.visitVarInsn(ASTORE, varCurrentMessagePosition);

    mv.visitVarInsn(ALOAD, varCurrentLevelPosition);
    Label l13 = new Label();
    mv.visitJumpInsn(IFNULL, l13);
    mv.visitVarInsn(ALOAD, varCurrentLevelPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_LEVEL, "intValue", "()I");
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "monitorable",
            "Lorg/fabric3/api/host/monitor/Monitorable;");
    mv.visitMethodInsn(INVOKEINTERFACE, "org/fabric3/api/host/monitor/Monitorable", "getLevel",
            "()L" + MONITOR_LEVEL + ";");
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_LEVEL, "intValue", "()I");
    Label l14 = new Label();
    mv.visitJumpInsn(IF_ICMPGE, l14);
    mv.visitLabel(l13);
    mv.visitLineNumber(75, l13);
    mv.visitInsn(RETURN);
    mv.visitLabel(l14);
    mv.visitLineNumber(77, l14);
    mv.visitMethodInsn(INVOKESTATIC, "java/lang/System", "currentTimeMillis", "()J");
    mv.visitVarInsn(LSTORE, varTimestampPosition);
    Label l15 = new Label();
    mv.visitLabel(l15);
    mv.visitLineNumber(78, l15);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "asyncEnabled", "Z");
    Label l16 = new Label();
    mv.visitJumpInsn(IFEQ, l16);
    Label l17 = new Label();
    mv.visitLabel(l17);
    mv.visitLineNumber(79, l17);
    mv.visitInsn(ACONST_NULL);
    mv.visitVarInsn(ASTORE, varArgsPosition);
    mv.visitLabel(l0);
    mv.visitLineNumber(81, l0);
    mv.visitMethodInsn(INVOKESTATIC, "java/lang/System", "nanoTime", "()J");
    mv.visitVarInsn(LSTORE, varStartPosition);
    Label l18 = new Label();
    mv.visitLabel(l18);
    mv.visitLineNumber(82, l18);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "router", "L" + DESTINATION_ROUTER + ";");
    mv.visitMethodInsn(INVOKEINTERFACE, DESTINATION_ROUTER, "get", "()L" + MONITOR_EVENT_ENTRY + ";");
    mv.visitVarInsn(ASTORE, varEntryPosition);
    Label l19 = new Label();
    mv.visitLabel(l19);
    mv.visitLineNumber(83, l19);
    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "destinationIndex", "I");
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "setDestinationIndex", "(I)V");
    Label l20 = new Label();
    mv.visitLabel(l20);
    mv.visitLineNumber(84, l20);
    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitVarInsn(LLOAD, varStartPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "setTimestampNanos", "(J)V");
    Label l21 = new Label();
    mv.visitLabel(l21);
    mv.visitLineNumber(85, l21);
    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "getBuffer",
            "()Lorg/fabric3/monitor/spi/buffer/ResizableByteBuffer;");
    mv.visitVarInsn(ASTORE, varBufferPosition);

    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitVarInsn(ALOAD, varCurrentMessagePosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "setTemplate", "(Ljava/lang/String;)V");

    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitMethodInsn(INVOKESTATIC, "java/lang/System", "currentTimeMillis", "()J");

    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "setEntryTimestamp", "(J)V");

    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitVarInsn(ALOAD, varCurrentLevelPosition);
    mv.visitMethodInsn(INVOKEVIRTUAL, MONITOR_EVENT_ENTRY, "setLevel", "(L" + MONITOR_LEVEL + ";)V");

    Label l22 = new Label();
    mv.visitLabel(l22);
    mv.visitLineNumber(87, l22);

    mv.visitVarInsn(ALOAD, 0);

    // Load the method arguments onto the stack. Note that we access the method arguments using i+1 since the 0 position is used by "this" (params begin
    // at 1).
    for (int i = 0; i < paramTypes.length; i++) {
        Class<?> paramType = paramTypes[i];
        if (paramType.isPrimitive()) {
            if (Integer.TYPE.equals(paramType)) {
                mv.visitVarInsn(ILOAD, i + 1);
            } else if (Long.TYPE.equals(paramType)) {
                mv.visitVarInsn(LLOAD, i + 1);
            } else if (Double.TYPE.equals(paramType)) {
                mv.visitVarInsn(DLOAD, i + 1);
            } else if (Boolean.TYPE.equals(paramType)) {
                mv.visitVarInsn(ILOAD, i + 1);
            } else if (Float.TYPE.equals(paramType)) {
                mv.visitVarInsn(FLOAD, i + 1);
            } else if (Short.TYPE.equals(paramType)) {
                mv.visitVarInsn(ILOAD, i + 1);
            } else if (Byte.TYPE.equals(paramType)) {
                mv.visitVarInsn(ILOAD, i + 1);
            } else if (Character.TYPE.equals(paramType)) {
                mv.visitVarInsn(ILOAD, i + 1);
            } else {
                throw new AssertionError("Unhandled type: " + paramType);
            }

        } else {
            mv.visitVarInsn(ALOAD, i + 1);
        }
    }

    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitMethodInsn(INVOKESPECIAL, proxyClassNameInternal, "writeParameters" + index,
            writeParametersSignature);

    Label l24 = new Label();
    mv.visitLabel(l24);
    mv.visitLineNumber(90, l24);

    mv.visitLabel(l1);
    mv.visitLineNumber(95, l1);
    mv.visitVarInsn(ALOAD, varEntryPosition);
    Label l27 = new Label();
    mv.visitJumpInsn(IFNULL, l27);
    Label l28 = new Label();
    mv.visitLabel(l28);
    mv.visitLineNumber(96, l28);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "router", "L" + DESTINATION_ROUTER + ";");
    mv.visitVarInsn(ALOAD, varEntryPosition);
    mv.visitMethodInsn(INVOKEINTERFACE, DESTINATION_ROUTER, "publish", "(L" + MONITOR_EVENT_ENTRY + ";)V");
    mv.visitJumpInsn(GOTO, l27);
    mv.visitLabel(l2);
    mv.visitLineNumber(95, l2);
    mv.visitVarInsn(ASTORE, 13);
    mv.visitLabel(l3);
    mv.visitVarInsn(ALOAD, varEntryPosition);
    Label l29 = new Label();
    mv.visitJumpInsn(IFNULL, l29);
    Label l30 = new Label();
    mv.visitLabel(l30);
    mv.visitLineNumber(96, l30);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "router", "L" + DESTINATION_ROUTER + ";");
    mv.visitVarInsn(ALOAD, varArgsPosition);
    mv.visitMethodInsn(INVOKEINTERFACE, DESTINATION_ROUTER, "publish", "(L" + MONITOR_EVENT_ENTRY + ";)V");
    mv.visitLabel(l29);
    mv.visitVarInsn(ALOAD, 13);
    mv.visitInsn(ATHROW);
    mv.visitLabel(l27);
    mv.visitLineNumber(99, l27);
    Label l31 = new Label();
    mv.visitJumpInsn(GOTO, l31);
    mv.visitLabel(l16);
    mv.visitLineNumber(100, l16);
    pushInteger(numParams, mv);
    mv.visitTypeInsn(ANEWARRAY, "java/lang/Object");
    mv.visitVarInsn(ASTORE, varArgsPosition);
    Label l32 = new Label();
    mv.visitLabel(l32);
    mv.visitLineNumber(101, l32);

    for (int i = 0; i < paramTypes.length; i++) {
        mv.visitVarInsn(ALOAD, varArgsPosition);
        pushInteger(i, mv);

        if (paramTypes[i].isPrimitive()) {
            // i+1 since that is the position of the method argument (position 0 is reserved for "this")
            if (Integer.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(ILOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Integer", "valueOf", "(I)Ljava/lang/Integer;");
            } else if (Long.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(LLOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Long", "valueOf", "(J)Ljava/lang/Long;");
            } else if (Double.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(DLOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Double", "valueOf", "(D)Ljava/lang/Double;");
            } else if (Float.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(FLOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Float", "valueOf", "(F)Ljava/lang/Float;");
            } else if (Boolean.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(ILOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Integer", "valueOf", "(Z)Ljava/lang/Boolean;");
            } else if (Short.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(ILOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Short", "valueOf", "(S)Ljava/lang/Short;");
            } else if (Byte.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(ILOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Byte", "valueOf", "(B)Ljava/lang/Byte;");
            } else if (Character.TYPE.equals(paramTypes[i])) {
                mv.visitVarInsn(ILOAD, i + 1);
                mv.visitMethodInsn(INVOKESTATIC, "java/lang/Character", "valueOf", "(C)Ljava/lang/Character;");
            }
        } else {
            mv.visitVarInsn(ALOAD, i + 1); // i+1 since that is the position of the method argument (position 0 is reserved for "this")
        }
        mv.visitInsn(AASTORE);
    }

    Label l34 = new Label();
    mv.visitLabel(l34);
    mv.visitLineNumber(103, l34);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "router", "L" + DESTINATION_ROUTER + ";");
    mv.visitVarInsn(ALOAD, varCurrentLevelPosition);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "destinationIndex", "I");
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "runtimeName", "Ljava/lang/String;");
    mv.visitVarInsn(LLOAD, varTimestampPosition);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, ABSTRACT_MONITOR_HANDLER, "source", "Ljava/lang/String;");
    mv.visitVarInsn(ALOAD, varCurrentMessagePosition);
    mv.visitVarInsn(ALOAD, varArgsPosition);
    mv.visitMethodInsn(INVOKEINTERFACE, DESTINATION_ROUTER, "send",
            "(Lorg/fabric3/api/annotation/monitor/MonitorLevel;ILjava/lang/String;JLjava/lang/String;Ljava/lang/String;[Ljava/lang/Object;)V");
    mv.visitLabel(l31);
    mv.visitLineNumber(106, l31);
    mv.visitInsn(RETURN);

    Label methodEnd = new Label();
    mv.visitLabel(methodEnd);

    mv.visitLocalVariable("this", "Lorg/fabric3/monitor/impl/proxy/AbstractMonitorHandler;", null, l4,
            methodEnd, 0);

    // Load the method params as local variables. Note the index starts at 1 since 0 is reserved for "this".
    for (int i = 1; i <= numParams; i++) {
        Class<?> paramType = paramTypes[i - 1];
        if (String.class.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "Ljava/lang/String;", null, l4, methodEnd, i);
        } else if (Integer.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "I", null, l4, methodEnd, i);
        } else if (Long.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "J", null, l4, methodEnd, i);
        } else if (Double.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "D", null, l4, methodEnd, i);
        } else if (Boolean.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "Z", null, l4, methodEnd, i);
        } else if (Float.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "F", null, l4, methodEnd, i);
        } else if (Short.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "S", null, l4, methodEnd, i);
        } else if (Byte.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "B", null, l4, methodEnd, i);
        } else if (Character.TYPE.equals(paramType)) {
            mv.visitLocalVariable("arg" + i, "C", null, l4, methodEnd, i);
        } else if (paramType.isPrimitive()) {
            throw new AssertionError("Unhandled type: " + paramType);
        } else {
            mv.visitLocalVariable("arg" + i, "Ljava/lang/Object;", null, l4, methodEnd, i);
        }

    }

    mv.visitLocalVariable("index", "I", null, l5, methodEnd, varIndexPosition);

    mv.visitLocalVariable("currentLevel", "L" + MONITOR_LEVEL + ";", null, l12, methodEnd,
            varCurrentLevelPosition);
    mv.visitLocalVariable("currentMessage", "Ljava/lang/String;", null, l12, methodEnd,
            varCurrentMessagePosition);
    mv.visitLocalVariable("timestamp", "J", null, l15, methodEnd, varTimestampPosition);

    mv.visitLocalVariable("info", "L" + DISPATCH_INFO + ";", null, l11, l12, varDispatchInfoPosition);

    mv.visitLocalVariable("entry", "L" + MONITOR_EVENT_ENTRY + ";", null, l0, l27, varEntryPosition);
    mv.visitLocalVariable("args", "[Ljava/lang/Object;", null, l32, l31, varArgsPosition);

    mv.visitLocalVariable("start", "J", null, l18, l1, varStartPosition);
    mv.visitLocalVariable("buffer", "Lorg/fabric3/monitor/spi/buffer/ResizableByteBuffer;", null, l22, l1,
            varBufferPosition);

    mv.visitMaxs(9, 14);
    mv.visitEnd();
}