Example usage for org.objectweb.asm.commons InstructionAdapter aconst

List of usage examples for org.objectweb.asm.commons InstructionAdapter aconst

Introduction

In this page you can find the example usage for org.objectweb.asm.commons InstructionAdapter aconst.

Prototype

public void aconst(final Object value) 

Source Link

Document

Generates the instruction to push the given value on the stack.

Usage

From source file:com.gargoylesoftware.js.nashorn.internal.runtime.linker.JavaAdapterBytecodeGenerator.java

License:Open Source License

private void generateClassInit() {
    final InstructionAdapter mv = new InstructionAdapter(
            cw.visitMethod(ACC_STATIC, CLASS_INIT, Type.getMethodDescriptor(Type.VOID_TYPE), null, null));

    mv.invokestatic(SERVICES_CLASS_TYPE_NAME, "getClassOverrides", GET_CLASS_INITIALIZER_DESCRIPTOR, false);
    final Label initGlobal;
    if (samName != null) {
        // If the class is a SAM, allow having a ScriptFunction passed as class overrides
        final Label notAFunction = new Label();
        mv.dup();/*from   www . ja v  a 2 s  .c o m*/
        mv.instanceOf(SCRIPT_FUNCTION_TYPE);
        mv.ifeq(notAFunction);
        mv.checkcast(SCRIPT_FUNCTION_TYPE);

        // Assign MethodHandle fields through invoking getHandle() for a ScriptFunction, only assigning the SAM
        // method(s).
        for (final MethodInfo mi : methodInfos) {
            if (mi.getName().equals(samName)) {
                mv.dup();
                loadMethodTypeAndGetHandle(mv, mi, GET_HANDLE_FUNCTION_DESCRIPTOR);
            } else {
                mv.visitInsn(ACONST_NULL);
            }
            mv.putstatic(generatedClassName, mi.methodHandleFieldName, METHOD_HANDLE_TYPE_DESCRIPTOR);
        }
        initGlobal = new Label();
        mv.goTo(initGlobal);
        mv.visitLabel(notAFunction);
    } else {
        initGlobal = null;
    }
    // Assign MethodHandle fields through invoking getHandle() for a ScriptObject
    for (final MethodInfo mi : methodInfos) {
        mv.dup();
        mv.aconst(mi.getName());
        loadMethodTypeAndGetHandle(mv, mi, GET_HANDLE_OBJECT_DESCRIPTOR);
        mv.putstatic(generatedClassName, mi.methodHandleFieldName, METHOD_HANDLE_TYPE_DESCRIPTOR);
    }

    if (initGlobal != null) {
        mv.visitLabel(initGlobal);
    }
    // Assign "global = Context.getGlobal()"
    invokeGetGlobalWithNullCheck(mv);
    mv.putstatic(generatedClassName, GLOBAL_FIELD_NAME, GLOBAL_TYPE_DESCRIPTOR);

    generateConverterInit(mv, false);
    endInitMethod(mv);
}

From source file:com.gargoylesoftware.js.nashorn.internal.runtime.linker.JavaAdapterBytecodeGenerator.java

License:Open Source License

private void generateConverterInit(final InstructionAdapter mv, final boolean samOnly) {
    assert !samOnly || !classOverride;
    for (final Map.Entry<Class<?>, String> converterField : converterFields.entrySet()) {
        final Class<?> returnType = converterField.getKey();
        if (!classOverride) {
            mv.visitVarInsn(ALOAD, 0);//  w  w w.j  a  v a  2  s . c  o  m
        }

        if (samOnly && !samReturnTypes.contains(returnType)) {
            mv.visitInsn(ACONST_NULL);
        } else {
            mv.aconst(Type.getType(converterField.getKey()));
            mv.invokestatic(SERVICES_CLASS_TYPE_NAME, "getObjectConverter", GET_CONVERTER_METHOD_DESCRIPTOR,
                    false);
        }

        if (classOverride) {
            mv.putstatic(generatedClassName, converterField.getValue(), METHOD_HANDLE_TYPE_DESCRIPTOR);
        } else {
            mv.putfield(generatedClassName, converterField.getValue(), METHOD_HANDLE_TYPE_DESCRIPTOR);
        }
    }
}

From source file:com.gargoylesoftware.js.nashorn.internal.runtime.linker.JavaAdapterBytecodeGenerator.java

License:Open Source License

