Example usage for org.objectweb.asm Opcodes GOTO

List of usage examples for org.objectweb.asm Opcodes GOTO

Introduction

In this page you can find the example usage for org.objectweb.asm Opcodes GOTO.

Prototype

int GOTO

To view the source code for org.objectweb.asm Opcodes GOTO.

Click Source Link

Usage

From source file:jpcsp.Allegrex.compiler.CompilerContext.java

License:Open Source License

@Override
public void endPfxCompiled(int vsize, boolean isFloat, boolean doFlush) {
    if (doFlush) {
        flushPfxCompiled(vsize, getVdRegisterIndex(), isFloat);
    }/* ww w.  jav  a 2s  .  com*/

    if (interpretPfxLabel != null) {
        Label continueLabel = new Label();
        mv.visitJumpInsn(Opcodes.GOTO, continueLabel);
        mv.visitLabel(interpretPfxLabel);
        compileInterpreterInstruction();
        mv.visitLabel(continueLabel);

        interpretPfxLabel = null;
    }

    pfxVdOverlap = false;
}

From source file:jpcsp.Allegrex.compiler.CompilerContext.java

License:Open Source License

@Override
public void compileVFPUInstr(Object cstBefore, int opcode, String mathFunction) {
    int vsize = getVsize();
    boolean useVt = getCodeInstruction().hasFlags(Instruction.FLAG_USES_VFPU_PFXT);

    if (mathFunction == null && opcode == Opcodes.NOP && !useVt && cstBefore == null && canUseVFPUInt(vsize)) {
        // VMOV should use int instead of float
        startPfxCompiled(false);//from   w w w. j  a v  a  2s . c  o m

        for (int n = 0; n < vsize; n++) {
            prepareVdForStoreInt(n);
            loadVsInt(n);
            storeVdInt(n);
        }

        endPfxCompiled(vsize, false);
    } else {
        startPfxCompiled(true);

        for (int n = 0; n < vsize; n++) {
            prepareVdForStore(n);
            if (cstBefore != null) {
                mv.visitLdcInsn(cstBefore);
            }

            loadVs(n);
            if (useVt) {
                loadVt(n);
            }
            if (mathFunction != null) {
                if ("abs".equals(mathFunction)) {
                    mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(Math.class), mathFunction,
                            "(F)F");
                } else if ("max".equals(mathFunction) || "min".equals(mathFunction)) {
                    mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(Math.class), mathFunction,
                            "(FF)F");
                } else {
                    mv.visitInsn(Opcodes.F2D);
                    mv.visitMethodInsn(Opcodes.INVOKESTATIC, Type.getInternalName(Math.class), mathFunction,
                            "(D)D");
                    mv.visitInsn(Opcodes.D2F);
                }
            }

            Label doneStore = null;
            if (opcode != Opcodes.NOP) {
                Label doneOpcode = null;

                if (opcode == Opcodes.FDIV && cstBefore == null) {
                    // if (value1 == 0f && value2 == 0f) {
                    //     result = PSP-NaN | (sign(value1) ^ sign(value2));
                    // } else {
                    //     result = value1 / value2;
                    // }
                    doneOpcode = new Label();
                    doneStore = new Label();
                    Label notZeroByZero = new Label();
                    Label notZeroByZeroPop = new Label();
                    mv.visitInsn(Opcodes.DUP2);
                    mv.visitInsn(Opcodes.FCONST_0);
                    mv.visitInsn(Opcodes.FCMPG);
                    mv.visitJumpInsn(Opcodes.IFNE, notZeroByZeroPop);
                    mv.visitInsn(Opcodes.FCONST_0);
                    mv.visitInsn(Opcodes.FCMPG);
                    mv.visitJumpInsn(Opcodes.IFNE, notZeroByZero);
                    convertVFloatToInt();
                    loadImm(0x80000000);
                    mv.visitInsn(Opcodes.IAND);
                    mv.visitInsn(Opcodes.SWAP);
                    convertVFloatToInt();
                    loadImm(0x80000000);
                    mv.visitInsn(Opcodes.IAND);
                    mv.visitInsn(Opcodes.IXOR);
                    storeTmp1();
                    // Store the NaN value as an "int" to not loose any bit.
                    // Storing as float results in 0x7FC00001 instead of 0x7F800001.
                    mv.visitInsn(Opcodes.DUP2_X2);
                    mv.visitInsn(Opcodes.POP2);
                    loadPspNaNInt();
                    loadTmp1();
                    mv.visitInsn(Opcodes.IOR);
                    int preparedRegister = preparedRegisterForStore;
                    storeVdInt(n);
                    preparedRegisterForStore = preparedRegister;
                    mv.visitJumpInsn(Opcodes.GOTO, doneStore);

                    mv.visitLabel(notZeroByZeroPop);
                    mv.visitInsn(Opcodes.POP);
                    mv.visitLabel(notZeroByZero);
                }

                mv.visitInsn(opcode);

                if (doneOpcode != null) {
                    mv.visitLabel(doneOpcode);
                }
            }

            storeVd(n);

            if (doneStore != null) {
                mv.visitLabel(doneStore);
            }
        }

        endPfxCompiled(vsize, true);
    }
}

