Implements VM natives for java/lang/reflect/Constructor. Most of the natives support only ()V constructors (there are appropriate assertions) which is enough for GtkToolkit to run.
Signed-off-by: Tomek Grabiec <tgrab...@gmail.com> --- Makefile | 1 + include/vm/preload.h | 7 ++- include/vm/reflection.h | 20 +++++++ vm/jato.c | 14 +++++ vm/preload.c | 10 ++++ vm/reflection.c | 126 +++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 177 insertions(+), 1 deletions(-) create mode 100644 include/vm/reflection.h create mode 100644 vm/reflection.c diff --git a/Makefile b/Makefile index 361f327..9505784 100644 --- a/Makefile +++ b/Makefile @@ -119,6 +119,7 @@ VM_OBJS = \ vm/utf8.o \ vm/zalloc.o \ vm/preload.o \ + vm/reflection.o \ vm/fault-inject.o \ vm/jni.o \ vm/jni-interface.o \ diff --git a/include/vm/preload.h b/include/vm/preload.h index 2a739f0..0cc1db0 100644 --- a/include/vm/preload.h +++ b/include/vm/preload.h @@ -1,6 +1,9 @@ #ifndef _VM_JAVA_LANG_H #define _VM_JAVA_LANG_H +extern struct vm_class *vm_array_of_java_lang_Class; +extern struct vm_class *vm_array_of_java_lang_StackTraceElement; +extern struct vm_class *vm_array_of_java_lang_reflect_Constructor; extern struct vm_class *vm_java_lang_Object; extern struct vm_class *vm_java_lang_Class; extern struct vm_class *vm_java_lang_Cloneable; @@ -9,7 +12,6 @@ extern struct vm_class *vm_java_lang_Throwable; extern struct vm_class *vm_java_util_Properties; extern struct vm_class *vm_java_lang_VMThrowable; extern struct vm_class *vm_java_lang_StackTraceElement; -extern struct vm_class *vm_array_of_java_lang_StackTraceElement; extern struct vm_class *vm_java_lang_Error; extern struct vm_class *vm_java_lang_ArithmeticException; extern struct vm_class *vm_java_lang_NullPointerException; @@ -29,6 +31,7 @@ extern struct vm_class *vm_java_lang_Thread; extern struct vm_class *vm_java_lang_ThreadGroup; extern struct vm_class *vm_java_lang_VMThread; extern struct vm_class *vm_java_lang_IllegalMonitorStateException; +extern struct vm_class *vm_java_lang_reflect_Constructor; extern struct vm_class *vm_boolean_class; extern struct vm_class *vm_char_class; extern struct vm_class *vm_float_class; @@ -53,6 +56,8 @@ extern struct vm_field *vm_java_lang_Thread_contextClassLoaderIsSystemClassLoade extern struct vm_field *vm_java_lang_Thread_vmThread; extern struct vm_field *vm_java_lang_VMThread_thread; extern struct vm_field *vm_java_lang_VMThread_vmdata; +extern struct vm_field *vm_java_lang_reflect_Constructor_clazz; +extern struct vm_field *vm_java_lang_reflect_Constructor_slot; extern struct vm_method *vm_java_util_Properties_setProperty; extern struct vm_method *vm_java_lang_Throwable_initCause; diff --git a/include/vm/reflection.h b/include/vm/reflection.h new file mode 100644 index 0000000..119e90f --- /dev/null +++ b/include/vm/reflection.h @@ -0,0 +1,20 @@ +#ifndef __JATO_VM_REFLECTION_H +#define __JATO_VM_REFLECTION_H + +#include "vm/jni.h" + +struct vm_object; + +struct vm_object * +native_vmclass_get_declared_constructors(struct vm_object *class_object, + jboolean public_only); +struct vm_object * +native_constructor_get_parameter_types(struct vm_object *ctor); +jint native_constructor_get_modifiers_internal(struct vm_object *ctor); +struct vm_object * +native_constructor_construct_native(struct vm_object *this, + struct vm_object *args, + struct vm_object *declaring_class, + int slot); + +#endif /* __JATO_VM_REFLECTION_H */ diff --git a/vm/jato.c b/vm/jato.c index ea176ca..37ccd66 100644 --- a/vm/jato.c +++ b/vm/jato.c @@ -65,6 +65,7 @@ #include "vm/method.h" #include "vm/natives.h" #include "vm/object.h" +#include "vm/reflection.h" #include "vm/signal.h" #include "vm/stack-trace.h" #include "vm/static.h" @@ -504,6 +505,14 @@ native_vmclass_isprimitive(struct vm_object *object) return class->kind == VM_CLASS_KIND_PRIMITIVE; } +static jint native_vmclass_getmodifiers(struct vm_object *clazz) +{ + struct vm_class *class = vm_class_get_class_from_class_object(clazz); + + NOT_IMPLEMENTED; + return class->class->access_flags; +} + static struct vm_object * native_vmclassloader_getprimitiveclass(int type) { @@ -613,9 +622,11 @@ static struct vm_native natives[] = { DEFINE_NATIVE("jato/internal/VM", "println", &native_vmruntime_println), DEFINE_NATIVE("jato/internal/VM", "throwNullPointerException", &native_vm_throw_null_pointer_exception), DEFINE_NATIVE("java/lang/VMClass", "getClassLoader", &native_vmclass_getclassloader), + DEFINE_NATIVE("java/lang/VMClass", "getDeclaredConstructors", &native_vmclass_get_declared_constructors), DEFINE_NATIVE("java/lang/VMClass", "getName", &native_vmclass_getname), DEFINE_NATIVE("java/lang/VMClass", "forName", &native_vmclass_forname), DEFINE_NATIVE("java/lang/VMClass", "isPrimitive", &native_vmclass_isprimitive), + DEFINE_NATIVE("java/lang/VMClass", "getModifiers", &native_vmclass_getmodifiers), DEFINE_NATIVE("java/lang/VMClassLoader", "getPrimitiveClass", &native_vmclassloader_getprimitiveclass), DEFINE_NATIVE("java/io/VMFile", "isDirectory", &native_vmfile_is_directory), DEFINE_NATIVE("java/lang/VMObject", "clone", &native_vmobject_clone), @@ -634,6 +645,9 @@ static struct vm_native natives[] = { DEFINE_NATIVE("java/lang/VMThread", "start", &native_vmthread_start), DEFINE_NATIVE("java/lang/VMThrowable", "fillInStackTrace", &native_vmthrowable_fill_in_stack_trace), DEFINE_NATIVE("java/lang/VMThrowable", "getStackTrace", &native_vmthrowable_get_stack_trace), + DEFINE_NATIVE("java/lang/reflect/Constructor", "getParameterTypes", &native_constructor_get_parameter_types), + DEFINE_NATIVE("java/lang/reflect/Constructor", "getModifiersInternal", &native_constructor_get_modifiers_internal), + DEFINE_NATIVE("java/lang/reflect/Constructor", "constructNative", &native_constructor_construct_native), DEFINE_NATIVE("jato/internal/VM", "enableFault", &native_vm_enable_fault), DEFINE_NATIVE("jato/internal/VM", "disableFault", &native_vm_disable_fault), }; diff --git a/vm/preload.c b/vm/preload.c index 7ea4902..c74c68c 100644 --- a/vm/preload.c +++ b/vm/preload.c @@ -66,6 +66,9 @@ struct vm_class *vm_java_lang_ThreadGroup; struct vm_class *vm_java_lang_VMThread; struct vm_class *vm_java_lang_IllegalMonitorStateException; struct vm_class *vm_java_lang_System; +struct vm_class *vm_java_lang_reflect_Constructor; +struct vm_class *vm_array_of_java_lang_reflect_Constructor; +struct vm_class *vm_array_of_java_lang_Class; struct vm_class *vm_boolean_class; struct vm_class *vm_char_class; struct vm_class *vm_float_class; @@ -105,6 +108,9 @@ static const struct preload_entry preload_entries[] = { { "java/lang/VMThread", &vm_java_lang_VMThread }, { "java/lang/IllegalMonitorStateException", &vm_java_lang_IllegalMonitorStateException }, { "java/lang/System", &vm_java_lang_System }, + { "java/lang/reflect/Constructor", &vm_java_lang_reflect_Constructor }, + { "[java/lang/Class", &vm_array_of_java_lang_Class }, + { "[java/lang/reflect/Constructor", &vm_array_of_java_lang_reflect_Constructor }, }; static const struct preload_entry primitive_preload_entries[] = { @@ -140,6 +146,8 @@ struct vm_field *vm_java_lang_Thread_contextClassLoaderIsSystemClassLoader; struct vm_field *vm_java_lang_Thread_vmThread; struct vm_field *vm_java_lang_VMThread_thread; struct vm_field *vm_java_lang_VMThread_vmdata; +struct vm_field *vm_java_lang_reflect_Constructor_clazz; +struct vm_field *vm_java_lang_reflect_Constructor_slot; static const struct field_preload_entry field_preload_entries[] = { { &vm_java_lang_Class, "vmdata", "Ljava/lang/Object;", &vm_java_lang_Class_vmdata }, @@ -157,6 +165,8 @@ static const struct field_preload_entry field_preload_entries[] = { { &vm_java_lang_Thread, "vmThread", "Ljava/lang/VMThread;", &vm_java_lang_Thread_vmThread }, { &vm_java_lang_VMThread, "thread", "Ljava/lang/Thread;", &vm_java_lang_VMThread_thread }, { &vm_java_lang_VMThread, "vmdata", "Ljava/lang/Object;", &vm_java_lang_VMThread_vmdata }, + { &vm_java_lang_reflect_Constructor, "clazz", "Ljava/lang/Class;", &vm_java_lang_reflect_Constructor_clazz }, + { &vm_java_lang_reflect_Constructor, "slot", "I", &vm_java_lang_reflect_Constructor_slot }, }; struct method_preload_entry { diff --git a/vm/reflection.c b/vm/reflection.c new file mode 100644 index 0000000..5e7085b --- /dev/null +++ b/vm/reflection.c @@ -0,0 +1,126 @@ +#include "vm/call.h" +#include "vm/class.h" +#include "vm/die.h" +#include "vm/preload.h" +#include "vm/reflection.h" + +struct vm_object * +native_vmclass_get_declared_constructors(struct vm_object *class_object, + jboolean public_only) +{ + struct vm_class *vmc; + + if (!vm_object_is_instance_of(class_object, vm_java_lang_Class)) + return NULL; + + vmc = vm_class_get_class_from_class_object(class_object); + + int count = 0; + + for (int i = 0; i < vmc->class->methods_count; i++) { + struct vm_method *vmm = &vmc->methods[i]; + + if (vm_method_is_constructor(vmm)) + count++; + } + + struct vm_object *array; + + array = vm_object_alloc_array(vm_array_of_java_lang_reflect_Constructor, + count); + if (!array) { + NOT_IMPLEMENTED; + return NULL; + } + + int index = 0; + + for (int i = 0; i < vmc->class->methods_count; i++) { + struct vm_method *vmm = &vmc->methods[i]; + + if (!vm_method_is_constructor(vmm)) + continue; + + struct vm_object *ctor + = vm_object_alloc(vm_java_lang_reflect_Constructor); + + if (!ctor) { + NOT_IMPLEMENTED; + return NULL; + } + + field_set_object(ctor, vm_java_lang_reflect_Constructor_clazz, + class_object); + field_set_int32(ctor, vm_java_lang_reflect_Constructor_slot, + i); + + array_set_field_ptr(array, index++, ctor); + } + + return array; +} + +struct vm_object * +native_constructor_get_parameter_types(struct vm_object *ctor) +{ + struct vm_object *array; + struct vm_object *clazz; + struct vm_class *class; + struct vm_method *vmm; + int slot; + + clazz = field_get_object(ctor, vm_java_lang_reflect_Constructor_clazz); + slot = field_get_int32(ctor, vm_java_lang_reflect_Constructor_slot); + + class = vm_class_get_class_from_class_object(clazz); + vmm = &class->methods[slot]; + + /* TODO: We support only ()V constructors yet. */ + assert(!strcmp(vmm->type, "()V")); + + array = vm_object_alloc_array(vm_array_of_java_lang_Class, 0); + return array; +} + +jint native_constructor_get_modifiers_internal(struct vm_object *ctor) +{ + struct vm_object *clazz; + struct vm_class *class; + struct vm_method *vmm; + int slot; + + clazz = field_get_object(ctor, vm_java_lang_reflect_Constructor_clazz); + slot = field_get_int32(ctor, vm_java_lang_reflect_Constructor_slot); + + class = vm_class_get_class_from_class_object(clazz); + vmm = &class->methods[slot]; + + return vmm->method->access_flags; +} + +struct vm_object * +native_constructor_construct_native(struct vm_object *this, + struct vm_object *args, + struct vm_object *declaring_class, + int slot) +{ + struct vm_object *result; + struct vm_class *class; + struct vm_method *vmm; + + if (!vm_object_is_instance_of(declaring_class, vm_java_lang_Class)) + return NULL; + + class = vm_class_get_class_from_class_object(declaring_class); + vmm = &class->methods[slot]; + + result = vm_object_alloc(class); + + NOT_IMPLEMENTED; + + /* TODO: We support only ()V constructors yet. */ + assert(args == NULL || args->array_length == 0); + + vm_call_method_object(vmm, result); + return result; +} -- 1.6.0.6 ------------------------------------------------------------------------------ Let Crystal Reports handle the reporting - Free Crystal Reports 2008 30-Day trial. Simplify your report design, integration and deployment - and focus on what you do best, core application coding. Discover what's new with Crystal Reports now. http://p.sf.net/sfu/bobj-july _______________________________________________ Jatovm-devel mailing list Jatovm-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/jatovm-devel