private static void loadMethodTypeAndGetHandle(final InstructionAdapter mv, final MethodInfo mi,
        final String getHandleDescriptor) {
    // NOTE: we're using generic() here because we'll be linking to the "generic" invoker version of
    // the functions anyway, so we cut down on megamorphism in the invokeExact() calls in adapter
    // bodies. Once we start linking to type-specializing invokers, this should be changed.
    mv.aconst(Type.getMethodType(mi.type.generic().toMethodDescriptorString()));
    mv.invokestatic(SERVICES_CLASS_TYPE_NAME, "getHandle", getHandleDescriptor, false);
}

From source file:com.gargoylesoftware.js.nashorn.internal.runtime.linker.JavaAdapterBytecodeGenerator.java

License:Open Source License

/**
 * Generates a constructor for the instance adapter class. This constructor will take the same arguments as the supertype
 * constructor passed as the argument here, and delegate to it. However, it will take an additional argument of
 * either ScriptObject or ScriptFunction type (based on the value of the "fromFunction" parameter), and initialize
 * all the method handle fields of the adapter instance with functions from the script object (or the script
 * function itself, if that's what's passed). There is one method handle field in the adapter class for every method
 * that can be implemented or overridden; the name of every field is same as the name of the method, with a number
 * suffix that makes it unique in case of overloaded methods. The generated constructor will invoke
 * {@link #getHandle(ScriptFunction, MethodType, boolean)} or {@link #getHandle(Object, String, MethodType,
 * boolean)} to obtain the method handles; these methods make sure to add the necessary conversions and arity
 * adjustments so that the resulting method handles can be invoked from generated methods using {@code invokeExact}.
 * The constructor that takes a script function will only initialize the methods with the same name as the single
 * abstract method. The constructor will also store the Nashorn global that was current at the constructor
 * invocation time in a field named "global". The generated constructor will be public, regardless of whether the
 * supertype constructor was public or protected. The generated constructor will not be variable arity, even if the
 * supertype constructor was./* ww  w. j a  v  a2 s.c o m*/
 * @param ctor the supertype constructor that is serving as the base for the generated constructor.
 * @param fromFunction true if we're generating a constructor that initializes SAM types from a single
 * ScriptFunction passed to it, false if we're generating a constructor that initializes an arbitrary type from a
 * ScriptObject passed to it.
 */
private void generateOverridingConstructor(final Constructor<?> ctor, final boolean fromFunction) {
    final Type originalCtorType = Type.getType(ctor);
    final Type[] originalArgTypes = originalCtorType.getArgumentTypes();
    final int argLen = originalArgTypes.length;
    final Type[] newArgTypes = new Type[argLen + 1];

    // Insert ScriptFunction|ScriptObject as the last argument to the constructor
    final Type extraArgumentType = fromFunction ? SCRIPT_FUNCTION_TYPE : SCRIPT_OBJECT_TYPE;
    newArgTypes[argLen] = extraArgumentType;
    System.arraycopy(originalArgTypes, 0, newArgTypes, 0, argLen);

    // All constructors must be public, even if in the superclass they were protected.
    // Existing super constructor <init>(this, args...) triggers generating <init>(this, args..., scriptObj).
    // Any variable arity constructors become fixed-arity with explicit array arguments.
    final InstructionAdapter mv = new InstructionAdapter(cw.visitMethod(ACC_PUBLIC, INIT,
            Type.getMethodDescriptor(originalCtorType.getReturnType(), newArgTypes), null, null));

    mv.visitCode();
    // First, invoke super constructor with original arguments. If the form of the constructor we're generating is
    // <init>(this, args..., scriptFn), then we're invoking super.<init>(this, args...).
    mv.visitVarInsn(ALOAD, 0);
    final Class<?>[] argTypes = ctor.getParameterTypes();
    int offset = 1; // First arg is at position 1, after this.
    for (int i = 0; i < argLen; ++i) {
        final Type argType = Type.getType(argTypes[i]);
        mv.load(offset, argType);
        offset += argType.getSize();
    }
    mv.invokespecial(superClassName, INIT, originalCtorType.getDescriptor(), false);

    // Get a descriptor to the appropriate "JavaAdapterFactory.getHandle" method.
    final String getHandleDescriptor = fromFunction ? GET_HANDLE_FUNCTION_DESCRIPTOR
            : GET_HANDLE_OBJECT_DESCRIPTOR;

    // Assign MethodHandle fields through invoking getHandle()
    for (final MethodInfo mi : methodInfos) {
        mv.visitVarInsn(ALOAD, 0);
        if (fromFunction && !mi.getName().equals(samName)) {
            // Constructors initializing from a ScriptFunction only initialize methods with the SAM name.
            // NOTE: if there's a concrete overloaded method sharing the SAM name, it'll be overridden too. This
            // is a deliberate design choice. All other method handles are initialized to null.
            mv.visitInsn(ACONST_NULL);
        } else {
            mv.visitVarInsn(ALOAD, offset);
            if (!fromFunction) {
                mv.aconst(mi.getName());
            }
            loadMethodTypeAndGetHandle(mv, mi, getHandleDescriptor);
        }
        mv.putfield(generatedClassName, mi.methodHandleFieldName, METHOD_HANDLE_TYPE_DESCRIPTOR);
    }

    // Assign "this.global = Context.getGlobal()"
    mv.visitVarInsn(ALOAD, 0);
    invokeGetGlobalWithNullCheck(mv);
    mv.putfield(generatedClassName, GLOBAL_FIELD_NAME, GLOBAL_TYPE_DESCRIPTOR);

    // Initialize converters
    generateConverterInit(mv, fromFunction);
    endInitMethod(mv);

    if (!fromFunction) {
        newArgTypes[argLen] = OBJECT_TYPE;
        final InstructionAdapter mv2 = new InstructionAdapter(cw.visitMethod(ACC_PUBLIC, INIT,
                Type.getMethodDescriptor(originalCtorType.getReturnType(), newArgTypes), null, null));
        generateOverridingConstructorWithObjectParam(mv2, ctor, originalCtorType.getDescriptor());
    }
}