From source file:lapin.comp.asm.ASMByteCodeGenerator.java

License:Open Source License

private void generateCall(CallableInfo ci, Env env) {
    /*/*from   w  ww .  j  a  va 2s.co m*/
     * local variables
     * <Callable#call>
     * 0: this
     * 1: args (list of arguments)
     * 2: env
     *
     * <Callable0#call0>
     * 0: this
     * 1: env
     *
     * <Callable1#call1>
     * 0: this
     * 1: arg0
     * 2: env
     *
     * <Callable2#call2>
     * 0: this
     * 1: arg0
     * 2: arg1
     * 3: env
     *
     * ...
     *
     */
    MethodVisitor mv = _cw.visitMethod(
            ci.mi.implCallable() ? Opcodes.ACC_PUBLIC + Opcodes.ACC_FINAL : Opcodes.ACC_FINAL, ci.mi.name(),
            Type.getMethodDescriptor(ci.retType, ci.paramTypes), null, null);

    // instruction list
    int len = ci.mi.instLen();
    // label
    Label label = null;

    // generate code
    for (int i = 0; i < len; i++) {
        Object inst = ci.mi.getInst(i);
        if (Logger.tracelevelp(env))
            Logger.trace("[asm:gen]" + i + ":\t~S", Lists.list(inst), env);

        // inst is symbol
        // -> convert tag (Symbol) to label (ASMe Label object)
        if (Data.isSymbol(inst)) {
            Symbol tag = Data.symbol(inst);
            Label l = (Label) ci.labelTable.get(tag);
            if (l == null) {
                throw new NotReachedException("label is null: ~S.", Lists.list(tag));
            } else if (l != label) {
                mv.visitLabel(l);
                label = l;
                if (Logger.tracelevelp(env))
                    Logger.trace("[asm:gen]" + i + ":\ttag ~S -> label ~S", Lists.list(tag, l), env);
            } else {
                if (Logger.tracelevelp(env))
                    Logger.trace("[asm:gen]" + i + ":\ttag ~S -> label ~S" + " (dup)", Lists.list(tag, l), env);
            }
            continue;
        }

        // inst must be the form of (id <arg1> <arg2> ....)
        Object id = Lists.car(inst);
        if (id == Insts.CONST) {
            /* push const on the stack. */
            Object obj = Lists.cadr(inst);
            String val = Data.string(constTable.get(obj));
            mv.visitVarInsn(Opcodes.ALOAD, 0);
            mv.visitFieldInsn(Opcodes.GETFIELD, toInternalName(super.classInfo.classname()), val,
                    TYPE_OBJECT.getDescriptor());
        } else if (id == Insts.VAR) {
            /* push var on the stack */
            Object var = Lists.cadr(inst);
            String val = Data.string(varTable.get(var));
            mv.visitVarInsn(Opcodes.ALOAD, 0);
            mv.visitFieldInsn(Opcodes.GETFIELD, toInternalName(super.classInfo.classname()), val,
                    TYPE_SYMBOL.getDescriptor());
        } else if (id == Insts.LAMBDA_LIST) {
            /* push lambdaList on the stack */
            Object var = Lists.cadr(inst);
            /* push _ll_<i> on the stack */
            String val = Data.string(llTable.get(var));
            mv.visitVarInsn(Opcodes.ALOAD, 0);
            mv.visitFieldInsn(Opcodes.GETFIELD, toInternalName(super.classInfo.classname()), val,
                    TYPE_LAMBDA_LIST.getDescriptor());
        } else if (id == Insts.ENV_GET) {
            /* env.get */
            Class type = Data.javaClass(Lists.cadr(inst));
            if (type.equals(int.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "getInt",
                        Type.getMethodDescriptor(Type.INT_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (type.equals(double.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "getDouble",
                        Type.getMethodDescriptor(Type.DOUBLE_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (type.equals(char.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "getChar",
                        Type.getMethodDescriptor(Type.CHAR_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (Object.class.isAssignableFrom(type)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "get",
                        Type.getMethodDescriptor(TYPE_OBJECT, new Type[] { TYPE_SYMBOL }));
            } else {
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
        } else if (id == Insts.ENV_SET) {
            /* env.set */
            Class type = Data.javaClass(Lists.cadr(inst));
            if (type.equals(int.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "set",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.INT_TYPE }));
            } else if (type.equals(double.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "set",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.DOUBLE_TYPE }));
            } else if (type.equals(char.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "set",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.CHAR_TYPE }));
            } else if (Object.class.isAssignableFrom(type)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "set",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, TYPE_OBJECT }));
            } else {
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
        } else if (id == Insts.ENV_BIND) {
            /* env.bind */
            Class type = Data.javaClass(Lists.cadr(inst));
            if (type.equals(int.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "bind",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.INT_TYPE }));
            } else if (type.equals(double.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "bind",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.DOUBLE_TYPE }));
            } else if (type.equals(char.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "bind",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, Type.CHAR_TYPE }));
            } else if (Object.class.isAssignableFrom(type)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "bind",
                        Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { TYPE_SYMBOL, TYPE_OBJECT }));
            } else {
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
        } else if (id == Insts.ENV_UNBIND) {
            /* env.unbind */
            Class type = Data.javaClass(Lists.cadr(inst));
            if (type.equals(int.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "unbindInt",
                        Type.getMethodDescriptor(Type.INT_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (type.equals(double.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "unbindDouble",
                        Type.getMethodDescriptor(Type.DOUBLE_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (type.equals(char.class)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "unbindChar",
                        Type.getMethodDescriptor(Type.CHAR_TYPE, new Type[] { TYPE_SYMBOL }));
            } else if (Object.class.isAssignableFrom(type)) {
                mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "unbind",
                        Type.getMethodDescriptor(TYPE_OBJECT, new Type[] { TYPE_SYMBOL }));
            } else {
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
        } else if (id == Insts.ENV_CHILD) {
            /* env.child */
            Object oldEnvVar = Lists.cadr(inst);
            Object newEnvVar = Lists.caddr(inst);
            Object oldSlot = Lists.cadr(oldEnvVar);
            Object newSlot = Lists.cadr(newEnvVar);
            int oldLocal = Data.fixnum(ci.localTable.get(oldSlot)).intValue();
            int newLocal = Data.fixnum(ci.localTable.get(newSlot)).intValue();
            if (Logger.tracelevelp(env))
                Logger.trace("[asm:gen]" + i + ":\tenv-child: local ~S -> ~S",
                        Lists.list(Data.toFixnum(oldLocal), Data.toFixnum(newLocal)), env);
            mv.visitVarInsn(Opcodes.ALOAD, oldLocal);
            mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, TYPE_ENV.getInternalName(), "child",
                    Type.getMethodDescriptor(TYPE_ENV, TYPE_NO_ARGS));
            mv.visitVarInsn(Opcodes.ASTORE, newLocal);
        } else if (id == Insts.CALL) {
            /* funcall */
            int nargs = Data.fixnum(Lists.cadr(inst)).intValue();
            String className = "lapin.eval.Funcall";
            String methodName = nargs < 0 ? "funcall" : "funcall" + nargs;
            Class rType = Object.class;
            Class[] pTypes;
            if (nargs < 0) {
                pTypes = new Class[] { Function.class, Object.class, // list of args
                        Env.class };
            } else {
                pTypes = new Class[nargs + 2];
                pTypes[0] = Function.class;
                for (int j = 0; j < nargs; j++) {
                    pTypes[j + 1] = Object.class;
                }
                pTypes[nargs + 1] = Env.class;
            }

            Type retType = Type.getType(rType);
            Type[] paramTypes = new Type[pTypes.length];
            for (int j = 0; j < pTypes.length; j++)
                paramTypes[j] = Type.getType(pTypes[j]);

            mv.visitMethodInsn(Opcodes.INVOKESTATIC, toInternalName(className), methodName,
                    Type.getMethodDescriptor(retType, paramTypes));
        } else if (id == Insts.CALL_DIRECT) {
            /*
             * public class Foo
             *   extends CompiledExpr implements Callable2 {
             *  public Object call2(Object arg0, Object arg1, Env env) {
             *   ...
             *  }
             * }
             */
            MethodInfo mi = (MethodInfo) Lists.cadr(inst);
            String className = mi.classInfo().classname();
            int nargs = mi.nargs();
            boolean rest = mi.rest();
            String methodName = mi.name();
            Class rType = mi.retType();
            Class[] pTypes = mi.paramTypes();

            Type retType = Type.getType(rType);
            Type[] paramTypes = new Type[pTypes.length];
            for (int j = 0; j < pTypes.length; j++)
                paramTypes[j] = Type.getType(pTypes[j]);

            mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, toInternalName(className), methodName,
                    Type.getMethodDescriptor(retType, paramTypes));
        } else if (id == Insts.COMPILED_EXPR) {
            /*
             * public class Foo extends CompiledExpr {
             *  static public Foo SELF;
             *  ...
             * }
             */
            String className = Data.string(Lists.cadr(inst));
            String fieldName = "SELF";
            String typeName = className;
            mv.visitFieldInsn(Opcodes.GETSTATIC, toInternalName(className), fieldName,
                    toTypeDescriptor(typeName));
        } else if (id == Insts.RETURN) {
            /* return */
            Class type = Data.javaClass(Lists.cadr(inst));
            if (type.equals(int.class) || type.equals(short.class) || type.equals(byte.class)
                    || type.equals(char.class)) {
                mv.visitInsn(Opcodes.IRETURN);
            } else if (type.equals(long.class)) {
                mv.visitInsn(Opcodes.LRETURN);
            } else if (type.equals(float.class)) {
                mv.visitInsn(Opcodes.FRETURN);
            } else if (type.equals(double.class)) {
                mv.visitInsn(Opcodes.DRETURN);
            } else if (type.equals(void.class)) {
                //mv.visitInsn(Opcodes.RETURN);
                throw new NotReachedException("unsupported returnType: ~S.", Lists.list(type));
            } else {
                mv.visitInsn(Opcodes.ARETURN);
            }
        } else if (id == Insts.IFEQ) {
            /* conditional jump */
            Symbol tag = Data.symbol(Lists.cadr(inst));
            Label l = (Label) ci.labelTable.get(tag);
            if (l == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tag));
            }
            mv.visitJumpInsn(Opcodes.IFEQ, l);
        } else if (id == Insts.IFNE) {
            /* conditional jump */
            Symbol tag = Data.symbol(Lists.cadr(inst));
            Label l = (Label) ci.labelTable.get(tag);
            if (l == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tag));
            }
            mv.visitJumpInsn(Opcodes.IFNE, l);
        } else if (id == Insts.GOTO) {
            /* jump */
            Symbol tag = Data.symbol(Lists.cadr(inst));
            Label l = (Label) ci.labelTable.get(tag);
            if (l == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tag));
            }
            mv.visitJumpInsn(Opcodes.GOTO, l);
        } else if (id == Insts.LOAD) {
            /* local -> stack */
            Object localVar = Lists.cadr(inst);
            Object slot = Lists.cadr(localVar);
            Class type = Data.javaClass(Lists.caddr(localVar));
            int local = Data.fixnum(ci.localTable.get(slot)).intValue();
            int op = Type.getType(type).getOpcode(Opcodes.ILOAD);
            if (Logger.tracelevelp(env))
                Logger.trace("[asm:gen]" + i + ":\tload: local=~S type=~S",
                        Lists.list(Data.toFixnum(local), type), env);
            mv.visitVarInsn(op, local);
        } else if (id == Insts.STORE) {
            /* stack -> local */
            Object localVar = Lists.cadr(inst);
            Object slot = Lists.cadr(localVar);
            Class type = Data.javaClass(Lists.caddr(localVar));
            int local = Data.fixnum(ci.localTable.get(slot)).intValue();
            int op = Type.getType(type).getOpcode(Opcodes.ISTORE);
            if (Logger.tracelevelp(env))
                Logger.trace("[asm:gen]" + i + ":\tstore: local=~S type=~S",
                        Lists.list(Data.toFixnum(local), type), env);
            mv.visitVarInsn(op, local);
        } else if (id == Insts.POP) {
            /* pop a value and discard it */
            Class type = Data.javaClass(Lists.cadr(inst));
            int op;
            switch (Classes.sizeOf(type)) {
            case 1:
                op = Opcodes.POP;
                break;
            case 2:
                op = Opcodes.POP2;
                break;
            default:
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
            mv.visitInsn(op);
        } else if (id == Insts.DUP) {
            /* peek a value and duplicate it */
            Class type = Data.javaClass(Lists.cadr(inst));
            int op;
            switch (Classes.sizeOf(type)) {
            case 1:
                op = Opcodes.DUP;
                break;
            case 2:
                op = Opcodes.DUP2;
                break;
            default:
                throw new NotReachedException("unsupported type: ~S.", Lists.list(type));
            }
            mv.visitInsn(op);
        } else if (id == Insts.PUSH) {
            /* push a constant */
            Object val = Lists.cadr(inst);
            if (Data.isJavaBoolean(val)) {
                if (Data.javaBoolean(val).booleanValue())
                    mv.visitInsn(Opcodes.ICONST_1);
                else
                    mv.visitInsn(Opcodes.ICONST_0);
            } else if (val instanceof Byte || val instanceof Short || val instanceof Integer) {
                int n = Data.javaNumber(val).intValue();
                if (n == -1)
                    mv.visitInsn(Opcodes.ICONST_M1);
                else if (n == 0)
                    mv.visitInsn(Opcodes.ICONST_0);
                else if (n == 1)
                    mv.visitInsn(Opcodes.ICONST_1);
                else if (n == 2)
                    mv.visitInsn(Opcodes.ICONST_2);
                else if (n == 3)
                    mv.visitInsn(Opcodes.ICONST_3);
                else if (n == 4)
                    mv.visitInsn(Opcodes.ICONST_4);
                else if (n == 5)
                    mv.visitInsn(Opcodes.ICONST_5);
                else if (Byte.MIN_VALUE <= n && n <= Byte.MAX_VALUE)
                    mv.visitIntInsn(Opcodes.BIPUSH, n);
                else if (Short.MIN_VALUE <= n && n <= Short.MAX_VALUE)
                    mv.visitIntInsn(Opcodes.SIPUSH, n);
                else
                    mv.visitLdcInsn(Data.toFixnum(n));
            } else if (val instanceof Long) {
                long n = Data.javaNumber(val).longValue();
                if (n == 0L)
                    mv.visitInsn(Opcodes.LCONST_0);
                else if (n == 1L)
                    mv.visitInsn(Opcodes.LCONST_1);
                else
                    mv.visitLdcInsn(val);
            } else if (val instanceof Float) {
                float n = Data.javaNumber(val).floatValue();
                if (n == 0.0f)
                    mv.visitInsn(Opcodes.FCONST_0);
                else if (n == 1.0f)
                    mv.visitInsn(Opcodes.FCONST_1);
                else if (n == 2.0f)
                    mv.visitInsn(Opcodes.FCONST_2);
                else
                    mv.visitLdcInsn(val);
            } else if (val instanceof Double) {
                double n = Data.javaNumber(val).doubleValue();
                if (n == 0.0)
                    mv.visitInsn(Opcodes.DCONST_0);
                else if (n == 1.0)
                    mv.visitInsn(Opcodes.DCONST_1);
                else
                    mv.visitLdcInsn(val);
            } else if (Data.isCharacter(val)) {
                Character c = Data.character(val);
                int n = (int) c.charValue();
                if (Byte.MIN_VALUE <= n && n <= Byte.MAX_VALUE)
                    mv.visitIntInsn(Opcodes.BIPUSH, n);
                else if (Short.MIN_VALUE <= n && n <= Short.MAX_VALUE)
                    mv.visitIntInsn(Opcodes.SIPUSH, n);
                else
                    mv.visitLdcInsn(Data.toFixnum(n));
            } else if (Data.isString(val)) {
                mv.visitLdcInsn(val);
            } else {
                throw new NotReachedException("cannot push: ~S.", Lists.list(val));
            }
        } else if (id == Insts.GET) {
            Field f = Data.javaField(Lists.cadr(inst));
            String fieldName = f.getName();
            Class c = f.getDeclaringClass();
            String className = c.getName();
            Class t = f.getType();
            String typeName = t.getName();

            boolean isStatic = Classes.isStatic(f);
            int op = isStatic ? Opcodes.GETSTATIC : Opcodes.GETFIELD;

            mv.visitFieldInsn(op, toInternalName(className), fieldName, toTypeDescriptor(typeName));
        } else if (id == Insts.PUT) {
            Field f = Data.javaField(Lists.cadr(inst));
            String fieldName = f.getName();
            Class c = f.getDeclaringClass();
            String className = c.getName();
            Class t = f.getType();
            String typeName = t.getName();

            boolean isStatic = Classes.isStatic(f);
            int op = isStatic ? Opcodes.PUTSTATIC : Opcodes.PUTFIELD;

            mv.visitFieldInsn(op, toInternalName(className), fieldName, toTypeDescriptor(typeName));
        } else if (id == Insts.INVOKE) {
            Method m = Data.javaMethod(Lists.cadr(inst));
            String methodName = m.getName();
            Class c = m.getDeclaringClass();
            String className = c.getName();
            Class rType = m.getReturnType();
            Class[] pTypes = m.getParameterTypes();
            if (rType.equals(void.class)) {
                throw new NotReachedException("unsupported returnType: ~S.", Lists.list(rType));
            }
            Type retType = Type.getType(rType);
            Type[] paramTypes = new Type[pTypes.length];
            for (int j = 0; j < pTypes.length; j++)
                paramTypes[j] = Type.getType(pTypes[j]);

            boolean isStatic = Classes.isStatic(m);
            boolean isInterface = c.isInterface();
            int op = isStatic ? Opcodes.INVOKESTATIC
                    : isInterface ? Opcodes.INVOKEINTERFACE : Opcodes.INVOKEVIRTUAL;

            mv.visitMethodInsn(op, toInternalName(className), methodName,
                    Type.getMethodDescriptor(retType, paramTypes));
        } else if (id == Insts.CHECKCAST) {
            Class c = Data.javaClass(Lists.cadr(inst));
            Type t = Type.getType(c);
            mv.visitTypeInsn(Opcodes.CHECKCAST, t.getInternalName());
        } else if (id == Insts.THROW) {
            mv.visitInsn(Opcodes.ATHROW);
        } else if (id == Insts.CATCH) {
            Symbol tagS = Data.symbol(Lists.cadr(inst));
            Symbol tagE = Data.symbol(Lists.caddr(inst));
            Symbol tagH = Data.symbol(Lists.cadddr(inst));
            String className;
            if (Lists.isEnd(Lists.cddddr(inst))) {
                className = null;
            } else {
                Class c = Data.javaClass(Lists.car(Lists.cddddr(inst)));
                className = toInternalName(c.getName());
            }
            Label labelS = (Label) ci.labelTable.get(tagS);
            if (labelS == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tagS));
            }
            Label labelE = (Label) ci.labelTable.get(tagE);
            if (labelE == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tagE));
            }
            Label labelH = (Label) ci.labelTable.get(tagH);
            if (labelH == null) {
                throw new NotReachedException("label not found: ~S.", Lists.list(tagH));
            }
            mv.visitTryCatchBlock(labelS, labelE, labelH, className);
        }
        //else if (id == Insts.CATCH_FROM ||
        //         id == Insts.CATCH_TO ||
        //         id == Insts.CATCH_HANDLER) {
        //    /* nothing emitted */
        //    continue;
        //}
        else {
            throw new NotReachedException("unknown inst: ~S.", Lists.list(inst));
        }
    }
    mv.visitMaxs(0, 0);
    mv.visitEnd();
}

