Add error tolerance with dbus signal handling 22/109822/1
authorKwangyoun Kim <ky85.kim@samsung.com>
Tue, 27 Dec 2016 04:47:02 +0000 (13:47 +0900)
committerSooyeon Kim <sooyeon.kim@samsung.com>
Thu, 12 Jan 2017 02:03:56 +0000 (18:03 -0800)
Change-Id: I3ab7f1d3fe9626872d0ec3af41f961ec17d7373a
Signed-off-by: Kwangyoun Kim <ky85.kim@samsung.com>
(cherry picked from commit f24c0f45f107f89775d54fe03925b53a53def940)

client/stt.c
client/stt_dbus.c
server/sttd_server.c

index 2fdd82f..780719e 100644 (file)
@@ -1794,34 +1794,81 @@ static Eina_Bool __stt_notify_error(void *data)
 
 int __stt_cb_error(int uid, int reason, char* err_msg)
 {
-       stt_client_s* client = stt_client_get_by_uid(uid);
-       if (NULL == client) {
-               SLOG(LOG_ERROR, TAG_STTC, "Handle not found");
-               return -1;
-       }
+       if (-1 == uid) {
+               GList* client_list = NULL;
+               client_list = stt_client_get_client_list();
 
-       client->reason = reason;
-       client->internal_state = STT_INTERNAL_STATE_NONE;
-       if (NULL != client->err_msg) {
-               free(client->err_msg);
-               client->err_msg = NULL;
-       }
-       client->err_msg = strdup(err_msg);
+               GList *iter = NULL;
+               stt_client_s *data = NULL;
 
-       SLOG(LOG_INFO, TAG_STTC, "internal state is initialized to 0");
+               if (g_list_length(client_list) > 0) {
+                       /* Get a first item */
+                       iter = g_list_first(client_list);
 
-       if (NULL != client->error_cb) {
-               ecore_timer_add(0, __stt_notify_error, client);
+                       while (NULL != iter) {
+                               data = iter->data;
+
+                               data->reason = reason;
+                               data->internal_state = STT_INTERNAL_STATE_NONE;
+                               if (NULL != data->err_msg) {
+                                       free(data->err_msg);
+                                       data->err_msg = NULL;
+                               }
+                               if (NULL != err_msg)
+                                       data->err_msg = strdup(err_msg);
+
+                               SLOG(LOG_INFO, TAG_STTC, "internal state is initialized to 0");
+
+                               if (NULL != data->error_cb) {
+                                       ecore_timer_add(0, __stt_notify_error, data);
+                               } else {
+                                       SLOG(LOG_WARN, TAG_STTC, "[WARNING] Error callback is null");
+                               }
+
+                               if (STT_ERROR_SERVICE_RESET == reason) {
+                                       SLOG(LOG_WARN, TAG_STTC, "[WARNING] Service reset");
+
+                                       data->current_state = STT_STATE_CREATED;
+                                       if (0 != stt_prepare(data->stt)) {
+                                               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to prepare");
+                                       }
+                               }
+
+                               /* Next item */
+                               iter = g_list_next(iter);
+                       }
+               }
        } else {
-               SLOG(LOG_WARN, TAG_STTC, "[WARNING] Error callback is null");
-       }
+               stt_client_s* client = stt_client_get_by_uid(uid);
+               if (NULL == client) {
+                       SLOG(LOG_ERROR, TAG_STTC, "Handle not found");
+                       return -1;
+               }
 
-       if (STT_ERROR_SERVICE_RESET == reason) {
-               SLOG(LOG_WARN, TAG_STTC, "[WARNING] Service reset");
+               client->reason = reason;
+               client->internal_state = STT_INTERNAL_STATE_NONE;
+               if (NULL != client->err_msg) {
+                       free(client->err_msg);
+                       client->err_msg = NULL;
+               }
+               if (NULL != err_msg)
+                       client->err_msg = strdup(err_msg);
+
+               SLOG(LOG_INFO, TAG_STTC, "internal state is initialized to 0");
+
+               if (NULL != client->error_cb) {
+                       ecore_timer_add(0, __stt_notify_error, client);
+               } else {
+                       SLOG(LOG_WARN, TAG_STTC, "[WARNING] Error callback is null");
+               }
 
-               client->current_state = STT_STATE_CREATED;
-               if (0 != stt_prepare(client->stt)) {
-                       SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to prepare");
+               if (STT_ERROR_SERVICE_RESET == reason) {
+                       SLOG(LOG_WARN, TAG_STTC, "[WARNING] Service reset");
+
+                       client->current_state = STT_STATE_CREATED;
+                       if (0 != stt_prepare(client->stt)) {
+                               SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to prepare");
+                       }
                }
        }
 
index 5f3a6a8..fe1dc72 100644 (file)
@@ -615,6 +615,13 @@ static Eina_Bool listener_event_callback(void* data, Ecore_Fd_Handler *fd_handle
                        SLOG(LOG_DEBUG, TAG_STTC, " ");
                } /* STTD_METHOD_SPEECH_STATUS */
 
+               else if (dbus_message_is_signal(msg, "org.freedesktop.DBus", "NameOwnerChanged")) {
+                       SLOG(LOG_DEBUG, TAG_STTC, "===== Owner Changed");
+                       __stt_cb_error(-1, STT_ERROR_SERVICE_RESET, "Daemon Reset");
+                       SLOG(LOG_DEBUG, TAG_STTC, "=====");
+                       SLOG(LOG_DEBUG, TAG_STTC, " ");
+               } /* NameOwnerChanged */
+
                else {
                        SLOG(LOG_DEBUG, TAG_STTC, "Message is NOT valid");
                        dbus_message_unref(msg);
@@ -965,6 +972,18 @@ int stt_dbus_request_initialize(int uid, bool* silence_supported, bool* credenti
                        if (0 == result) {
                                SLOG(LOG_DEBUG, TAG_STTC, "<<<< stt initialize : result = %d, silence(%d), credential(%d)",
                                        result, *silence_supported, *credential_needed);
+
+                               /* add a rule for daemon error */
+                               char rule_err[256] = {0, };
+                               snprintf(rule_err, 256, "sender='org.freedesktop.DBus',path='/org/freedesktop/DBus',interface='org.freedesktop.DBus',member='NameOwnerChanged',type='signal',arg0='%s'", STT_SERVER_SERVICE_INTERFACE);
+                               dbus_bus_add_match(g_conn_listener, rule_err, &err);
+                               dbus_connection_flush(g_conn_listener);
+
+                               if (dbus_error_is_set(&err)) {
+                                       SLOG(LOG_ERROR, TAG_STTC, "Match Error (%s)", err.message);
+                                       dbus_error_free(&err);
+                                       return STT_ERROR_OPERATION_FAILED;
+                               }
                        } else {
                                SLOG(LOG_ERROR, TAG_STTC, "<<<< stt initialize : result = %d", result);
                        }
@@ -987,6 +1006,19 @@ int stt_dbus_request_finalize(int uid)
 {
        DBusMessage* msg;
 
+       DBusError err;
+       dbus_error_init(&err);
+
+       /* remove a rule for daemon error */
+       char rule_err[256] = {0, };
+       snprintf(rule_err, 256, "sender='org.freedesktop.DBus',path='/org/freedesktop/DBus',interface='org.freedesktop.DBus',member='NameOwnerChanged',type='signal',arg0='%s'", STT_SERVER_SERVICE_INTERFACE);
+       dbus_bus_remove_match(g_conn_listener, rule_err, &err);
+       dbus_connection_flush(g_conn_listener);
+       if (dbus_error_is_set(&err)) {
+               SLOG(LOG_ERROR, TAG_STTC, "Match Error (%s)", err.message);
+               dbus_error_free(&err);
+       }
+
        SLOG(LOG_DEBUG, TAG_STTC, "[dbus_info] service name: %s, service object: %s, service interface: %s", g_server_service_name, g_server_service_object, g_server_service_interface);
 
        msg = dbus_message_new_method_call(
@@ -1004,9 +1036,6 @@ int stt_dbus_request_finalize(int uid)
 
        dbus_message_append_args(msg, DBUS_TYPE_INT32, &uid, DBUS_TYPE_INVALID);
 
-       DBusError err;
-       dbus_error_init(&err);
-
        DBusMessage* result_msg;
        int result = STT_ERROR_OPERATION_FAILED;
 
index bbb6a52..ed69892 100755 (executable)
@@ -429,51 +429,10 @@ void __sttd_server_silence_changed_cb(bool value, void* user_data)
 /*
 * Daemon function
 */
-
-static void __sig_handler(int signo)
-{
-       /* restore signal handler */
-       signal(signo, SIG_DFL);
-
-       /* Send error signal to clients */
-       int* client_list = NULL;
-       int client_count = 0;
-       int i = 0;
-       if (0 != sttd_client_get_list(&client_list, &client_count)) {
-               if (NULL != client_list) {
-                       free(client_list);
-                       client_list = NULL;
-               }
-       }
-
-       if (NULL != client_list) {
-               for (i = 0; i < client_count; i++) {
-                       sttdc_send_error_signal(client_list[i], STTD_ERROR_SERVICE_RESET, "Service Reset");
-               }
-
-               free(client_list);
-               client_list = NULL;
-       }
-
-       /* invoke signal again */
-       raise(signo);
-}
-
-static void __register_sig_handler()
-{
-       signal(SIGSEGV, __sig_handler);
-       signal(SIGABRT, __sig_handler);
-       signal(SIGTERM, __sig_handler);
-       signal(SIGINT, __sig_handler);
-       signal(SIGQUIT, __sig_handler);
-}
-
 int sttd_initialize(stte_request_callback_s *callback)
 {
        int ret = 0;
 
-       __register_sig_handler();
-
        if (0 != pthread_mutex_init(&stte_result_mutex, NULL)) {
                SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to initialize stte result mutex.");
        }