894
892
new_call.add_argument (new CCodeConstant ("\"%s\"".printf (dbus_iface_name)));
895
893
new_call.add_argument (new CCodeConstant ("NULL"));
897
new_block.add_statement (new CCodeReturnStatement (new_call));
895
var cdecl = new CCodeDeclaration (iface.get_cname () + "*");
896
cdecl.add_declarator (new CCodeVariableDeclarator ("self", new_call));
897
new_block.add_statement (cdecl);
899
var raw_connection = new CCodeFunctionCall (new CCodeIdentifier ("dbus_g_connection_get_connection"));
900
raw_connection.add_argument (new CCodeIdentifier ("connection"));
902
// add filter to handle signals from the remote object
903
var filter_call = new CCodeFunctionCall (new CCodeIdentifier ("dbus_connection_add_filter"));
904
filter_call.add_argument (raw_connection);
905
filter_call.add_argument (new CCodeIdentifier (lower_cname + "_filter"));
906
filter_call.add_argument (new CCodeIdentifier ("self"));
907
filter_call.add_argument (new CCodeConstant ("NULL"));
908
new_block.add_statement (new CCodeExpressionStatement (filter_call));
910
var filter_printf = new CCodeFunctionCall (new CCodeIdentifier ("g_strdup_printf"));
911
filter_printf.add_argument (new CCodeConstant ("\"type='signal',path='%s'\""));
912
filter_printf.add_argument (new CCodeIdentifier ("path"));
914
cdecl = new CCodeDeclaration ("char*");
915
cdecl.add_declarator (new CCodeVariableDeclarator ("filter", filter_printf));
916
new_block.add_statement (cdecl);
918
// ensure we receive signals from the remote object
919
var match_call = new CCodeFunctionCall (new CCodeIdentifier ("dbus_bus_add_match"));
920
match_call.add_argument (raw_connection);
921
match_call.add_argument (new CCodeIdentifier ("filter"));
922
match_call.add_argument (new CCodeConstant ("NULL"));
923
new_block.add_statement (new CCodeExpressionStatement (match_call));
925
var filter_free = new CCodeFunctionCall (new CCodeIdentifier ("g_free"));
926
filter_free.add_argument (new CCodeIdentifier ("filter"));
927
new_block.add_statement (new CCodeExpressionStatement (filter_free));
929
new_block.add_statement (new CCodeReturnStatement (new CCodeIdentifier ("self")));
899
931
member_decl_frag.append (proxy_new.copy ());
900
932
proxy_new.block = new_block;
901
933
source_type_member_definition.append (proxy_new);
935
generate_proxy_filter_function (iface);
937
// dbus proxy dispose
938
var proxy_dispose = new CCodeFunction (lower_cname + "_dispose", "void");
939
proxy_dispose.add_parameter (new CCodeFormalParameter ("self", "GObject*"));
940
proxy_dispose.modifiers = CCodeModifiers.STATIC;
941
proxy_dispose.block = new CCodeBlock ();
943
cdecl = new CCodeDeclaration ("DBusGConnection");
944
cdecl.add_declarator (new CCodeVariableDeclarator ("*connection"));
945
proxy_dispose.block.add_statement (cdecl);
947
var gconnection = new CCodeFunctionCall (new CCodeIdentifier ("g_object_get"));
948
gconnection.add_argument (new CCodeIdentifier ("self"));
949
gconnection.add_argument (new CCodeConstant ("\"connection\""));
950
gconnection.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, new CCodeIdentifier ("connection")));
951
gconnection.add_argument (new CCodeConstant ("NULL"));
952
proxy_dispose.block.add_statement (new CCodeExpressionStatement (gconnection));
955
filter_call = new CCodeFunctionCall (new CCodeIdentifier ("dbus_connection_remove_filter"));
956
filter_call.add_argument (raw_connection);
957
filter_call.add_argument (new CCodeIdentifier (lower_cname + "_filter"));
958
filter_call.add_argument (new CCodeIdentifier ("self"));
959
proxy_dispose.block.add_statement (new CCodeExpressionStatement (filter_call));
962
var parent_class = new CCodeFunctionCall (new CCodeIdentifier ("G_OBJECT_CLASS"));
963
parent_class.add_argument (new CCodeIdentifier (lower_cname + "_parent_class"));
964
var chainup = new CCodeFunctionCall (new CCodeMemberAccess.pointer (parent_class, "dispose"));
965
chainup.add_argument (new CCodeIdentifier ("self"));
966
proxy_dispose.block.add_statement (new CCodeExpressionStatement (chainup));
968
source_type_member_definition.append (proxy_dispose);
903
970
var proxy_class_init = new CCodeFunction (lower_cname + "_class_init", "void");
904
971
proxy_class_init.add_parameter (new CCodeFormalParameter ("klass", cname + "Class*"));
905
972
proxy_class_init.modifiers = CCodeModifiers.STATIC;
906
973
proxy_class_init.block = new CCodeBlock ();
974
var gobject_class = new CCodeFunctionCall (new CCodeIdentifier ("G_OBJECT_CLASS"));
975
gobject_class.add_argument (new CCodeIdentifier ("klass"));
976
proxy_class_init.block.add_statement (new CCodeExpressionStatement (new CCodeAssignment (new CCodeMemberAccess.pointer (gobject_class, "dispose"), new CCodeIdentifier (lower_cname + "_dispose"))));
907
977
source_type_member_definition.append (proxy_class_init);
909
979
var proxy_instance_init = new CCodeFunction (lower_cname + "_init", "void");
934
1004
source_type_member_definition.append (proxy_iface_init);
1007
void generate_proxy_filter_function (Interface iface) {
1008
string lower_cname = iface.get_lower_case_cprefix () + "dbus_proxy";
1010
var proxy_filter = new CCodeFunction (lower_cname + "_filter", "DBusHandlerResult");
1011
proxy_filter.add_parameter (new CCodeFormalParameter ("connection", "DBusConnection*"));
1012
proxy_filter.add_parameter (new CCodeFormalParameter ("message", "DBusMessage*"));
1013
proxy_filter.add_parameter (new CCodeFormalParameter ("user_data", "void*"));
1015
var filter_block = new CCodeBlock ();
1017
// only handle signals concering the object path
1018
var path = new CCodeFunctionCall (new CCodeIdentifier ("dbus_g_proxy_get_path"));
1019
path.add_argument (new CCodeIdentifier ("user_data"));
1021
var ccheck = new CCodeFunctionCall (new CCodeIdentifier ("dbus_message_has_path"));
1022
ccheck.add_argument (new CCodeIdentifier ("message"));
1023
ccheck.add_argument (path);
1025
var object_filter_block = new CCodeBlock ();
1026
filter_block.add_statement (new CCodeIfStatement (ccheck, object_filter_block));
1028
handle_signals (iface, object_filter_block);
1030
filter_block.add_statement (new CCodeReturnStatement (new CCodeIdentifier ("DBUS_HANDLER_RESULT_NOT_YET_HANDLED")));
1032
source_type_member_declaration.append (proxy_filter.copy ());
1033
proxy_filter.block = filter_block;
1034
source_type_member_definition.append (proxy_filter);
1037
string generate_dbus_signal_handler (Signal sig, ObjectTypeSymbol sym) {
1038
string wrapper_name = "_dbus_handle_%s_%s".printf (sym.get_lower_case_cname (), sig.get_cname ());
1042
CCodeDeclaration cdecl;
1044
var function = new CCodeFunction (wrapper_name, "void");
1045
function.modifiers = CCodeModifiers.STATIC;
1047
function.add_parameter (new CCodeFormalParameter ("self", sym.get_cname () + "*"));
1048
function.add_parameter (new CCodeFormalParameter ("connection", "DBusConnection*"));
1049
function.add_parameter (new CCodeFormalParameter ("message", "DBusMessage*"));
1051
var block = new CCodeBlock ();
1052
var prefragment = new CCodeFragment ();
1054
cdecl = new CCodeDeclaration ("DBusMessageIter");
1055
cdecl.add_declarator (new CCodeVariableDeclarator ("iter"));
1056
block.add_statement (cdecl);
1058
block.add_statement (prefragment);
1060
var message_signature = new CCodeFunctionCall (new CCodeIdentifier ("dbus_message_get_signature"));
1061
message_signature.add_argument (new CCodeIdentifier ("message"));
1062
var signature_check = new CCodeFunctionCall (new CCodeIdentifier ("strcmp"));
1063
signature_check.add_argument (message_signature);
1064
var signature_error_block = new CCodeBlock ();
1065
signature_error_block.add_statement (new CCodeReturnStatement ());
1066
prefragment.append (new CCodeIfStatement (signature_check, signature_error_block));
1068
var iter_call = new CCodeFunctionCall (new CCodeIdentifier ("dbus_message_iter_init"));
1069
iter_call.add_argument (new CCodeIdentifier ("message"));
1070
iter_call.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, new CCodeIdentifier ("iter")));
1071
prefragment.append (new CCodeExpressionStatement (iter_call));
1073
var ccall = new CCodeFunctionCall (new CCodeIdentifier ("g_signal_emit_by_name"));
1074
ccall.add_argument (new CCodeIdentifier ("self"));
1075
ccall.add_argument (sig.get_canonical_cconstant ());
1077
// expected type signature for input parameters
1078
string type_signature = "";
1080
foreach (FormalParameter param in sig.get_parameters ()) {
1081
cdecl = new CCodeDeclaration (param.parameter_type.get_cname ());
1082
cdecl.add_declarator (new CCodeVariableDeclarator (param.name, default_value_for_type (param.parameter_type, true)));
1083
prefragment.append (cdecl);
1085
if (param.parameter_type.get_type_signature () == null) {
1086
Report.error (param.parameter_type.source_reference, "D-Bus serialization of type `%s' is not supported".printf (param.parameter_type.to_string ()));
1090
var st = param.parameter_type.data_type as Struct;
1091
if (st != null && !st.is_simple_type ()) {
1092
ccall.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, new CCodeIdentifier (param.name)));
1094
ccall.add_argument (new CCodeIdentifier (param.name));
1097
if (param.parameter_type is ArrayType) {
1098
var array_type = (ArrayType) param.parameter_type;
1100
for (int dim = 1; dim <= array_type.rank; dim++) {
1101
string length_cname = get_array_length_cname (param.name, dim);
1103
cdecl = new CCodeDeclaration ("int");
1104
cdecl.add_declarator (new CCodeVariableDeclarator (length_cname, new CCodeConstant ("0")));
1105
prefragment.append (cdecl);
1106
ccall.add_argument (new CCodeIdentifier (length_cname));
1110
type_signature += param.parameter_type.get_type_signature ();
1112
var target = new CCodeIdentifier (param.name);
1113
var expr = read_expression (prefragment, param.parameter_type, new CCodeIdentifier ("iter"), target);
1114
prefragment.append (new CCodeExpressionStatement (new CCodeAssignment (target, expr)));
1117
signature_check.add_argument (new CCodeConstant ("\"%s\"".printf (type_signature)));
1119
block.add_statement (new CCodeExpressionStatement (ccall));
1121
cdecl = new CCodeDeclaration ("DBusMessage*");
1122
cdecl.add_declarator (new CCodeVariableDeclarator ("reply"));
1123
block.add_statement (cdecl);
1125
source_type_member_declaration.append (function.copy ());
1127
function.block = block;
1128
source_type_member_definition.append (function);
1130
return wrapper_name;
1133
void handle_signal (string dbus_iface_name, string dbus_signal_name, string handler_name, CCodeBlock block, ref CCodeIfStatement clastif) {
1134
var ccheck = new CCodeFunctionCall (new CCodeIdentifier ("dbus_message_is_signal"));
1135
ccheck.add_argument (new CCodeIdentifier ("message"));
1136
ccheck.add_argument (new CCodeConstant ("\"%s\"".printf (dbus_iface_name)));
1137
ccheck.add_argument (new CCodeConstant ("\"%s\"".printf (dbus_signal_name)));
1139
var callblock = new CCodeBlock ();
1141
var ccall = new CCodeFunctionCall (new CCodeIdentifier (handler_name));
1142
ccall.add_argument (new CCodeIdentifier ("user_data"));
1143
ccall.add_argument (new CCodeIdentifier ("connection"));
1144
ccall.add_argument (new CCodeIdentifier ("message"));
1146
callblock.add_statement (new CCodeExpressionStatement (ccall));
1148
var cif = new CCodeIfStatement (ccheck, callblock);
1149
if (clastif == null) {
1150
block.add_statement (cif);
1152
clastif.false_statement = cif;
1158
void handle_signals (Interface iface, CCodeBlock block) {
1159
string dbus_iface_name = iface.get_attribute ("DBus").get_string ("name");
1161
CCodeIfStatement clastif = null;
1162
foreach (Signal sig in iface.get_signals ()) {
1163
if (sig.access != SymbolAccessibility.PUBLIC) {
1167
handle_signal (dbus_iface_name, Symbol.lower_case_to_camel_case (sig.name), generate_dbus_signal_handler (sig, iface), block, ref clastif);
937
1171
void generate_marshalling (Method m, string dbus_iface_name, CCodeFragment prefragment, CCodeFragment postfragment) {
938
1172
CCodeDeclaration cdecl;