From source file:lucee.transformer.bytecode.op.OpBool.java

License:Open Source License

/**
 *
 * @see lucee.transformer.bytecode.expression.ExpressionBase#_writeOut(org.objectweb.asm.commons.GeneratorAdapter, int)
 *///from ww  w .  jav a  2 s.  c  o  m
public Type _writeOut(BytecodeContext bc, int mode) throws BytecodeException {
    GeneratorAdapter adapter = bc.getAdapter();

    if (mode == MODE_REF) {
        _writeOut(bc, MODE_VALUE);
        adapter.invokeStatic(Types.CASTER, Methods.METHOD_TO_BOOLEAN_FROM_BOOLEAN);
        return Types.BOOLEAN;
    }

    Label doFalse = new Label();
    Label end = new Label();

    if (operation == AND) {
        left.writeOut(bc, MODE_VALUE);
        adapter.ifZCmp(Opcodes.IFEQ, doFalse);

        right.writeOut(bc, MODE_VALUE);
        adapter.ifZCmp(Opcodes.IFEQ, doFalse);
        adapter.push(true);

        adapter.visitJumpInsn(Opcodes.GOTO, end);
        adapter.visitLabel(doFalse);

        adapter.push(false);
        adapter.visitLabel(end);
    }
    if (operation == OR) {
        left.writeOut(bc, MODE_VALUE);
        adapter.ifZCmp(Opcodes.IFNE, doFalse);

        right.writeOut(bc, MODE_VALUE);
        adapter.ifZCmp(Opcodes.IFNE, doFalse);

        adapter.push(false);
        adapter.visitJumpInsn(Opcodes.GOTO, end);
        adapter.visitLabel(doFalse);

        adapter.push(true);
        adapter.visitLabel(end);
    } else if (operation == XOR) {
        left.writeOut(bc, MODE_VALUE);
        right.writeOut(bc, MODE_VALUE);
        adapter.visitInsn(Opcodes.IXOR);
    } else if (operation == EQV) {

        left.writeOut(bc, MODE_VALUE);
        right.writeOut(bc, MODE_VALUE);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_EQV_BV_BV);
    } else if (operation == IMP) {

        left.writeOut(bc, MODE_VALUE);
        right.writeOut(bc, MODE_VALUE);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_IMP_BV_BV);
    }
    return Types.BOOLEAN_VALUE;

}

