[gobject-introspection] Make Full the default transfer for returned foreign structs.



commit a18d88dd1a42ef646852b32dc00b07d7895b6dc7
Author: Tomeu Vizoso <tomeu vizoso collabora co uk>
Date:   Sat Sep 11 14:25:27 2010 +0200

    Make Full the default transfer for returned foreign structs.
    
    For that we also need to read the annotations for foreign structs
    before guessing the transfer mode of return values.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=629188

 giscanner/maintransformer.py       |   20 ++++++++++++++++----
 tests/scanner/Foo-1.0-expected.gir |    5 +++++
 tests/scanner/foo.c                |    9 +++++++++
 tests/scanner/foo.h                |    1 +
 4 files changed, 31 insertions(+), 4 deletions(-)
---
diff --git a/giscanner/maintransformer.py b/giscanner/maintransformer.py
index f2527b5..b7d64a6 100644
--- a/giscanner/maintransformer.py
+++ b/giscanner/maintransformer.py
@@ -65,6 +65,9 @@ class MainTransformer(object):
         # Type() types and see if they match up with something.
         self._namespace.walk(self._pass_type_resolution)
 
+        # Read in annotations needed early
+        self._namespace.walk(self._pass_read_annotations_early)
+
         # Determine some default values for transfer etc.
         # based on the current tree.
         self._namespace.walk(self._pass_callable_defaults)
@@ -166,6 +169,15 @@ usage is void (*_gtk_reserved1)(void);"""
         block = self._blocks.get(node.symbol)
         self._apply_annotations_callable(node, chain, block)
 
+    def _pass_read_annotations_early(self, node, chain):
+        if isinstance(node, ast.Record):
+            if node.ctype is not None:
+                block = self._blocks.get(node.ctype)
+            else:
+                block = self._blocks.get(node.c_name)
+            self._apply_annotations_annotated(node, block)
+        return True
+
     def _pass_callable_defaults(self, node, chain):
         if isinstance(node, (ast.Callable, ast.Signal)):
             for param in node.parameters:
@@ -198,9 +210,8 @@ usage is void (*_gtk_reserved1)(void);"""
             self._apply_annotations_function(node, chain)
         if isinstance(node, ast.Callback):
             self._apply_annotations_callable(node, chain, block = self._get_block(node))
-        if isinstance(node, (ast.Class, ast.Interface, ast.Record,
-                             ast.Union, ast.Enum, ast.Bitfield,
-                             ast.Callback)):
+        if isinstance(node, (ast.Class, ast.Interface, ast.Union, ast.Enum,
+                             ast.Bitfield, ast.Callback)):
             self._apply_annotations_annotated(node, self._get_block(node))
         if isinstance(node, (ast.Class, ast.Interface, ast.Record, ast.Union)):
             block = self._get_block(node)
@@ -384,7 +395,8 @@ usage is void (*_gtk_reserved1)(void);"""
         if isinstance(target, ast.Alias):
             return self._get_transfer_default_returntype_basic(target.target)
         elif (isinstance(target, ast.Boxed)
-              or (isinstance(target, (ast.Record, ast.Union)) and target.gtype_name is not None)):
+              or (isinstance(target, (ast.Record, ast.Union))
+                  and (target.gtype_name is not None or target.foreign))):
             return ast.PARAM_TRANSFER_FULL
         elif isinstance(target, (ast.Enum, ast.Bitfield)):
             return ast.PARAM_TRANSFER_NONE
diff --git a/tests/scanner/Foo-1.0-expected.gir b/tests/scanner/Foo-1.0-expected.gir
index a0cb696..378852e 100644
--- a/tests/scanner/Foo-1.0-expected.gir
+++ b/tests/scanner/Foo-1.0-expected.gir
@@ -260,6 +260,11 @@ and/or use gtk-doc annotations.  -->
           <type name="ForeignStruct" c:type="FooForeignStruct*"/>
         </return-value>
       </constructor>
+      <method name="copy" c:identifier="foo_foreign_struct_copy">
+        <return-value transfer-ownership="full">
+          <type name="ForeignStruct" c:type="FooForeignStruct*"/>
+        </return-value>
+      </method>
     </record>
     <interface name="Interface"
                c:symbol-prefix="interface"
diff --git a/tests/scanner/foo.c b/tests/scanner/foo.c
index a2901f1..8b8b40d 100644
--- a/tests/scanner/foo.c
+++ b/tests/scanner/foo.c
@@ -717,6 +717,15 @@ foo_foreign_struct_new (void)
   return g_slice_new0 (FooForeignStruct);
 }
 
+FooForeignStruct*
+foo_foreign_struct_copy (FooForeignStruct *original)
+{
+    FooForeignStruct *copy;
+    copy = foo_foreign_struct_new ();
+    copy->foo = original->foo;
+    return copy;
+}
+
 /**
  * foo_test_varargs_callback: (skip)
  *
diff --git a/tests/scanner/foo.h b/tests/scanner/foo.h
index 6c57266..e648e60 100644
--- a/tests/scanner/foo.h
+++ b/tests/scanner/foo.h
@@ -424,6 +424,7 @@ struct _FooForeignStruct
 };
 
 FooForeignStruct* foo_foreign_struct_new (void);
+FooForeignStruct* foo_foreign_struct_copy (FooForeignStruct *original);
 
 /* This one should be a global, not a method on UtilityObject since
  * it's a separate namespace.



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