From: Jürg Billeter Date: Sun, 20 Jun 2010 12:12:39 +0000 (+0200) Subject: D-Bus: Support [DBus (signature = "...")] Variant X-Git-Tag: 0.9.2~8 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=1eae18544f198ac64ec32c1e531c2c8fe1be8456;p=thirdparty%2Fvala.git D-Bus: Support [DBus (signature = "...")] Variant This makes it possible to use GVariant in D-Bus clients and servers without automatic boxing/unboxing. --- diff --git a/codegen/valagdbusclientmodule.vala b/codegen/valagdbusclientmodule.vala index 170196ab6..e83d3c6c8 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 3914117b4..57e8550f9 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 0f3861e1a..0694edf57 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));