From source file:lucee.transformer.bytecode.op.OpContional.java

License:Open Source License

/**
 *
 * @see lucee.transformer.bytecode.expression.ExpressionBase#_writeOut(org.objectweb.asm.commons.GeneratorAdapter, int)
 *//*from   w ww.  j  a  v a2  s.c  o  m*/
public Type _writeOut(BytecodeContext bc, int mode) throws BytecodeException {
    GeneratorAdapter adapter = bc.getAdapter();

    Label yes = new Label();
    Label end = new Label();

    // cont
    ExpressionUtil.visitLine(bc, cont.getStart());
    cont.writeOut(bc, MODE_VALUE);
    ExpressionUtil.visitLine(bc, cont.getEnd());
    adapter.visitJumpInsn(Opcodes.IFEQ, yes);

    // left
    ExpressionUtil.visitLine(bc, left.getStart());
    left.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, left.getEnd());
    adapter.visitJumpInsn(Opcodes.GOTO, end);

    // right
    ExpressionUtil.visitLine(bc, right.getStart());
    adapter.visitLabel(yes);
    right.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, right.getEnd());
    adapter.visitLabel(end);

    return Types.OBJECT;

}

From source file:lucee.transformer.bytecode.op.OPDecision.java

License:Open Source License

public Type _writeOut(BytecodeContext bc, int mode) throws BytecodeException {
    GeneratorAdapter adapter = bc.getAdapter();
    if (mode == MODE_REF) {
        _writeOut(bc, MODE_VALUE);/* w ww  . j  a  v  a 2  s.c o  m*/
        adapter.invokeStatic(Types.CASTER, Methods.METHOD_TO_BOOLEAN_FROM_BOOLEAN);
        return Types.BOOLEAN;
    }

    if (operation == CT) {
        left.writeOut(bc, MODE_REF);
        right.writeOut(bc, MODE_REF);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_CT);
    } else if (operation == NCT) {
        left.writeOut(bc, MODE_REF);
        right.writeOut(bc, MODE_REF);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_NCT);
    } else if (operation == EEQ) {
        left.writeOut(bc, MODE_REF);
        right.writeOut(bc, MODE_REF);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_EEQ);
    } else if (operation == NEEQ) {
        left.writeOut(bc, MODE_REF);
        right.writeOut(bc, MODE_REF);
        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATOR_NEEQ);
    } else {
        int iLeft = Types.getType(left.writeOut(bc, MODE_VALUE));
        int iRight = Types.getType(right.writeOut(bc, MODE_VALUE));

        adapter.invokeStatic(Types.OPERATOR, Methods_Operator.OPERATORS[iLeft][iRight]);

        adapter.visitInsn(Opcodes.ICONST_0);

        Label l1 = new Label();
        Label l2 = new Label();
        adapter.ifCmp(Type.INT_TYPE, operation, l1);
        //adapter.visitJumpInsn(Opcodes.IF_ICMPEQ, l1);
        adapter.visitInsn(Opcodes.ICONST_0);
        adapter.visitJumpInsn(Opcodes.GOTO, l2);
        adapter.visitLabel(l1);
        adapter.visitInsn(Opcodes.ICONST_1);
        adapter.visitLabel(l2);
    }
    return Types.BOOLEAN_VALUE;
}

