[vala] Register all types when using [ModuleInit]



commit 0e8eddd844f8f93ac36c39a1bddd89d8e216508f
Author: Jürg Billeter <j bitron ch>
Date:   Tue Oct 20 21:56:36 2009 +0200

    Register all types when using [ModuleInit]
    
    Fixes bug 553928.

 codegen/valaccodebasemodule.vala   |    2 -
 codegen/valaccodemethodmodule.vala |   56 +++++++++++++++++++++++++++++++++++-
 codegen/valagtypemodule.vala       |    7 ----
 3 files changed, 55 insertions(+), 10 deletions(-)
---
diff --git a/codegen/valaccodebasemodule.vala b/codegen/valaccodebasemodule.vala
index 0afddfa..2b2edde 100644
--- a/codegen/valaccodebasemodule.vala
+++ b/codegen/valaccodebasemodule.vala
@@ -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;
diff --git a/codegen/valaccodemethodmodule.vala b/codegen/valaccodemethodmodule.vala
index d66cfcd..748c8aa 100644
--- a/codegen/valaccodemethodmodule.vala
+++ b/codegen/valaccodemethodmodule.vala
@@ -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 ()) {
diff --git a/codegen/valagtypemodule.vala b/codegen/valagtypemodule.vala
index cd8135e..e24ab34 100644
--- a/codegen/valagtypemodule.vala
+++ b/codegen/valagtypemodule.vala
@@ -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");



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