00001 #include <glib.h> 00002 #include "dbus-glib.h" 00003 #include <stdio.h> 00004 #include <string.h> 00005 00006 #include "test-thread.h" 00007 00008 typedef struct { 00009 guint32 counters[N_TEST_THREADS]; 00010 } ThreadTestData; 00011 00012 static ThreadTestData * 00013 thread_test_data_new (void) 00014 { 00015 ThreadTestData *data; 00016 00017 data = g_new0 (ThreadTestData, 1); 00018 00019 return data; 00020 } 00021 00022 static void 00023 thread_test_data_free (ThreadTestData *data) 00024 { 00025 g_free (data); 00026 } 00027 00028 static DBusMessageHandler *disconnect_handler; 00029 static DBusMessageHandler *filter_handler; 00030 static dbus_int32_t handler_slot = -1; 00031 00032 static DBusHandlerResult 00033 handle_test_message (DBusMessageHandler *handler, 00034 DBusConnection *connection, 00035 DBusMessage *message, 00036 void *user_data) 00037 { 00038 ThreadTestData *data = user_data; 00039 DBusMessageIter iter; 00040 gint32 threadnr; 00041 guint32 counter; 00042 char *str, *expected_str; 00043 GString *counter_str; 00044 int i; 00045 00046 dbus_message_iter_init (message, &iter); 00047 00048 if (dbus_message_iter_get_arg_type (&iter) != DBUS_TYPE_INT32) 00049 { 00050 g_print ("First arg not right type\n"); 00051 goto out; 00052 } 00053 threadnr = dbus_message_iter_get_int32 (&iter); 00054 if (threadnr < 0 || threadnr >= N_TEST_THREADS) 00055 { 00056 g_print ("Invalid thread nr\n"); 00057 goto out; 00058 } 00059 00060 if (! dbus_message_iter_next (&iter)) 00061 { 00062 g_print ("Couldn't get second arg\n"); 00063 goto out; 00064 } 00065 00066 if (dbus_message_iter_get_arg_type (&iter) != DBUS_TYPE_UINT32) 00067 { 00068 g_print ("Second arg not right type\n"); 00069 goto out; 00070 } 00071 00072 counter = dbus_message_iter_get_uint32 (&iter); 00073 00074 if (counter != data->counters[threadnr]) 00075 { 00076 g_print ("Thread %d, counter %d, expected %d\n", threadnr, counter, data->counters[threadnr]); 00077 goto out; 00078 } 00079 data->counters[threadnr]++; 00080 00081 if (! dbus_message_iter_next (&iter)) 00082 { 00083 g_print ("Couldn't get third arg\n"); 00084 goto out; 00085 } 00086 00087 if (dbus_message_iter_get_arg_type (&iter) != DBUS_TYPE_STRING) 00088 { 00089 g_print ("Third arg not right type\n"); 00090 goto out; 00091 } 00092 00093 str = dbus_message_iter_get_string (&iter); 00094 00095 if (str == NULL) 00096 { 00097 g_print ("No third arg\n"); 00098 goto out; 00099 } 00100 00101 expected_str = g_strdup_printf ("Thread %d-%d\n", threadnr, counter); 00102 if (strcmp (expected_str, str) != 0) 00103 { 00104 g_print ("Wrong string '%s', expected '%s'\n", str, expected_str); 00105 goto out; 00106 } 00107 g_free (str); 00108 g_free (expected_str); 00109 00110 if (dbus_message_iter_next (&iter)) 00111 { 00112 g_print ("Extra args on end of message\n"); 00113 goto out; 00114 } 00115 00116 dbus_connection_flush (connection); 00117 00118 counter_str = g_string_new (""); 00119 for (i = 0; i < N_TEST_THREADS; i++) 00120 { 00121 g_string_append_printf (counter_str, "%d ", data->counters[i]); 00122 } 00123 g_print ("%s\r", counter_str->str); 00124 g_string_free (counter_str, TRUE); 00125 00126 out: 00127 return DBUS_HANDLER_RESULT_ALLOW_MORE_HANDLERS; 00128 } 00129 00130 static DBusHandlerResult 00131 handle_filter (DBusMessageHandler *handler, 00132 DBusConnection *connection, 00133 DBusMessage *message, 00134 void *user_data) 00135 { 00136 return DBUS_HANDLER_RESULT_ALLOW_MORE_HANDLERS; 00137 } 00138 00139 static DBusHandlerResult 00140 handle_disconnect (DBusMessageHandler *handler, 00141 DBusConnection *connection, 00142 DBusMessage *message, 00143 void *user_data) 00144 { 00145 g_print ("connection disconnected\n"); 00146 dbus_connection_unref (connection); 00147 00148 return DBUS_HANDLER_RESULT_ALLOW_MORE_HANDLERS; 00149 } 00150 00151 00152 static void 00153 new_connection_callback (DBusServer *server, 00154 DBusConnection *new_connection, 00155 void *user_data) 00156 { 00157 const char *test_messages[] = { "org.freedesktop.ThreadTest" }; 00158 const char *disconnect_messages[] = { "org.freedesktop.Local.Disconnect" }; 00159 DBusMessageHandler *test_message_handler; 00160 ThreadTestData * data; 00161 00162 g_print ("new_connection_callback\n"); 00163 00164 dbus_connection_ref (new_connection); 00165 dbus_connection_setup_with_g_main (new_connection, NULL); 00166 00167 data = thread_test_data_new (); 00168 00169 test_message_handler = 00170 dbus_message_handler_new (handle_test_message, 00171 data, (DBusFreeFunction)thread_test_data_free); 00172 00173 if (!dbus_connection_register_handler (new_connection, 00174 test_message_handler, 00175 test_messages, 1)) 00176 goto nomem; 00177 00178 if (!dbus_connection_set_data (new_connection, 00179 handler_slot, 00180 test_message_handler, 00181 (DBusFreeFunction)dbus_message_handler_unref)) 00182 goto nomem; 00183 00184 if (!dbus_connection_register_handler (new_connection, 00185 disconnect_handler, 00186 disconnect_messages, 1)) 00187 goto nomem; 00188 00189 if (!dbus_connection_add_filter (new_connection, 00190 filter_handler)) 00191 goto nomem; 00192 00193 return; 00194 00195 nomem: 00196 g_error ("no memory to setup new connection"); 00197 } 00198 00199 int 00200 main (int argc, char *argv[]) 00201 { 00202 GMainLoop *loop; 00203 DBusServer *server; 00204 DBusError error; 00205 00206 g_thread_init (NULL); 00207 dbus_gthread_init (); 00208 00209 if (argc < 2) 00210 { 00211 fprintf (stderr, "Give the server address as an argument\n"); 00212 return 1; 00213 } 00214 00215 dbus_error_init (&error); 00216 server = dbus_server_listen (argv[1], &error); 00217 if (server == NULL) 00218 { 00219 fprintf (stderr, "Failed to start server on %s: %s\n", 00220 argv[1], error.message); 00221 dbus_error_free (&error); 00222 return 1; 00223 } 00224 00225 if (!dbus_connection_allocate_data_slot (&handler_slot)) 00226 g_error ("no memory for data slot"); 00227 00228 filter_handler = 00229 dbus_message_handler_new (handle_filter, NULL, NULL); 00230 if (filter_handler == NULL) 00231 g_error ("no memory for handler"); 00232 00233 disconnect_handler = 00234 dbus_message_handler_new (handle_disconnect, NULL, NULL); 00235 if (disconnect_handler == NULL) 00236 g_error ("no memory for handler"); 00237 00238 dbus_server_set_new_connection_function (server, 00239 new_connection_callback, 00240 NULL, NULL); 00241 00242 dbus_server_setup_with_g_main (server, NULL); 00243 00244 loop = g_main_loop_new (NULL, FALSE); 00245 g_main_run (loop); 00246 00247 return 0; 00248 }