From source file:lucee.transformer.bytecode.op.OpElvis.java

License:Open Source License

/**
 *
 * @see lucee.transformer.bytecode.expression.ExpressionBase#_writeOut(org.objectweb.asm.commons.GeneratorAdapter, int)
 *///w  w  w  .j  av  a2s . c om
public Type _writeOut(BytecodeContext bc, int mode) throws BytecodeException {
    if (ASMUtil.hasOnlyDataMembers(left))
        return _writeOutPureDataMember(bc, mode);

    Label notNull = new Label();
    Label end = new Label();

    GeneratorAdapter ga = bc.getAdapter();

    int l = ga.newLocal(Types.OBJECT);
    ExpressionUtil.visitLine(bc, left.getStart());
    left.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, left.getEnd());
    ga.dup();
    ga.storeLocal(l);

    ga.visitJumpInsn(Opcodes.IFNONNULL, notNull);
    ExpressionUtil.visitLine(bc, right.getStart());
    right.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, right.getEnd());
    ga.visitJumpInsn(Opcodes.GOTO, end);
    ga.visitLabel(notNull);
    ga.loadLocal(l);
    ga.visitLabel(end);

    return Types.OBJECT;
}

From source file:lucee.transformer.bytecode.op.OpElvis.java

License:Open Source License

