Throw exception for invalid types.

closes 
This commit is contained in:
NathanSweet 2017-08-17 10:26:41 +02:00
parent ade0542b62
commit 54f453484e
2 changed files with 24 additions and 15 deletions
src/com/esotericsoftware/reflectasm

View File

@ -108,7 +108,11 @@ public abstract class FieldAccess {
abstract public float getFloat (Object instance, int fieldIndex);
/** @param type Must not be the Object class, an interface, a primitive type, or void. */
static public FieldAccess get (Class type) {
if (type.getSuperclass() == null)
throw new IllegalArgumentException("The type must not be the Object class, an interface, a primitive type, or void.");
ArrayList<Field> fields = new ArrayList<Field>();
Class nextClass = type;
while (nextClass != Object.class) {
@ -424,8 +428,8 @@ public abstract class FieldAccess {
break;
case Type.DOUBLE:
setterMethodName = "setDouble";
loadValueInstruction = DLOAD; // (LLOAD and DLOAD actually load two slots)
maxLocals++;
loadValueInstruction = DLOAD;
maxLocals++; // (LLOAD and DLOAD actually load two slots)
break;
default:
setterMethodName = "set";

View File

@ -62,7 +62,8 @@ public abstract class MethodAccess {
public int getIndex (String methodName, int paramsCount) {
for (int i = 0, n = methodNames.length; i < n; i++)
if (methodNames[i].equals(methodName) && parameterTypes[i].length == paramsCount) return i;
throw new IllegalArgumentException("Unable to find non-private method: " + methodName + " with " + paramsCount + " params.");
throw new IllegalArgumentException(
"Unable to find non-private method: " + methodName + " with " + paramsCount + " params.");
}
public String[] getMethodNames () {
@ -77,7 +78,11 @@ public abstract class MethodAccess {
return returnTypes;
}
/** @param type Must not be the Object class, an interface, a primitive type, or void. */
static public MethodAccess get (Class type) {
if (type.getSuperclass() == null)
throw new IllegalArgumentException("The type must not be the Object class, an interface, a primitive type, or void.");
ArrayList<Method> methods = new ArrayList<Method>();
boolean isInterface = type.isInterface();
if (!isInterface) {
@ -116,11 +121,11 @@ public abstract class MethodAccess {
} catch (ClassNotFoundException ignored2) {
String accessClassNameInternal = accessClassName.replace('.', '/');
String classNameInternal = className.replace('.', '/');
ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
MethodVisitor mv;
cw.visit(V1_1, ACC_PUBLIC + ACC_SUPER, accessClassNameInternal, null, "com/esotericsoftware/reflectasm/MethodAccess",
null);
cw.visit(V1_1, ACC_PUBLIC + ACC_SUPER, accessClassNameInternal, null,
"com/esotericsoftware/reflectasm/MethodAccess", null);
{
mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
mv.visitCode();
@ -134,19 +139,19 @@ public abstract class MethodAccess {
mv = cw.visitMethod(ACC_PUBLIC + ACC_VARARGS, "invoke",
"(Ljava/lang/Object;I[Ljava/lang/Object;)Ljava/lang/Object;", null, null);
mv.visitCode();
if (!methods.isEmpty()) {
mv.visitVarInsn(ALOAD, 1);
mv.visitTypeInsn(CHECKCAST, classNameInternal);
mv.visitVarInsn(ASTORE, 4);
mv.visitVarInsn(ILOAD, 2);
Label[] labels = new Label[n];
for (int i = 0; i < n; i++)
labels[i] = new Label();
Label defaultLabel = new Label();
mv.visitTableSwitchInsn(0, labels.length - 1, defaultLabel, labels);
StringBuilder buffer = new StringBuilder(128);
for (int i = 0; i < n; i++) {
mv.visitLabel(labels[i]);
@ -155,10 +160,10 @@ public abstract class MethodAccess {
else
mv.visitFrame(Opcodes.F_SAME, 0, null, 0, null);
mv.visitVarInsn(ALOAD, 4);
buffer.setLength(0);
buffer.append('(');
Class[] paramTypes = parameterTypes[i];
Class returnType = returnTypes[i];
for (int paramIndex = 0; paramIndex < paramTypes.length; paramIndex++) {
@ -208,7 +213,7 @@ public abstract class MethodAccess {
}
buffer.append(paramType.getDescriptor());
}
buffer.append(')');
buffer.append(Type.getDescriptor(returnType));
int invoke;
@ -219,7 +224,7 @@ public abstract class MethodAccess {
else
invoke = INVOKEVIRTUAL;
mv.visitMethodInsn(invoke, classNameInternal, methodNames[i], buffer.toString());
switch (Type.getType(returnType).getSort()) {
case Type.VOID:
mv.visitInsn(ACONST_NULL);
@ -249,10 +254,10 @@ public abstract class MethodAccess {
mv.visitMethodInsn(INVOKESTATIC, "java/lang/Double", "valueOf", "(D)Ljava/lang/Double;");
break;
}
mv.visitInsn(ARETURN);
}
mv.visitLabel(defaultLabel);
mv.visitFrame(Opcodes.F_SAME, 0, null, 0, null);
}