You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tapestry.apache.org by th...@apache.org on 2018/11/29 00:34:06 UTC
[19/46] tapestry-5 git commit: TAP5-2588: upgrading from ASM 6 to 7
for Java 9+ support
http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/1c71aec7/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/MethodNode.java
----------------------------------------------------------------------
diff --git a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/MethodNode.java b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/MethodNode.java
old mode 100644
new mode 100755
index 68b4e31..39114ac
--- a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/MethodNode.java
+++ b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/MethodNode.java
@@ -1,41 +1,38 @@
-/***
- * ASM: a very small and fast Java bytecode manipulation framework
- * Copyright (c) 2000-2011 INRIA, France Telecom
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
+// ASM: a very small and fast Java bytecode manipulation framework
+// Copyright (c) 2000-2011 INRIA, France Telecom
+// All rights reserved.
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+// 1. Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// 2. Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+// 3. Neither the name of the copyright holders nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+// THE POSSIBILITY OF SUCH DAMAGE.
package org.apache.tapestry5.internal.plastic.asm.tree;
import java.util.ArrayList;
-import java.util.Arrays;
import java.util.List;
-
import org.apache.tapestry5.internal.plastic.asm.AnnotationVisitor;
import org.apache.tapestry5.internal.plastic.asm.Attribute;
import org.apache.tapestry5.internal.plastic.asm.ClassVisitor;
+import org.apache.tapestry5.internal.plastic.asm.ConstantDynamic;
import org.apache.tapestry5.internal.plastic.asm.Handle;
import org.apache.tapestry5.internal.plastic.asm.Label;
import org.apache.tapestry5.internal.plastic.asm.MethodVisitor;
@@ -45,796 +42,774 @@ import org.apache.tapestry5.internal.plastic.asm.TypePath;
/**
* A node that represents a method.
- *
+ *
* @author Eric Bruneton
*/
public class MethodNode extends MethodVisitor {
- /**
- * The method's access flags (see {@link Opcodes}). This field also
- * indicates if the method is synthetic and/or deprecated.
- */
- public int access;
-
- /**
- * The method's name.
- */
- public String name;
-
- /**
- * The method's descriptor (see {@link Type}).
- */
- public String desc;
-
- /**
- * The method's signature. May be <tt>null</tt>.
- */
- public String signature;
-
- /**
- * The internal names of the method's exception classes (see
- * {@link Type#getInternalName() getInternalName}). This list is a list of
- * {@link String} objects.
- */
- public List<String> exceptions;
-
- /**
- * The method parameter info (access flags and name)
- */
- public List<ParameterNode> parameters;
-
- /**
- * The runtime visible annotations of this method. This list is a list of
- * {@link AnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.AnnotationNode
- * @label visible
- */
- public List<AnnotationNode> visibleAnnotations;
-
- /**
- * The runtime invisible annotations of this method. This list is a list of
- * {@link AnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.AnnotationNode
- * @label invisible
- */
- public List<AnnotationNode> invisibleAnnotations;
-
- /**
- * The runtime visible type annotations of this method. This list is a list
- * of {@link TypeAnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.TypeAnnotationNode
- * @label visible
- */
- public List<TypeAnnotationNode> visibleTypeAnnotations;
-
- /**
- * The runtime invisible type annotations of this method. This list is a
- * list of {@link TypeAnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.TypeAnnotationNode
- * @label invisible
- */
- public List<TypeAnnotationNode> invisibleTypeAnnotations;
-
- /**
- * The non standard attributes of this method. This list is a list of
- * {@link Attribute} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.Attribute
- */
- public List<Attribute> attrs;
-
- /**
- * The default value of this annotation interface method. This field must be
- * a {@link Byte}, {@link Boolean}, {@link Character}, {@link Short},
- * {@link Integer}, {@link Long}, {@link Float}, {@link Double},
- * {@link String} or {@link Type}, or an two elements String array (for
- * enumeration values), a {@link AnnotationNode}, or a {@link List} of
- * values of one of the preceding types. May be <tt>null</tt>.
- */
- public Object annotationDefault;
-
- /**
- * The runtime visible parameter annotations of this method. These lists are
- * lists of {@link AnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.AnnotationNode
- * @label invisible parameters
- */
- public List<AnnotationNode>[] visibleParameterAnnotations;
-
- /**
- * The runtime invisible parameter annotations of this method. These lists
- * are lists of {@link AnnotationNode} objects. May be <tt>null</tt>.
- *
- * @associates org.objectweb.asm.tree.AnnotationNode
- * @label visible parameters
- */
- public List<AnnotationNode>[] invisibleParameterAnnotations;
-
- /**
- * The instructions of this method. This list is a list of
- * {@link AbstractInsnNode} objects.
- *
- * @associates org.objectweb.asm.tree.AbstractInsnNode
- * @label instructions
- */
- public InsnList instructions;
-
- /**
- * The try catch blocks of this method. This list is a list of
- * {@link TryCatchBlockNode} objects.
- *
- * @associates org.objectweb.asm.tree.TryCatchBlockNode
- */
- public List<TryCatchBlockNode> tryCatchBlocks;
-
- /**
- * The maximum stack size of this method.
- */
- public int maxStack;
-
- /**
- * The maximum number of local variables of this method.
- */
- public int maxLocals;
-
- /**
- * The local variables of this method. This list is a list of
- * {@link LocalVariableNode} objects. May be <tt>null</tt>
- *
- * @associates org.objectweb.asm.tree.LocalVariableNode
- */
- public List<LocalVariableNode> localVariables;
-
- /**
- * The visible local variable annotations of this method. This list is a
- * list of {@link LocalVariableAnnotationNode} objects. May be <tt>null</tt>
- *
- * @associates org.objectweb.asm.tree.LocalVariableAnnotationNode
- */
- public List<LocalVariableAnnotationNode> visibleLocalVariableAnnotations;
-
- /**
- * The invisible local variable annotations of this method. This list is a
- * list of {@link LocalVariableAnnotationNode} objects. May be <tt>null</tt>
- *
- * @associates org.objectweb.asm.tree.LocalVariableAnnotationNode
- */
- public List<LocalVariableAnnotationNode> invisibleLocalVariableAnnotations;
-
- /**
- * If the accept method has been called on this object.
- */
- private boolean visited;
-
- /**
- * Constructs an uninitialized {@link MethodNode}. <i>Subclasses must not
- * use this constructor</i>. Instead, they must use the
- * {@link #MethodNode(int)} version.
- *
- * @throws IllegalStateException
- * If a subclass calls this constructor.
- */
- public MethodNode() {
- this(Opcodes.ASM6);
- if (getClass() != MethodNode.class) {
- throw new IllegalStateException();
- }
- }
-
- /**
- * Constructs an uninitialized {@link MethodNode}.
- *
- * @param api
- * the ASM API version implemented by this visitor. Must be one
- * of {@link Opcodes#ASM4}, {@link Opcodes#ASM5} or {@link Opcodes#ASM6}.
- */
- public MethodNode(final int api) {
- super(api);
- this.instructions = new InsnList();
- }
-
- /**
- * Constructs a new {@link MethodNode}. <i>Subclasses must not use this
- * constructor</i>. Instead, they must use the
- * {@link #MethodNode(int, int, String, String, String, String[])} version.
- *
- * @param access
- * the method's access flags (see {@link Opcodes}). This
- * parameter also indicates if the method is synthetic and/or
- * deprecated.
- * @param name
- * the method's name.
- * @param desc
- * the method's descriptor (see {@link Type}).
- * @param signature
- * the method's signature. May be <tt>null</tt>.
- * @param exceptions
- * the internal names of the method's exception classes (see
- * {@link Type#getInternalName() getInternalName}). May be
- * <tt>null</tt>.
- * @throws IllegalStateException
- * If a subclass calls this constructor.
- */
- public MethodNode(final int access, final String name, final String desc,
- final String signature, final String[] exceptions) {
- this(Opcodes.ASM6, access, name, desc, signature, exceptions);
- if (getClass() != MethodNode.class) {
- throw new IllegalStateException();
- }
- }
-
- /**
- * Constructs a new {@link MethodNode}.
- *
- * @param api
- * the ASM API version implemented by this visitor. Must be one
- * of {@link Opcodes#ASM4}, {@link Opcodes#ASM5} or {@link Opcodes#ASM6}.
- * @param access
- * the method's access flags (see {@link Opcodes}). This
- * parameter also indicates if the method is synthetic and/or
- * deprecated.
- * @param name
- * the method's name.
- * @param desc
- * the method's descriptor (see {@link Type}).
- * @param signature
- * the method's signature. May be <tt>null</tt>.
- * @param exceptions
- * the internal names of the method's exception classes (see
- * {@link Type#getInternalName() getInternalName}). May be
- * <tt>null</tt>.
- */
- public MethodNode(final int api, final int access, final String name,
- final String desc, final String signature, final String[] exceptions) {
- super(api);
- this.access = access;
- this.name = name;
- this.desc = desc;
- this.signature = signature;
- this.exceptions = new ArrayList<String>(exceptions == null ? 0
- : exceptions.length);
- boolean isAbstract = (access & Opcodes.ACC_ABSTRACT) != 0;
- if (!isAbstract) {
- this.localVariables = new ArrayList<LocalVariableNode>(5);
- }
- this.tryCatchBlocks = new ArrayList<TryCatchBlockNode>();
- if (exceptions != null) {
- this.exceptions.addAll(Arrays.asList(exceptions));
- }
- this.instructions = new InsnList();
- }
-
- // ------------------------------------------------------------------------
- // Implementation of the MethodVisitor abstract class
- // ------------------------------------------------------------------------
-
- @Override
- public void visitParameter(String name, int access) {
- if (parameters == null) {
- parameters = new ArrayList<ParameterNode>(5);
- }
- parameters.add(new ParameterNode(name, access));
- }
-
- @Override
- @SuppressWarnings("serial")
- public AnnotationVisitor visitAnnotationDefault() {
- return new AnnotationNode(new ArrayList<Object>(0) {
- @Override
- public boolean add(final Object o) {
- annotationDefault = o;
- return super.add(o);
- }
+ /**
+ * The method's access flags (see {@link Opcodes}). This field also indicates if the method is
+ * synthetic and/or deprecated.
+ */
+ public int access;
+
+ /** The method's name. */
+ public String name;
+
+ /** The method's descriptor (see {@link Type}). */
+ public String desc;
+
+ /** The method's signature. May be {@literal null}. */
+ public String signature;
+
+ /** The internal names of the method's exception classes (see {@link Type#getInternalName()}). */
+ public List<String> exceptions;
+
+ /** The method parameter info (access flags and name). */
+ public List<ParameterNode> parameters;
+
+ /** The runtime visible annotations of this method. May be {@literal null}. */
+ public List<AnnotationNode> visibleAnnotations;
+
+ /** The runtime invisible annotations of this method. May be {@literal null}. */
+ public List<AnnotationNode> invisibleAnnotations;
+
+ /** The runtime visible type annotations of this method. May be {@literal null}. */
+ public List<TypeAnnotationNode> visibleTypeAnnotations;
+
+ /** The runtime invisible type annotations of this method. May be {@literal null}. */
+ public List<TypeAnnotationNode> invisibleTypeAnnotations;
+
+ /** The non standard attributes of this method. May be {@literal null}. */
+ public List<Attribute> attrs;
+
+ /**
+ * The default value of this annotation interface method. This field must be a {@link Byte},
+ * {@link Boolean}, {@link Character}, {@link Short}, {@link Integer}, {@link Long}, {@link
+ * Float}, {@link Double}, {@link String} or {@link Type}, or an two elements String array (for
+ * enumeration values), a {@link AnnotationNode}, or a {@link List} of values of one of the
+ * preceding types. May be {@literal null}.
+ */
+ public Object annotationDefault;
+
+ /**
+ * The number of method parameters than can have runtime visible annotations. This number must be
+ * less or equal than the number of parameter types in the method descriptor (the default value 0
+ * indicates that all the parameters described in the method descriptor can have annotations). It
+ * can be strictly less when a method has synthetic parameters and when these parameters are
+ * ignored when computing parameter indices for the purpose of parameter annotations (see
+ * https://docs.oracle.com/javase/specs/jvms/se9/html/jvms-4.html#jvms-4.7.18).
+ */
+ public int visibleAnnotableParameterCount;
+
+ /**
+ * The runtime visible parameter annotations of this method. These lists are lists of {@link
+ * AnnotationNode} objects. May be {@literal null}.
+ */
+ public List<AnnotationNode>[] visibleParameterAnnotations;
+
+ /**
+ * The number of method parameters than can have runtime invisible annotations. This number must
+ * be less or equal than the number of parameter types in the method descriptor (the default value
+ * 0 indicates that all the parameters described in the method descriptor can have annotations).
+ * It can be strictly less when a method has synthetic parameters and when these parameters are
+ * ignored when computing parameter indices for the purpose of parameter annotations (see
+ * https://docs.oracle.com/javase/specs/jvms/se9/html/jvms-4.html#jvms-4.7.18).
+ */
+ public int invisibleAnnotableParameterCount;
+
+ /**
+ * The runtime invisible parameter annotations of this method. These lists are lists of {@link
+ * AnnotationNode} objects. May be {@literal null}.
+ */
+ public List<AnnotationNode>[] invisibleParameterAnnotations;
+
+ /** The instructions of this method. */
+ public InsnList instructions;
+
+ /** The try catch blocks of this method. */
+ public List<TryCatchBlockNode> tryCatchBlocks;
+
+ /** The maximum stack size of this method. */
+ public int maxStack;
+
+ /** The maximum number of local variables of this method. */
+ public int maxLocals;
+
+ /** The local variables of this method. May be {@literal null} */
+ public List<LocalVariableNode> localVariables;
+
+ /** The visible local variable annotations of this method. May be {@literal null} */
+ public List<LocalVariableAnnotationNode> visibleLocalVariableAnnotations;
+
+ /** The invisible local variable annotations of this method. May be {@literal null} */
+ public List<LocalVariableAnnotationNode> invisibleLocalVariableAnnotations;
+
+ /** Whether the accept method has been called on this object. */
+ private boolean visited;
+
+ /**
+ * Constructs an uninitialized {@link MethodNode}. <i>Subclasses must not use this
+ * constructor</i>. Instead, they must use the {@link #MethodNode(int)} version.
+ *
+ * @throws IllegalStateException If a subclass calls this constructor.
+ */
+ public MethodNode() {
+ this(Opcodes.ASM7);
+ if (getClass() != MethodNode.class) {
+ throw new IllegalStateException();
+ }
+ }
+
+ /**
+ * Constructs an uninitialized {@link MethodNode}.
+ *
+ * @param api the ASM API version implemented by this visitor. Must be one of {@link
+ * Opcodes#ASM4}, {@link Opcodes#ASM5}, {@link Opcodes#ASM6} or {@link Opcodes#ASM7}.
+ */
+ public MethodNode(final int api) {
+ super(api);
+ this.instructions = new InsnList();
+ }
+
+ /**
+ * Constructs a new {@link MethodNode}. <i>Subclasses must not use this constructor</i>. Instead,
+ * they must use the {@link #MethodNode(int, int, String, String, String, String[])} version.
+ *
+ * @param access the method's access flags (see {@link Opcodes}). This parameter also indicates if
+ * the method is synthetic and/or deprecated.
+ * @param name the method's name.
+ * @param descriptor the method's descriptor (see {@link Type}).
+ * @param signature the method's signature. May be {@literal null}.
+ * @param exceptions the internal names of the method's exception classes (see {@link
+ * Type#getInternalName()}). May be {@literal null}.
+ * @throws IllegalStateException If a subclass calls this constructor.
+ */
+ public MethodNode(
+ final int access,
+ final String name,
+ final String descriptor,
+ final String signature,
+ final String[] exceptions) {
+ this(Opcodes.ASM7, access, name, descriptor, signature, exceptions);
+ if (getClass() != MethodNode.class) {
+ throw new IllegalStateException();
+ }
+ }
+
+ /**
+ * Constructs a new {@link MethodNode}.
+ *
+ * @param api the ASM API version implemented by this visitor. Must be one of {@link
+ * Opcodes#ASM4}, {@link Opcodes#ASM5}, {@link Opcodes#ASM6} or {@link Opcodes#ASM7}.
+ * @param access the method's access flags (see {@link Opcodes}). This parameter also indicates if
+ * the method is synthetic and/or deprecated.
+ * @param name the method's name.
+ * @param descriptor the method's descriptor (see {@link Type}).
+ * @param signature the method's signature. May be {@literal null}.
+ * @param exceptions the internal names of the method's exception classes (see {@link
+ * Type#getInternalName()}). May be {@literal null}.
+ */
+ public MethodNode(
+ final int api,
+ final int access,
+ final String name,
+ final String descriptor,
+ final String signature,
+ final String[] exceptions) {
+ super(api);
+ this.access = access;
+ this.name = name;
+ this.desc = descriptor;
+ this.signature = signature;
+ this.exceptions = Util.asArrayList(exceptions);
+ if ((access & Opcodes.ACC_ABSTRACT) == 0) {
+ this.localVariables = new ArrayList<LocalVariableNode>(5);
+ }
+ this.tryCatchBlocks = new ArrayList<TryCatchBlockNode>();
+ this.instructions = new InsnList();
+ }
+
+ // -----------------------------------------------------------------------------------------------
+ // Implementation of the MethodVisitor abstract class
+ // -----------------------------------------------------------------------------------------------
+
+ @Override
+ public void visitParameter(final String name, final int access) {
+ if (parameters == null) {
+ parameters = new ArrayList<ParameterNode>(5);
+ }
+ parameters.add(new ParameterNode(name, access));
+ }
+
+ @Override
+ @SuppressWarnings("serial")
+ public AnnotationVisitor visitAnnotationDefault() {
+ return new AnnotationNode(
+ new ArrayList<Object>(0) {
+ @Override
+ public boolean add(final Object o) {
+ annotationDefault = o;
+ return super.add(o);
+ }
});
- }
-
- @Override
- public AnnotationVisitor visitAnnotation(final String desc,
- final boolean visible) {
- AnnotationNode an = new AnnotationNode(desc);
- if (visible) {
- if (visibleAnnotations == null) {
- visibleAnnotations = new ArrayList<AnnotationNode>(1);
- }
- visibleAnnotations.add(an);
- } else {
- if (invisibleAnnotations == null) {
- invisibleAnnotations = new ArrayList<AnnotationNode>(1);
- }
- invisibleAnnotations.add(an);
- }
- return an;
- }
-
- @Override
- public AnnotationVisitor visitTypeAnnotation(int typeRef,
- TypePath typePath, String desc, boolean visible) {
- TypeAnnotationNode an = new TypeAnnotationNode(typeRef, typePath, desc);
- if (visible) {
- if (visibleTypeAnnotations == null) {
- visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
- }
- visibleTypeAnnotations.add(an);
- } else {
- if (invisibleTypeAnnotations == null) {
- invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
- }
- invisibleTypeAnnotations.add(an);
- }
- return an;
- }
-
- @Override
- @SuppressWarnings("unchecked")
- public AnnotationVisitor visitParameterAnnotation(final int parameter,
- final String desc, final boolean visible) {
- AnnotationNode an = new AnnotationNode(desc);
- if (visible) {
- if (visibleParameterAnnotations == null) {
- int params = Type.getArgumentTypes(this.desc).length;
- visibleParameterAnnotations = (List<AnnotationNode>[]) new List<?>[params];
- }
- if (visibleParameterAnnotations[parameter] == null) {
- visibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(
- 1);
- }
- visibleParameterAnnotations[parameter].add(an);
- } else {
- if (invisibleParameterAnnotations == null) {
- int params = Type.getArgumentTypes(this.desc).length;
- invisibleParameterAnnotations = (List<AnnotationNode>[]) new List<?>[params];
- }
- if (invisibleParameterAnnotations[parameter] == null) {
- invisibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(
- 1);
- }
- invisibleParameterAnnotations[parameter].add(an);
- }
- return an;
- }
-
- @Override
- public void visitAttribute(final Attribute attr) {
- if (attrs == null) {
- attrs = new ArrayList<Attribute>(1);
- }
- attrs.add(attr);
- }
-
- @Override
- public void visitCode() {
- }
-
- @Override
- public void visitFrame(final int type, final int nLocal,
- final Object[] local, final int nStack, final Object[] stack) {
- instructions.add(new FrameNode(type, nLocal, local == null ? null
- : getLabelNodes(local), nStack, stack == null ? null
- : getLabelNodes(stack)));
- }
-
- @Override
- public void visitInsn(final int opcode) {
- instructions.add(new InsnNode(opcode));
- }
-
- @Override
- public void visitIntInsn(final int opcode, final int operand) {
- instructions.add(new IntInsnNode(opcode, operand));
- }
-
- @Override
- public void visitVarInsn(final int opcode, final int var) {
- instructions.add(new VarInsnNode(opcode, var));
- }
-
- @Override
- public void visitTypeInsn(final int opcode, final String type) {
- instructions.add(new TypeInsnNode(opcode, type));
- }
-
- @Override
- public void visitFieldInsn(final int opcode, final String owner,
- final String name, final String desc) {
- instructions.add(new FieldInsnNode(opcode, owner, name, desc));
- }
-
- @Deprecated
- @Override
- public void visitMethodInsn(int opcode, String owner, String name,
- String desc) {
- if (api >= Opcodes.ASM5) {
- super.visitMethodInsn(opcode, owner, name, desc);
- return;
- }
- instructions.add(new MethodInsnNode(opcode, owner, name, desc));
- }
-
- @Override
- public void visitMethodInsn(int opcode, String owner, String name,
- String desc, boolean itf) {
- if (api < Opcodes.ASM5) {
- super.visitMethodInsn(opcode, owner, name, desc, itf);
- return;
- }
- instructions.add(new MethodInsnNode(opcode, owner, name, desc, itf));
- }
-
- @Override
- public void visitInvokeDynamicInsn(String name, String desc, Handle bsm,
- Object... bsmArgs) {
- instructions.add(new InvokeDynamicInsnNode(name, desc, bsm, bsmArgs));
- }
-
- @Override
- public void visitJumpInsn(final int opcode, final Label label) {
- instructions.add(new JumpInsnNode(opcode, getLabelNode(label)));
- }
-
- @Override
- public void visitLabel(final Label label) {
- instructions.add(getLabelNode(label));
- }
-
- @Override
- public void visitLdcInsn(final Object cst) {
- instructions.add(new LdcInsnNode(cst));
- }
-
- @Override
- public void visitIincInsn(final int var, final int increment) {
- instructions.add(new IincInsnNode(var, increment));
- }
-
- @Override
- public void visitTableSwitchInsn(final int min, final int max,
- final Label dflt, final Label... labels) {
- instructions.add(new TableSwitchInsnNode(min, max, getLabelNode(dflt),
- getLabelNodes(labels)));
- }
-
- @Override
- public void visitLookupSwitchInsn(final Label dflt, final int[] keys,
- final Label[] labels) {
- instructions.add(new LookupSwitchInsnNode(getLabelNode(dflt), keys,
- getLabelNodes(labels)));
- }
-
- @Override
- public void visitMultiANewArrayInsn(final String desc, final int dims) {
- instructions.add(new MultiANewArrayInsnNode(desc, dims));
- }
-
- @Override
- public AnnotationVisitor visitInsnAnnotation(int typeRef,
- TypePath typePath, String desc, boolean visible) {
- // Finds the last real instruction, i.e. the instruction targeted by
- // this annotation.
- AbstractInsnNode insn = instructions.getLast();
- while (insn.getOpcode() == -1) {
- insn = insn.getPrevious();
+ }
+
+ @Override
+ public AnnotationVisitor visitAnnotation(final String descriptor, final boolean visible) {
+ AnnotationNode annotation = new AnnotationNode(descriptor);
+ if (visible) {
+ if (visibleAnnotations == null) {
+ visibleAnnotations = new ArrayList<AnnotationNode>(1);
+ }
+ visibleAnnotations.add(annotation);
+ } else {
+ if (invisibleAnnotations == null) {
+ invisibleAnnotations = new ArrayList<AnnotationNode>(1);
+ }
+ invisibleAnnotations.add(annotation);
+ }
+ return annotation;
+ }
+
+ @Override
+ public AnnotationVisitor visitTypeAnnotation(
+ final int typeRef, final TypePath typePath, final String descriptor, final boolean visible) {
+ TypeAnnotationNode typeAnnotation = new TypeAnnotationNode(typeRef, typePath, descriptor);
+ if (visible) {
+ if (visibleTypeAnnotations == null) {
+ visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ visibleTypeAnnotations.add(typeAnnotation);
+ } else {
+ if (invisibleTypeAnnotations == null) {
+ invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ invisibleTypeAnnotations.add(typeAnnotation);
+ }
+ return typeAnnotation;
+ }
+
+ @Override
+ public void visitAnnotableParameterCount(final int parameterCount, final boolean visible) {
+ if (visible) {
+ visibleAnnotableParameterCount = parameterCount;
+ } else {
+ invisibleAnnotableParameterCount = parameterCount;
+ }
+ }
+
+ @Override
+ @SuppressWarnings("unchecked")
+ public AnnotationVisitor visitParameterAnnotation(
+ final int parameter, final String descriptor, final boolean visible) {
+ AnnotationNode annotation = new AnnotationNode(descriptor);
+ if (visible) {
+ if (visibleParameterAnnotations == null) {
+ int params = Type.getArgumentTypes(desc).length;
+ visibleParameterAnnotations = (List<AnnotationNode>[]) new List<?>[params];
+ }
+ if (visibleParameterAnnotations[parameter] == null) {
+ visibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(1);
+ }
+ visibleParameterAnnotations[parameter].add(annotation);
+ } else {
+ if (invisibleParameterAnnotations == null) {
+ int params = Type.getArgumentTypes(desc).length;
+ invisibleParameterAnnotations = (List<AnnotationNode>[]) new List<?>[params];
+ }
+ if (invisibleParameterAnnotations[parameter] == null) {
+ invisibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(1);
+ }
+ invisibleParameterAnnotations[parameter].add(annotation);
+ }
+ return annotation;
+ }
+
+ @Override
+ public void visitAttribute(final Attribute attribute) {
+ if (attrs == null) {
+ attrs = new ArrayList<Attribute>(1);
+ }
+ attrs.add(attribute);
+ }
+
+ @Override
+ public void visitCode() {
+ // Nothing to do.
+ }
+
+ @Override
+ public void visitFrame(
+ final int type,
+ final int numLocal,
+ final Object[] local,
+ final int numStack,
+ final Object[] stack) {
+ instructions.add(
+ new FrameNode(
+ type,
+ numLocal,
+ local == null ? null : getLabelNodes(local),
+ numStack,
+ stack == null ? null : getLabelNodes(stack)));
+ }
+
+ @Override
+ public void visitInsn(final int opcode) {
+ instructions.add(new InsnNode(opcode));
+ }
+
+ @Override
+ public void visitIntInsn(final int opcode, final int operand) {
+ instructions.add(new IntInsnNode(opcode, operand));
+ }
+
+ @Override
+ public void visitVarInsn(final int opcode, final int var) {
+ instructions.add(new VarInsnNode(opcode, var));
+ }
+
+ @Override
+ public void visitTypeInsn(final int opcode, final String type) {
+ instructions.add(new TypeInsnNode(opcode, type));
+ }
+
+ @Override
+ public void visitFieldInsn(
+ final int opcode, final String owner, final String name, final String descriptor) {
+ instructions.add(new FieldInsnNode(opcode, owner, name, descriptor));
+ }
+
+ /**
+ * Deprecated.
+ *
+ * @deprecated use {@link #visitMethodInsn(int, String, String, String, boolean)} instead.
+ */
+ @Deprecated
+ @Override
+ public void visitMethodInsn(
+ final int opcode, final String owner, final String name, final String descriptor) {
+ if (api >= Opcodes.ASM5) {
+ super.visitMethodInsn(opcode, owner, name, descriptor);
+ return;
+ }
+ instructions.add(new MethodInsnNode(opcode, owner, name, descriptor));
+ }
+
+ @Override
+ public void visitMethodInsn(
+ final int opcode,
+ final String owner,
+ final String name,
+ final String descriptor,
+ final boolean isInterface) {
+ if (api < Opcodes.ASM5) {
+ super.visitMethodInsn(opcode, owner, name, descriptor, isInterface);
+ return;
+ }
+ instructions.add(new MethodInsnNode(opcode, owner, name, descriptor, isInterface));
+ }
+
+ @Override
+ public void visitInvokeDynamicInsn(
+ final String name,
+ final String descriptor,
+ final Handle bootstrapMethodHandle,
+ final Object... bootstrapMethodArguments) {
+ instructions.add(
+ new InvokeDynamicInsnNode(
+ name, descriptor, bootstrapMethodHandle, bootstrapMethodArguments));
+ }
+
+ @Override
+ public void visitJumpInsn(final int opcode, final Label label) {
+ instructions.add(new JumpInsnNode(opcode, getLabelNode(label)));
+ }
+
+ @Override
+ public void visitLabel(final Label label) {
+ instructions.add(getLabelNode(label));
+ }
+
+ @Override
+ public void visitLdcInsn(final Object value) {
+ instructions.add(new LdcInsnNode(value));
+ }
+
+ @Override
+ public void visitIincInsn(final int var, final int increment) {
+ instructions.add(new IincInsnNode(var, increment));
+ }
+
+ @Override
+ public void visitTableSwitchInsn(
+ final int min, final int max, final Label dflt, final Label... labels) {
+ instructions.add(new TableSwitchInsnNode(min, max, getLabelNode(dflt), getLabelNodes(labels)));
+ }
+
+ @Override
+ public void visitLookupSwitchInsn(final Label dflt, final int[] keys, final Label[] labels) {
+ instructions.add(new LookupSwitchInsnNode(getLabelNode(dflt), keys, getLabelNodes(labels)));
+ }
+
+ @Override
+ public void visitMultiANewArrayInsn(final String descriptor, final int numDimensions) {
+ instructions.add(new MultiANewArrayInsnNode(descriptor, numDimensions));
+ }
+
+ @Override
+ public AnnotationVisitor visitInsnAnnotation(
+ final int typeRef, final TypePath typePath, final String descriptor, final boolean visible) {
+ // Find the last real instruction, i.e. the instruction targeted by this annotation.
+ AbstractInsnNode currentInsn = instructions.getLast();
+ while (currentInsn.getOpcode() == -1) {
+ currentInsn = currentInsn.getPrevious();
+ }
+ // Add the annotation to this instruction.
+ TypeAnnotationNode typeAnnotation = new TypeAnnotationNode(typeRef, typePath, descriptor);
+ if (visible) {
+ if (currentInsn.visibleTypeAnnotations == null) {
+ currentInsn.visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ currentInsn.visibleTypeAnnotations.add(typeAnnotation);
+ } else {
+ if (currentInsn.invisibleTypeAnnotations == null) {
+ currentInsn.invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ currentInsn.invisibleTypeAnnotations.add(typeAnnotation);
+ }
+ return typeAnnotation;
+ }
+
+ @Override
+ public void visitTryCatchBlock(
+ final Label start, final Label end, final Label handler, final String type) {
+ tryCatchBlocks.add(
+ new TryCatchBlockNode(getLabelNode(start), getLabelNode(end), getLabelNode(handler), type));
+ }
+
+ @Override
+ public AnnotationVisitor visitTryCatchAnnotation(
+ final int typeRef, final TypePath typePath, final String descriptor, final boolean visible) {
+ TryCatchBlockNode tryCatchBlock = tryCatchBlocks.get((typeRef & 0x00FFFF00) >> 8);
+ TypeAnnotationNode typeAnnotation = new TypeAnnotationNode(typeRef, typePath, descriptor);
+ if (visible) {
+ if (tryCatchBlock.visibleTypeAnnotations == null) {
+ tryCatchBlock.visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ tryCatchBlock.visibleTypeAnnotations.add(typeAnnotation);
+ } else {
+ if (tryCatchBlock.invisibleTypeAnnotations == null) {
+ tryCatchBlock.invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(1);
+ }
+ tryCatchBlock.invisibleTypeAnnotations.add(typeAnnotation);
+ }
+ return typeAnnotation;
+ }
+
+ @Override
+ public void visitLocalVariable(
+ final String name,
+ final String descriptor,
+ final String signature,
+ final Label start,
+ final Label end,
+ final int index) {
+ localVariables.add(
+ new LocalVariableNode(
+ name, descriptor, signature, getLabelNode(start), getLabelNode(end), index));
+ }
+
+ @Override
+ public AnnotationVisitor visitLocalVariableAnnotation(
+ final int typeRef,
+ final TypePath typePath,
+ final Label[] start,
+ final Label[] end,
+ final int[] index,
+ final String descriptor,
+ final boolean visible) {
+ LocalVariableAnnotationNode localVariableAnnotation =
+ new LocalVariableAnnotationNode(
+ typeRef, typePath, getLabelNodes(start), getLabelNodes(end), index, descriptor);
+ if (visible) {
+ if (visibleLocalVariableAnnotations == null) {
+ visibleLocalVariableAnnotations = new ArrayList<LocalVariableAnnotationNode>(1);
+ }
+ visibleLocalVariableAnnotations.add(localVariableAnnotation);
+ } else {
+ if (invisibleLocalVariableAnnotations == null) {
+ invisibleLocalVariableAnnotations = new ArrayList<LocalVariableAnnotationNode>(1);
+ }
+ invisibleLocalVariableAnnotations.add(localVariableAnnotation);
+ }
+ return localVariableAnnotation;
+ }
+
+ @Override
+ public void visitLineNumber(final int line, final Label start) {
+ instructions.add(new LineNumberNode(line, getLabelNode(start)));
+ }
+
+ @Override
+ public void visitMaxs(final int maxStack, final int maxLocals) {
+ this.maxStack = maxStack;
+ this.maxLocals = maxLocals;
+ }
+
+ @Override
+ public void visitEnd() {
+ // Nothing to do.
+ }
+
+ /**
+ * Returns the LabelNode corresponding to the given Label. Creates a new LabelNode if necessary.
+ * The default implementation of this method uses the {@link Label#info} field to store
+ * associations between labels and label nodes.
+ *
+ * @param label a Label.
+ * @return the LabelNode corresponding to label.
+ */
+ protected LabelNode getLabelNode(final Label label) {
+ if (!(label.info instanceof LabelNode)) {
+ label.info = new LabelNode();
+ }
+ return (LabelNode) label.info;
+ }
+
+ private LabelNode[] getLabelNodes(final Label[] labels) {
+ LabelNode[] labelNodes = new LabelNode[labels.length];
+ for (int i = 0, n = labels.length; i < n; ++i) {
+ labelNodes[i] = getLabelNode(labels[i]);
+ }
+ return labelNodes;
+ }
+
+ private Object[] getLabelNodes(final Object[] objects) {
+ Object[] labelNodes = new Object[objects.length];
+ for (int i = 0, n = objects.length; i < n; ++i) {
+ Object o = objects[i];
+ if (o instanceof Label) {
+ o = getLabelNode((Label) o);
+ }
+ labelNodes[i] = o;
+ }
+ return labelNodes;
+ }
+
+ // -----------------------------------------------------------------------------------------------
+ // Accept method
+ // -----------------------------------------------------------------------------------------------
+
+ /**
+ * Checks that this method node is compatible with the given ASM API version. This method checks
+ * that this node, and all its children recursively, do not contain elements that were introduced
+ * in more recent versions of the ASM API than the given version.
+ *
+ * @param api an ASM API version. Must be one of {@link Opcodes#ASM4}, {@link Opcodes#ASM5},
+ * {@link Opcodes#ASM6} or {@link Opcodes#ASM7}.
+ */
+ public void check(final int api) {
+ if (api == Opcodes.ASM4) {
+ if (parameters != null && !parameters.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ if (visibleTypeAnnotations != null && !visibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ if (invisibleTypeAnnotations != null && !invisibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ if (tryCatchBlocks != null) {
+ for (int i = tryCatchBlocks.size() - 1; i >= 0; --i) {
+ TryCatchBlockNode tryCatchBlock = tryCatchBlocks.get(i);
+ if (tryCatchBlock.visibleTypeAnnotations != null
+ && !tryCatchBlock.visibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ if (tryCatchBlock.invisibleTypeAnnotations != null
+ && !tryCatchBlock.invisibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
}
- // Adds the annotation to this instruction.
- TypeAnnotationNode an = new TypeAnnotationNode(typeRef, typePath, desc);
- if (visible) {
- if (insn.visibleTypeAnnotations == null) {
- insn.visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(
- 1);
- }
- insn.visibleTypeAnnotations.add(an);
- } else {
- if (insn.invisibleTypeAnnotations == null) {
- insn.invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(
- 1);
- }
- insn.invisibleTypeAnnotations.add(an);
+ }
+ for (int i = instructions.size() - 1; i >= 0; --i) {
+ AbstractInsnNode insn = instructions.get(i);
+ if (insn.visibleTypeAnnotations != null && !insn.visibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
}
- return an;
- }
-
- @Override
- public void visitTryCatchBlock(final Label start, final Label end,
- final Label handler, final String type) {
- tryCatchBlocks.add(new TryCatchBlockNode(getLabelNode(start),
- getLabelNode(end), getLabelNode(handler), type));
- }
-
- @Override
- public AnnotationVisitor visitTryCatchAnnotation(int typeRef,
- TypePath typePath, String desc, boolean visible) {
- TryCatchBlockNode tcb = tryCatchBlocks.get((typeRef & 0x00FFFF00) >> 8);
- TypeAnnotationNode an = new TypeAnnotationNode(typeRef, typePath, desc);
- if (visible) {
- if (tcb.visibleTypeAnnotations == null) {
- tcb.visibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(
- 1);
- }
- tcb.visibleTypeAnnotations.add(an);
- } else {
- if (tcb.invisibleTypeAnnotations == null) {
- tcb.invisibleTypeAnnotations = new ArrayList<TypeAnnotationNode>(
- 1);
- }
- tcb.invisibleTypeAnnotations.add(an);
+ if (insn.invisibleTypeAnnotations != null && !insn.invisibleTypeAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
}
- return an;
- }
-
- @Override
- public void visitLocalVariable(final String name, final String desc,
- final String signature, final Label start, final Label end,
- final int index) {
- localVariables.add(new LocalVariableNode(name, desc, signature,
- getLabelNode(start), getLabelNode(end), index));
- }
-
- @Override
- public AnnotationVisitor visitLocalVariableAnnotation(int typeRef,
- TypePath typePath, Label[] start, Label[] end, int[] index,
- String desc, boolean visible) {
- LocalVariableAnnotationNode an = new LocalVariableAnnotationNode(
- typeRef, typePath, getLabelNodes(start), getLabelNodes(end),
- index, desc);
- if (visible) {
- if (visibleLocalVariableAnnotations == null) {
- visibleLocalVariableAnnotations = new ArrayList<LocalVariableAnnotationNode>(
- 1);
- }
- visibleLocalVariableAnnotations.add(an);
- } else {
- if (invisibleLocalVariableAnnotations == null) {
- invisibleLocalVariableAnnotations = new ArrayList<LocalVariableAnnotationNode>(
- 1);
- }
- invisibleLocalVariableAnnotations.add(an);
+ if (insn instanceof MethodInsnNode) {
+ boolean isInterface = ((MethodInsnNode) insn).itf;
+ if (isInterface != (insn.opcode == Opcodes.INVOKEINTERFACE)) {
+ throw new UnsupportedClassVersionException();
+ }
+ } else if (insn instanceof LdcInsnNode) {
+ Object value = ((LdcInsnNode) insn).cst;
+ if (value instanceof Handle
+ || (value instanceof Type && ((Type) value).getSort() == Type.METHOD)) {
+ throw new UnsupportedClassVersionException();
+ }
}
- return an;
- }
-
- @Override
- public void visitLineNumber(final int line, final Label start) {
- instructions.add(new LineNumberNode(line, getLabelNode(start)));
- }
-
- @Override
- public void visitMaxs(final int maxStack, final int maxLocals) {
- this.maxStack = maxStack;
- this.maxLocals = maxLocals;
- }
-
- @Override
- public void visitEnd() {
- }
-
- /**
- * Returns the LabelNode corresponding to the given Label. Creates a new
- * LabelNode if necessary. The default implementation of this method uses
- * the {@link Label#info} field to store associations between labels and
- * label nodes.
- *
- * @param l
- * a Label.
- * @return the LabelNode corresponding to l.
- */
- protected LabelNode getLabelNode(final Label l) {
- if (!(l.info instanceof LabelNode)) {
- l.info = new LabelNode();
+ }
+ if (visibleLocalVariableAnnotations != null && !visibleLocalVariableAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ if (invisibleLocalVariableAnnotations != null
+ && !invisibleLocalVariableAnnotations.isEmpty()) {
+ throw new UnsupportedClassVersionException();
+ }
+ }
+ if (api != Opcodes.ASM7) {
+ for (int i = instructions.size() - 1; i >= 0; --i) {
+ AbstractInsnNode insn = instructions.get(i);
+ if (insn instanceof LdcInsnNode) {
+ Object value = ((LdcInsnNode) insn).cst;
+ if (value instanceof ConstantDynamic) {
+ throw new UnsupportedClassVersionException();
+ }
}
- return (LabelNode) l.info;
- }
-
- private LabelNode[] getLabelNodes(final Label[] l) {
- LabelNode[] nodes = new LabelNode[l.length];
- for (int i = 0; i < l.length; ++i) {
- nodes[i] = getLabelNode(l[i]);
+ }
+ }
+ }
+
+ /**
+ * Makes the given class visitor visit this method.
+ *
+ * @param classVisitor a class visitor.
+ */
+ public void accept(final ClassVisitor classVisitor) {
+ String[] exceptionsArray = new String[this.exceptions.size()];
+ this.exceptions.toArray(exceptionsArray);
+ MethodVisitor methodVisitor =
+ classVisitor.visitMethod(access, name, desc, signature, exceptionsArray);
+ if (methodVisitor != null) {
+ accept(methodVisitor);
+ }
+ }
+
+ /**
+ * Makes the given method visitor visit this method.
+ *
+ * @param methodVisitor a method visitor.
+ */
+ public void accept(final MethodVisitor methodVisitor) {
+ // Visit the parameters.
+ if (parameters != null) {
+ for (int i = 0, n = parameters.size(); i < n; i++) {
+ parameters.get(i).accept(methodVisitor);
+ }
+ }
+ // Visit the annotations.
+ if (annotationDefault != null) {
+ AnnotationVisitor annotationVisitor = methodVisitor.visitAnnotationDefault();
+ AnnotationNode.accept(annotationVisitor, null, annotationDefault);
+ if (annotationVisitor != null) {
+ annotationVisitor.visitEnd();
+ }
+ }
+ if (visibleAnnotations != null) {
+ for (int i = 0, n = visibleAnnotations.size(); i < n; ++i) {
+ AnnotationNode annotation = visibleAnnotations.get(i);
+ annotation.accept(methodVisitor.visitAnnotation(annotation.desc, true));
+ }
+ }
+ if (invisibleAnnotations != null) {
+ for (int i = 0, n = invisibleAnnotations.size(); i < n; ++i) {
+ AnnotationNode annotation = invisibleAnnotations.get(i);
+ annotation.accept(methodVisitor.visitAnnotation(annotation.desc, false));
+ }
+ }
+ if (visibleTypeAnnotations != null) {
+ for (int i = 0, n = visibleTypeAnnotations.size(); i < n; ++i) {
+ TypeAnnotationNode typeAnnotation = visibleTypeAnnotations.get(i);
+ typeAnnotation.accept(
+ methodVisitor.visitTypeAnnotation(
+ typeAnnotation.typeRef, typeAnnotation.typePath, typeAnnotation.desc, true));
+ }
+ }
+ if (invisibleTypeAnnotations != null) {
+ for (int i = 0, n = invisibleTypeAnnotations.size(); i < n; ++i) {
+ TypeAnnotationNode typeAnnotation = invisibleTypeAnnotations.get(i);
+ typeAnnotation.accept(
+ methodVisitor.visitTypeAnnotation(
+ typeAnnotation.typeRef, typeAnnotation.typePath, typeAnnotation.desc, false));
+ }
+ }
+ if (visibleAnnotableParameterCount > 0) {
+ methodVisitor.visitAnnotableParameterCount(visibleAnnotableParameterCount, true);
+ }
+ if (visibleParameterAnnotations != null) {
+ for (int i = 0, n = visibleParameterAnnotations.length; i < n; ++i) {
+ List<AnnotationNode> parameterAnnotations = visibleParameterAnnotations[i];
+ if (parameterAnnotations == null) {
+ continue;
}
- return nodes;
- }
-
- private Object[] getLabelNodes(final Object[] objs) {
- Object[] nodes = new Object[objs.length];
- for (int i = 0; i < objs.length; ++i) {
- Object o = objs[i];
- if (o instanceof Label) {
- o = getLabelNode((Label) o);
- }
- nodes[i] = o;
- }
- return nodes;
- }
-
- // ------------------------------------------------------------------------
- // Accept method
- // ------------------------------------------------------------------------
-
- /**
- * Checks that this method node is compatible with the given ASM API
- * version. This methods checks that this node, and all its nodes
- * recursively, do not contain elements that were introduced in more recent
- * versions of the ASM API than the given version.
- *
- * @param api
- * an ASM API version. Must be one of {@link Opcodes#ASM4},
- * {@link Opcodes#ASM5} or {@link Opcodes#ASM6}.
- */
- public void check(final int api) {
- if (api == Opcodes.ASM4) {
- if (visibleTypeAnnotations != null
- && visibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- if (invisibleTypeAnnotations != null
- && invisibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- int n = tryCatchBlocks == null ? 0 : tryCatchBlocks.size();
- for (int i = 0; i < n; ++i) {
- TryCatchBlockNode tcb = tryCatchBlocks.get(i);
- if (tcb.visibleTypeAnnotations != null
- && tcb.visibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- if (tcb.invisibleTypeAnnotations != null
- && tcb.invisibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- }
- for (int i = 0; i < instructions.size(); ++i) {
- AbstractInsnNode insn = instructions.get(i);
- if (insn.visibleTypeAnnotations != null
- && insn.visibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- if (insn.invisibleTypeAnnotations != null
- && insn.invisibleTypeAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- if (insn instanceof MethodInsnNode) {
- boolean itf = ((MethodInsnNode) insn).itf;
- if (itf != (insn.opcode == Opcodes.INVOKEINTERFACE)) {
- throw new RuntimeException();
- }
- }
- }
- if (visibleLocalVariableAnnotations != null
- && visibleLocalVariableAnnotations.size() > 0) {
- throw new RuntimeException();
- }
- if (invisibleLocalVariableAnnotations != null
- && invisibleLocalVariableAnnotations.size() > 0) {
- throw new RuntimeException();
- }
+ for (int j = 0, m = parameterAnnotations.size(); j < m; ++j) {
+ AnnotationNode annotation = parameterAnnotations.get(j);
+ annotation.accept(methodVisitor.visitParameterAnnotation(i, annotation.desc, true));
}
+ }
}
-
- /**
- * Makes the given class visitor visit this method.
- *
- * @param cv
- * a class visitor.
- */
- public void accept(final ClassVisitor cv) {
- String[] exceptions = new String[this.exceptions.size()];
- this.exceptions.toArray(exceptions);
- MethodVisitor mv = cv.visitMethod(access, name, desc, signature,
- exceptions);
- if (mv != null) {
- accept(mv);
- }
+ if (invisibleAnnotableParameterCount > 0) {
+ methodVisitor.visitAnnotableParameterCount(invisibleAnnotableParameterCount, false);
}
-
- /**
- * Makes the given method visitor visit this method.
- *
- * @param mv
- * a method visitor.
- */
- public void accept(final MethodVisitor mv) {
- // visits the method parameters
- int i, j, n;
- n = parameters == null ? 0 : parameters.size();
- for (i = 0; i < n; i++) {
- ParameterNode parameter = parameters.get(i);
- mv.visitParameter(parameter.name, parameter.access);
- }
- // visits the method attributes
- if (annotationDefault != null) {
- AnnotationVisitor av = mv.visitAnnotationDefault();
- AnnotationNode.accept(av, null, annotationDefault);
- if (av != null) {
- av.visitEnd();
- }
- }
- n = visibleAnnotations == null ? 0 : visibleAnnotations.size();
- for (i = 0; i < n; ++i) {
- AnnotationNode an = visibleAnnotations.get(i);
- an.accept(mv.visitAnnotation(an.desc, true));
- }
- n = invisibleAnnotations == null ? 0 : invisibleAnnotations.size();
- for (i = 0; i < n; ++i) {
- AnnotationNode an = invisibleAnnotations.get(i);
- an.accept(mv.visitAnnotation(an.desc, false));
- }
- n = visibleTypeAnnotations == null ? 0 : visibleTypeAnnotations.size();
- for (i = 0; i < n; ++i) {
- TypeAnnotationNode an = visibleTypeAnnotations.get(i);
- an.accept(mv.visitTypeAnnotation(an.typeRef, an.typePath, an.desc,
- true));
- }
- n = invisibleTypeAnnotations == null ? 0 : invisibleTypeAnnotations
- .size();
- for (i = 0; i < n; ++i) {
- TypeAnnotationNode an = invisibleTypeAnnotations.get(i);
- an.accept(mv.visitTypeAnnotation(an.typeRef, an.typePath, an.desc,
- false));
+ if (invisibleParameterAnnotations != null) {
+ for (int i = 0, n = invisibleParameterAnnotations.length; i < n; ++i) {
+ List<AnnotationNode> parameterAnnotations = invisibleParameterAnnotations[i];
+ if (parameterAnnotations == null) {
+ continue;
}
- n = visibleParameterAnnotations == null ? 0
- : visibleParameterAnnotations.length;
- for (i = 0; i < n; ++i) {
- List<?> l = visibleParameterAnnotations[i];
- if (l == null) {
- continue;
- }
- for (j = 0; j < l.size(); ++j) {
- AnnotationNode an = (AnnotationNode) l.get(j);
- an.accept(mv.visitParameterAnnotation(i, an.desc, true));
- }
+ for (int j = 0, m = parameterAnnotations.size(); j < m; ++j) {
+ AnnotationNode annotation = parameterAnnotations.get(j);
+ annotation.accept(methodVisitor.visitParameterAnnotation(i, annotation.desc, false));
}
- n = invisibleParameterAnnotations == null ? 0
- : invisibleParameterAnnotations.length;
- for (i = 0; i < n; ++i) {
- List<?> l = invisibleParameterAnnotations[i];
- if (l == null) {
- continue;
- }
- for (j = 0; j < l.size(); ++j) {
- AnnotationNode an = (AnnotationNode) l.get(j);
- an.accept(mv.visitParameterAnnotation(i, an.desc, false));
- }
+ }
+ }
+ // Visit the non standard attributes.
+ if (visited) {
+ instructions.resetLabels();
+ }
+ if (attrs != null) {
+ for (int i = 0, n = attrs.size(); i < n; ++i) {
+ methodVisitor.visitAttribute(attrs.get(i));
+ }
+ }
+ // Visit the code.
+ if (instructions.size() > 0) {
+ methodVisitor.visitCode();
+ // Visits the try catch blocks.
+ if (tryCatchBlocks != null) {
+ for (int i = 0, n = tryCatchBlocks.size(); i < n; ++i) {
+ tryCatchBlocks.get(i).updateIndex(i);
+ tryCatchBlocks.get(i).accept(methodVisitor);
}
- if (visited) {
- instructions.resetLabels();
+ }
+ // Visit the instructions.
+ instructions.accept(methodVisitor);
+ // Visits the local variables.
+ if (localVariables != null) {
+ for (int i = 0, n = localVariables.size(); i < n; ++i) {
+ localVariables.get(i).accept(methodVisitor);
}
- n = attrs == null ? 0 : attrs.size();
- for (i = 0; i < n; ++i) {
- mv.visitAttribute(attrs.get(i));
+ }
+ // Visits the local variable annotations.
+ if (visibleLocalVariableAnnotations != null) {
+ for (int i = 0, n = visibleLocalVariableAnnotations.size(); i < n; ++i) {
+ visibleLocalVariableAnnotations.get(i).accept(methodVisitor, true);
}
- // visits the method's code
- if (instructions.size() > 0) {
- mv.visitCode();
- // visits try catch blocks
- n = tryCatchBlocks == null ? 0 : tryCatchBlocks.size();
- for (i = 0; i < n; ++i) {
- tryCatchBlocks.get(i).updateIndex(i);
- tryCatchBlocks.get(i).accept(mv);
- }
- // visits instructions
- instructions.accept(mv);
- // visits local variables
- n = localVariables == null ? 0 : localVariables.size();
- for (i = 0; i < n; ++i) {
- localVariables.get(i).accept(mv);
- }
- // visits local variable annotations
- n = visibleLocalVariableAnnotations == null ? 0
- : visibleLocalVariableAnnotations.size();
- for (i = 0; i < n; ++i) {
- visibleLocalVariableAnnotations.get(i).accept(mv, true);
- }
- n = invisibleLocalVariableAnnotations == null ? 0
- : invisibleLocalVariableAnnotations.size();
- for (i = 0; i < n; ++i) {
- invisibleLocalVariableAnnotations.get(i).accept(mv, false);
- }
- // visits maxs
- mv.visitMaxs(maxStack, maxLocals);
- visited = true;
+ }
+ if (invisibleLocalVariableAnnotations != null) {
+ for (int i = 0, n = invisibleLocalVariableAnnotations.size(); i < n; ++i) {
+ invisibleLocalVariableAnnotations.get(i).accept(methodVisitor, false);
}
- mv.visitEnd();
+ }
+ methodVisitor.visitMaxs(maxStack, maxLocals);
+ visited = true;
}
+ methodVisitor.visitEnd();
+ }
}
http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/1c71aec7/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleExportNode.java
----------------------------------------------------------------------
diff --git a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleExportNode.java b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleExportNode.java
old mode 100644
new mode 100755
index 946872d..c4f6503
--- a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleExportNode.java
+++ b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleExportNode.java
@@ -1,82 +1,79 @@
-/***
- * ASM: a very small and fast Java bytecode manipulation framework
- * Copyright (c) 2000-2011 INRIA, France Telecom
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
+// ASM: a very small and fast Java bytecode manipulation framework
+// Copyright (c) 2000-2011 INRIA, France Telecom
+// All rights reserved.
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+// 1. Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// 2. Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+// 3. Neither the name of the copyright holders nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+// THE POSSIBILITY OF SUCH DAMAGE.
package org.apache.tapestry5.internal.plastic.asm.tree;
import java.util.List;
-
import org.apache.tapestry5.internal.plastic.asm.ModuleVisitor;
/**
* A node that represents an exported package with its name and the module that can access to it.
- *
+ *
* @author Remi Forax
*/
public class ModuleExportNode {
- /**
- * The package name.
- */
- public String packaze;
-
- /**
- * The access flags (see {@link org.objectweb.asm.Opcodes}).
- * Valid values are {@code ACC_SYNTHETIC} and {@code ACC_MANDATED}.
- */
- public int access;
- /**
- * A list of modules that can access to this exported package.
- * May be <tt>null</tt>.
- */
- public List<String> modules;
+ /** The internal name of the exported package. */
+ public String packaze;
+
+ /**
+ * The access flags (see {@link org.apache.tapestry5.internal.plastic.asm.Opcodes}). Valid values are {@code
+ * ACC_SYNTHETIC} and {@code ACC_MANDATED}.
+ */
+ public int access;
+
+ /**
+ * The list of modules that can access this exported package, specified with fully qualified names
+ * (using dots). May be {@literal null}.
+ */
+ public List<String> modules;
- /**
- * Constructs a new {@link ModuleExportNode}.
- *
- * @param packaze
- * the parameter's name.
- * @param modules
- * a list of modules that can access to this exported package.
- */
- public ModuleExportNode(final String packaze, final int access, final List<String> modules) {
- this.packaze = packaze;
- this.access = access;
- this.modules = modules;
- }
+ /**
+ * Constructs a new {@link ModuleExportNode}.
+ *
+ * @param packaze the internal name of the exported package.
+ * @param access the package access flags, one or more of {@code ACC_SYNTHETIC} and {@code
+ * ACC_MANDATED}.
+ * @param modules a list of modules that can access this exported package, specified with fully
+ * qualified names (using dots).
+ */
+ public ModuleExportNode(final String packaze, final int access, final List<String> modules) {
+ this.packaze = packaze;
+ this.access = access;
+ this.modules = modules;
+ }
- /**
- * Makes the given module visitor visit this export declaration.
- *
- * @param mv
- * a module visitor.
- */
- public void accept(final ModuleVisitor mv) {
- mv.visitExport(packaze, access, (modules == null) ? null : modules.toArray(new String[0]));
- }
+ /**
+ * Makes the given module visitor visit this export declaration.
+ *
+ * @param moduleVisitor a module visitor.
+ */
+ public void accept(final ModuleVisitor moduleVisitor) {
+ moduleVisitor.visitExport(
+ packaze, access, modules == null ? null : modules.toArray(new String[0]));
+ }
}
http://git-wip-us.apache.org/repos/asf/tapestry-5/blob/1c71aec7/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleNode.java
----------------------------------------------------------------------
diff --git a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleNode.java b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleNode.java
old mode 100644
new mode 100755
index e76dbf1..fe05259
--- a/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleNode.java
+++ b/plastic/src/external/java/org/apache/tapestry5/internal/plastic/asm/tree/ModuleNode.java
@@ -1,115 +1,116 @@
-/***
- * ASM: a very small and fast Java bytecode manipulation framework
- * Copyright (c) 2000-2011 INRIA, France Telecom
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the copyright holders nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
- * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
- * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
- * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
- * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
- * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
- * THE POSSIBILITY OF SUCH DAMAGE.
- */
+// ASM: a very small and fast Java bytecode manipulation framework
+// Copyright (c) 2000-2011 INRIA, France Telecom
+// All rights reserved.
+//
+// Redistribution and use in source and binary forms, with or without
+// modification, are permitted provided that the following conditions
+// are met:
+// 1. Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+// 2. Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+// 3. Neither the name of the copyright holders nor the names of its
+// contributors may be used to endorse or promote products derived from
+// this software without specific prior written permission.
+//
+// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+// THE POSSIBILITY OF SUCH DAMAGE.
package org.apache.tapestry5.internal.plastic.asm.tree;
import java.util.ArrayList;
import java.util.List;
-
import org.apache.tapestry5.internal.plastic.asm.ClassVisitor;
import org.apache.tapestry5.internal.plastic.asm.ModuleVisitor;
import org.apache.tapestry5.internal.plastic.asm.Opcodes;
/**
* A node that represents a module declaration.
- *
+ *
* @author Remi Forax
*/
public class ModuleNode extends ModuleVisitor {
- /**
- * Module name
- */
- public String name;
-
- /**
- * Module access flags, among {@code ACC_OPEN}, {@code ACC_SYNTHETIC}
- * and {@code ACC_MANDATED}.
- */
- public int access;
-
- /**
- * Version of the module.
- * May be <tt>null</tt>.
- */
- public String version;
-
- /**
- * Name of the main class in internal form
- * May be <tt>null</tt>.
- */
- public String mainClass;
-
- /**
- * A list of packages that are declared by the current module.
- * May be <tt>null</tt>.
- */
- public List<String> packages;
-
- /**
- * A list of modules can are required by the current module.
- * May be <tt>null</tt>.
- */
- public List<ModuleRequireNode> requires;
-
- /**
- * A list of packages that are exported by the current module.
- * May be <tt>null</tt>.
- */
- public List<ModuleExportNode> exports;
-
- /**
- * A list of packages that are opened by the current module.
- * May be <tt>null</tt>.
- */
- public List<ModuleOpenNode> opens;
-
- /**
- * A list of classes in their internal forms that are used
- * as a service by the current module. May be <tt>null</tt>.
- */
- public List<String> uses;
-
- /**
- * A list of services along with their implementations provided
- * by the current module. May be <tt>null</tt>.
- */
- public List<ModuleProvideNode> provides;
-
- public ModuleNode(final String name, final int access,
- final String version) {
- super(Opcodes.ASM6);
- this.name = name;
- this.access = access;
- this.version = version;
+
+ /** The fully qualified name (using dots) of this module. */
+ public String name;
+
+ /**
+ * The module's access flags, among {@code ACC_OPEN}, {@code ACC_SYNTHETIC} and {@code
+ * ACC_MANDATED}.
+ */
+ public int access;
+
+ /** The version of this module. May be {@literal null}. */
+ public String version;
+
+ /** The internal name of the main class of this module. May be {@literal null}. */
+ public String mainClass;
+
+ /** The internal name of the packages declared by this module. May be {@literal null}. */
+ public List<String> packages;
+
+ /** The dependencies of this module. May be {@literal null}. */
+ public List<ModuleRequireNode> requires;
+
+ /** The packages exported by this module. May be {@literal null}. */
+ public List<ModuleExportNode> exports;
+
+ /** The packages opened by this module. May be {@literal null}. */
+ public List<ModuleOpenNode> opens;
+
+ /** The internal names of the services used by this module. May be {@literal null}. */
+ public List<String> uses;
+
+ /** The services provided by this module. May be {@literal null}. */
+ public List<ModuleProvideNode> provides;
+
+ /**
+ * Constructs a {@link ModuleNode}. <i>Subclasses must not use this constructor</i>. Instead, they
+ * must use the {@link #ModuleNode(int,String,int,String,List,List,List,List,List)} version.
+ *
+ * @param name the fully qualified name (using dots) of the module.
+ * @param access the module access flags, among {@code ACC_OPEN}, {@code ACC_SYNTHETIC} and {@code
+ * ACC_MANDATED}.
+ * @param version the module version, or {@literal null}.
+ * @throws IllegalStateException If a subclass calls this constructor.
+ */
+ public ModuleNode(final String name, final int access, final String version) {
+ super(Opcodes.ASM7);
+ if (getClass() != ModuleNode.class) {
+ throw new IllegalStateException();
}
-
- public ModuleNode(final int api,
+ this.name = name;
+ this.access = access;
+ this.version = version;
+ }
+
+ // TODO(forax): why is there no 'mainClass' and 'packages' parameters in this constructor?
+ /**
+ * Constructs a {@link ModuleNode}.
+ *
+ * @param api the ASM API version implemented by this visitor. Must be one of {@link Opcodes#ASM6}
+ * or {@link Opcodes#ASM7}.
+ * @param name the fully qualified name (using dots) of the module.
+ * @param access the module access flags, among {@code ACC_OPEN}, {@code ACC_SYNTHETIC} and {@code
+ * ACC_MANDATED}.
+ * @param version the module version, or {@literal null}.
+ * @param requires The dependencies of this module. May be {@literal null}.
+ * @param exports The packages exported by this module. May be {@literal null}.
+ * @param opens The packages opened by this module. May be {@literal null}.
+ * @param uses The internal names of the services used by this module. May be {@literal null}.
+ * @param provides The services provided by this module. May be {@literal null}.
+ */
+ public ModuleNode(
+ final int api,
final String name,
final int access,
final String version,
@@ -118,134 +119,117 @@ public class ModuleNode extends ModuleVisitor {
final List<ModuleOpenNode> opens,
final List<String> uses,
final List<ModuleProvideNode> provides) {
- super(api);
- this.name = name;
- this.access = access;
- this.version = version;
- this.requires = requires;
- this.exports = exports;
- this.opens = opens;
- this.uses = uses;
- this.provides = provides;
- if (getClass() != ModuleNode.class) {
- throw new IllegalStateException();
- }
+ super(api);
+ this.name = name;
+ this.access = access;
+ this.version = version;
+ this.requires = requires;
+ this.exports = exports;
+ this.opens = opens;
+ this.uses = uses;
+ this.provides = provides;
+ }
+
+ @Override
+ public void visitMainClass(final String mainClass) {
+ this.mainClass = mainClass;
+ }
+
+ @Override
+ public void visitPackage(final String packaze) {
+ if (packages == null) {
+ packages = new ArrayList<String>(5);
}
-
- @Override
- public void visitMainClass(String mainClass) {
- this.mainClass = mainClass;
+ packages.add(packaze);
+ }
+
+ @Override
+ public void visitRequire(final String module, final int access, final String version) {
+ if (requires == null) {
+ requires = new ArrayList<ModuleRequireNode>(5);
+ }
+ requires.add(new ModuleRequireNode(module, access, version));
+ }
+
+ @Override
+ public void visitExport(final String packaze, final int access, final String... modules) {
+ if (exports == null) {
+ exports = new ArrayList<ModuleExportNode>(5);
}
-
- @Override
- public void visitPackage(String packaze) {
- if (packages == null) {
- packages = new ArrayList<String>(5);
- }
- packages.add(packaze);
+ exports.add(new ModuleExportNode(packaze, access, Util.asArrayList(modules)));
+ }
+
+ @Override
+ public void visitOpen(final String packaze, final int access, final String... modules) {
+ if (opens == null) {
+ opens = new ArrayList<ModuleOpenNode>(5);
+ }
+ opens.add(new ModuleOpenNode(packaze, access, Util.asArrayList(modules)));
+ }
+
+ @Override
+ public void visitUse(final String service) {
+ if (uses == null) {
+ uses = new ArrayList<String>(5);
+ }
+ uses.add(service);
+ }
+
+ @Override
+ public void visitProvide(final String service, final String... providers) {
+ if (provides == null) {
+ provides = new ArrayList<ModuleProvideNode>(5);
+ }
+ provides.add(new ModuleProvideNode(service, Util.asArrayList(providers)));
+ }
+
+ @Override
+ public void visitEnd() {
+ // Nothing to do.
+ }
+
+ /**
+ * Makes the given class visitor visit this module.
+ *
+ * @param classVisitor a class visitor.
+ */
+ public void accept(final ClassVisitor classVisitor) {
+ ModuleVisitor moduleVisitor = classVisitor.visitModule(name, access, version);
+ if (moduleVisitor == null) {
+ return;
}
-
- @Override
- public void visitRequire(String module, int access, String version) {
- if (requires == null) {
- requires = new ArrayList<ModuleRequireNode>(5);
- }
- requires.add(new ModuleRequireNode(module, access, version));
+ if (mainClass != null) {
+ moduleVisitor.visitMainClass(mainClass);
}
-
- @Override
- public void visitExport(String packaze, int access, String... modules) {
- if (exports == null) {
- exports = new ArrayList<ModuleExportNode>(5);
- }
- List<String> moduleList = null;
- if (modules != null) {
- moduleList = new ArrayList<String>(modules.length);
- for (int i = 0; i < modules.length; i++) {
- moduleList.add(modules[i]);
- }
- }
- exports.add(new ModuleExportNode(packaze, access, moduleList));
+ if (packages != null) {
+ for (int i = 0, n = packages.size(); i < n; i++) {
+ moduleVisitor.visitPackage(packages.get(i));
+ }
}
-
- @Override
- public void visitOpen(String packaze, int access, String... modules) {
- if (opens == null) {
- opens = new ArrayList<ModuleOpenNode>(5);
- }
- List<String> moduleList = null;
- if (modules != null) {
- moduleList = new ArrayList<String>(modules.length);
- for (int i = 0; i < modules.length; i++) {
- moduleList.add(modules[i]);
- }
- }
- opens.add(new ModuleOpenNode(packaze, access, moduleList));
+ if (requires != null) {
+ for (int i = 0, n = requires.size(); i < n; i++) {
+ requires.get(i).accept(moduleVisitor);
+ }
}
-
- @Override
- public void visitUse(String service) {
- if (uses == null) {
- uses = new ArrayList<String>(5);
- }
- uses.add(service);
+ if (exports != null) {
+ for (int i = 0, n = exports.size(); i < n; i++) {
+ exports.get(i).accept(moduleVisitor);
+ }
}
-
- @Override
- public void visitProvide(String service, String... providers) {
- if (provides == null) {
- provides = new ArrayList<ModuleProvideNode>(5);
- }
- ArrayList<String> providerList =
- new ArrayList<String>(providers.length);
- for (int i = 0; i < providers.length; i++) {
- providerList.add(providers[i]);
- }
- provides.add(new ModuleProvideNode(service, providerList));
+ if (opens != null) {
+ for (int i = 0, n = opens.size(); i < n; i++) {
+ opens.get(i).accept(moduleVisitor);
+ }
}
-
- @Override
- public void visitEnd() {
+ if (uses != null) {
+ for (int i = 0, n = uses.size(); i < n; i++) {
+ moduleVisitor.visitUse(uses.get(i));
+ }
}
-
- public void accept(final ClassVisitor cv) {
- ModuleVisitor mv = cv.visitModule(name, access, version);
- if (mv == null) {
- return;
- }
- if (mainClass != null) {
- mv.visitMainClass(mainClass);
- }
- if (packages != null) {
- for (int i = 0; i < packages.size(); i++) {
- mv.visitPackage(packages.get(i));
- }
- }
-
- if (requires != null) {
- for (int i = 0; i < requires.size(); i++) {
- requires.get(i).accept(mv);
- }
- }
- if (exports != null) {
- for (int i = 0; i < exports.size(); i++) {
- exports.get(i).accept(mv);
- }
- }
- if (opens != null) {
- for (int i = 0; i < opens.size(); i++) {
- opens.get(i).accept(mv);
- }
- }
- if (uses != null) {
- for (int i = 0; i < uses.size(); i++) {
- mv.visitUse(uses.get(i));
- }
- }
- if (provides != null) {
- for (int i = 0; i < provides.size(); i++) {
- provides.get(i).accept(mv);
- }
- }
+ if (provides != null) {
+ for (int i = 0, n = provides.size(); i < n; i++) {
+ provides.get(i).accept(moduleVisitor);
+ }
}
+ }
}