[1.7.10] ASM transforming causes ArrayIndexOutOfBoundsException in Modder Support Posted November 12, 2014 What I'm trying to do is adding a hooks for changing sky color without creating a new biome. (I'm new to ASM, I used this tutorial : http://www.minecraftforum.net/forums/mapping-and-modding/mapping-and-modding-tutorials/1571568-tutorial-1-6-2-changing-vanilla-without-editing) The crash: java.lang.NoClassDefFoundError: net/minecraftforge/client/ForgeHooksClient at net.minecraft.client.Minecraft.startGame(Minecraft.java:474) at net.minecraft.client.Minecraft.run(Minecraft.java:931) at net.minecraft.client.main.Main.main(Main.java:164) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at net.minecraft.launchwrapper.Launch.launch(Launch.java:135) at net.minecraft.launchwrapper.Launch.main(Launch.java:28) at net.minecraftforge.gradle.GradleStartCommon.launch(GradleStartCommon.java:78) at GradleStart.main(GradleStart.java:45) Caused by: java.lang.ClassNotFoundException: net.minecraftforge.client.ForgeHooksClient at net.minecraft.launchwrapper.LaunchClassLoader.findClass(LaunchClassLoader.java:191) at java.lang.ClassLoader.loadClass(Unknown Source) at java.lang.ClassLoader.loadClass(Unknown Source) ... 11 more Caused by: java.lang.ArrayIndexOutOfBoundsException: -1 at org.objectweb.asm.Frame.merge(Frame.java:1311) at org.objectweb.asm.MethodWriter.visitMaxs(MethodWriter.java:1475) at org.objectweb.asm.tree.MethodNode.accept(MethodNode.java:834) at org.objectweb.asm.tree.MethodNode.accept(MethodNode.java:726) at org.objectweb.asm.tree.ClassNode.accept(ClassNode.java:412) at com.starsheep.colorevents.ColorTransformer.transformClientHooks(ColorTransformer.java:114) at com.starsheep.colorevents.ColorTransformer.transform(ColorTransformer.java:43) at net.minecraft.launchwrapper.LaunchClassLoader.runTransformers(LaunchClassLoader.java:279) at net.minecraft.launchwrapper.LaunchClassLoader.findClass(LaunchClassLoader.java:176) ... 13 more A detailed walkthrough of the error, its code path and all known details is as follows: --------------------------------------------------------------------------------------- -- Head -- Stacktrace: at net.minecraft.client.Minecraft.startGame(Minecraft.java:474) -- Initialization -- Details: Stacktrace: at net.minecraft.client.Minecraft.run(Minecraft.java:931) at net.minecraft.client.main.Main.main(Main.java:164) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at net.minecraft.launchwrapper.Launch.launch(Launch.java:135) at net.minecraft.launchwrapper.Launch.main(Launch.java:28) at net.minecraftforge.gradle.GradleStartCommon.launch(GradleStartCommon.java:78) at GradleStart.main(GradleStart.java:45) The code: package com.starsheep.colorevents; import static org.objectweb.asm.Opcodes.*; import net.minecraft.launchwrapper.IClassTransformer; import org.objectweb.asm.ClassReader; import org.objectweb.asm.ClassWriter; import org.objectweb.asm.Type; import org.objectweb.asm.commons.LocalVariablesSorter; import org.objectweb.asm.tree.AbstractInsnNode; import org.objectweb.asm.tree.ClassNode; import org.objectweb.asm.tree.FieldInsnNode; import org.objectweb.asm.tree.InsnList; import org.objectweb.asm.tree.InsnNode; import org.objectweb.asm.tree.IntInsnNode; import org.objectweb.asm.tree.MethodInsnNode; import org.objectweb.asm.tree.MethodNode; import org.objectweb.asm.tree.VarInsnNode; public class ColorTransformer implements IClassTransformer { @Override public byte[] transform(String name, String transformedName, byte[] bytes) { if(name.equals("net.minecraftforge.client.ForgeHooksClient")) { System.out.println("Going To Transform: " + name); return transformClientHooks(bytes); } return bytes; } private byte[] transformClientHooks(byte[] bytes) { ClassNode classNode = new ClassNode(); ClassReader classReader = new ClassReader(bytes); classReader.accept(classNode, 0); MethodNode method = ASMHelper.findMethod(classNode.methods, new String[] {"getSkyBlendColour"}, "(Lnet/minecraft/world/World;III)I"); LocalVariablesSorter sorter = new LocalVariablesSorter(method.access, method.desc, method); InsnList toFind = new InsnList(); toFind.add(new VarInsnNode(ILOAD, 7)); toFind.add(new VarInsnNode(ILOAD, 10)); toFind.add(new InsnNode(IDIV)); toFind.add(new IntInsnNode(SIPUSH, 255)); toFind.add(new InsnNode(IAND)); toFind.add(new IntInsnNode(BIPUSH, 16)); toFind.add(new InsnNode(ISHL)); toFind.add(new VarInsnNode(ILOAD, ); toFind.add(new VarInsnNode(ILOAD, 10)); toFind.add(new InsnNode(IDIV)); toFind.add(new IntInsnNode(SIPUSH, 255)); toFind.add(new InsnNode(IAND)); toFind.add(new IntInsnNode(BIPUSH, ); toFind.add(new InsnNode(ISHL)); toFind.add(new InsnNode(IOR)); toFind.add(new VarInsnNode(ILOAD, 9)); toFind.add(new VarInsnNode(ILOAD, 10)); toFind.add(new InsnNode(IDIV)); toFind.add(new IntInsnNode(SIPUSH, 255)); toFind.add(new InsnNode(IAND)); toFind.add(new InsnNode(IOR)); toFind.add(new VarInsnNode(ISTORE, 11)); //int multiplier = (r / divider & 255) << 16 | (g / divider & 255) << 8 | b / divider & 255; AbstractInsnNode node = ASMHelper.findFirst(toFind, method.instructions); InsnList toInject = new InsnList(); int fieldEvent = sorter.newLocal(Type.getType(EventSkyColor.class)); toInject.add(new InsnNode(DUP)); toInject.add(new VarInsnNode(ILOAD, 7)); toInject.add(new VarInsnNode(ILOAD, ); toInject.add(new VarInsnNode(ILOAD, 9)); toInject.add(new MethodInsnNode(INVOKESPECIAL, "com/starsheep/colorevents/EventSkyColor", "<init>", "(III)V", false)); toInject.add(new VarInsnNode(ASTORE, fieldEvent)); //EventSkyColor event = new EventSkyColor(red, green, blue); toInject.add(new FieldInsnNode(GETSTATIC, "net/minecraftforge/common/MinecraftForge", "EVENT_BUS", "Lcpw/mods/fml/common/eventhandler/EventBus;")); toInject.add(new VarInsnNode(ALOAD, fieldEvent)); toInject.add(new FieldInsnNode(INVOKEVIRTUAL, "cpw/mods/fml/common/eventhandler/EventBus", "post", "(Lcpw/mods/fml/common/eventhandler/Event;)Z")); toInject.add(new InsnNode(POP)); //MinecraftForge.EVENT_BUS.post(event); toInject.add(new VarInsnNode(ALOAD, fieldEvent)); toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "red", "I")); toInject.add(new VarInsnNode(ASTORE, 7)); // red = event.red; toInject.add(new VarInsnNode(ALOAD, fieldEvent)); toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "green", "I")); toInject.add(new VarInsnNode(ASTORE, ); // green = event.green; toInject.add(new VarInsnNode(ALOAD, fieldEvent)); toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "blue", "I")); toInject.add(new VarInsnNode(ASTORE, 9)); //blue = event.blue; method.instructions.insertBefore(node, toInject); ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS | ClassWriter.COMPUTE_FRAMES); classNode.accept(writer); return writer.toByteArray(); } } ASMHelper (some parts are stolen from https://github.com/SanAndreasP/SAPManagerPack/blob/master/java/de/sanandrew/core/manpack/transformer/ASMHelper.java) package com.starsheep.colorevents; import java.util.Iterator; import java.util.List; import org.objectweb.asm.tree.*; import static org.objectweb.asm.tree.AbstractInsnNode.*; public class ASMHelper { public static MethodNode findMethod(List<MethodNode> methods, String[] names, String desc) { Iterator<MethodNode> iterator = methods.iterator(); MethodNode method = null; while(iterator.hasNext()) { MethodNode m = iterator.next(); boolean flag = true; for(String name : names) { if(m.name.equals(name)) flag = false; } if(flag) continue; if(m.desc.equals("(Lnet/minecraft/world/World;III)I")) { System.out.println("Found Method: " + m.name); method = m; break; } } return method; } public static AbstractInsnNode findFirst(InsnList key, InsnList fings) { Iterator<AbstractInsnNode> iterator = fings.iterator(); while(iterator.hasNext()) { AbstractInsnNode n = iterator.next(); if(isInsnEqual(key, n)) { return n; } } return null; } public static AbstractInsnNode findLast(InsnList key, InsnList fings) { Iterator<AbstractInsnNode> iterator = fings.iterator(); int number = 0; while(iterator.hasNext()) { AbstractInsnNode n = iterator.next(); if(isInsnEqual(key, n)) { return fings.get(number + key.size() - 1); } number++; } return null; } public static boolean isInsnEqual(InsnList key, AbstractInsnNode node) { Iterator<AbstractInsnNode> iterator = key.iterator(); while(iterator.hasNext()) { AbstractInsnNode n = iterator.next(); if(!nodeEqual(node, n)) { return false; } node = node.getNext(); } return true; } public static boolean nodeEqual(AbstractInsnNode node1, AbstractInsnNode node2) { if( node1.getType() != node2.getType() ) { return false; } else if( node1.getOpcode() != node2.getOpcode() ) { return false; } switch( node2.getType() ) { case VAR_INSN : return varInsnEqual((VarInsnNode) node1, (VarInsnNode) node2); case TYPE_INSN : return typeInsnEqual((TypeInsnNode) node1, (TypeInsnNode) node2); case FIELD_INSN : return fieldInsnEqual((FieldInsnNode) node1, (FieldInsnNode) node2); case METHOD_INSN : return methodInsnEqual((MethodInsnNode) node1, (MethodInsnNode) node2); case LDC_INSN : return ldcInsnEqual((LdcInsnNode) node1, (LdcInsnNode) node2); case IINC_INSN : return iincInsnEqual((IincInsnNode) node1, (IincInsnNode) node2); case INT_INSN : return intInsnEqual((IntInsnNode) node1, (IntInsnNode) node2); default : return true; } } public static boolean varInsnEqual(VarInsnNode insn1, VarInsnNode insn2) { return insn1.var == -1 || insn2.var == -1 || insn1.var == insn2.var; } public static boolean typeInsnEqual(TypeInsnNode insn1, TypeInsnNode insn2) { return insn1.desc.equals("~") || insn2.desc.equals("~") || insn1.desc.equals(insn2.desc); } public static boolean fieldInsnEqual(FieldInsnNode insn1, FieldInsnNode insn2) { return insn1.owner.equals(insn2.owner) && insn1.name.equals(insn2.name) && insn1.desc.equals(insn2.desc); } public static boolean methodInsnEqual(MethodInsnNode insn1, MethodInsnNode insn2) { return insn1.owner.equals(insn2.owner) && insn1.name.equals(insn2.name) && insn1.desc.equals(insn2.desc); } public static boolean ldcInsnEqual(LdcInsnNode insn1, LdcInsnNode insn2) { return insn1.cst.equals("~") || insn2.cst.equals("~") || insn1.cst.equals(insn2.cst); } public static boolean iincInsnEqual(IincInsnNode node1, IincInsnNode node2) { return node1.var == node2.var && node1.incr == node2.incr; } public static boolean intInsnEqual(IntInsnNode node1, IntInsnNode node2) { return node1.operand == -1 || node2.operand == -1 || node1.operand == node2.operand; } }
[1.7.10] ASM transforming causes ArrayIndexOutOfBoundsException
in Modder Support
Posted
What I'm trying to do is adding a hooks for changing sky color without creating a new biome.
(I'm new to ASM, I used this tutorial : http://www.minecraftforum.net/forums/mapping-and-modding/mapping-and-modding-tutorials/1571568-tutorial-1-6-2-changing-vanilla-without-editing)
The crash:
java.lang.NoClassDefFoundError: net/minecraftforge/client/ForgeHooksClient
at net.minecraft.client.Minecraft.startGame(Minecraft.java:474)
at net.minecraft.client.Minecraft.run(Minecraft.java:931)
at net.minecraft.client.main.Main.main(Main.java:164)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at net.minecraft.launchwrapper.Launch.launch(Launch.java:135)
at net.minecraft.launchwrapper.Launch.main(Launch.java:28)
at net.minecraftforge.gradle.GradleStartCommon.launch(GradleStartCommon.java:78)
at GradleStart.main(GradleStart.java:45)
Caused by: java.lang.ClassNotFoundException: net.minecraftforge.client.ForgeHooksClient
at net.minecraft.launchwrapper.LaunchClassLoader.findClass(LaunchClassLoader.java:191)
at java.lang.ClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
... 11 more
Caused by: java.lang.ArrayIndexOutOfBoundsException: -1
at org.objectweb.asm.Frame.merge(Frame.java:1311)
at org.objectweb.asm.MethodWriter.visitMaxs(MethodWriter.java:1475)
at org.objectweb.asm.tree.MethodNode.accept(MethodNode.java:834)
at org.objectweb.asm.tree.MethodNode.accept(MethodNode.java:726)
at org.objectweb.asm.tree.ClassNode.accept(ClassNode.java:412)
at com.starsheep.colorevents.ColorTransformer.transformClientHooks(ColorTransformer.java:114)
at com.starsheep.colorevents.ColorTransformer.transform(ColorTransformer.java:43)
at net.minecraft.launchwrapper.LaunchClassLoader.runTransformers(LaunchClassLoader.java:279)
at net.minecraft.launchwrapper.LaunchClassLoader.findClass(LaunchClassLoader.java:176)
... 13 more
A detailed walkthrough of the error, its code path and all known details is as follows:
---------------------------------------------------------------------------------------
-- Head --
Stacktrace:
at net.minecraft.client.Minecraft.startGame(Minecraft.java:474)
-- Initialization --
Details:
Stacktrace:
at net.minecraft.client.Minecraft.run(Minecraft.java:931)
at net.minecraft.client.main.Main.main(Main.java:164)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at net.minecraft.launchwrapper.Launch.launch(Launch.java:135)
at net.minecraft.launchwrapper.Launch.main(Launch.java:28)
at net.minecraftforge.gradle.GradleStartCommon.launch(GradleStartCommon.java:78)
at GradleStart.main(GradleStart.java:45)
The code:
package com.starsheep.colorevents;
import static org.objectweb.asm.Opcodes.*;
import net.minecraft.launchwrapper.IClassTransformer;
import org.objectweb.asm.ClassReader;
import org.objectweb.asm.ClassWriter;
import org.objectweb.asm.Type;
import org.objectweb.asm.commons.LocalVariablesSorter;
import org.objectweb.asm.tree.AbstractInsnNode;
import org.objectweb.asm.tree.ClassNode;
import org.objectweb.asm.tree.FieldInsnNode;
import org.objectweb.asm.tree.InsnList;
import org.objectweb.asm.tree.InsnNode;
import org.objectweb.asm.tree.IntInsnNode;
import org.objectweb.asm.tree.MethodInsnNode;
import org.objectweb.asm.tree.MethodNode;
import org.objectweb.asm.tree.VarInsnNode;
public class ColorTransformer implements IClassTransformer {
@Override
public byte[] transform(String name, String transformedName, byte[] bytes)
{
if(name.equals("net.minecraftforge.client.ForgeHooksClient"))
{
System.out.println("Going To Transform: " + name);
return transformClientHooks(bytes);
}
return bytes;
}
private byte[] transformClientHooks(byte[] bytes)
{
ClassNode classNode = new ClassNode();
ClassReader classReader = new ClassReader(bytes);
classReader.accept(classNode, 0);
MethodNode method = ASMHelper.findMethod(classNode.methods, new String[] {"getSkyBlendColour"}, "(Lnet/minecraft/world/World;III)I");
LocalVariablesSorter sorter = new LocalVariablesSorter(method.access, method.desc, method);
InsnList toFind = new InsnList();
toFind.add(new VarInsnNode(ILOAD, 7));
toFind.add(new VarInsnNode(ILOAD, 10));
toFind.add(new InsnNode(IDIV));
toFind.add(new IntInsnNode(SIPUSH, 255));
toFind.add(new InsnNode(IAND));
toFind.add(new IntInsnNode(BIPUSH, 16));
toFind.add(new InsnNode(ISHL));
toFind.add(new VarInsnNode(ILOAD, );
toFind.add(new VarInsnNode(ILOAD, 10));
toFind.add(new InsnNode(IDIV));
toFind.add(new IntInsnNode(SIPUSH, 255));
toFind.add(new InsnNode(IAND));
toFind.add(new IntInsnNode(BIPUSH, );
toFind.add(new InsnNode(ISHL));
toFind.add(new InsnNode(IOR));
toFind.add(new VarInsnNode(ILOAD, 9));
toFind.add(new VarInsnNode(ILOAD, 10));
toFind.add(new InsnNode(IDIV));
toFind.add(new IntInsnNode(SIPUSH, 255));
toFind.add(new InsnNode(IAND));
toFind.add(new InsnNode(IOR));
toFind.add(new VarInsnNode(ISTORE, 11)); //int multiplier = (r / divider & 255) << 16 | (g / divider & 255) << 8 | b / divider & 255;
AbstractInsnNode node = ASMHelper.findFirst(toFind, method.instructions);
InsnList toInject = new InsnList();
int fieldEvent = sorter.newLocal(Type.getType(EventSkyColor.class));
toInject.add(new InsnNode(DUP));
toInject.add(new VarInsnNode(ILOAD, 7));
toInject.add(new VarInsnNode(ILOAD, );
toInject.add(new VarInsnNode(ILOAD, 9));
toInject.add(new MethodInsnNode(INVOKESPECIAL, "com/starsheep/colorevents/EventSkyColor", "<init>", "(III)V", false));
toInject.add(new VarInsnNode(ASTORE, fieldEvent)); //EventSkyColor event = new EventSkyColor(red, green, blue);
toInject.add(new FieldInsnNode(GETSTATIC, "net/minecraftforge/common/MinecraftForge", "EVENT_BUS", "Lcpw/mods/fml/common/eventhandler/EventBus;"));
toInject.add(new VarInsnNode(ALOAD, fieldEvent));
toInject.add(new FieldInsnNode(INVOKEVIRTUAL, "cpw/mods/fml/common/eventhandler/EventBus", "post", "(Lcpw/mods/fml/common/eventhandler/Event;)Z"));
toInject.add(new InsnNode(POP)); //MinecraftForge.EVENT_BUS.post(event);
toInject.add(new VarInsnNode(ALOAD, fieldEvent));
toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "red", "I"));
toInject.add(new VarInsnNode(ASTORE, 7)); // red = event.red;
toInject.add(new VarInsnNode(ALOAD, fieldEvent));
toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "green", "I"));
toInject.add(new VarInsnNode(ASTORE, ); // green = event.green;
toInject.add(new VarInsnNode(ALOAD, fieldEvent));
toInject.add(new FieldInsnNode(GETFIELD, "com/starsheep/colorevents/EventSkyColor", "blue", "I"));
toInject.add(new VarInsnNode(ASTORE, 9)); //blue = event.blue;
method.instructions.insertBefore(node, toInject);
ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS | ClassWriter.COMPUTE_FRAMES);
classNode.accept(writer);
return writer.toByteArray();
}
}
ASMHelper (some parts are stolen from https://github.com/SanAndreasP/SAPManagerPack/blob/master/java/de/sanandrew/core/manpack/transformer/ASMHelper.java)
package com.starsheep.colorevents;
import java.util.Iterator;
import java.util.List;
import org.objectweb.asm.tree.*;
import static org.objectweb.asm.tree.AbstractInsnNode.*;
public class ASMHelper {
public static MethodNode findMethod(List<MethodNode> methods, String[] names, String desc)
{
Iterator<MethodNode> iterator = methods.iterator();
MethodNode method = null;
while(iterator.hasNext())
{
MethodNode m = iterator.next();
boolean flag = true;
for(String name : names)
{
if(m.name.equals(name)) flag = false;
}
if(flag) continue;
if(m.desc.equals("(Lnet/minecraft/world/World;III)I"))
{
System.out.println("Found Method: " + m.name);
method = m;
break;
}
}
return method;
}
public static AbstractInsnNode findFirst(InsnList key, InsnList fings)
{
Iterator<AbstractInsnNode> iterator = fings.iterator();
while(iterator.hasNext())
{
AbstractInsnNode n = iterator.next();
if(isInsnEqual(key, n))
{
return n;
}
}
return null;
}
public static AbstractInsnNode findLast(InsnList key, InsnList fings)
{
Iterator<AbstractInsnNode> iterator = fings.iterator();
int number = 0;
while(iterator.hasNext())
{
AbstractInsnNode n = iterator.next();
if(isInsnEqual(key, n))
{
return fings.get(number + key.size() - 1);
}
number++;
}
return null;
}
public static boolean isInsnEqual(InsnList key, AbstractInsnNode node)
{
Iterator<AbstractInsnNode> iterator = key.iterator();
while(iterator.hasNext())
{
AbstractInsnNode n = iterator.next();
if(!nodeEqual(node, n))
{
return false;
}
node = node.getNext();
}
return true;
}
public static boolean nodeEqual(AbstractInsnNode node1, AbstractInsnNode node2)
{
if( node1.getType() != node2.getType() ) {
return false;
} else if( node1.getOpcode() != node2.getOpcode() ) {
return false;
}
switch( node2.getType() )
{
case VAR_INSN :
return varInsnEqual((VarInsnNode) node1, (VarInsnNode) node2);
case TYPE_INSN :
return typeInsnEqual((TypeInsnNode) node1, (TypeInsnNode) node2);
case FIELD_INSN :
return fieldInsnEqual((FieldInsnNode) node1, (FieldInsnNode) node2);
case METHOD_INSN :
return methodInsnEqual((MethodInsnNode) node1, (MethodInsnNode) node2);
case LDC_INSN :
return ldcInsnEqual((LdcInsnNode) node1, (LdcInsnNode) node2);
case IINC_INSN :
return iincInsnEqual((IincInsnNode) node1, (IincInsnNode) node2);
case INT_INSN :
return intInsnEqual((IntInsnNode) node1, (IntInsnNode) node2);
default :
return true;
}
}
public static boolean varInsnEqual(VarInsnNode insn1, VarInsnNode insn2)
{
return insn1.var == -1 || insn2.var == -1 || insn1.var == insn2.var;
}
public static boolean typeInsnEqual(TypeInsnNode insn1, TypeInsnNode insn2)
{
return insn1.desc.equals("~") || insn2.desc.equals("~") || insn1.desc.equals(insn2.desc);
}
public static boolean fieldInsnEqual(FieldInsnNode insn1, FieldInsnNode insn2)
{
return insn1.owner.equals(insn2.owner) && insn1.name.equals(insn2.name) && insn1.desc.equals(insn2.desc);
}
public static boolean methodInsnEqual(MethodInsnNode insn1, MethodInsnNode insn2)
{
return insn1.owner.equals(insn2.owner) && insn1.name.equals(insn2.name) && insn1.desc.equals(insn2.desc);
}
public static boolean ldcInsnEqual(LdcInsnNode insn1, LdcInsnNode insn2)
{
return insn1.cst.equals("~") || insn2.cst.equals("~") || insn1.cst.equals(insn2.cst);
}
public static boolean iincInsnEqual(IincInsnNode node1, IincInsnNode node2)
{
return node1.var == node2.var && node1.incr == node2.incr;
}
public static boolean intInsnEqual(IntInsnNode node1, IntInsnNode node2)
{
return node1.operand == -1 || node2.operand == -1 || node1.operand == node2.operand;
}
}