public Type _writeOutPureDataMember(BytecodeContext bc, int mode) throws BytecodeException {
    // TODO use function isNull for this
    GeneratorAdapter adapter = bc.getAdapter();

    Label yes = new Label();
    Label end = new Label();

    List<Member> members = left.getMembers();

    // to array//from  ww w  .  ja  v  a  2  s . co  m
    Iterator<Member> it = members.iterator();
    List<DataMember> list = new ArrayList<DataMember>();
    while (it.hasNext()) {
        list.add((DataMember) it.next());
    }
    DataMember[] arr = list.toArray(new DataMember[members.size()]);

    ExpressionUtil.visitLine(bc, left.getStart());

    // public static boolean call(PageContext pc , double scope,String[] varNames)
    // pc
    adapter.loadArg(0);
    // scope
    adapter.push((double) left.getScope());
    //varNames

    // all literal string?
    boolean allLiteral = true;
    for (int i = 0; i < arr.length; i++) {
        if (!(arr[i].getName() instanceof Literal))
            allLiteral = false;
    }

    ArrayVisitor av = new ArrayVisitor();
    if (!allLiteral) {
        // String Array
        av.visitBegin(adapter, Types.STRING, arr.length);
        for (int i = 0; i < arr.length; i++) {
            av.visitBeginItem(adapter, i);
            arr[i].getName().writeOut(bc, MODE_REF);
            av.visitEndItem(adapter);
        }
    } else {
        // Collection.Key Array
        av.visitBegin(adapter, Types.COLLECTION_KEY, arr.length);
        for (int i = 0; i < arr.length; i++) {
            av.visitBeginItem(adapter, i);
            Variable.registerKey(bc, arr[i].getName());
            av.visitEndItem(adapter);
        }
    }
    av.visitEnd();

    // allowNull
    //adapter.push(false);

    //ASMConstants.NULL(adapter);

    // call IsDefined.invoke
    adapter.invokeStatic(ELVIS, allLiteral ? INVOKE_KEY : INVOKE_STR);
    ExpressionUtil.visitLine(bc, left.getEnd());

    adapter.visitJumpInsn(Opcodes.IFEQ, yes);

    // left
    ExpressionUtil.visitLine(bc, left.getStart());
    left.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, left.getEnd());
    adapter.visitJumpInsn(Opcodes.GOTO, end);

    // right
    ExpressionUtil.visitLine(bc, right.getStart());
    adapter.visitLabel(yes);
    right.writeOut(bc, MODE_REF);
    ExpressionUtil.visitLine(bc, right.getEnd());
    adapter.visitLabel(end);

    return Types.OBJECT;

}

