summaryrefslogtreecommitdiffstats
path: root/libart/src/main/java/java/lang/reflect/AbstractMethod.java
diff options
context:
space:
mode:
Diffstat (limited to 'libart/src/main/java/java/lang/reflect/AbstractMethod.java')
-rw-r--r--libart/src/main/java/java/lang/reflect/AbstractMethod.java86
1 files changed, 70 insertions, 16 deletions
diff --git a/libart/src/main/java/java/lang/reflect/AbstractMethod.java b/libart/src/main/java/java/lang/reflect/AbstractMethod.java
index 7e6491d..95d90cc 100644
--- a/libart/src/main/java/java/lang/reflect/AbstractMethod.java
+++ b/libart/src/main/java/java/lang/reflect/AbstractMethod.java
@@ -39,28 +39,39 @@ import libcore.reflect.AnnotationAccess;
import libcore.reflect.GenericSignatureParser;
import libcore.reflect.ListOfTypes;
import libcore.reflect.Types;
+import libcore.util.EmptyArray;
/**
* This class represents an abstract method. Abstract methods are either methods or constructors.
* @hide
*/
public abstract class AbstractMethod extends AccessibleObject {
+ /** Bits encoding access (e.g. public, private) as well as other runtime specific flags */
+ protected int accessFlags;
/**
+ * The ArtMethod associated with this Method, requried for dispatching due to entrypoints
+ * Classloader is held live by the declaring class.
* Hidden to workaround b/16828157.
* @hide
*/
- protected final ArtMethod artMethod;
+ protected long artMethod;
+
+ /** Method's declaring class */
+ protected Class<?> declaringClass;
+
+ /** Overriden method's declaring class (same as declaringClass unless declaringClass
+ * is a proxy class) */
+ protected Class<?> declaringClassOfOverriddenMethod;
+
+ /** The method index of this method within its defining dex file */
+ protected int dexMethodIndex;
/**
* Hidden to workaround b/16828157.
* @hide
*/
- protected AbstractMethod(ArtMethod artMethod) {
- if (artMethod == null) {
- throw new NullPointerException("artMethod == null");
- }
- this.artMethod = artMethod;
+ protected AbstractMethod() {
}
public <T extends Annotation> T getAnnotation(Class<T> annotationClass) {
@@ -90,33 +101,33 @@ public abstract class AbstractMethod extends AccessibleObject {
}
int getModifiers() {
- return fixMethodFlags(artMethod.getAccessFlags());
+ return fixMethodFlags(accessFlags);
}
boolean isVarArgs() {
- return (artMethod.getAccessFlags() & Modifier.VARARGS) != 0;
+ return (accessFlags & Modifier.VARARGS) != 0;
}
boolean isBridge() {
- return (artMethod.getAccessFlags() & Modifier.BRIDGE) != 0;
+ return (accessFlags & Modifier.BRIDGE) != 0;
}
boolean isSynthetic() {
- return (artMethod.getAccessFlags() & Modifier.SYNTHETIC) != 0;
+ return (accessFlags & Modifier.SYNTHETIC) != 0;
}
/**
* @hide
*/
public final int getAccessFlags() {
- return artMethod.getAccessFlags();
+ return accessFlags;
}
/**
* Returns the class that declares this constructor or method.
*/
Class<?> getDeclaringClass() {
- return artMethod.getDeclaringClass();
+ return declaringClass;
}
/**
@@ -125,7 +136,7 @@ public abstract class AbstractMethod extends AccessibleObject {
* @hide
*/
public final int getDexMethodIndex() {
- return artMethod.getDexMethodIndex();
+ return dexMethodIndex;
}
/**
@@ -144,7 +155,17 @@ public abstract class AbstractMethod extends AccessibleObject {
* @return the parameter types
*/
Class<?>[] getParameterTypes() {
- return artMethod.getParameterTypes();
+ Dex dex = declaringClassOfOverriddenMethod.getDex();
+ short[] types = dex.parameterTypeIndicesFromMethodIndex(dexMethodIndex);
+ if (types.length == 0) {
+ return EmptyArray.CLASS;
+ }
+ Class<?>[] parametersArray = new Class[types.length];
+ for (int i = 0; i < types.length; i++) {
+ // Note, in the case of a Proxy the dex cache types are equal.
+ parametersArray[i] = declaringClassOfOverriddenMethod.getDexCacheType(dex, types[i]);
+ }
+ return parametersArray;
}
/**
@@ -155,8 +176,10 @@ public abstract class AbstractMethod extends AccessibleObject {
if (!(other instanceof AbstractMethod)) {
return false;
}
- // exactly one instance of each member in this runtime
- return this.artMethod == ((AbstractMethod) other).artMethod;
+ // Exactly one instance of each member in this runtime, todo, does this work for proxies?
+ AbstractMethod otherMethod = (AbstractMethod) other;
+ return this.declaringClass == otherMethod.declaringClass &&
+ this.dexMethodIndex == otherMethod.dexMethodIndex;
}
String toGenericString() {
@@ -252,6 +275,37 @@ public abstract class AbstractMethod extends AccessibleObject {
parser.returnType, parser.formalTypeParameters);
}
+ protected boolean equalMethodParameters(Class<?>[] params) {
+ Dex dex = declaringClassOfOverriddenMethod.getDex();
+ short[] types = dex.parameterTypeIndicesFromMethodIndex(dexMethodIndex);
+ if (types.length != params.length) {
+ return false;
+ }
+ for (int i = 0; i < types.length; i++) {
+ if (declaringClassOfOverriddenMethod.getDexCacheType(dex, types[i]) != params[i]) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ protected int compareParameters(Class<?>[] params) {
+ Dex dex = declaringClassOfOverriddenMethod.getDex();
+ short[] types = dex.parameterTypeIndicesFromMethodIndex(dexMethodIndex);
+ int length = Math.min(types.length, params.length);
+ for (int i = 0; i < length; i++) {
+ Class<?> aType = declaringClassOfOverriddenMethod.getDexCacheType(dex, types[i]);
+ Class<?> bType = params[i];
+ if (aType != bType) {
+ int comparison = aType.getName().compareTo(bType.getName());
+ if (comparison != 0) {
+ return comparison;
+ }
+ }
+ }
+ return types.length - params.length;
+ }
+
/**
* Helper for Method and Constructor for toGenericString
*/