[vala] D-Bus: Support [DBus (signature = "...")] Variant



commit 1eae18544f198ac64ec32c1e531c2c8fe1be8456
Author: Jürg Billeter <j bitron ch>
Date:   Sun Jun 20 14:12:39 2010 +0200

    D-Bus: Support [DBus (signature = "...")] Variant
    
    This makes it possible to use GVariant in D-Bus clients and servers
    without automatic boxing/unboxing.

 codegen/valagdbusclientmodule.vala |   26 +++++++-------
 codegen/valagdbusservermodule.vala |   18 +++++-----
 codegen/valagvariantmodule.vala    |   62 ++++++++++++++++++++++++++----------
 3 files changed, 67 insertions(+), 39 deletions(-)
---
diff --git a/codegen/valagdbusclientmodule.vala b/codegen/valagdbusclientmodule.vala
index 170196a..e83d3c6 100644
--- a/codegen/valagdbusclientmodule.vala
+++ b/codegen/valagdbusclientmodule.vala
@@ -341,7 +341,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 				}
 			}
 
-			read_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_iter"), new CCodeIdentifier (param.name));
+			read_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_iter"), new CCodeIdentifier (param.name), param);
 
 			if (requires_destroy (owned_type)) {
 				// keep local alive (symbol_reference is weak)
@@ -438,7 +438,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 				if (param.parameter_type.is_real_struct_type ()) {
 					expr = new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, expr);
 				}
-				write_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_builder"), expr);
+				write_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_builder"), expr, param);
 			} else {
 				cdecl = new CCodeDeclaration (param.parameter_type.get_cname ());
 				cdecl.add_declarator (new CCodeVariableDeclarator ("_" + param.name));
@@ -455,7 +455,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 				}
 
 				var target = new CCodeIdentifier ("_" + param.name);
-				read_expression (postfragment, param.parameter_type, new CCodeIdentifier ("_reply_iter"), target);
+				read_expression (postfragment, param.parameter_type, new CCodeIdentifier ("_reply_iter"), target, param);
 
 				// TODO check that parameter is not NULL (out parameters are optional)
 				// free value if parameter is NULL
@@ -473,7 +473,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 		if (!(m.return_type is VoidType)) {
 			if (m.return_type.is_real_non_null_struct_type ()) {
 				var target = new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, new CCodeIdentifier ("result"));
-				read_expression (postfragment, m.return_type, new CCodeIdentifier ("_reply_iter"), target);
+				read_expression (postfragment, m.return_type, new CCodeIdentifier ("_reply_iter"), target, m);
 			} else {
 				cdecl = new CCodeDeclaration (m.return_type.get_cname ());
 				cdecl.add_declarator (new CCodeVariableDeclarator ("_result"));
@@ -489,7 +489,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 					}
 				}
 
-				read_expression (postfragment, m.return_type, new CCodeIdentifier ("_reply_iter"), new CCodeIdentifier ("_result"));
+				read_expression (postfragment, m.return_type, new CCodeIdentifier ("_reply_iter"), new CCodeIdentifier ("_result"), m);
 
 				if (array_type != null) {
 					for (int dim = 1; dim <= array_type.rank; dim++) {
@@ -725,9 +725,9 @@ public class Vala.GDBusClientModule : GDBusModule {
 		prefragment.append (new CCodeExpressionStatement (builder_init));
 
 		// interface name
-		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (dbus_iface_name)));
+		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (dbus_iface_name)), null);
 		// property name
-		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (get_dbus_name_for_member (prop))));
+		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (get_dbus_name_for_member (prop))), null);
 
 		var builder_end = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_builder_end"));
 		builder_end.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, new CCodeIdentifier ("_arguments_builder")));
@@ -749,7 +749,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 
 		if (prop.property_type.is_real_non_null_struct_type ()) {
 			var target = new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, new CCodeIdentifier ("result"));