From source file:lucee.transformer.bytecode.op.OpNegate.java

License:Open Source License

/**
 *
 * @see lucee.transformer.bytecode.expression.ExpressionBase#_writeOut(org.objectweb.asm.commons.GeneratorAdapter, int)
 */// www  .j  a v  a 2s  .  c o m
public Type _writeOut(BytecodeContext bc, int mode) throws BytecodeException {
    GeneratorAdapter adapter = bc.getAdapter();
    if (mode == MODE_REF) {
        _writeOut(bc, MODE_VALUE);
        adapter.invokeStatic(Types.CASTER, Methods.METHOD_TO_BOOLEAN_FROM_BOOLEAN);
        return Types.BOOLEAN;
    }

    Label l1 = new Label();
    Label l2 = new Label();

    expr.writeOut(bc, MODE_VALUE);
    adapter.ifZCmp(Opcodes.IFEQ, l1);

    adapter.visitInsn(Opcodes.ICONST_0);
    adapter.visitJumpInsn(Opcodes.GOTO, l2);
    adapter.visitLabel(l1);
    adapter.visitInsn(Opcodes.ICONST_1);
    adapter.visitLabel(l2);

    return Types.BOOLEAN_VALUE;

}

From source file:lucee.transformer.bytecode.statement.For.java

