Merge with Tizen 2.3
[platform/core/uifw/stt.git] / client / stt.c
1 /*
2 *  Copyright (c) 2011-2014 Samsung Electronics Co., Ltd All Rights Reserved 
3 *  Licensed under the Apache License, Version 2.0 (the "License");
4 *  you may not use this file except in compliance with the License.
5 *  You may obtain a copy of the License at
6 *  http://www.apache.org/licenses/LICENSE-2.0
7 *  Unless required by applicable law or agreed to in writing, software
8 *  distributed under the License is distributed on an "AS IS" BASIS,
9 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
10 *  See the License for the specific language governing permissions and
11 *  limitations under the License.
12 */
13
14 #include <aul.h>
15 #include <dirent.h>
16 #include <Ecore.h>
17 #include <fcntl.h>
18 #include <pthread.h>
19 #include <sys/stat.h>
20 #include <sys/types.h> 
21 #include <sys/wait.h>
22 #include <system_info.h>
23 #include <unistd.h>
24
25 #include "stt.h"
26 #include "stt_client.h"
27 #include "stt_dbus.h"
28 #include "stt_config_mgr.h"
29 #include "stt_main.h"
30
31
32 static bool g_is_daemon_started = false;
33
34 static Ecore_Timer* g_connect_timer = NULL;
35
36 static Eina_Bool __stt_notify_state_changed(void *data);
37 static Eina_Bool __stt_notify_error(void *data);
38
39 static int g_stt_daemon_pid = -1;
40 static int g_count_check_daemon = 0;
41
42 const char* stt_tag()
43 {
44         return "sttc";
45 }
46
47 static const char* __stt_get_error_code(stt_error_e err)
48 {
49         switch(err) {
50         case STT_ERROR_NONE:                    return "STT_ERROR_NONE";
51         case STT_ERROR_OUT_OF_MEMORY:           return "STT_ERROR_OUT_OF_MEMORY";
52         case STT_ERROR_IO_ERROR:                return "STT_ERROR_IO_ERROR";
53         case STT_ERROR_INVALID_PARAMETER:       return "STT_ERROR_INVALID_PARAMETER";
54         case STT_ERROR_TIMED_OUT:               return "STT_ERROR_TIMED_OUT";
55         case STT_ERROR_RECORDER_BUSY:           return "STT_ERROR_RECORDER_BUSY";
56         case STT_ERROR_OUT_OF_NETWORK:          return "STT_ERROR_OUT_OF_NETWORK";
57         case STT_ERROR_PERMISSION_DENIED:       return "STT_ERROR_PERMISSION_DENIED";
58         case STT_ERROR_NOT_SUPPORTED:           return "STT_ERROR_NOT_SUPPORTED";
59         case STT_ERROR_INVALID_STATE:           return "STT_ERROR_INVALID_STATE";
60         case STT_ERROR_INVALID_LANGUAGE:        return "STT_ERROR_INVALID_LANGUAGE";
61         case STT_ERROR_ENGINE_NOT_FOUND:        return "STT_ERROR_ENGINE_NOT_FOUND";
62         case STT_ERROR_OPERATION_FAILED:        return "STT_ERROR_OPERATION_FAILED";
63         case STT_ERROR_NOT_SUPPORTED_FEATURE:   return "STT_ERROR_NOT_SUPPORTED_FEATURE";
64         default:
65                 return "Invalid error code";
66         }
67 }
68
69 static int __stt_convert_config_error_code(stt_config_error_e code)
70 {
71         if (code == STT_CONFIG_ERROR_NONE)                      return STT_ERROR_NONE;
72         if (code == STT_CONFIG_ERROR_OUT_OF_MEMORY)             return STT_ERROR_OUT_OF_MEMORY;
73         if (code == STT_CONFIG_ERROR_IO_ERROR)                  return STT_ERROR_IO_ERROR;
74         if (code == STT_CONFIG_ERROR_INVALID_PARAMETER)         return STT_ERROR_INVALID_PARAMETER;
75         if (code == STT_CONFIG_ERROR_PERMISSION_DENIED)         return STT_ERROR_PERMISSION_DENIED;
76         if (code == STT_CONFIG_ERROR_NOT_SUPPORTED)             return STT_ERROR_NOT_SUPPORTED;
77         if (code == STT_CONFIG_ERROR_INVALID_STATE)             return STT_ERROR_INVALID_STATE;
78         if (code == STT_CONFIG_ERROR_INVALID_LANGUAGE)          return STT_ERROR_INVALID_LANGUAGE;
79         if (code == STT_CONFIG_ERROR_ENGINE_NOT_FOUND)          return STT_ERROR_ENGINE_NOT_FOUND;
80         if (code == STT_CONFIG_ERROR_OPERATION_FAILED)          return STT_ERROR_OPERATION_FAILED;
81
82         return code;
83 }
84
85 void __stt_config_lang_changed_cb(const char* before_language, const char* current_language, void* user_data)
86 {
87         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Language changed : Before lang(%s) Current lang(%s)", 
88                 before_language, current_language);
89
90         if (0 == strcmp(before_language, current_language)) {
91                 return;
92         }
93
94         GList* client_list = NULL;
95         client_list = stt_client_get_client_list();
96
97         GList *iter = NULL;
98         stt_client_s *data = NULL;
99
100         if (g_list_length(client_list) > 0) {
101                 /* Get a first item */
102                 iter = g_list_first(client_list);
103
104                 while (NULL != iter) {
105                         data = iter->data;
106                         if (NULL != data->default_lang_changed_cb) {
107                                 SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Call default language changed callback : uid(%d)", data->uid);
108                                 data->default_lang_changed_cb(data->stt, before_language, current_language, 
109                                         data->default_lang_changed_user_data);
110                         }
111
112                         /* Next item */
113                         iter = g_list_next(iter);
114                 }
115         }
116
117         return; 
118 }
119
120 int stt_create(stt_h* stt)
121 {
122         bool stt_supported = false;
123         bool mic_supported = false;
124         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
125                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
126                         if (false == stt_supported || false == mic_supported) {
127                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
128                                 return STT_ERROR_NOT_SUPPORTED;
129                         }
130                 }
131         }
132
133         SLOG(LOG_DEBUG, TAG_STTC, "===== Create STT");
134
135         if (NULL == stt) {
136                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is null");
137                 return STT_ERROR_INVALID_PARAMETER;
138         }
139
140         if (0 == stt_client_get_size()) {
141                 if (0 != stt_dbus_open_connection()) {
142                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to open connection");
143                         return STT_ERROR_OPERATION_FAILED;
144                 }
145         }
146
147         if (0 != stt_client_new(stt)) {
148                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to create client!");
149                 return STT_ERROR_OUT_OF_MEMORY;
150         }
151
152         stt_client_s* client = stt_client_get(*stt);
153         if (NULL == client) {
154                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to create client");
155                 stt_client_destroy(*stt);
156                 return STT_ERROR_OPERATION_FAILED;
157         }
158
159         int ret = stt_config_mgr_initialize(client->uid);
160         ret = __stt_convert_config_error_code(ret);
161         if (0 != ret) {
162                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to init config manager : %s", __stt_get_error_code(ret));
163                 stt_client_destroy(*stt);
164                 return ret;
165         }
166
167         ret = stt_config_mgr_set_callback(client->uid, NULL, __stt_config_lang_changed_cb, NULL, NULL);
168         ret = __stt_convert_config_error_code(ret);
169         if (0 != ret) {
170                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to set config changed : %s", __stt_get_error_code(ret));
171                 stt_client_destroy(*stt);
172                 return ret;
173         }
174
175         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[Success] uid(%d)", (*stt)->handle);
176
177         SLOG(LOG_DEBUG, TAG_STTC, "=====");
178         SLOG(LOG_DEBUG, TAG_STTC, " ");
179
180         return STT_ERROR_NONE;
181 }
182
183 int stt_destroy(stt_h stt)
184 {
185         bool stt_supported = false;
186         bool mic_supported = false;
187         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
188                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
189                         if (false == stt_supported || false == mic_supported) {
190                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
191                                 return STT_ERROR_NOT_SUPPORTED;
192                         }
193                 }
194         }
195
196         SLOG(LOG_DEBUG, TAG_STTC, "===== Destroy STT");
197
198         if (NULL == stt) {
199                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input handle is null");
200                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
201                 SLOG(LOG_DEBUG, TAG_STTC, " ");
202                 return STT_ERROR_INVALID_PARAMETER;
203         }
204         
205         stt_client_s* client = stt_client_get(stt);
206
207         /* check handle */
208         if (NULL == client) {
209                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
210                 return STT_ERROR_INVALID_PARAMETER;
211         }
212
213         /* check used callback */
214         if (0 != stt_client_get_use_callback(client)) {
215                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Cannot destroy in Callback function");
216                 return STT_ERROR_OPERATION_FAILED;
217         }
218
219         stt_config_mgr_finalize(client->uid);
220
221         int ret = -1;
222
223         /* check state */
224         switch (client->current_state) {
225         case STT_STATE_PROCESSING:
226         case STT_STATE_RECORDING:
227         case STT_STATE_READY:
228                 ret = stt_dbus_request_finalize(client->uid);
229                 if (0 != ret) {
230                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request finalize : %s", __stt_get_error_code(ret));
231                 }
232
233                 g_is_daemon_started = false;
234         case STT_STATE_CREATED:
235                 if (NULL != g_connect_timer) {
236                         SLOG(LOG_DEBUG, TAG_STTC, "Connect Timer is deleted");
237                         ecore_timer_del(g_connect_timer);
238                         g_connect_timer = NULL;
239                 }
240
241                 /* Free resources */
242                 stt_client_destroy(stt);
243                 break;
244         default:
245                 break;
246         }
247
248         if (0 == stt_client_get_size()) {
249                 if (0 != stt_dbus_close_connection()) {
250                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to close connection");
251                 }
252         }
253
254         SLOG(LOG_DEBUG, TAG_STTC, "=====");
255         SLOG(LOG_DEBUG, TAG_STTC, " ");
256
257         return STT_ERROR_NONE;
258 }
259
260 bool __stt_config_supported_engine_cb(const char* engine_id, const char* engine_name, 
261                                       const char* setting, bool support_silence, void* user_data)
262 {
263         stt_h stt = (stt_h)user_data;
264
265         stt_client_s* client = stt_client_get(stt);
266         if (NULL == client) {
267                 SLOG(LOG_ERROR, TAG_STTC, "[WARNING] A handle is not valid");
268                 return false;
269         }
270
271         /* call callback function */
272         if (NULL != client->supported_engine_cb) {
273                 return client->supported_engine_cb(stt, engine_id, engine_name, client->supported_engine_user_data);
274         } else {
275                 SLOG(LOG_WARN, TAG_STTC, "No registered callback function of supported engine");
276         }
277         
278         return false;
279 }
280
281 int stt_foreach_supported_engines(stt_h stt, stt_supported_engine_cb callback, void* user_data)
282 {
283         bool stt_supported = false;
284         bool mic_supported = false;
285         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
286                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
287                         if (false == stt_supported || false == mic_supported) {
288                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
289                                 return STT_ERROR_NOT_SUPPORTED;
290                         }
291                 }
292         }
293
294         SLOG(LOG_DEBUG, TAG_STTC, "===== Foreach Supported engine");
295
296         if (NULL == stt || NULL == callback) {
297                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
298                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
299                 SLOG(LOG_DEBUG, TAG_STTC, " ");
300                 return STT_ERROR_INVALID_PARAMETER;
301         }
302
303         stt_client_s* client = stt_client_get(stt);
304
305         /* check handle */
306         if (NULL == client) {
307                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
308                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
309                 SLOG(LOG_DEBUG, TAG_STTC, " ");
310                 return STT_ERROR_INVALID_PARAMETER;
311         }
312
313         if (client->current_state != STT_STATE_CREATED) {
314                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not CREATE");
315                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
316                 SLOG(LOG_DEBUG, TAG_STTC, " ");
317                 return STT_ERROR_INVALID_STATE;
318         }
319
320         client->supported_engine_cb = callback;
321         client->supported_engine_user_data = user_data;
322
323         int ret = 0;
324         ret = stt_config_mgr_get_engine_list(__stt_config_supported_engine_cb, client->stt);
325         ret = __stt_convert_config_error_code(ret);
326         if (0 != ret) {
327                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get engines : %s", __stt_get_error_code(ret));
328         }
329
330         client->supported_engine_cb = NULL;
331         client->supported_engine_user_data = NULL;
332
333         SLOG(LOG_DEBUG, TAG_STTC, "=====");
334         SLOG(LOG_DEBUG, TAG_STTC, " ");
335
336         return ret;
337 }
338
339 int stt_get_engine(stt_h stt, char** engine_id)
340 {
341         bool stt_supported = false;
342         bool mic_supported = false;
343         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
344                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
345                         if (false == stt_supported || false == mic_supported) {
346                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
347                                 return STT_ERROR_NOT_SUPPORTED;
348                         }
349                 }
350         }
351
352         SLOG(LOG_DEBUG, TAG_STTC, "===== Get current engine");
353
354         if (NULL == stt || NULL == engine_id) {
355                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
356                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
357                 SLOG(LOG_DEBUG, TAG_STTC, " ");
358                 return STT_ERROR_INVALID_PARAMETER;
359         }
360
361         stt_client_s* client = stt_client_get(stt);
362
363         /* check handle */
364         if (NULL == client) {
365                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
366                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
367                 SLOG(LOG_DEBUG, TAG_STTC, " ");
368                 return STT_ERROR_INVALID_PARAMETER;
369         }
370
371         if (client->current_state != STT_STATE_CREATED) {
372                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not CREATE");
373                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
374                 SLOG(LOG_DEBUG, TAG_STTC, " ");
375                 return STT_ERROR_INVALID_STATE;
376         }
377
378         int ret = 0;
379         ret = stt_config_mgr_get_engine(engine_id);
380         ret = __stt_convert_config_error_code(ret);
381         if (0 != ret) {
382                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request get current engine : %s", __stt_get_error_code(ret));
383         } else {
384                 SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Current engine uuid = %s", *engine_id);
385         }
386
387         SLOG(LOG_DEBUG, TAG_STTC, "=====");
388         SLOG(LOG_DEBUG, TAG_STTC, " ");
389
390         return ret;
391 }
392
393 int stt_set_engine(stt_h stt, const char* engine_id)
394 {
395         bool stt_supported = false;
396         bool mic_supported = false;
397         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
398                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
399                         if (false == stt_supported || false == mic_supported) {
400                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
401                                 return STT_ERROR_NOT_SUPPORTED;
402                         }
403                 }
404         }
405
406         SLOG(LOG_DEBUG, TAG_STTC, "===== Set current engine");
407
408         if (NULL == stt || NULL == engine_id) {
409                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
410                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
411                 SLOG(LOG_DEBUG, TAG_STTC, " ");
412                 return STT_ERROR_INVALID_PARAMETER;
413         }
414
415         stt_client_s* client = stt_client_get(stt);
416
417         /* check handle */
418         if (NULL == client) {
419                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
420                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
421                 SLOG(LOG_DEBUG, TAG_STTC, " ");
422                 return STT_ERROR_INVALID_PARAMETER;
423         }
424
425         /* check state */
426         if (client->current_state != STT_STATE_CREATED) {
427                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not CREATE");
428                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
429                 SLOG(LOG_DEBUG, TAG_STTC, " ");
430                 return STT_ERROR_INVALID_STATE;
431         }
432
433         if (NULL != client->current_engine_id) {
434                 free(client->current_engine_id);
435         }
436
437         client->current_engine_id = strdup(engine_id);
438 #if 0
439         if (client->current_state == STT_STATE_READY) {
440                 int ret = 0;
441                 bool silence_supported = false;
442
443                 ret = stt_dbus_request_set_current_engine(client->uid, engine_id, &silence_supported);
444
445                 if (0 != ret) {
446                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to set current engine : %s", __stt_get_error_code(ret));
447                         return ret;
448                 } else {
449                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Current engine uuid = %s", engine_id);
450
451                         /* success to change engine */
452                         client->silence_supported = silence_supported;
453                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Supported options : silence(%s)", silence_supported ? "true" : "false");
454                 }
455         }
456 #endif
457         SLOG(LOG_DEBUG, TAG_STTC, "=====");
458         SLOG(LOG_DEBUG, TAG_STTC, " ");
459
460         return 0;
461 }
462
463 static int __read_proc(const char *path, char *buf, int size)
464 {
465         int fd;
466         int ret;
467
468         if (NULL == buf || NULL == path) {
469                 return -1;
470         }
471
472         fd = open(path, O_RDONLY);
473         if (fd < 0) {
474                 return -1;
475         }
476
477         ret = read(fd, buf, size - 1);
478         if (0 >= ret) {
479                 close(fd);
480                 return -1;
481         } else {
482                 buf[ret] = 0;
483         }
484         close(fd);
485         return ret;
486 }
487
488 static bool __stt_check_daemon_exist()
489 {
490         char buf[128];
491         int ret;
492
493         FILE* fp;
494         fp = fopen(STT_PID_FILE_PATH, "r");
495         if (NULL == fp) {
496                 return false;
497         }
498
499         g_stt_daemon_pid = -1;
500         int pid;
501         if (0 >= fscanf(fp, "%d", &pid)) {
502                 SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Fail to read pid");
503                 fclose(fp);
504                 return false;
505         }
506
507         fclose(fp);
508         snprintf(buf, sizeof(buf), "/proc/%d/cmdline", pid);
509         ret = __read_proc(buf, buf, sizeof(buf));
510         if (0 >= ret) {
511                 return false;
512         } else {
513                 if (!strcmp(buf, "/usr/bin/stt-daemon")) {
514                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Daemon existed - [%d]%s", pid, buf);
515                         g_stt_daemon_pid = pid;
516                         return true;
517                 }
518         }
519         return false;
520 }
521
522 static void* __fork_stt_daemon(void* NotUsed)
523 {
524         int pid, i;
525         pid = fork();
526
527         switch(pid) {
528         case -1:
529                 SLOG(LOG_DEBUG, TAG_STTC, "[STT ERROR] fail to create STT-DAEMON");
530                 break;
531
532         case 0:
533                 setsid();
534                 for (i = 0;i < _NSIG;i++)
535                         signal(i, SIG_DFL);
536
537                 execl("/usr/bin/stt-daemon", "/usr/bin/stt-daemon", NULL);
538                 break;
539
540         default:
541                 break;
542         }
543
544         return (void*) 1;
545 }
546
547 static Eina_Bool __stt_connect_daemon(void *data)
548 {
549         stt_client_s* client = (stt_client_s*)data;
550
551         if (NULL == client) {
552                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
553                 return EINA_FALSE;
554         }
555
556         /* Send hello */
557         int ret = -1;
558         ret = stt_dbus_request_hello();
559
560         if (STT_DAEMON_NORMAL != ret) {
561                 if (STT_ERROR_INVALID_STATE == ret) {
562                         return EINA_FALSE;
563                 }
564
565                 if (STT_DAEMON_ON_TERMINATING == ret) {
566                         /* Todo - Wait for terminating and do it again*/
567                         usleep(50);
568                         return EINA_TRUE;
569                 } else {
570                         /* for new daemon */
571                         bool check = __stt_check_daemon_exist();
572                         if (true == check) {
573                                 g_count_check_daemon++;
574                                 if (3 < g_count_check_daemon) {
575                                         /* Todo - Kill daemon and restart */
576                                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Need to Kill daemon");
577                                 }
578                                 usleep(50);
579                                 return EINA_TRUE;
580                         } else {
581                                 if (false == g_is_daemon_started) {
582                                         g_is_daemon_started = true;
583                                         
584                                         pthread_t thread;
585                                         int thread_id;
586                                         thread_id = pthread_create(&thread, NULL, __fork_stt_daemon, NULL);
587                                         if (thread_id < 0) {
588                                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to make thread");
589                                                 g_connect_timer = NULL;
590                                                 return EINA_FALSE;
591                                         }
592
593                                         pthread_detach(thread);
594                                 }
595
596                                 usleep(50);
597                                 return EINA_TRUE;
598                         }
599                 }
600         }
601
602         g_connect_timer = NULL;
603         SLOG(LOG_DEBUG, TAG_STTC, "===== Connect daemon");
604
605         /* request initialization */
606
607         bool silence_supported = false;
608
609         ret = stt_dbus_request_initialize(client->uid, &silence_supported);
610
611         if (STT_ERROR_ENGINE_NOT_FOUND == ret) {
612                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to initialize : %s", __stt_get_error_code(ret));
613                 
614                 client->reason = STT_ERROR_ENGINE_NOT_FOUND;
615                 ecore_timer_add(0, __stt_notify_error, (void*)client);
616
617                 return EINA_FALSE;
618
619         } else if (STT_ERROR_NONE != ret) {
620                 SLOG(LOG_ERROR, TAG_STTC, "[WARNING] Fail to connection. Retry to connect");
621                 return EINA_TRUE;
622         } else {
623                 /* success to connect stt-daemon */
624                 client->silence_supported = silence_supported;
625                 SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Supported options : silence(%s)", silence_supported ? "true" : "false");
626         }
627
628         if (NULL != client->current_engine_id) {
629                 ret = -1;
630                 int count = 0;
631                 silence_supported = false;
632                 while (0 != ret) {
633                         ret = stt_dbus_request_set_current_engine(client->uid, client->current_engine_id, &silence_supported);
634                         if (0 != ret) {
635                                 if (STT_ERROR_TIMED_OUT != ret) {
636                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to set current engine : %s", __stt_get_error_code(ret));
637                                         return ret;
638                                 } else {
639                                         SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
640                                         usleep(10);
641                                         count++;
642                                         if (10 == count) {
643                                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
644                                                 return ret;
645                                         }
646                                 }
647                         } else {
648                                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Current engine uuid = %s", client->current_engine_id);
649
650                                 /* success to change engine */
651                                 client->silence_supported = silence_supported;
652                                 SLOG(LOG_DEBUG, TAG_STTC, "Supported options : silence(%s)", silence_supported ? "true" : "false");
653                         }
654                 }
655         }
656
657         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] uid(%d)", client->uid);
658
659         client->before_state = client->current_state;
660         client->current_state = STT_STATE_READY;
661
662         if (NULL != client->state_changed_cb) {
663                 stt_client_use_callback(client);
664                 client->state_changed_cb(client->stt, client->before_state, 
665                         client->current_state, client->state_changed_user_data); 
666                 stt_client_not_use_callback(client);
667                 SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called");
668         } else {
669                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
670         }
671
672         SLOG(LOG_DEBUG, TAG_STTC, "=====");
673         SLOG(LOG_DEBUG, TAG_STTC, "  ");
674
675         return EINA_FALSE;
676 }
677
678 int stt_prepare(stt_h stt)
679 {
680         bool stt_supported = false;
681         bool mic_supported = false;
682         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
683                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
684                         if (false == stt_supported || false == mic_supported) {
685                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
686                                 return STT_ERROR_NOT_SUPPORTED;
687                         }
688                 }
689         }
690
691         SLOG(LOG_DEBUG, TAG_STTC, "===== Prepare STT");
692
693         stt_client_s* client = stt_client_get(stt);
694
695         /* check handle */
696         if (NULL == client) {
697                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
698                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
699                 SLOG(LOG_DEBUG, TAG_STTC, " ");
700                 return STT_ERROR_INVALID_PARAMETER;
701         }
702
703         /* check state */
704         if (client->current_state != STT_STATE_CREATED) {
705                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not 'CREATED'");
706                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
707                 SLOG(LOG_DEBUG, TAG_STTC, " ");
708                 return STT_ERROR_INVALID_STATE;
709         }
710
711         g_count_check_daemon = 0;
712         g_connect_timer = ecore_timer_add(0, __stt_connect_daemon, (void*)client);
713
714         SLOG(LOG_DEBUG, TAG_STTC, "=====");
715         SLOG(LOG_DEBUG, TAG_STTC, " ");
716
717         return STT_ERROR_NONE;
718 }
719
720 int stt_unprepare(stt_h stt)
721 {
722         bool supported = false;
723         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &supported)) {
724                 if (false == supported) {
725                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
726                         return STT_ERROR_NOT_SUPPORTED;
727                 }
728         }
729
730         SLOG(LOG_DEBUG, TAG_STTC, "===== Unprepare STT");
731
732         stt_client_s* client = stt_client_get(stt);
733
734         /* check handle */
735         if (NULL == client) {
736                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
737                 return STT_ERROR_INVALID_PARAMETER;
738         }
739
740         /* check state */
741         if (client->current_state != STT_STATE_READY) {
742                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not 'READY'");
743                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
744                 SLOG(LOG_DEBUG, TAG_STTC, " ");
745                 return STT_ERROR_INVALID_STATE;
746         }
747
748         int ret = -1;
749         int count = 0;
750         while (0 != ret) {
751                 ret = stt_dbus_request_finalize(client->uid);
752                 if (0 != ret) {
753                         if (STT_ERROR_TIMED_OUT != ret) {
754                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request finalize : %s", __stt_get_error_code(ret));
755                                 break;
756                         } else {
757                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
758                                 usleep(10);
759                                 count++;
760                                 if (10 == count) {
761                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
762                                         break;
763                                 }
764                         }
765                 }
766         }
767
768         g_is_daemon_started = false;
769
770         client->internal_state = STT_INTERNAL_STATE_NONE;
771
772         client->before_state = client->current_state;
773         client->current_state = STT_STATE_CREATED;
774
775         if (NULL != client->state_changed_cb) {
776                 stt_client_use_callback(client);
777                 client->state_changed_cb(client->stt, client->before_state, 
778                         client->current_state, client->state_changed_user_data); 
779                 stt_client_not_use_callback(client);
780         } else {
781                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
782         }
783
784         SLOG(LOG_DEBUG, TAG_STTC, "=====");
785         SLOG(LOG_DEBUG, TAG_STTC, " ");
786
787         return STT_ERROR_NONE;
788 }
789
790 bool __stt_config_supported_language_cb(const char* engine_id, const char* language, void* user_data)
791 {
792         stt_h stt = (stt_h)user_data;
793
794         stt_client_s* client = stt_client_get(stt);
795         if (NULL == client) {
796                 SLOG(LOG_ERROR, TAG_STTC, "[WARNING] A handle is not valid");
797                 return false;
798         }
799
800         /* call callback function */
801         if (NULL != client->supported_lang_cb) {
802                 return client->supported_lang_cb(stt, language, client->supported_lang_user_data);
803         } else {
804                 SLOG(LOG_WARN, TAG_STTC, "No registered callback function of supported languages");
805         }
806
807         return false;
808 }
809
810 int stt_foreach_supported_languages(stt_h stt, stt_supported_language_cb callback, void* user_data)
811 {
812         bool stt_supported = false;
813         bool mic_supported = false;
814         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
815                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
816                         if (false == stt_supported || false == mic_supported) {
817                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
818                                 return STT_ERROR_NOT_SUPPORTED;
819                         }
820                 }
821         }
822
823         SLOG(LOG_DEBUG, TAG_STTC, "===== Foreach Supported Language");
824
825         if (NULL == stt || NULL == callback) {
826                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
827                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
828                 SLOG(LOG_DEBUG, TAG_STTC, " ");
829                 return STT_ERROR_INVALID_PARAMETER;
830         }
831
832         stt_client_s* client = stt_client_get(stt);
833
834         /* check handle */
835         if (NULL == client) {
836                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
837                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
838                 SLOG(LOG_DEBUG, TAG_STTC, " ");
839                 return STT_ERROR_INVALID_PARAMETER;
840         }
841
842         int ret;
843         char* current_engine_id = NULL;
844
845         if (NULL == client->current_engine_id) {
846                 ret = stt_config_mgr_get_engine(&current_engine_id);
847                 ret = __stt_convert_config_error_code(ret);
848                 if (0 != ret) {
849                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get default engine id : %s", __stt_get_error_code(ret));
850                         return ret;
851                 }
852         } else {
853                 current_engine_id = strdup(client->current_engine_id);
854         }
855
856         client->supported_lang_cb = callback;
857         client->supported_lang_user_data = user_data;
858
859         ret = stt_config_mgr_get_language_list(current_engine_id, __stt_config_supported_language_cb, client->stt);
860         ret = __stt_convert_config_error_code(ret);
861         if (0 != ret) {
862                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get languages : %s", __stt_get_error_code(ret));
863         }
864
865         if (NULL != current_engine_id) {
866                 free(current_engine_id);
867         }
868
869         client->supported_lang_cb = NULL;
870         client->supported_lang_user_data = NULL;
871
872         SLOG(LOG_DEBUG, TAG_STTC, "=====");
873         SLOG(LOG_DEBUG, TAG_STTC, " ");
874
875         return ret;
876 }
877
878 int stt_get_default_language(stt_h stt, char** language)
879 {
880         bool stt_supported = false;
881         bool mic_supported = false;
882         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
883                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
884                         if (false == stt_supported || false == mic_supported) {
885                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
886                                 return STT_ERROR_NOT_SUPPORTED;
887                         }
888                 }
889         }
890
891         SLOG(LOG_DEBUG, TAG_STTC, "===== Get Default Language");
892
893         if (NULL == stt || NULL == language) {
894                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
895                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
896                 SLOG(LOG_DEBUG, TAG_STTC, " ");
897                 return STT_ERROR_INVALID_PARAMETER;
898         }
899
900         stt_client_s* client = stt_client_get(stt);
901
902         /* check handle */
903         if (NULL == client) {
904                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
905                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
906                 SLOG(LOG_DEBUG, TAG_STTC, " ");
907                 return STT_ERROR_INVALID_PARAMETER;
908         }
909
910         int ret = 0;
911         ret = stt_config_mgr_get_default_language(language);
912         ret = __stt_convert_config_error_code(ret);
913         if (0 != ret) {
914                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get default language : %s", __stt_get_error_code(ret));
915         } else {
916                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Current language = %s", *language);
917         }
918
919         SLOG(LOG_DEBUG, TAG_STTC, "=====");
920         SLOG(LOG_DEBUG, TAG_STTC, " ");
921
922         return ret;
923 }
924
925 int stt_get_state(stt_h stt, stt_state_e* state)
926 {
927         bool stt_supported = false;
928         bool mic_supported = false;
929         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
930                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
931                         if (false == stt_supported || false == mic_supported) {
932                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
933                                 return STT_ERROR_NOT_SUPPORTED;
934                         }
935                 }
936         }
937
938         if (NULL == stt || NULL == state) {
939                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
940                 return STT_ERROR_INVALID_PARAMETER;
941         }
942
943         stt_client_s* client = stt_client_get(stt);
944
945         if (NULL == client) {
946                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
947                 return STT_ERROR_INVALID_PARAMETER;
948         }
949
950         *state = client->current_state;
951
952         switch(*state) {
953                 case STT_STATE_CREATED:         SLOG(LOG_DEBUG, TAG_STTC, "Current state is 'CREATED'");        break;
954                 case STT_STATE_READY:           SLOG(LOG_DEBUG, TAG_STTC, "Current state is 'Ready'");          break;
955                 case STT_STATE_RECORDING:       SLOG(LOG_DEBUG, TAG_STTC, "Current state is 'Recording'");      break;
956                 case STT_STATE_PROCESSING:      SLOG(LOG_DEBUG, TAG_STTC, "Current state is 'Processing'");     break;
957                 default:                        SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid value");             break;
958         }
959
960         return STT_ERROR_NONE;
961 }
962
963 int stt_is_recognition_type_supported(stt_h stt, const char* type, bool* support)
964 {
965         bool stt_supported = false;
966         bool mic_supported = false;
967         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
968                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
969                         if (false == stt_supported || false == mic_supported) {
970                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
971                                 return STT_ERROR_NOT_SUPPORTED;
972                         }
973                 }
974         }
975
976         if (NULL == stt || NULL == type || NULL == support) {
977                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
978                 return STT_ERROR_INVALID_PARAMETER;
979         }
980
981         stt_client_s* client = stt_client_get(stt);
982
983         if (NULL == client) {
984                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not valid");
985                 return STT_ERROR_INVALID_PARAMETER;
986         }
987
988         /* check state */
989         if (client->current_state != STT_STATE_READY) {
990                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
991                 return STT_ERROR_INVALID_STATE;
992         }
993
994         int ret = -1;
995         int count = 0;
996         while (0 != ret) {
997                 ret = stt_dbus_request_is_recognition_type_supported(client->uid, type, support);
998                 if (0 != ret) {
999                         if (STT_ERROR_TIMED_OUT != ret) {
1000                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get recognition type supported : %s", __stt_get_error_code(ret));
1001                                 return ret;
1002                         } else {
1003                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1004                                 usleep(10);
1005                                 count++;
1006                                 if (10 == count) {
1007                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1008                                         return ret;
1009                                 }
1010                         }
1011                 } else {
1012                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] recognition type is %s", *support ? "true " : "false");
1013                         break;
1014                 }
1015         }
1016
1017         return STT_ERROR_NONE;
1018 }
1019
1020 int stt_set_silence_detection(stt_h stt, stt_option_silence_detection_e type)
1021 {
1022         bool stt_supported = false;
1023         bool mic_supported = false;
1024         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1025                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1026                         if (false == stt_supported || false == mic_supported) {
1027                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1028                                 return STT_ERROR_NOT_SUPPORTED;
1029                         }
1030                 }
1031         }
1032
1033         if (NULL == stt) {
1034                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1035                 return STT_ERROR_INVALID_PARAMETER;
1036         }
1037
1038         stt_client_s* client = stt_client_get(stt);
1039
1040         if (NULL == client) {
1041                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
1042                 return STT_ERROR_INVALID_PARAMETER;
1043         }
1044
1045         /* check state */
1046         if (client->current_state != STT_STATE_READY) {
1047                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1048                 return STT_ERROR_INVALID_STATE;
1049         }
1050
1051         if (true == client->silence_supported) {
1052                 if (type >= STT_OPTION_SILENCE_DETECTION_FALSE && type <= STT_OPTION_SILENCE_DETECTION_AUTO) {
1053                         client->silence = type; 
1054                 } else {
1055                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Type is invalid");
1056                         return STT_ERROR_INVALID_PARAMETER;
1057                 }
1058         } else {
1059                 return STT_ERROR_NOT_SUPPORTED_FEATURE; 
1060         }
1061
1062         return STT_ERROR_NONE;
1063 }
1064
1065 int stt_set_start_sound(stt_h stt, const char* filename)
1066 {
1067         bool stt_supported = false;
1068         bool mic_supported = false;
1069         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1070                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1071                         if (false == stt_supported || false == mic_supported) {
1072                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1073                                 return STT_ERROR_NOT_SUPPORTED;
1074                         }
1075                 }
1076         }
1077
1078         SLOG(LOG_DEBUG, TAG_STTC, "===== STT SET START SOUND");
1079
1080         if (NULL == stt || NULL == filename) {
1081                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1082                 return STT_ERROR_INVALID_PARAMETER;
1083         }
1084
1085         stt_client_s* client = stt_client_get(stt);
1086
1087         if (NULL == client) {
1088                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
1089                 return STT_ERROR_INVALID_PARAMETER;
1090         }
1091
1092         /* check state */
1093         if (client->current_state != STT_STATE_READY) {
1094                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1095                 return STT_ERROR_INVALID_STATE;
1096         }
1097
1098         int ret = -1;
1099         int count = 0;
1100         while (0 != ret) {
1101                 ret = stt_dbus_request_set_start_sound(client->uid, filename);
1102                 if (0 != ret) {
1103                         if (STT_ERROR_TIMED_OUT != ret) {
1104                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to set start sound : %s", __stt_get_error_code(ret));
1105                                 return ret;
1106                         } else {
1107                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1108                                 usleep(10);
1109                                 count++;
1110                                 if (10 == count) {
1111                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1112                                         return ret;
1113                                 }
1114                         }
1115                 } else {
1116                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Set start sound : %s", filename);
1117                         break;
1118                 }
1119         }
1120
1121         return STT_ERROR_NONE;
1122 }
1123
1124 int stt_unset_start_sound(stt_h stt)
1125 {
1126         bool stt_supported = false;
1127         bool mic_supported = false;
1128         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1129                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1130                         if (false == stt_supported || false == mic_supported) {
1131                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1132                                 return STT_ERROR_NOT_SUPPORTED;
1133                         }
1134                 }
1135         }
1136
1137         SLOG(LOG_DEBUG, TAG_STTC, "===== STT UNSET START SOUND");
1138
1139         if (NULL == stt) {
1140                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1141                 return STT_ERROR_INVALID_PARAMETER;
1142         }
1143
1144         stt_client_s* client = stt_client_get(stt);
1145
1146         if (NULL == client) {
1147                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
1148                 return STT_ERROR_INVALID_PARAMETER;
1149         }
1150
1151         /* check state */
1152         if (client->current_state != STT_STATE_READY) {
1153                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1154                 return STT_ERROR_INVALID_STATE;
1155         }
1156
1157         int ret = -1;
1158         int count = 0;
1159         while (0 != ret) {
1160                 ret = stt_dbus_request_unset_start_sound(client->uid);
1161                 if (0 != ret) {
1162                         if (STT_ERROR_TIMED_OUT != ret) {
1163                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to unset start sound : %s", __stt_get_error_code(ret));
1164                                 return ret;
1165                         } else {
1166                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1167                                 usleep(10);
1168                                 count++;
1169                                 if (10 == count) {
1170                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1171                                         return ret;
1172                                 }
1173                         }
1174                 } else {
1175                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Unset start sound");
1176                         break;
1177                 }
1178         }
1179
1180         return STT_ERROR_NONE;
1181 }
1182
1183 int stt_set_stop_sound(stt_h stt, const char* filename)
1184 {
1185         bool stt_supported = false;
1186         bool mic_supported = false;
1187         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1188                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1189                         if (false == stt_supported || false == mic_supported) {
1190                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1191                                 return STT_ERROR_NOT_SUPPORTED;
1192                         }
1193                 }
1194         }
1195
1196         SLOG(LOG_DEBUG, TAG_STTC, "===== STT SET STOP SOUND");
1197
1198         if (NULL == stt || NULL == filename) {
1199                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1200                 return STT_ERROR_INVALID_PARAMETER;
1201         }
1202
1203         stt_client_s* client = stt_client_get(stt);
1204
1205         if (NULL == client) {
1206                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
1207                 return STT_ERROR_INVALID_PARAMETER;
1208         }
1209
1210         /* check state */
1211         if (client->current_state != STT_STATE_READY) {
1212                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1213                 return STT_ERROR_INVALID_STATE;
1214         }
1215
1216         int ret = -1;
1217         int count = 0;
1218         while (0 != ret) {
1219                 ret = stt_dbus_request_set_stop_sound(client->uid, filename);
1220                 if (0 != ret) {
1221                         if (STT_ERROR_TIMED_OUT != ret) {
1222                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to set stop sound : %s", __stt_get_error_code(ret));
1223                                 return ret;
1224                         } else {
1225                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1226                                 usleep(10);
1227                                 count++;
1228                                 if (10 == count) {
1229                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1230                                         return ret;
1231                                 }
1232                         }
1233                 } else {
1234                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Set stop sound : %s", filename);
1235                         break;
1236                 }
1237         }
1238
1239         return STT_ERROR_NONE;
1240 }
1241
1242 int stt_unset_stop_sound(stt_h stt)
1243 {
1244         bool stt_supported = false;
1245         bool mic_supported = false;
1246         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1247                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1248                         if (false == stt_supported || false == mic_supported) {
1249                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1250                                 return STT_ERROR_NOT_SUPPORTED;
1251                         }
1252                 }
1253         }
1254
1255         SLOG(LOG_DEBUG, TAG_STTC, "===== STT UNSET STOP SOUND");
1256
1257         if (NULL == stt) {
1258                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1259                 return STT_ERROR_INVALID_PARAMETER;
1260         }
1261
1262         stt_client_s* client = stt_client_get(stt);
1263
1264         if (NULL == client) {
1265                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Get state : A handle is not valid");
1266                 return STT_ERROR_INVALID_PARAMETER;
1267         }
1268
1269         /* check state */
1270         if (client->current_state != STT_STATE_READY) {
1271                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1272                 return STT_ERROR_INVALID_STATE;
1273         }
1274
1275         int ret = -1;
1276         int count = 0;
1277         while (0 != ret) {
1278                 ret = stt_dbus_request_unset_stop_sound(client->uid);
1279                 if (0 != ret) {
1280                         if (STT_ERROR_TIMED_OUT != ret) {
1281                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to unset stop sound : %s", __stt_get_error_code(ret));
1282                                 return ret;
1283                         } else {
1284                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1285                                 usleep(10);
1286                                 count++;
1287                                 if (10 == count) {
1288                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1289                                         return ret;
1290                                 }
1291                         }
1292                 } else {
1293                         SECURE_SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Unset stop sound");
1294                         break;
1295                 }
1296         }
1297
1298         return STT_ERROR_NONE;
1299 }
1300
1301 int stt_start(stt_h stt, const char* language, const char* type)
1302 {
1303         bool stt_supported = false;
1304         bool mic_supported = false;
1305         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1306                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1307                         if (false == stt_supported || false == mic_supported) {
1308                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1309                                 return STT_ERROR_NOT_SUPPORTED;
1310                         }
1311                 }
1312         }
1313
1314         SLOG(LOG_DEBUG, TAG_STTC, "===== STT START");
1315
1316         if (NULL == stt) {
1317                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1318                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1319                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1320                 return STT_ERROR_INVALID_PARAMETER;
1321         }
1322
1323         stt_client_s* client = stt_client_get(stt);
1324
1325         /* check handle */
1326         if (NULL == client) {
1327                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
1328                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1329                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1330                 return STT_ERROR_INVALID_PARAMETER;
1331         }
1332
1333         /* check state */
1334         if (client->current_state != STT_STATE_READY) {
1335                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State: Current state is not READY");
1336                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1337                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1338                 return STT_ERROR_INVALID_STATE;
1339         }
1340
1341         if (STT_INTERNAL_STATE_NONE != client->internal_state) {
1342                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is NOT none : %d", client->internal_state);
1343                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1344                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1345                 return STT_ERROR_INVALID_STATE;
1346         }
1347
1348         char appid[128] = {0, };
1349         aul_app_get_appid_bypid(getpid(), appid, sizeof(appid));
1350         
1351         if (0 == strlen(appid)) {
1352                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get application ID");
1353         } else {
1354                 SLOG(LOG_DEBUG, TAG_STTC, "[DEBUG] Current app id is %s", appid);
1355         }
1356
1357         char* temp = NULL;
1358         if (NULL == language) {
1359                 temp = strdup("default");
1360         } else {
1361                 temp = strdup(language);
1362         }
1363
1364         int ret = -1;
1365         /* do request */
1366         int count = 0;
1367         while (0 != ret) {
1368                 ret = stt_dbus_request_start(client->uid, temp, type, client->silence, appid);
1369                 if (0 > ret) {
1370                         /* Failure */                   
1371                         if (STT_ERROR_TIMED_OUT != ret) {
1372                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to start : %s", __stt_get_error_code(ret));
1373                                 if (NULL != temp)       free(temp);
1374                                 return ret;
1375                         } else {
1376                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry to start");
1377                                 usleep(10);
1378                                 count++;
1379                                 if (10 == count) {
1380                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1381                                         if (NULL != temp)       free(temp);
1382                                         return ret;
1383                                 }
1384                         }
1385                 } else {
1386                         /* Success */
1387                         if (NULL != temp)       free(temp);
1388
1389                         if (STT_RESULT_STATE_DONE == ret) {
1390                                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Start is done : %d", ret);
1391                                 client->before_state = client->current_state;
1392                                 client->current_state = STT_STATE_RECORDING;
1393
1394                                 if (NULL != client->state_changed_cb) {
1395                                         stt_client_use_callback(client);
1396                                         client->state_changed_cb(client->stt, client->before_state, 
1397                                                 client->current_state, client->state_changed_user_data);
1398                                         stt_client_not_use_callback(client);
1399                                         SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called");
1400                                 } else {
1401                                         SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
1402                                 }
1403                         } else if (STT_RESULT_STATE_NOT_DONE == ret) {
1404                                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Start is not done : %d", ret);
1405                                 client->internal_state = STT_INTERNAL_STATE_STARTING;
1406                         } else {
1407                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid result : %d", ret);
1408                         }
1409
1410                         ret = STT_ERROR_NONE;
1411                         break;
1412                 }
1413         }
1414
1415         SLOG(LOG_DEBUG, TAG_STTC, "=====");
1416         SLOG(LOG_DEBUG, TAG_STTC, " ");
1417
1418         return ret;
1419 }
1420
1421 int stt_stop(stt_h stt)
1422 {
1423         bool stt_supported = false;
1424         bool mic_supported = false;
1425         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1426                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1427                         if (false == stt_supported || false == mic_supported) {
1428                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1429                                 return STT_ERROR_NOT_SUPPORTED;
1430                         }
1431                 }
1432         }
1433
1434         SLOG(LOG_DEBUG, TAG_STTC, "===== STT STOP");
1435
1436         if (NULL == stt) {
1437                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1438                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1439                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1440                 return STT_ERROR_INVALID_PARAMETER;
1441         }
1442
1443         stt_client_s* client = stt_client_get(stt);
1444
1445         /* check handle */
1446         if (NULL == client) {
1447                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
1448                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1449                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1450                 return STT_ERROR_INVALID_PARAMETER;
1451         }   
1452         
1453         /* check state */
1454         if (client->current_state != STT_STATE_RECORDING) {
1455                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Current state is NOT RECORDING");
1456                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1457                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1458                 return STT_ERROR_INVALID_STATE;
1459         }
1460
1461         if (STT_INTERNAL_STATE_NONE != client->internal_state) {
1462                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is NOT none : %d", client->internal_state);
1463                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1464                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1465                 return STT_ERROR_INVALID_STATE;
1466         }
1467
1468         int ret = -1;
1469         /* do request */
1470         int count = 0;
1471         while (0 != ret) {
1472                 ret = stt_dbus_request_stop(client->uid);
1473                 if (0 > ret) {
1474                         /* Failure */                   
1475                         if (STT_ERROR_TIMED_OUT != ret) {
1476                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to stop : %s", __stt_get_error_code(ret));
1477                                 return ret;
1478                         } else {
1479                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry stop");
1480                                 usleep(10);
1481                                 count++;
1482                                 if (10 == count) {
1483                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1484                                         return ret;
1485                                 }
1486                         }
1487                 } else {
1488                         if (STT_RESULT_STATE_DONE == ret) {
1489                                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Stop is done : %d", ret);
1490                                 client->before_state = client->current_state;
1491                                 client->current_state = STT_STATE_PROCESSING;
1492
1493                                 if (NULL != client->state_changed_cb) {
1494                                         stt_client_use_callback(client);
1495                                         client->state_changed_cb(client->stt, client->before_state, 
1496                                                 client->current_state, client->state_changed_user_data); 
1497                                         stt_client_not_use_callback(client);
1498                                         SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called");
1499                                 } else {
1500                                         SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
1501                                 }
1502                         } else if (STT_RESULT_STATE_NOT_DONE == ret) {
1503                                 SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS] Stop is not done : %d", ret);
1504                                 client->internal_state = STT_INTERNAL_STATE_STOPING;
1505                         } else {
1506                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid result : %d", ret);
1507                         }
1508                         ret = STT_ERROR_NONE;
1509                         break;
1510                 }
1511         }
1512
1513         SLOG(LOG_DEBUG, TAG_STTC, "=====");
1514         SLOG(LOG_DEBUG, TAG_STTC, " ");
1515
1516         return ret;
1517 }
1518
1519
1520 int stt_cancel(stt_h stt)
1521 {
1522         bool stt_supported = false;
1523         bool mic_supported = false;
1524         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1525                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1526                         if (false == stt_supported || false == mic_supported) {
1527                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1528                                 return STT_ERROR_NOT_SUPPORTED;
1529                         }
1530                 }
1531         }
1532
1533         SLOG(LOG_DEBUG, TAG_STTC, "===== STT CANCEL");
1534
1535         if (NULL == stt) {
1536                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input handle is null");
1537                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1538                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1539                 return STT_ERROR_INVALID_PARAMETER;
1540         }
1541
1542         stt_client_s* client = stt_client_get(stt);
1543
1544         /* check handle */
1545         if (NULL == client) {
1546                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
1547                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1548                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1549                 return STT_ERROR_INVALID_PARAMETER;
1550         }       
1551
1552         /* check state */
1553         if (STT_STATE_RECORDING != client->current_state && STT_STATE_PROCESSING != client->current_state) {
1554                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid state : Current state is 'Ready'");
1555                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1556                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1557                 return STT_ERROR_INVALID_STATE;
1558         }
1559
1560         if (STT_INTERNAL_STATE_NONE != client->internal_state) {
1561                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Invalid State : Internal state is NOT none : %d", client->internal_state);
1562                 SLOG(LOG_DEBUG, TAG_STTC, "=====");
1563                 SLOG(LOG_DEBUG, TAG_STTC, " ");
1564                 return STT_ERROR_INVALID_STATE;
1565         }
1566
1567         int ret = -1;
1568         /* do request */
1569         int count = 0;
1570         while (0 != ret) {
1571                 ret = stt_dbus_request_cancel(client->uid);
1572                 if (0 != ret) { 
1573                         /* Failure */                   
1574                         if (STT_ERROR_TIMED_OUT != ret) {
1575                                 SLOG(LOG_DEBUG, TAG_STTC, "[ERROR] Fail to cancel : %s", __stt_get_error_code(ret));
1576                                 return ret;
1577                         } else {
1578                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] retry");
1579                                 usleep(10);
1580                                 count++;
1581                                 if (10 == count) {
1582                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to request");
1583                                         return ret;
1584                                 }
1585                         }
1586                 } else {
1587                         SLOG(LOG_DEBUG, TAG_STTC, "[SUCCESS]");
1588
1589                         client->before_state = client->current_state;
1590                         client->current_state = STT_STATE_READY;
1591
1592                         if (NULL != client->state_changed_cb) {
1593                                 stt_client_use_callback(client);
1594                                 client->state_changed_cb(client->stt, client->before_state, 
1595                                         client->current_state, client->state_changed_user_data); 
1596                                 stt_client_not_use_callback(client);
1597                                 SLOG(LOG_DEBUG, TAG_STTC, "State changed callback is called");
1598                         } else {
1599                                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
1600                         }
1601                         ret = STT_ERROR_NONE;
1602                         break;
1603                 }
1604         }
1605
1606         SLOG(LOG_DEBUG, TAG_STTC, "=====");
1607         SLOG(LOG_DEBUG, TAG_STTC, " ");
1608
1609         return ret;
1610 }
1611
1612 static int __stt_get_audio_volume(float* volume)
1613 {
1614         FILE* fp = fopen(STT_AUDIO_VOLUME_PATH, "rb");
1615         if (!fp) {
1616                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to open Volume File");
1617                 return STT_ERROR_OPERATION_FAILED;
1618         }
1619
1620         int readlen = fread((void*)volume, sizeof(*volume), 1, fp);
1621         fclose(fp);
1622
1623         if (0 == readlen)
1624                 *volume = 0.0f;
1625
1626         return 0;
1627 }
1628
1629 int stt_get_recording_volume(stt_h stt, float* volume)
1630 {
1631         bool stt_supported = false;
1632         bool mic_supported = false;
1633         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1634                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1635                         if (false == stt_supported || false == mic_supported) {
1636                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1637                                 return STT_ERROR_NOT_SUPPORTED;
1638                         }
1639                 }
1640         }
1641
1642         if (NULL == stt || NULL == volume) {
1643                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1644                 return STT_ERROR_INVALID_PARAMETER;
1645         }
1646
1647         stt_client_s* client = stt_client_get(stt);
1648
1649         /* check handle */
1650         if (NULL == client) {
1651                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
1652                 return STT_ERROR_INVALID_PARAMETER;
1653         } 
1654         
1655         if (STT_STATE_RECORDING != client->current_state) {
1656                 SLOG(LOG_DEBUG, TAG_STTC, "[ERROR] Invalid state : NO 'Recording' state");
1657                 return STT_ERROR_INVALID_STATE;
1658         }    
1659         
1660         int ret = 0;
1661         ret = __stt_get_audio_volume(volume);
1662         if (0 != ret) {
1663                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to get audio volume : %s", __stt_get_error_code(ret));
1664                 return STT_ERROR_OPERATION_FAILED;
1665         }
1666
1667         return STT_ERROR_NONE;
1668 }
1669
1670 bool __stt_result_time_cb(int index, int event, const char* text, long start_time, long end_time, void* user_data) 
1671 {
1672         stt_client_s* client = (stt_client_s*)user_data;
1673
1674         /* check handle */
1675         if (NULL == client) {
1676                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to notify error : A handle is not valid");
1677                 return EINA_FALSE;
1678         }
1679
1680         if (NULL != client->result_time_cb) {
1681                 SLOG(LOG_DEBUG, TAG_STTC, "(%d) event(%d) text(%s) start(%ld) end(%ld)",
1682                         index, event, text, start_time, end_time);
1683                 client->result_time_cb(client->stt, index, (stt_result_time_event_e)event, 
1684                         text, start_time, end_time, client->result_time_user_data);
1685         } else {
1686                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Callback is NULL");
1687                 return false;
1688         }
1689
1690         return true;
1691 }
1692
1693 int stt_foreach_detailed_result(stt_h stt, stt_result_time_cb callback, void* user_data)
1694 {
1695         bool stt_supported = false;
1696         bool mic_supported = false;
1697         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1698                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1699                         if (false == stt_supported || false == mic_supported) {
1700                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1701                                 return STT_ERROR_NOT_SUPPORTED;
1702                         }
1703                 }
1704         }
1705
1706         SLOG(LOG_DEBUG, TAG_STTC, "===== STT FOREACH DETAILED RESULT");
1707
1708         if (NULL == callback) {
1709                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Input parameter is NULL");
1710                 return STT_ERROR_INVALID_PARAMETER;
1711         }
1712
1713         stt_client_s* client = stt_client_get(stt);
1714
1715         /* check handle */
1716         if (NULL == client) {
1717                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail : A handle is not valid");
1718                 return STT_ERROR_INVALID_PARAMETER;
1719         }
1720
1721         client->result_time_cb = callback;
1722         client->result_time_user_data = user_data;
1723
1724         int ret = -1;
1725         ret = stt_config_mgr_foreach_time_info(__stt_result_time_cb, client);
1726         ret = __stt_convert_config_error_code(ret);
1727         if (0 != ret) {
1728                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to foreach time info : %s", __stt_get_error_code(ret));
1729         }
1730
1731         client->result_time_cb = NULL;
1732         client->result_time_user_data = NULL;
1733
1734         SLOG(LOG_DEBUG, TAG_STTC, "=====");
1735         SLOG(LOG_DEBUG, TAG_STTC, " ");
1736
1737         return ret;
1738 }
1739
1740 static Eina_Bool __stt_notify_error(void *data)
1741 {
1742         stt_client_s* client = (stt_client_s*)data;
1743
1744         /* check handle */
1745         if (NULL == client) {
1746                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to notify error : A handle is not valid");
1747                 return EINA_FALSE;
1748         }
1749
1750         if (NULL == stt_client_get_by_uid(client->uid))
1751                 return EINA_FALSE;
1752
1753         if (NULL != client->error_cb) {
1754                 stt_client_use_callback(client);
1755                 client->error_cb(client->stt, client->reason, client->error_user_data); 
1756                 stt_client_not_use_callback(client);
1757                 SLOG(LOG_DEBUG, TAG_STTC, "Error callback is called");
1758         } else {
1759                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] Error callback is null");
1760         }
1761
1762         return EINA_FALSE;
1763 }
1764
1765 int __stt_cb_error(int uid, int reason)
1766 {
1767         stt_client_s* client = stt_client_get_by_uid(uid);
1768         if( NULL == client ) {
1769                 SLOG(LOG_ERROR, TAG_STTC, "Handle not found\n");
1770                 return -1;
1771         }
1772
1773         client->reason = reason;
1774
1775         if (NULL != client->error_cb) {
1776                 ecore_timer_add(0, __stt_notify_error, client);
1777         } else {
1778                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] Error callback is null");
1779         }    
1780
1781         return 0;
1782 }
1783
1784 static Eina_Bool __stt_notify_state_changed(void *data)
1785 {
1786         stt_client_s* client = (stt_client_s*)data;
1787
1788         /* check handle */
1789         if (NULL == client) {
1790                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to notify error : A handle is not valid");
1791                 return EINA_FALSE;
1792         }
1793
1794         if (NULL == stt_client_get_by_uid(client->uid))
1795                 return EINA_FALSE;
1796
1797         if (STT_INTERNAL_STATE_STARTING == client->internal_state && STT_STATE_RECORDING == client->current_state) {
1798                 client->internal_state = STT_INTERNAL_STATE_NONE;
1799                 SLOG(LOG_DEBUG, TAG_STTC, "Internal state change NULL");
1800         } else if (STT_INTERNAL_STATE_STOPING == client->internal_state && STT_STATE_PROCESSING == client->current_state) {
1801                 client->internal_state = STT_INTERNAL_STATE_NONE;
1802                 SLOG(LOG_DEBUG, TAG_STTC, "Internal state change NULL");
1803         }
1804
1805         if (NULL != client->state_changed_cb) {
1806                 stt_client_use_callback(client);
1807                 client->state_changed_cb(client->stt, client->before_state, 
1808                         client->current_state, client->state_changed_user_data); 
1809                 stt_client_not_use_callback(client);
1810         } else {
1811                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
1812         }
1813
1814         return EINA_FALSE;
1815 }
1816
1817 static Eina_Bool __stt_notify_result(void *data)
1818 {
1819         stt_client_s* client = (stt_client_s*)data;
1820
1821         /* check handle */
1822         if (NULL == client) {
1823                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Fail to notify error : A handle is not valid");
1824                 return EINA_FALSE;
1825         }
1826
1827         if (NULL == stt_client_get_by_uid(client->uid)) {
1828                 return EINA_FALSE;
1829         }
1830
1831         if (NULL != client->recognition_result_cb) {
1832                 stt_client_use_callback(client);
1833                 client->recognition_result_cb(client->stt, client->event, (const char**)client->data_list, client->data_count, 
1834                         client->msg, client->recognition_result_user_data);
1835                 stt_client_not_use_callback(client);
1836                 SLOG(LOG_DEBUG, TAG_STTC, "client recognition result callback called");
1837         } else {
1838                 SLOG(LOG_WARN, TAG_STTC, "[WARNING] User recognition result callback is NULL");
1839         }
1840
1841         if (NULL != client->msg) {
1842                 free(client->msg);
1843                 client->msg = NULL;
1844         }
1845
1846         if (NULL != client->data_list) {
1847                 char **temp = NULL;
1848                 temp = client->data_list;
1849
1850                 int i = 0;
1851                 for (i = 0;i < client->data_count;i++) {
1852                         if (NULL != temp[i]) {
1853                                 free(temp[i]);
1854                                 temp[i] = NULL;
1855                         } else {
1856                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Result data is error");
1857                         }
1858                 }
1859                 free(client->data_list);
1860                 client->data_list = NULL;
1861         }
1862
1863         client->data_count = 0;
1864
1865         stt_config_mgr_remove_time_info_file();
1866         
1867         if (STT_RESULT_EVENT_FINAL_RESULT == client->event || STT_RESULT_EVENT_ERROR == client->event) {
1868                 client->before_state = client->current_state;
1869                 client->current_state = STT_STATE_READY;
1870
1871                 if (NULL != client->state_changed_cb) {
1872                         ecore_timer_add(0, __stt_notify_state_changed, client);
1873                 } else {
1874                         SLOG(LOG_WARN, TAG_STTC, "[WARNING] State changed callback is null");
1875                 }
1876         }
1877
1878         return EINA_FALSE;
1879 }
1880
1881 int __stt_cb_result(int uid, int event, char** data, int data_count, const char* msg)
1882 {
1883         stt_client_s* client = NULL;
1884         
1885         client = stt_client_get_by_uid(uid);
1886         if (NULL == client) {
1887                 SLOG(LOG_ERROR, TAG_STTC, "Handle is NOT valid");
1888                 return -1;
1889         }
1890
1891         if (NULL != msg)        SLOG(LOG_DEBUG, TAG_STTC, "Recognition Result Message = %s", msg);
1892
1893         int i=0;
1894         for (i = 0;i < data_count;i++) {
1895                 if (NULL != data[i])    SECURE_SLOG(LOG_DEBUG, TAG_STTC, "Recognition Result[%d] = %s", i, data[i]);
1896         }       
1897
1898         if (NULL != client->recognition_result_cb) {
1899                 client->event = event;
1900                 if (NULL != msg) {
1901                         client->msg = strdup(msg);
1902                 }
1903
1904                 client->data_count = data_count;
1905
1906                 if (data_count > 0) {
1907                         char **temp = NULL;
1908                         temp = (char**)calloc(data_count, sizeof(char*));
1909
1910                         for (i = 0;i < data_count;i++) {
1911                                 if(NULL != data[i])
1912                                         temp[i] = strdup(data[i]);
1913                                 else 
1914                                         SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Result data is error");
1915                         }
1916
1917                         client->data_list = temp;
1918                 }
1919
1920                 ecore_timer_add(0, __stt_notify_result, client);
1921         } else {
1922                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] User result callback is null");
1923         }
1924
1925         return 0;
1926 }
1927
1928 int __stt_cb_set_state(int uid, int state)
1929 {
1930         stt_client_s* client = stt_client_get_by_uid(uid);
1931         if( NULL == client ) {
1932                 SLOG(LOG_ERROR, TAG_STTC, "Handle not found");
1933                 return -1;
1934         }
1935
1936         stt_state_e state_from_daemon = (stt_state_e)state;
1937
1938         if (client->current_state == state_from_daemon) {
1939                 SLOG(LOG_DEBUG, TAG_STTC, "Current state has already been %d", client->current_state);
1940                 return 0;
1941         }
1942
1943         client->before_state = client->current_state;
1944         client->current_state = state_from_daemon;
1945
1946         ecore_timer_add(0, __stt_notify_state_changed, client);
1947         return 0;
1948 }
1949
1950 int stt_set_recognition_result_cb(stt_h stt, stt_recognition_result_cb callback, void* user_data)
1951 {
1952         bool stt_supported = false;
1953         bool mic_supported = false;
1954         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1955                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1956                         if (false == stt_supported || false == mic_supported) {
1957                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1958                                 return STT_ERROR_NOT_SUPPORTED;
1959                         }
1960                 }
1961         }
1962
1963         if (stt == NULL || callback == NULL)
1964                 return STT_ERROR_INVALID_PARAMETER;
1965
1966         stt_client_s* client = stt_client_get(stt);
1967
1968         /* check handle */
1969         if (NULL == client) {
1970                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
1971                 return STT_ERROR_INVALID_PARAMETER;
1972         }
1973
1974         if (STT_STATE_CREATED != client->current_state) {
1975                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
1976                 return STT_ERROR_INVALID_STATE;
1977         }
1978
1979         client->recognition_result_cb = callback;
1980         client->recognition_result_user_data = user_data;
1981
1982         return 0;
1983 }
1984
1985 int stt_unset_recognition_result_cb(stt_h stt)
1986 {
1987         bool stt_supported = false;
1988         bool mic_supported = false;
1989         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
1990                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
1991                         if (false == stt_supported || false == mic_supported) {
1992                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
1993                                 return STT_ERROR_NOT_SUPPORTED;
1994                         }
1995                 }
1996         }
1997
1998         if (NULL == stt)
1999                 return STT_ERROR_INVALID_PARAMETER;
2000
2001         stt_client_s* client = stt_client_get(stt);
2002
2003         /* check handle */
2004         if (NULL == client) {
2005                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2006                 return STT_ERROR_INVALID_PARAMETER;
2007         }
2008
2009         if (STT_STATE_CREATED != client->current_state) {
2010                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2011                 return STT_ERROR_INVALID_STATE;
2012         }
2013
2014         client->recognition_result_cb = NULL;
2015         client->recognition_result_user_data = NULL;
2016
2017         return 0;
2018 }
2019
2020 int stt_set_state_changed_cb(stt_h stt, stt_state_changed_cb callback, void* user_data)
2021 {
2022         bool stt_supported = false;
2023         bool mic_supported = false;
2024         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2025                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2026                         if (false == stt_supported || false == mic_supported) {
2027                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2028                                 return STT_ERROR_NOT_SUPPORTED;
2029                         }
2030                 }
2031         }
2032
2033         if (NULL == stt || NULL == callback)
2034                 return STT_ERROR_INVALID_PARAMETER;
2035
2036         stt_client_s* client = stt_client_get(stt);
2037
2038         /* check handle */
2039         if (NULL == client) {
2040                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2041                 return STT_ERROR_INVALID_PARAMETER;
2042         }
2043
2044         if (STT_STATE_CREATED != client->current_state) {
2045                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2046                 return STT_ERROR_INVALID_STATE;
2047         }
2048
2049         client->state_changed_cb = callback;
2050         client->state_changed_user_data = user_data;
2051
2052         return 0;
2053 }
2054
2055 int stt_unset_state_changed_cb(stt_h stt)
2056 {
2057         bool stt_supported = false;
2058         bool mic_supported = false;
2059         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2060                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2061                         if (false == stt_supported || false == mic_supported) {
2062                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2063                                 return STT_ERROR_NOT_SUPPORTED;
2064                         }
2065                 }
2066         }
2067
2068         if (NULL == stt)
2069                 return STT_ERROR_INVALID_PARAMETER;
2070
2071         stt_client_s* client = stt_client_get(stt);
2072
2073         /* check handle */
2074         if (NULL == client) {
2075                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2076                 return STT_ERROR_INVALID_PARAMETER;
2077         }
2078
2079         if (STT_STATE_CREATED != client->current_state) {
2080                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2081                 return STT_ERROR_INVALID_STATE;
2082         }
2083
2084         client->state_changed_cb = NULL;
2085         client->state_changed_user_data = NULL;
2086
2087         return 0;
2088 }
2089
2090 int stt_set_error_cb(stt_h stt, stt_error_cb callback, void* user_data)
2091 {
2092         bool stt_supported = false;
2093         bool mic_supported = false;
2094         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2095                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2096                         if (false == stt_supported || false == mic_supported) {
2097                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2098                                 return STT_ERROR_NOT_SUPPORTED;
2099                         }
2100                 }
2101         }
2102
2103         if (NULL == stt || NULL == callback)
2104                 return STT_ERROR_INVALID_PARAMETER;
2105
2106         stt_client_s* client = stt_client_get(stt);
2107
2108         /* check handle */
2109         if (NULL == client) {
2110                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2111                 return STT_ERROR_INVALID_PARAMETER;
2112         }
2113
2114         if (STT_STATE_CREATED != client->current_state) {
2115                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2116                 return STT_ERROR_INVALID_STATE;
2117         }
2118
2119         client->error_cb = callback;
2120         client->error_user_data = user_data;
2121
2122         return 0;
2123 }
2124
2125 int stt_unset_error_cb(stt_h stt)
2126 {
2127         bool stt_supported = false;
2128         bool mic_supported = false;
2129         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2130                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2131                         if (false == stt_supported || false == mic_supported) {
2132                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2133                                 return STT_ERROR_NOT_SUPPORTED;
2134                         }
2135                 }
2136         }
2137
2138         if (NULL == stt)
2139                 return STT_ERROR_INVALID_PARAMETER;
2140
2141         stt_client_s* client = stt_client_get(stt);
2142
2143         /* check handle */
2144         if (NULL == client) {
2145                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2146                 return STT_ERROR_INVALID_PARAMETER;
2147         }
2148
2149         if (STT_STATE_CREATED != client->current_state) {
2150                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2151                 return STT_ERROR_INVALID_STATE;
2152         }
2153
2154         client->error_cb = NULL;
2155         client->error_user_data = NULL;
2156
2157         return 0;
2158 }
2159
2160 int stt_set_default_language_changed_cb(stt_h stt, stt_default_language_changed_cb callback, void* user_data)
2161 {
2162         bool stt_supported = false;
2163         bool mic_supported = false;
2164         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2165                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2166                         if (false == stt_supported || false == mic_supported) {
2167                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2168                                 return STT_ERROR_NOT_SUPPORTED;
2169                         }
2170                 }
2171         }
2172
2173         if (NULL == stt || NULL == callback)
2174                 return STT_ERROR_INVALID_PARAMETER;
2175
2176         stt_client_s* client = stt_client_get(stt);
2177
2178         /* check handle */
2179         if (NULL == client) {
2180                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2181                 return STT_ERROR_INVALID_PARAMETER;
2182         }
2183
2184         if (STT_STATE_CREATED != client->current_state) {
2185                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2186                 return STT_ERROR_INVALID_STATE;
2187         }
2188
2189         client->default_lang_changed_cb = callback;
2190         client->default_lang_changed_user_data = user_data;
2191
2192         return 0;
2193 }
2194
2195 int stt_unset_default_language_changed_cb(stt_h stt)
2196 {
2197         bool stt_supported = false;
2198         bool mic_supported = false;
2199         if (0 == system_info_get_platform_bool(STT_FEATURE_PATH, &stt_supported)) {
2200                 if (0 == system_info_get_platform_bool(STT_MIC_FEATURE_PATH, &mic_supported)) {
2201                         if (false == stt_supported || false == mic_supported) {
2202                                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] STT NOT supported");
2203                                 return STT_ERROR_NOT_SUPPORTED;
2204                         }
2205                 }
2206         }
2207
2208         if (NULL == stt)
2209                 return STT_ERROR_INVALID_PARAMETER;
2210
2211         stt_client_s* client = stt_client_get(stt);
2212
2213         /* check handle */
2214         if (NULL == client) {
2215                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] A handle is not available");
2216                 return STT_ERROR_INVALID_PARAMETER;
2217         }
2218
2219         if (STT_STATE_CREATED != client->current_state) {
2220                 SLOG(LOG_ERROR, TAG_STTC, "[ERROR] Current state is not 'ready'");
2221                 return STT_ERROR_INVALID_STATE;
2222         }
2223
2224         client->default_lang_changed_cb = NULL;
2225         client->default_lang_changed_user_data = NULL;
2226
2227         return 0;
2228 }