-			read_expression (postfragment, prop.get_accessor.value_type, new CCodeIdentifier ("_reply_iter"), target);
+			read_expression (postfragment, prop.get_accessor.value_type, new CCodeIdentifier ("_reply_iter"), target, prop);
 		} else {
 			cdecl = new CCodeDeclaration (prop.get_accessor.value_type.get_cname ());
 			cdecl.add_declarator (new CCodeVariableDeclarator ("_result"));
@@ -763,7 +763,7 @@ public class Vala.GDBusClientModule : GDBusModule {
 				}
 			}
 
-			read_expression (postfragment, prop.get_accessor.value_type, new CCodeIdentifier ("_reply_iter"), new CCodeIdentifier ("_result"));
+			read_expression (postfragment, prop.get_accessor.value_type, new CCodeIdentifier ("_reply_iter"), new CCodeIdentifier ("_result"), prop);
 
 			if (array_type != null) {
 				for (int dim = 1; dim <= array_type.rank; dim++) {
@@ -859,9 +859,9 @@ public class Vala.GDBusClientModule : GDBusModule {
 		prefragment.append (new CCodeExpressionStatement (builder_init));
 
 		// interface name
-		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (dbus_iface_name)));
+		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (dbus_iface_name)), null);
 		// property name
-		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (get_dbus_name_for_member (prop))));
+		write_expression (prefragment, string_type, new CCodeIdentifier ("_arguments_builder"), new CCodeConstant ("\"%s\"".printf (get_dbus_name_for_member (prop))), null);
 
 		// property value (as variant)
 		var builder_open = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_builder_open"));
@@ -870,9 +870,9 @@ public class Vala.GDBusClientModule : GDBusModule {
 		prefragment.append (new CCodeExpressionStatement (builder_open));
 
 		if (prop.property_type.is_real_non_null_struct_type ()) {
-			write_expression (prefragment, prop.set_accessor.value_type, new CCodeIdentifier ("_arguments_builder"), new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, new CCodeIdentifier ("value")));
+			write_expression (prefragment, prop.set_accessor.value_type, new CCodeIdentifier ("_arguments_builder"), new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, new CCodeIdentifier ("value")), prop);
 		} else {
-			write_expression (prefragment, prop.set_accessor.value_type, new CCodeIdentifier ("_arguments_builder"), new CCodeIdentifier ("value"));
+			write_expression (prefragment, prop.set_accessor.value_type, new CCodeIdentifier ("_arguments_builder"), new CCodeIdentifier ("value"), prop);
 		}
 
 		var builder_close = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_builder_close"));
diff --git a/codegen/valagdbusservermodule.vala b/codegen/valagdbusservermodule.vala
index 3914117..57e8550 100644
--- a/codegen/valagdbusservermodule.vala
+++ b/codegen/valagdbusservermodule.vala
@@ -184,9 +184,9 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 			}
 
 			if (param.direction == ParameterDirection.IN) {
-				read_expression (in_prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_iter"), new CCodeIdentifier (param.name));
+				read_expression (in_prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_iter"), new CCodeIdentifier (param.name), param);
 			} else {
-				write_expression (out_postfragment, param.parameter_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier (param.name));
+				write_expression (out_postfragment, param.parameter_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier (param.name), param);
 			}
 
 			if (requires_destroy (owned_type)) {
@@ -215,7 +215,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 					finish_ccall.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, new CCodeIdentifier ("result")));
 				}
 
-				write_expression (out_postfragment, m.return_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier ("result"));
+				write_expression (out_postfragment, m.return_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier ("result"), m);
 
 				if (requires_destroy (m.return_type)) {
 					// keep local alive (symbol_reference is weak)
@@ -259,7 +259,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 					}
 				}
 