License:Open Source License

@Override
public void _writeOut(BytecodeContext bc) throws BytecodeException {
    GeneratorAdapter adapter = bc.getAdapter();
    Label beforeInit = new Label();
    Label afterInit = new Label();
    Label afterUpdate = new Label();

    ExpressionUtil.visitLine(bc, getStart());
    adapter.visitLabel(beforeInit);/*from  w w w.j a va 2 s  . co m*/
    if (init != null) {
        init.writeOut(bc, Expression.MODE_VALUE);
        adapter.pop();
    }
    adapter.visitJumpInsn(Opcodes.GOTO, afterUpdate);
    adapter.visitLabel(afterInit);

    body.writeOut(bc);

    adapter.visitLabel(beforeUpdate);
    //ExpressionUtil.visitLine(bc, getStartLine());
    if (update != null) {
        update.writeOut(bc, Expression.MODE_VALUE);
        ASMUtil.pop(adapter, update, Expression.MODE_VALUE);
    }
    //ExpressionUtil.visitLine(bc, getStartLine());
    adapter.visitLabel(afterUpdate);

    if (condition != null)
        condition.writeOut(bc, Expression.MODE_VALUE);
    else
        LitBoolean.TRUE.writeOut(bc, Expression.MODE_VALUE);
    adapter.visitJumpInsn(Opcodes.IFNE, afterInit);
    //ExpressionUtil.visitLine(bc, getEndLine());
    adapter.visitLabel(end);

}