java-gobject-introspection r104 - in trunk: src/org/gnome/gir/compiler src/org/gnome/gir/gobject stub-examples



Author: walters
Date: Thu Oct 23 00:16:51 2008
New Revision: 104
URL: http://svn.gnome.org/viewvc/java-gobject-introspection?rev=104&view=rev

Log:
Rework boxed handling for GValues


Modified:
   trunk/src/org/gnome/gir/compiler/CodeFactory.java
   trunk/src/org/gnome/gir/gobject/BoxedStructure.java
   trunk/src/org/gnome/gir/gobject/BoxedUnion.java
   trunk/src/org/gnome/gir/gobject/GBoxed.java
   trunk/src/org/gnome/gir/gobject/GBoxedAPI.java
   trunk/src/org/gnome/gir/gobject/GClosure.java
   trunk/src/org/gnome/gir/gobject/GHashTable.java
   trunk/src/org/gnome/gir/gobject/GTypeMapper.java
   trunk/src/org/gnome/gir/gobject/GValue.java
   trunk/stub-examples/TestStructure.java

Modified: trunk/src/org/gnome/gir/compiler/CodeFactory.java
==============================================================================
--- trunk/src/org/gnome/gir/compiler/CodeFactory.java	(original)
+++ trunk/src/org/gnome/gir/compiler/CodeFactory.java	Thu Oct 23 00:16:51 2008
@@ -119,6 +119,7 @@
 import com.sun.jna.Native;
 import com.sun.jna.NativeLibrary;
 import com.sun.jna.Pointer;
+import com.sun.jna.TypeMapper;
 import com.sun.jna.ptr.ByteByReference;
 import com.sun.jna.ptr.DoubleByReference;
 import com.sun.jna.ptr.FloatByReference;
@@ -1876,20 +1877,30 @@
 		String internalName = getInternalName(info);
 		String typeInit = info.getTypeInit();
 		boolean isRegistered = typeInit != null;
-		boolean hasFields = fields.length > 0;
-		if (hasFields) {
-			compilation.writer.visit(V1_6, ACC_PUBLIC + ACC_SUPER, internalName, null, 
-					(isRegistered ? "org/gnome/gir/gobject/Boxed" : "com/sun/jna/") + type, null);
+		String parentInternalName;
+		boolean hasFields = fields.length > 0;		
+		if (isRegistered) {
+			if (hasFields)
+				parentInternalName = "org/gnome/gir/gobject/Boxed" + type;
+			else
+				parentInternalName = "org/gnome/gir/gobject/GBoxed";	
 		} else {
-			compilation.writer.visit(V1_6, ACC_PUBLIC + ACC_SUPER, internalName, null, 
-					"com/sun/jna/PointerType", null);
+			if (hasFields)
+				parentInternalName = "com/sun/jna/" + type;				
+			else
+				parentInternalName = "com/sun/jna/PointerType";
+		}
+		compilation.writer.visit(V1_6, ACC_PUBLIC + ACC_SUPER, internalName, null, 
+				parentInternalName, null);
+		
+		if (!hasFields) {
 			/* Write out a no-args ctor, though people shouldn't use this */
 			MethodVisitor mv = compilation.writer.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
 			mv.visitCode();
 			Label l0 = new Label();
 			mv.visitLabel(l0);
 			mv.visitVarInsn(ALOAD, 0);
-			mv.visitMethodInsn(INVOKESPECIAL, "com/sun/jna/PointerType", "<init>", "()V");
+			mv.visitMethodInsn(INVOKESPECIAL, parentInternalName, "<init>", "()V");
 			mv.visitInsn(RETURN);
 			Label l1 = new Label();
 			mv.visitLabel(l1);
@@ -1898,8 +1909,31 @@
 			mv.visitEnd();			
 		}
 		
-		if (hasFields && isRegistered)
-			writeGetGType(info, compilation);
+		if (isRegistered) {			
+			/* constructor; protected, taking GType, Pointer, TypeMapper; used in GValue */			
+			MethodVisitor mv = compilation.writer.visitMethod(ACC_PROTECTED, "<init>", 
+					Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { Type.getType(GType.class), Type.getType(Pointer.class), Type.getType(TypeMapper.class)} ), 
+					null, null);
+			mv.visitCode();
+			Label l0 = new Label();
+			mv.visitLabel(l0);
+			mv.visitVarInsn(ALOAD, 0);
+			mv.visitVarInsn(ALOAD, 1);
+			mv.visitVarInsn(ALOAD, 2);
+			mv.visitVarInsn(ALOAD, 3);			
+			mv.visitMethodInsn(INVOKESPECIAL, parentInternalName, "<init>", 
+					Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { Type.getType(GType.class), Type.getType(Pointer.class), Type.getType(TypeMapper.class)} ));
+			mv.visitInsn(RETURN);
+			Label l1 = new Label();
+			mv.visitLabel(l1);
+			mv.visitLocalVariable("this", "L" + compilation.internalName + ";", null, l0, l1, 0);
+			mv.visitLocalVariable("gtype", Type.getDescriptor(GType.class), null, l0, l1, 0);		
+			mv.visitLocalVariable("ptr", Type.getDescriptor(Pointer.class), null, l0, l1, 0);				
+			mv.visitLocalVariable("mapper", Type.getDescriptor(TypeMapper.class), null, l0, l1, 0);		
+			mv.visitMaxs(0, 0);
+			mv.visitEnd();			
+						
+		}
 		
 		if (hasFields) {
 			InnerClassCompilation byRef = compilation.newInner("ByReference");
@@ -1916,8 +1950,6 @@
 					new String[] { "com/sun/jna/Structure$ByValue" });
 			writeStructUnionInnerCtor(byValue, internalName, fields);
 
