]> git.ipfire.org Git - thirdparty/vala.git/commitdiff
Register all types when using [ModuleInit]
authorJürg Billeter <j@bitron.ch>
Tue, 20 Oct 2009 19:56:36 +0000 (21:56 +0200)
committerJürg Billeter <j@bitron.ch>
Tue, 20 Oct 2009 19:56:36 +0000 (21:56 +0200)
Fixes bug 553928.

codegen/valaccodebasemodule.vala
codegen/valaccodemethodmodule.vala
codegen/valagtypemodule.vala

index 0afddfa577553f2bd5e12d9f458c5db8f74402a9..2b2edde7a6996a0812a60d721a012bb74e6b8c3d 100644 (file)
@@ -126,7 +126,6 @@ internal class Vala.CCodeBaseModule : CCodeModule {
        public CCodeFragment instance_init_fragment;
        public CCodeFragment instance_finalize_fragment;
        public CCodeFragment source_signal_marshaller_definition;
-       public CCodeFragment module_init_fragment;
        
        public CCodeStruct param_spec_struct;
        public CCodeStruct closure_struct;
@@ -337,7 +336,6 @@ internal class Vala.CCodeBaseModule : CCodeModule {
                        type_module_type = (TypeSymbol) glib_ns.scope.lookup ("TypeModule");
 
                        if (context.module_init_method != null) {
-                               module_init_fragment = new CCodeFragment ();
                                foreach (FormalParameter parameter in context.module_init_method.get_parameters ()) {
                                        if (parameter.parameter_type.data_type == type_module_type) {
                                                in_plugin = true;
index d66cfcd1994f44f651ce905c22ba295c7925ff6d..748c8aad4c9f19dd4910d00b63b966a5ac86ade8 100644 (file)
@@ -206,6 +206,60 @@ internal class Vala.CCodeMethodModule : CCodeStructModule {
                }
        }
 
+       void register_plugin_types (CCodeFragment module_init_fragment, Symbol sym, Set<Symbol> registered_types) {
+               var ns = sym as Namespace;
+               var cl = sym as Class;
+               var iface = sym as Interface;
+               if (ns != null) {
+                       foreach (var ns_ns in ns.get_namespaces ()) {
+                               register_plugin_types (module_init_fragment, ns_ns, registered_types);
+                       }
+                       foreach (var ns_cl in ns.get_classes ()) {
+                               register_plugin_types (module_init_fragment, ns_cl, registered_types);
+                       }
+                       foreach (var ns_iface in ns.get_interfaces ()) {
+                               register_plugin_types (module_init_fragment, ns_iface, registered_types);
+                       }
+               } else if (cl != null) {
+                       register_plugin_type (module_init_fragment, cl, registered_types);
+                       foreach (var cl_cl in cl.get_classes ()) {
+                               register_plugin_types (module_init_fragment, cl_cl, registered_types);
+                       }
+               } else if (iface != null) {
+                       register_plugin_type (module_init_fragment, iface, registered_types);
+                       foreach (var iface_cl in iface.get_classes ()) {
+                               register_plugin_types (module_init_fragment, iface_cl, registered_types);
+                       }
+               }
+       }
+
+       void register_plugin_type (CCodeFragment module_init_fragment, ObjectTypeSymbol type_symbol, Set<Symbol> registered_types) {
+               if (type_symbol.external_package) {
+                       return;
+               }
+
+               if (!registered_types.add (type_symbol)) {
+                       // already registered
+                       return;
+               }
+
+               var cl = type_symbol as Class;
+               if (cl != null) {
+                       if (cl.is_compact) {
+                               return;
+                       }
+
+                       // register base types first
+                       foreach (var base_type in cl.get_base_types ()) {
+                               register_plugin_type (module_init_fragment, (ObjectTypeSymbol) base_type.data_type, registered_types);
+                       }
+               }
+
+               var register_call = new CCodeFunctionCall (new CCodeIdentifier ("%s_register_type".printf (type_symbol.get_lower_case_cname (null))));
+               register_call.add_argument (new CCodeIdentifier (module_init_param_name));
+               module_init_fragment.append (new CCodeExpressionStatement (register_call));
+       }
+
        public override void visit_method (Method m) {
                var old_symbol = current_symbol;
                bool old_method_inner_error = current_method_inner_error;
@@ -632,7 +686,7 @@ internal class Vala.CCodeMethodModule : CCodeStructModule {
 
                                if (context.module_init_method == m && in_plugin) {
                                        // GTypeModule-based plug-in, register types
-                                       cinit.append (module_init_fragment);
+                                       register_plugin_types (cinit, context.root, new HashSet<Symbol> ());
                                }
 
                                foreach (Expression precondition in m.get_preconditions ()) {
index cd8135e61088a3eb51b11d002c5370fe055252da..e24ab34ff43b718990f3ad034c86b1c7d449a957 100644 (file)
@@ -563,13 +563,6 @@ internal class Vala.GTypeModule : GErrorModule {
                        type_fun.init_from_type (in_plugin);
                        source_declarations.add_type_member_declaration (type_fun.get_source_declaration ());
                        source_type_member_definition.append (type_fun.get_definition ());
-                       
-                       if (in_plugin) {
-                               // FIXME resolve potential dependency issues, i.e. base types have to be registered before derived types
-                               var register_call = new CCodeFunctionCall (new CCodeIdentifier ("%s_register_type".printf (cl.get_lower_case_cname (null))));
-                               register_call.add_argument (new CCodeIdentifier (module_init_param_name));
-                               module_init_fragment.append (new CCodeExpressionStatement (register_call));
-                       }
 
                        if (is_fundamental) {
                                var ref_fun = new CCodeFunction (cl.get_lower_case_cprefix () + "ref", "gpointer");