-				write_expression (out_postfragment, m.return_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier ("result"));
+				write_expression (out_postfragment, m.return_type, new CCodeIdentifier ("_reply_builder"), new CCodeIdentifier ("result"), m);
 
 				if (requires_destroy (m.return_type)) {
 					// keep local alive (symbol_reference is weak)
@@ -408,7 +408,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 			if (param.parameter_type.is_real_struct_type ()) {
 				expr = new CCodeUnaryExpression (CCodeUnaryOperator.POINTER_INDIRECTION, expr);
 			}
-			write_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_builder"), expr);
+			write_expression (prefragment, param.parameter_type, new CCodeIdentifier ("_arguments_builder"), expr, param);
 		}
 
 		var builder_end = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_builder_end"));
@@ -810,7 +810,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 				var info = new CCodeInitializerList ();
 				info.append (new CCodeConstant ("-1"));
 				info.append (new CCodeConstant ("\"%s\"".printf (param.name)));
-				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (param.parameter_type))));
+				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (param.parameter_type, param))));
 
 				var cdecl = new CCodeDeclaration ("const GDBusArgInfo");
 				cdecl.add_declarator (new CCodeVariableDeclarator ("_" + sym.get_lower_case_cprefix () + "dbus_arg_info_" + m.name + "_" + param.name, info));
@@ -828,7 +828,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 				var info = new CCodeInitializerList ();
 				info.append (new CCodeConstant ("-1"));
 				info.append (new CCodeConstant ("\"%s\"".printf (dbus_result_name (m))));
-				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (m.return_type))));
+				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (m.return_type, m))));
 
 				var cdecl = new CCodeDeclaration ("const GDBusArgInfo");
 				cdecl.add_declarator (new CCodeVariableDeclarator ("_" + sym.get_lower_case_cprefix () + "dbus_arg_info_" + m.name + "_result", info));
@@ -892,7 +892,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 				var info = new CCodeInitializerList ();
 				info.append (new CCodeConstant ("-1"));
 				info.append (new CCodeConstant ("\"%s\"".printf (param.name)));
-				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (param.parameter_type))));
+				info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (param.parameter_type, param))));
 
 				var cdecl = new CCodeDeclaration ("const GDBusArgInfo");
 				cdecl.add_declarator (new CCodeVariableDeclarator ("_" + sym.get_lower_case_cprefix () + "dbus_arg_info_" + sig.get_cname () + "_" + param.name, info));