-			String parentInternalName = "com/sun/jna/" + type;
-			
 			/* constructor; public no-args */
 			MethodVisitor mv = compilation.writer.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
 			mv.visitCode();
@@ -1935,21 +1967,23 @@
 			mv.visitEnd();
 
 			/* constructor; protected, taking TypeMapper */			
-			mv = compilation.writer.visitMethod(ACC_PROTECTED, "<init>", "(Lcom/sun/jna/TypeMapper;)V", null, null);
+			mv = compilation.writer.visitMethod(ACC_PROTECTED, "<init>", 
+					Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { Type.getType(TypeMapper.class)} ), null, null);
 			mv.visitCode();
 			l0 = new Label();
 			mv.visitLabel(l0);
 			mv.visitVarInsn(ALOAD, 0);
 			mv.visitVarInsn(ALOAD, 1);
-			mv.visitMethodInsn(INVOKESPECIAL, parentInternalName, "<init>", "(Lcom/sun/jna/TypeMapper;)V");
+			mv.visitMethodInsn(INVOKESPECIAL, parentInternalName, "<init>", 
+					Type.getMethodDescriptor(Type.VOID_TYPE, new Type[] { Type.getType(TypeMapper.class)} ));
 			mv.visitInsn(RETURN);
 			l1 = new Label();
 			mv.visitLabel(l1);
 			mv.visitLocalVariable("this", "L" + compilation.internalName + ";", null, l0, l1, 0);
-			mv.visitLocalVariable("mapper", "Lcom/sun/jna/TypeMapper;", null, l0, l1, 0);		
+			mv.visitLocalVariable("mapper", Type.getDescriptor(TypeMapper.class), null, l0, l1, 0);		
 			mv.visitMaxs(0, 0);
 			mv.visitEnd();
-			
+
 			/* constructor that takes all of the fields */
 			LocalVariableTable locals = new LocalVariableTable(Type.getObjectType(compilation.internalName), null, null);			
 			List<Type> args = new ArrayList<Type>();