From source file:com.gargoylesoftware.js.nashorn.internal.runtime.linker.JavaAdapterBytecodeGenerator.java

License:Open Source License

private void generateFinalizerOverride(final String finalizerDelegateName) {
    final InstructionAdapter mv = new InstructionAdapter(
            cw.visitMethod(ACC_PUBLIC, "finalize", VOID_NOARG_METHOD_DESCRIPTOR, null, null));
    // Overridden finalizer will take a MethodHandle to the finalizer delegating method, ...
    mv.aconst(new Handle(Opcodes.H_INVOKESTATIC, generatedClassName, finalizerDelegateName,
            Type.getMethodDescriptor(Type.VOID_TYPE, OBJECT_TYPE)));
    mv.visitVarInsn(ALOAD, 0);//from w ww.ja  v a2 s .  com
    // ...and invoke it through JavaAdapterServices.invokeNoPermissions
    mv.invokestatic(SERVICES_CLASS_TYPE_NAME, "invokeNoPermissions",
            Type.getMethodDescriptor(METHOD_HANDLE_TYPE, OBJECT_TYPE), false);
    mv.visitInsn(RETURN);
    endMethod(mv);
}

From source file:com.github.jasmo.obfuscate.ScrambleStrings.java

License:Open Source License

private void createStaticConstructor(ClassNode owner) throws UnsupportedEncodingException {
    MethodNode original = BytecodeHelper.getMethod(owner, "<clinit>", "()V");
    MethodVisitor mv = owner.visitMethod(Opcodes.ACC_STATIC, "<clinit>", "()V", null, null);
    // generate instructions
    InstructionAdapter builder = new InstructionAdapter(mv);
    builder.iconst(stringList.size());/*  w  w  w.j a  v a 2s  .c om*/
    builder.newarray(Type.getType(String.class));
    for (int i = 0; i < stringList.size(); i++) {
        builder.dup();
        builder.iconst(i);
        builder.aconst(Base64.getEncoder().encodeToString(stringList.get(i).getBytes("UTF-8")));
        builder.astore(InstructionAdapter.OBJECT_TYPE);
    }
    builder.putstatic(unscrambleClass.name, FIELD_NAME, "[Ljava/lang/String;");
    // merge with original if it exists
    if (original != null) {
        // original should already end with RETURN
        owner.methods.remove(original);
        original.instructions.accept(builder);
    } else {
        builder.areturn(Type.VOID_TYPE);
    }
}

From source file:edu.ubc.mirrors.holograms.HologramMethodGenerator.java

License:Open Source License

public static void initializeStaticFields(Type owner, InstructionAdapter mv) {
    // Initialize the static field that holds the ClassMirror for this holographic Class
    mv.aconst(owner);
    new MethodHandle() {
        protected void methodCall() throws Throwable {
            ObjectHologram.getClassMirrorForHolographicClass(null);
        }//from   w  w  w.jav  a  2  s.com
    }.invoke(mv);
    mv.dup();
    mv.putstatic(owner.getInternalName(), "classMirror", classMirrorType.getDescriptor());
}