@@ -947,7 +947,7 @@ public class Vala.GDBusServerModule : GDBusClientModule {
 			var info = new CCodeInitializerList ();
 			info.append (new CCodeConstant ("-1"));
 			info.append (new CCodeConstant ("\"%s\"".printf (get_dbus_name_for_member (prop))));
-			info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (prop.property_type))));
+			info.append (new CCodeConstant ("\"%s\"".printf (get_type_signature (prop.property_type, prop))));
 			if (prop.get_accessor != null && prop.set_accessor != null) {
 				info.append (new CCodeConstant ("G_DBUS_PROPERTY_INFO_FLAGS_READABLE | G_DBUS_PROPERTY_INFO_FLAGS_WRITABLE"));
 			} else if (prop.get_accessor != null) {
diff --git a/codegen/valagvariantmodule.vala b/codegen/valagvariantmodule.vala
index 0f3861e..0694edf 100644
--- a/codegen/valagvariantmodule.vala
+++ b/codegen/valagvariantmodule.vala
@@ -55,16 +55,25 @@ public class Vala.GVariantModule : GAsyncModule {
 	}
 
 	string get_dbus_value (EnumValue value, string default_value) {
-			var dbus = value.get_attribute ("DBus");
-			if (dbus == null) {
-				return default_value;
-			}
+		var dbus = value.get_attribute ("DBus");
+		if (dbus == null) {
+			return default_value;
+		}
 
-			string dbus_value = dbus.get_string ("value");
-			if (dbus_value == null) {
-				return default_value;
-			}
-			return dbus_value;
+		string dbus_value = dbus.get_string ("value");
+		if (dbus_value == null) {
+			return default_value;
+		}
+		return dbus_value;
+	}
+
+	public static string? get_dbus_signature (Symbol symbol) {
+		var dbus = symbol.get_attribute ("DBus");
+		if (dbus == null) {
+			return null;
+		}
+
+		return dbus.get_string ("signature");
 	}
 
 	bool get_basic_type_info (string signature, out BasicTypeInfo basic_type) {
@@ -77,7 +86,15 @@ public class Vala.GVariantModule : GAsyncModule {
 		return false;
 	}
 
-	public static string? get_type_signature (DataType datatype) {
+	public static string? get_type_signature (DataType datatype, Symbol? symbol = null) {
+		if (symbol != null) {
+			string sig = get_dbus_signature (symbol);
+			if (sig != null) {
+				// allow overriding signature in attribute, used for raw GVariants
+				return sig;
+			}
+		}
+
 		var array_type = datatype as ArrayType;
 
 		if (array_type != null) {
@@ -380,7 +397,7 @@ public class Vala.GVariantModule : GAsyncModule {
 
 			field_found = true;
 
-			read_expression (fragment, f.field_type, new CCodeIdentifier (subiter_name), new CCodeMemberAccess (new CCodeIdentifier (temp_name), f.get_cname ()));
+			read_expression (fragment, f.field_type, new CCodeIdentifier (subiter_name), new CCodeMemberAccess (new CCodeIdentifier (temp_name), f.get_cname ()), f);
 		}
 
 		if (!field_found) {
@@ -506,7 +523,16 @@ public class Vala.GVariantModule : GAsyncModule {
 		return result;
 	}
 
-	public void read_expression (CCodeFragment fragment, DataType type, CCodeExpression iter_expr, CCodeExpression target_expr) {
+	public void read_expression (CCodeFragment fragment, DataType type, CCodeExpression iter_expr, CCodeExpression target_expr, Symbol? sym) {
+		var iter_call = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_iter_next_value"));
+		iter_call.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, iter_expr));
+
+		if (sym != null && get_dbus_signature (sym) != null) {
+			// raw GVariant
+			fragment.append (new CCodeExpressionStatement (new CCodeAssignment (target_expr, iter_call)));
+			return;
+		}
+
 		string temp_name = "_tmp%d_".printf (next_temp_var_id++);
 
 		var cdecl = new CCodeDeclaration ("GVariant*");
@@ -515,8 +541,6 @@ public class Vala.GVariantModule : GAsyncModule {
 
 		var variant_expr = new CCodeIdentifier (temp_name);
 
-		var iter_call = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_iter_next_value"));
-		iter_call.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, iter_expr));
 		fragment.append (new CCodeExpressionStatement (new CCodeAssignment (variant_expr, iter_call)));
 
 		var result = deserialize_expression (fragment, type, variant_expr, target_expr);
@@ -661,7 +685,7 @@ public class Vala.GVariantModule : GAsyncModule {
 
 			field_found = true;
 
-			write_expression (fragment, f.field_type, new CCodeIdentifier (builder_name), new CCodeMemberAccess (struct_expr, f.get_cname ()));
+			write_expression (fragment, f.field_type, new CCodeIdentifier (builder_name), new CCodeMemberAccess (struct_expr, f.get_cname ()), f);
 		}
 
 		if (!field_found) {
@@ -776,8 +800,12 @@ public class Vala.GVariantModule : GAsyncModule {
 		return result;
 	}
 
-	public void write_expression (CCodeFragment fragment, DataType type, CCodeExpression builder_expr, CCodeExpression expr) {
-		var variant_expr = serialize_expression (fragment, type, expr);
+	public void write_expression (CCodeFragment fragment, DataType type, CCodeExpression builder_expr, CCodeExpression expr, Symbol? sym) {
+		var variant_expr = expr;
+		if (sym == null || get_dbus_signature (sym) == null) {
+			// perform boxing
+			variant_expr = serialize_expression (fragment, type, expr);
+		}
 		if (variant_expr != null) {
 			var builder_add = new CCodeFunctionCall (new CCodeIdentifier ("g_variant_builder_add_value"));
 			builder_add.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, builder_expr));



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