diff options
author | Rico Tzschichholz <ricotz@ubuntu.com> | 2019-11-14 12:32:15 +0100 |
---|---|---|
committer | Rico Tzschichholz <ricotz@ubuntu.com> | 2019-11-14 13:23:19 +0100 |
commit | 9c7a7891b024e66df377fc2b5d60abfbfbdd9edd (patch) | |
tree | 0e3d4e2afe05c49e8ffc482c14f537663884366a | |
parent | 07ff8734d0712921787681d20e59cc1531cdf7af (diff) | |
download | vala-9c7a7891b024e66df377fc2b5d60abfbfbdd9edd.tar.gz |
codegen: Fix support of dynamic DBus methods
-rw-r--r-- | codegen/valaccodemethodcallmodule.vala | 7 | ||||
-rw-r--r-- | codegen/valagdbusclientmodule.vala | 6 | ||||
-rw-r--r-- | tests/Makefile.am | 1 | ||||
-rw-r--r-- | tests/dbus/dynamic-method.test | 63 | ||||
-rw-r--r-- | vala/valamemberaccess.vala | 1 |
5 files changed, 74 insertions, 4 deletions
diff --git a/codegen/valaccodemethodcallmodule.vala b/codegen/valaccodemethodcallmodule.vala index c5b36f86a..2413bc99a 100644 --- a/codegen/valaccodemethodcallmodule.vala +++ b/codegen/valaccodemethodcallmodule.vala @@ -296,6 +296,7 @@ public class Vala.CCodeMethodCallModule : CCodeAssignmentModule { csizeof.add_argument (new CCodeIdentifier (get_ccode_name (array_type.element_type))); in_arg_map.set (get_param_pos (0.1), csizeof); } else if (m is DynamicMethod) { + emit_context.push_symbol (m); m.clear_parameters (); int param_nr = 1; foreach (Expression arg in expr.get_argument_list ()) { @@ -320,6 +321,7 @@ public class Vala.CCodeMethodCallModule : CCodeAssignmentModule { param.accept (this); } generate_dynamic_method_wrapper ((DynamicMethod) m); + emit_context.pop_symbol (); } else if (m is CreationMethod && context.profile == Profile.GOBJECT && m.parent_symbol is Class) { ccode.add_assignment (get_this_cexpression (), new CCodeCastExpression (ccall, get_ccode_name (current_class) + "*")); @@ -904,6 +906,11 @@ public class Vala.CCodeMethodCallModule : CCodeAssignmentModule { ccode.add_expression (destroy_value (unary.inner.target_value)); } + // infer type of out-parameter from argument + if (ma.symbol_reference is DynamicMethod && unary.target_value.value_type == null) { + unary.target_value.value_type = unary.inner.value_type.copy (); + } + // assign new value store_value (unary.inner.target_value, transform_value (unary.target_value, unary.inner.value_type, arg), expr.source_reference); diff --git a/codegen/valagdbusclientmodule.vala b/codegen/valagdbusclientmodule.vala index 3e79a3f3e..12a7693d2 100644 --- a/codegen/valagdbusclientmodule.vala +++ b/codegen/valagdbusclientmodule.vala @@ -43,8 +43,6 @@ public class Vala.GDBusClientModule : GDBusModule { } public override void generate_dynamic_method_wrapper (DynamicMethod method) { - var dynamic_method = (DynamicMethod) method; - var func = new CCodeFunction (get_ccode_name (method)); func.modifiers = CCodeModifiers.STATIC; @@ -54,10 +52,10 @@ public class Vala.GDBusClientModule : GDBusModule { push_function (func); - if (dynamic_method.dynamic_type.type_symbol == dbus_proxy_type) { + if (method.dynamic_type.type_symbol == dbus_proxy_type) { generate_marshalling (method, CallType.SYNC, null, method.name, -1); } else { - Report.error (method.source_reference, "dynamic methods are not supported for `%s'".printf (dynamic_method.dynamic_type.to_string ())); + Report.error (method.source_reference, "dynamic methods are not supported for `%s'".printf (method.dynamic_type.to_string ())); } pop_function (); diff --git a/tests/Makefile.am b/tests/Makefile.am index 3d0cef528..2bbd134b9 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -521,6 +521,7 @@ TESTS = \ dbus/errors.test \ dbus/async.test \ dbus/async-errors.test \ + dbus/dynamic-method.test \ dbus/enum-string-marshalling.vala \ dbus/signals.test \ dbus/filedescriptor.test \ diff --git a/tests/dbus/dynamic-method.test b/tests/dbus/dynamic-method.test new file mode 100644 index 000000000..fd3bc8a99 --- /dev/null +++ b/tests/dbus/dynamic-method.test @@ -0,0 +1,63 @@ +Packages: gio-2.0 +D-Bus + +Program: client + +async void run () { + try { + var bus = yield Bus.@get (BusType.SESSION); + dynamic DBusProxy test = yield new DBusProxy (bus, DBusProxyFlags.NONE, null, bus.get_unique_name (), "/org/example/test", "org.example.Test"); + string s; + int i = test.do_foo (42, out s); + assert (i == 23); + assert (s == "foo"); + } catch { + } + + main_loop.quit (); +} + +MainLoop main_loop; + +void main () { + main_loop = new MainLoop (); + run.begin (); + main_loop.run (); +} + +Program: server + +[DBus (name = "org.example.Test")] +class Test : Object { + public int do_foo (int i, out string s) throws Error { + assert (i == 42); + s = "foo"; + return 23; + } +} + +MainLoop main_loop; + +void client_exit (Pid pid, int status) { + // client finished, terminate server + assert (status == 0); + main_loop.quit (); +} + +void main () { + var conn = Bus.get_sync (BusType.SESSION); + conn.register_object ("/org/example/test", new Test ()); + + // try to register service in session bus + var request_result = conn.call_sync ("org.freedesktop.DBus", "/org/freedesktop/DBus", "org.freedesktop.DBus", "RequestName", + new Variant ("(su)", "org.example.Test", 0x4), null, 0, -1); + assert ((uint) request_result.get_child_value (0) == 1); + + // server ready, spawn client + Pid client_pid; + Process.spawn_async (null, { "dbus_dynamic_method_client" }, null, SpawnFlags.DO_NOT_REAP_CHILD, null, out client_pid); + ChildWatch.add (client_pid, client_exit); + + main_loop = new MainLoop (); + main_loop.run (); +} diff --git a/vala/valamemberaccess.vala b/vala/valamemberaccess.vala index b6b67bfcd..946bd2b0a 100644 --- a/vala/valamemberaccess.vala +++ b/vala/valamemberaccess.vala @@ -408,6 +408,7 @@ public class Vala.MemberAccess : Expression { m.add_error_type (err); m.access = SymbolAccessibility.PUBLIC; m.add_parameter (new Parameter.with_ellipsis ()); + m.this_parameter = new Parameter ("this", dynamic_object_type.copy ()); dynamic_object_type.type_symbol.scope.add (null, m); symbol_reference = m; } |