Modified: trunk/src/org/gnome/gir/gobject/BoxedStructure.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/BoxedStructure.java	(original)
+++ trunk/src/org/gnome/gir/gobject/BoxedStructure.java	Thu Oct 23 00:16:51 2008
@@ -7,20 +7,24 @@
 
 public abstract class BoxedStructure extends Structure implements RegisteredType {
 
-	private boolean isNative = false;
+	private final GType gtype;
+	private final boolean isNative;
 	
 	protected BoxedStructure(TypeMapper mapper) {
 		super(mapper);
+		gtype = GType.INVALID; // Should not be used
+		isNative = false;
 	}	
 	
-	public BoxedStructure(Pointer pointer) {
-		Pointer retptr = GBoxedAPI.gboxed.g_boxed_copy(GType.of(this.getClass()), pointer);		
-		useMemory(retptr);
+	protected BoxedStructure(GType gtype, Pointer pointer, TypeMapper mapper) {
+		super(mapper);
+		useMemory(pointer);		
+		this.gtype = gtype;
 		isNative = true;
 	}
-
-	protected void free() {
-		GBoxedAPI.gboxed.g_boxed_free(GType.of(this.getClass()), this.getPointer());
+	
+	protected void free() {	
+		GBoxedAPI.gboxed.g_boxed_free(gtype, this.getPointer());
 	}
 	
 	@Override
@@ -32,6 +36,6 @@
 	
 	@Override
 	public String toString() {
-		return GObjectAPI.gobj.g_type_name(GType.of(this.getClass())) + "(" + super.toString() + ")";
+		return String.format("BoxedStructure<%s>(%s)", GObjectAPI.gobj.g_type_name(gtype), super.toString());
 	}
 }

Modified: trunk/src/org/gnome/gir/gobject/BoxedUnion.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/BoxedUnion.java	(original)
+++ trunk/src/org/gnome/gir/gobject/BoxedUnion.java	Thu Oct 23 00:16:51 2008
@@ -7,20 +7,24 @@
 
 public abstract class BoxedUnion extends Union implements RegisteredType {
 	
-	private boolean isNative = false;
+	private final GType gtype;
+	private final boolean isNative;
 	
 	protected BoxedUnion(TypeMapper mapper) {
 		super(mapper);
+		gtype = GType.INVALID;
+		isNative = false;
 	}
 	
-	public BoxedUnion(Pointer pointer) {
-		Pointer retptr = GBoxedAPI.gboxed.g_boxed_copy(GType.of(this.getClass()), pointer);		
-		useMemory(retptr);
+	protected BoxedUnion(GType gtype, Pointer pointer, TypeMapper mapper) {
+		super(mapper);
+		useMemory(pointer);		
+		this.gtype = gtype;
 		isNative = true;
 	}
 
 	protected void free() {
-		GBoxedAPI.gboxed.g_boxed_free(GType.of(this.getClass()), this.getPointer());
+		GBoxedAPI.gboxed.g_boxed_free(gtype, this.getPointer());
 	}
 	
 	@Override
@@ -32,6 +36,6 @@
 	
 	@Override
 	public String toString() {
-		return GObjectAPI.gobj.g_type_name(GType.of(this.getClass())) + "(" + super.toString() + ")";
+		return GObjectAPI.gobj.g_type_name(gtype) + "(" + super.toString() + ")";
 	}	
 }

Modified: trunk/src/org/gnome/gir/gobject/GBoxed.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GBoxed.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GBoxed.java	Thu Oct 23 00:16:51 2008
@@ -1,10 +1,39 @@
 package org.gnome.gir.gobject;
 
+import java.lang.reflect.Constructor;
+
 import com.sun.jna.Pointer;
 import com.sun.jna.PointerType;
 import com.sun.jna.Structure;
+import com.sun.jna.TypeMapper;
 
 public abstract class GBoxed extends PointerType implements RegisteredType {
+	
+	protected GType gtype;
+	
+	public GBoxed(GType gtype, Pointer ptr) {
+		super(ptr);
+		this.gtype = gtype;
+	}
+	
+	protected void free() {
+		GBoxedAPI.gboxed.g_boxed_free(gtype, this.getPointer());
+	}
+	
+	@Override
+	public void finalize() throws Throwable {
+		free();
+		super.finalize();
+	}		
+	
+	/* A stub class we return for boxed reference types that we don't know about */
+	private static class AnonBoxed extends GBoxed {
+
+		public AnonBoxed(GType gtype, Pointer ptr) {
+			super(gtype, ptr);			
+		}	
+	}
+	
 	public static Pointer getPointerFor(Object data) {
 		Pointer ptr;
 		/* Since we're denaturing it here, we need to ensure that the structure
@@ -29,4 +58,19 @@
 			return;
 		((Structure) data).read();
 	}
+	
+	public static Object boxedFor(GType gtype, Pointer ptr) {
+		Class<?> boxedKlass = GType.lookupProxyClass(gtype);
+		if (boxedKlass != null && Structure.class.isAssignableFrom(boxedKlass)) {
+			try {
+				Constructor<?> ctor = boxedKlass.getDeclaredConstructor(new Class<?>[] { GType.class, Pointer.class, TypeMapper.class });
+				ctor.setAccessible(true);
+				return ctor.newInstance(new Object[] { gtype, ptr, GTypeMapper.getInstance() });
+			} catch (Exception e) {
+				throw new RuntimeException(e);
+			}
+		} else {
+			return new AnonBoxed(gtype, ptr);
+		}
+	}
 }

Modified: trunk/src/org/gnome/gir/gobject/GBoxedAPI.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GBoxedAPI.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GBoxedAPI.java	Thu Oct 23 00:16:51 2008
@@ -62,6 +62,7 @@
 	});
     
     GType g_closure_get_type();
+    GType g_hash_table_get_type();    
     Pointer g_boxed_copy(GType gtype, Pointer obj);
     void g_boxed_free(GType gtype, Pointer obj);    
 }

Modified: trunk/src/org/gnome/gir/gobject/GClosure.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GClosure.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GClosure.java	Thu Oct 23 00:16:51 2008
@@ -1,8 +1,10 @@
 package org.gnome.gir.gobject;
 
+import com.sun.jna.Pointer;
+
 
 public abstract class GClosure extends GBoxed {
-	public GType getType() {
-		return GBoxedAPI.gboxed.g_closure_get_type();
+	public GClosure(Pointer ptr) {
+		super(GBoxedAPI.gboxed.g_closure_get_type(), ptr);
 	}
 }

Modified: trunk/src/org/gnome/gir/gobject/GHashTable.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GHashTable.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GHashTable.java	Thu Oct 23 00:16:51 2008
@@ -1,6 +1,10 @@
 package org.gnome.gir.gobject;
 
+import com.sun.jna.Pointer;
+
 
 public class GHashTable extends GBoxed {
-	
+	public GHashTable(Pointer ptr) {
+		super(GBoxedAPI.gboxed.g_hash_table_get_type(), ptr);
+	}
 }

Modified: trunk/src/org/gnome/gir/gobject/GTypeMapper.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GTypeMapper.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GTypeMapper.java	Thu Oct 23 00:16:51 2008
@@ -190,7 +190,7 @@
     
     private TypeConverter booleanConverter = new TypeConverter() {
         public Object toNative(Object arg, ToNativeContext context) {
-            return Integer.valueOf(Boolean.TRUE.equals(arg) ? 1 : 0);
+            return Integer.valueOf(((Boolean) arg).booleanValue() ? 1 : 0);
         }
 
         public Object fromNative(Object arg0, FromNativeContext arg1) {

Modified: trunk/src/org/gnome/gir/gobject/GValue.java
==============================================================================
--- trunk/src/org/gnome/gir/gobject/GValue.java	(original)
+++ trunk/src/org/gnome/gir/gobject/GValue.java	Thu Oct 23 00:16:51 2008
@@ -211,7 +211,8 @@
 			return GValueAPI.gvalue.g_value_get_string(this);
 		} else if (fundamental.equals(GType.OBJECT)) {
 			return GValueAPI.gvalue.g_value_dup_object(this);
-			/* FIXME implement boxed mapping */
+		} else if (fundamental.equals(GType.BOXED)) {
+			return GBoxed.boxedFor(g_type, GValueAPI.gvalue.g_value_dup_boxed(this));
 		} else if (GValueAPI.gvalue.g_value_type_transformable(g_type, GType.OBJECT)) {
 			return GValueAPI.gvalue.g_value_dup_object(transform(this, GType.OBJECT));
 		} else if (GValueAPI.gvalue.g_value_type_transformable(g_type, GType.INT)) {

Modified: trunk/stub-examples/TestStructure.java
==============================================================================
--- trunk/stub-examples/TestStructure.java	(original)
+++ trunk/stub-examples/TestStructure.java	Thu Oct 23 00:16:51 2008
@@ -1,10 +1,12 @@
 
 
+import org.gnome.gir.gobject.BoxedStructure;
+import org.gnome.gir.gobject.GType;
 import org.gnome.gir.gobject.GTypeMapper;
 
 import com.sun.jna.Structure;
 
-public class TestStructure extends Structure {
+public class TestStructure extends BoxedStructure {
 	public static class ByValue extends TestStructure implements Structure.ByValue {
 		
 	};
@@ -18,6 +20,10 @@
 	public int bar;
 	public TestStructure.ByRereference refed;
 	
+	public static GType getGType() {
+		return GType.INVALID;
+	}
+	
 	public TestStructure(String foo, int bar) {
 		super(GTypeMapper.getInstance());		
 		this.foo = foo;



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]