¿Cómo evitar el “tipo ilegal en la piscina constante” por medio de “ldc_w ” en Jasmin?
Pregunta
Estoy escribiendo un compilador que genera código y Jasmin desea invocar un método que toma una clase como un parámetro.
public class CTest
{
public static void main(String[] args)
throws Exception
{
java.lang.reflect.Array.newInstance(CTest.class, 0);
}
}
Así que en Jasmin, creo que debería ser:
.class public CTest2
.super java/lang/Object
.method public static main([Ljava/lang/String;)V
.limit stack 2
.limit locals 1
ldc_w CTest2
iconst_0
invokestatic java/lang/reflect/Array/newInstance(Ljava/lang/Class;I)Ljava/lang/Object;
pop
return
.end method
Cuando montarlo y ejecutarlo me sale:
Excepción en hilo "principal" java.lang.VerifyError: (clase: CTest2, método: firma principal: ([Ljava / lang / cadena;) V) tipo ilegal en la piscina constante
Si examina el código desensamblado tanto para CTest.class (la versión Java) y CTest2.class (la versión Jasmin) con "javap -c -verbose" ambos parecen configurar la piscina constante de la misma manera:
const #2 = class #16; // CTest
const #16 = Asciz CTest;
0: ldc_w #2; //class CTest
const #14 = Asciz CTest2;
const #17 = class #14; // CTest2
0: ldc_w #17; //class CTest2
he fijado dos errores en Jasmin ya, pero no puedo ver lo que es haciendo mal al poner la clase en la piscina constante para "ldc_w" se pone clases en la piscina constante para otras instrucciones, como "Nuevo" y "anewarray" correctamente.
He intentado buscar en los archivos .class con TraceClassVisitor en ASM, pero no volcar la piscina constante.
Alguna idea de lo que pueda intentar después?
Solución
Usted tiene que asegurarse de que el número de versión de la clase es de al menos 49 (ver el visitLdcInsn en este ASM página Javadoc ).