aboutsummaryrefslogtreecommitdiff
path: root/libjava/java/lang/reflect/natMethod.cc
diff options
context:
space:
mode:
Diffstat (limited to 'libjava/java/lang/reflect/natMethod.cc')
-rw-r--r--libjava/java/lang/reflect/natMethod.cc31
1 files changed, 20 insertions, 11 deletions
diff --git a/libjava/java/lang/reflect/natMethod.cc b/libjava/java/lang/reflect/natMethod.cc
index 736103b63dd..4ff2c9596ae 100644
--- a/libjava/java/lang/reflect/natMethod.cc
+++ b/libjava/java/lang/reflect/natMethod.cc
@@ -1,6 +1,6 @@
// natMethod.cc - Native code for Method class.
-/* Copyright (C) 1998, 1999, 2000, 2001 , 2002, 2003 Free Software Foundation
+/* Copyright (C) 1998, 1999, 2000, 2001 , 2002, 2003, 2005 Free Software Foundation
This file is part of libgcj.
@@ -464,7 +464,7 @@ _Jv_CallAnyMethodA (jobject obj,
break;
}
- void *ncode;
+ void *ncode = meth->ncode;
// FIXME: If a vtable index is -1 at this point it is invalid, so we
// have to use the ncode.
@@ -473,16 +473,25 @@ _Jv_CallAnyMethodA (jobject obj,
// vtable entries, but _Jv_isVirtualMethod() doesn't know that. We
// could solve this problem by allocating a vtable index for methods
// in final classes.
- if (is_virtual_call
- && ! Modifier::isFinal (meth->accflags)
- && (_Jv_ushort)-1 != meth->index)
- {
+ if (is_virtual_call)
+ {
_Jv_VTable *vtable = *(_Jv_VTable **) obj;
- ncode = vtable->get_method (meth->index);
- }
- else
- {
- ncode = meth->ncode;
+ if ((_Jv_ushort)-1 == meth->index)
+ {
+ if (ncode == NULL)
+ // We have no vtable index, and we have no code pointer.
+ // Look method up by name.
+ ncode = _Jv_LookupInterfaceMethod (vtable->clas,
+ meth->name,
+ meth->signature);
+ }
+ else
+ {
+ // We have an index. If METH is not final, use virtual
+ // dispatch.
+ if (! Modifier::isFinal (meth->accflags))
+ ncode = vtable->get_method (meth->index);
+ }
}
try