Я использую ASM для изменения байт-кода любого класса Java, чтобы добавить проверку нуля для каждого объекта.
Например, для этого фрагмента кода:
Object a = new Object();
a.doSomething();
Я хочу изменить байт-код, чтобы он выглядел так:
Object a = new Object();
assertNotNull(a);
a.doSomething();
или это:
Object a = new Object();
if(a != null){
a.doSomething();}
else return 1 //or throw exception
Я застрял, потому что не знаю, какое число следует за ALOAD. Я думаю, что ALOAD всегда идет с ALOAD 1 (или в этом формате ALOAD n). Что я могу сделать, чтобы получить номер, который идет с ALOAD? Вот моя работа (с использованием Junit assertNotNull)
/*
* Use JUnit assertNotNull to check object/item for null
*/
private void addAssertNullMethod() {
//need to add ALOAD here, but I don't know the location of the object on the stack.
mv.visitMethodInsn(Opcodes.INVOKESTATIC, "org/junit/Assert", "assertNull", "(Ljava/lang/Object;)V", false);
mv.visitEnd();
}
Вы не показали логику своей программы, чтобы решить, когда вызывать
addAssertNullMethod()
. Когда вы вызываете его прямо перед доступом другого члена, применяется ответ апангина, значение будет в стеке операндов. Но независимо от того, где вы его вызываете, вызовmv.visitEnd();
в середине метода никогда не будет правильным. И, кстати, я не могу понять назначение этой аппаратуры. Вы просто заменяетеNullPointerException
другим исключением. Кроме того, ваш «assertNotNull» в тексте вашего вопроса сталassertNull
в коде…