Fix spelling errata
[platform/core/uifw/tts.git] / client / tts.c
1 /*
2 *  Copyright (c) 2011-2016 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 <app_manager.h>
15 #include <dirent.h>
16 #include <Ecore.h>
17 #include <iconv.h>
18 #include <sys/stat.h>
19 #include <sys/types.h>
20 #include <sys/wait.h>
21 #include <system_info.h>
22 #include <vconf.h>
23
24 #include "tts.h"
25 #include "tts_client.h"
26 #include "tts_config_mgr.h"
27 #include "tts_dbus.h"
28 #include "tts_main.h"
29
30 #include "tts_internal.h"
31
32 static bool g_screen_reader;
33
34 static int g_feature_enabled = -1;
35
36 static bool g_err_callback_status = false;
37
38 static int g_max_text_size = -1;
39
40 /* for repetition */
41 static char* g_language = NULL;
42
43 static int g_voice_type = -1;
44
45 static int g_speed = -1;
46
47
48 /* Function definition */
49 static Eina_Bool __tts_notify_state_changed(void *data);
50 static Eina_Bool __tts_notify_error(void *data);
51
52 const char* tts_tag()
53 {
54         return "ttsc";
55 }
56
57 static int __tts_get_feature_enabled()
58 {
59         if (0 == g_feature_enabled) {
60                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] TTS feature NOT supported");
61                 return TTS_ERROR_NOT_SUPPORTED;
62         } else if (-1 == g_feature_enabled) {
63                 bool tts_supported = false;
64                 if (0 == system_info_get_platform_bool(TTS_FEATURE_PATH, &tts_supported)) {
65                         if (false == tts_supported) {
66                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] TTS feature NOT supported");
67                                 g_feature_enabled = 0;
68                                 return TTS_ERROR_NOT_SUPPORTED;
69                         }
70
71                         g_feature_enabled = 1;
72                 } else {
73                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get feature value");
74                         return TTS_ERROR_NOT_SUPPORTED;
75                 }
76         }
77
78         return 0;
79 }
80
81 static const char* __tts_get_error_code(tts_error_e err)
82 {
83         switch (err) {
84         case TTS_ERROR_NONE:                    return "TTS_ERROR_NONE";
85         case TTS_ERROR_OUT_OF_MEMORY:           return "TTS_ERROR_OUT_OF_MEMORY";
86         case TTS_ERROR_IO_ERROR:                return "TTS_ERROR_IO_ERROR";
87         case TTS_ERROR_INVALID_PARAMETER:       return "TTS_ERROR_INVALID_PARAMETER";
88         case TTS_ERROR_OUT_OF_NETWORK:          return "TTS_ERROR_OUT_OF_NETWORK";
89         case TTS_ERROR_TIMED_OUT:               return "TTS_ERROR_TIMED_OUT";
90         case TTS_ERROR_PERMISSION_DENIED:       return "TTS_ERROR_PERMISSION_DENIED";
91         case TTS_ERROR_NOT_SUPPORTED:           return "TTS_ERROR_NOT_SUPPORTED";
92         case TTS_ERROR_INVALID_STATE:           return "TTS_ERROR_INVALID_STATE";
93         case TTS_ERROR_INVALID_VOICE:           return "TTS_ERROR_INVALID_VOICE";
94         case TTS_ERROR_ENGINE_NOT_FOUND:        return "TTS_ERROR_ENGINE_NOT_FOUND";
95         case TTS_ERROR_OPERATION_FAILED:        return "TTS_ERROR_OPERATION_FAILED";
96         case TTS_ERROR_AUDIO_POLICY_BLOCKED:    return "TTS_ERROR_AUDIO_POLICY_BLOCKED";
97         case TTS_ERROR_NOT_SUPPORTED_FEATURE:   return "TTS_ERROR_NOT_SUPPORTED_FEATURE";
98         case TTS_ERROR_SERVICE_RESET:           return "TTS_ERROR_SERVICE_RESET";
99         default:
100                 return "Invalid error code";
101         }
102         return NULL;
103 }
104
105 static int __tts_convert_config_error_code(tts_config_error_e code)
106 {
107         if (code == TTS_CONFIG_ERROR_NONE)                      return TTS_ERROR_NONE;
108         if (code == TTS_CONFIG_ERROR_OUT_OF_MEMORY)             return TTS_ERROR_OUT_OF_MEMORY;
109         if (code == TTS_CONFIG_ERROR_IO_ERROR)                  return TTS_ERROR_IO_ERROR;
110         if (code == TTS_CONFIG_ERROR_INVALID_PARAMETER)         return TTS_ERROR_INVALID_PARAMETER;
111         if (code == TTS_CONFIG_ERROR_INVALID_STATE)             return TTS_ERROR_INVALID_STATE;
112         if (code == TTS_CONFIG_ERROR_INVALID_VOICE)             return TTS_ERROR_INVALID_VOICE;
113         if (code == TTS_CONFIG_ERROR_ENGINE_NOT_FOUND)          return TTS_ERROR_ENGINE_NOT_FOUND;
114         if (code == TTS_CONFIG_ERROR_OPERATION_FAILED)          return TTS_ERROR_OPERATION_FAILED;
115         if (code == TTS_CONFIG_ERROR_NOT_SUPPORTED_FEATURE)     return TTS_ERROR_NOT_SUPPORTED_FEATURE;
116
117         return code;
118 }
119
120 //LCOV_EXCL_START
121 void __tts_config_voice_changed_cb(const char* before_lang, int before_voice_type, const char* language, int voice_type, bool auto_voice, void* user_data)
122 {
123         SLOG(LOG_DEBUG, TAG_TTSC, "Voice changed : Before lang(%s) type(%d) , Current lang(%s), type(%d)",
124                 before_lang, before_voice_type, language, voice_type);
125
126         GList* client_list = NULL;
127         client_list = tts_client_get_client_list();
128
129         GList *iter = NULL;
130         tts_client_s *data = NULL;
131
132         if (g_list_length(client_list) > 0) {
133                 /* Get a first item */
134                 iter = g_list_first(client_list);
135
136                 while (NULL != iter) {
137                         data = iter->data;
138                         if (NULL != data->default_voice_changed_cb) {
139                                 SLOG(LOG_DEBUG, TAG_TTSC, "Call default voice changed callback : uid(%d)", data->uid);
140                                 data->default_voice_changed_cb(data->tts, before_lang, before_voice_type, 
141                                         language, voice_type, data->default_voice_changed_user_data);
142                         }
143
144                         /* Check whether language is changed or not. If it is changed, make 'text_repeat' NULL */
145                         if (0 != strncmp(before_lang, language, strlen(before_lang))) {
146                                 if (NULL != data->text_repeat) {
147                                         free(data->text_repeat);
148                                         data->text_repeat = NULL;
149                                 }
150                         }
151
152                         /* Next item */
153                         iter = g_list_next(iter);
154                 }
155         }
156
157         return;
158 }
159
160 static Eina_Bool __reconnect_by_engine_changed(void* data)
161 {
162         tts_h tts = (tts_h)data;
163
164         tts_client_s* client = tts_client_get(tts);
165         if (NULL == client) {
166                 SLOG(LOG_ERROR, TAG_TTSC, "[WARNING] A handle is not valid");
167                 return EINA_FALSE;
168         }
169
170         if (TTS_STATE_READY != client->current_state) {
171                 usleep(10000);
172                 return EINA_TRUE;
173         }
174
175         int ret = tts_unprepare(tts);
176         if (0 != ret) {
177                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to prepare for setting a new engine... (%d)", ret);
178         }
179         ret = tts_prepare(tts);
180         if (0 != ret) {
181                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to prepare for setting a new engine... (%d)", ret);
182         }
183
184         return EINA_FALSE;
185 }
186
187 void _tts_config_engine_changed_cb(const char* engine_id, const char* setting, const char* language, int voice_type, bool auto_voice, bool need_credential, void* user_data)
188 {
189         tts_h tts = (tts_h)user_data;
190
191         tts_client_s* client = tts_client_get(tts);
192         if (NULL == client) {
193                 SLOG(LOG_ERROR, TAG_TTSC, "[WARNING] A handle is not valid");
194                 return;
195         }
196
197         if (NULL != engine_id)  SLOG(LOG_DEBUG, TAG_TTSC, "Engine id(%s)", engine_id);
198         if (NULL != setting)    SLOG(LOG_DEBUG, TAG_TTSC, "Engine setting(%s)", setting);
199         if (NULL != language)   SLOG(LOG_DEBUG, TAG_TTSC, "Language(%s)", language);
200         SLOG(LOG_DEBUG, TAG_TTSC, "Voice type(%d), Auto voice(%s), Credential(%s)", voice_type, auto_voice ? "on" : "off", need_credential ? "need" : "no need");
201
202         /* When the default engine is changed, please unload the old engine and load the new one. */
203         int ret = -1;
204
205         if (TTS_STATE_PLAYING == client->current_state || TTS_STATE_PAUSED == client->current_state) {
206                 ret = tts_stop(tts);
207                 if (0 != ret) {
208                         SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] TTS client stopping...");
209                 }
210
211                 ecore_idler_add(__reconnect_by_engine_changed, (void*)tts);
212         } else if (TTS_STATE_READY == client->current_state) {
213                 ret = tts_unprepare(tts);
214                 if (0 != ret) {
215                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to unprepare for setting a new engine... (%d)", ret);
216                 }
217                 ret = tts_prepare(tts);
218                 if (0 != ret) {
219                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to prepare for setting a new engine... (%d)", ret);
220                 }
221         }
222
223         /* call callback function */
224         if (NULL != client->engine_changed_cb) {
225                 client->engine_changed_cb(tts, engine_id, language, voice_type, need_credential, client->engine_changed_user_data);
226         } else {
227                 SLOG(LOG_WARN, TAG_TTSC, "No registered callback function for changed engine");
228         }
229         return;
230 }
231 //LCOV_EXCL_STOP
232
233 int tts_create(tts_h* tts)
234 {
235         if (0 != __tts_get_feature_enabled()) {
236                 return TTS_ERROR_NOT_SUPPORTED;
237         }
238
239         SLOG(LOG_INFO, TAG_TTSC, "@@@ Create TTS");
240
241         /* check param */
242         if (NULL == tts) {
243                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
244                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
245                 return TTS_ERROR_INVALID_PARAMETER;
246         }
247
248         if (0 == tts_client_get_size()) {
249                 if (0 != tts_dbus_open_connection()) {
250                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to open dbus connection");
251                         return TTS_ERROR_OPERATION_FAILED;
252                 }
253         }
254
255         if (0 != tts_client_new(tts)) {
256                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to create client!!!!!");
257                 return TTS_ERROR_OUT_OF_MEMORY;
258         }
259
260         tts_client_s* client = tts_client_get(*tts);
261         if (NULL == client) {
262                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get client");
263                 return TTS_ERROR_OPERATION_FAILED;
264         }
265
266         int ret = tts_config_mgr_initialize(client->uid);
267         if (0 != ret) {
268                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to init config manager : %d", ret);
269                 tts_client_destroy(*tts);
270                 return __tts_convert_config_error_code(ret);
271         }
272
273         ret = tts_config_mgr_set_callback(client->uid, _tts_config_engine_changed_cb, __tts_config_voice_changed_cb, NULL, NULL, client->tts);
274         if (0 != ret) {
275                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to set config changed : %d", ret);
276                 tts_client_destroy(*tts);
277                 return __tts_convert_config_error_code(ret);
278         }
279
280         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
281         SLOG(LOG_DEBUG, TAG_TTSC, " ");
282
283         return TTS_ERROR_NONE;
284 }
285
286 int tts_destroy(tts_h tts)
287 {
288         if (0 != __tts_get_feature_enabled()) {
289                 return TTS_ERROR_NOT_SUPPORTED;
290         }
291
292         SLOG(LOG_INFO, TAG_TTSC, "@@@ Destroy TTS");
293
294         if (NULL == tts) {
295                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
296                 return TTS_ERROR_INVALID_PARAMETER;
297         }
298
299         tts_client_s* client = tts_client_get(tts);
300
301         /* check handle */
302         if (NULL == client) {
303                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
304                 return TTS_ERROR_INVALID_PARAMETER;
305         }
306
307         /* check used callback */
308         if (0 != tts_client_get_use_callback(client)) {
309                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Cannot destroy in Callback function");
310                 return TTS_ERROR_OPERATION_FAILED;
311         }
312
313         tts_config_mgr_finalize(client->uid);
314
315         int ret = -1;
316         int count = 0;
317         int screen_reader = -1;
318
319         /* check state */
320         switch (client->current_state) {
321         case TTS_STATE_PAUSED:
322         case TTS_STATE_PLAYING:
323         case TTS_STATE_READY:
324                 ret = vconf_get_bool(TTS_ACCESSIBILITY_KEY, &screen_reader);
325                 if (0 != ret) {
326                         SLOG(LOG_ERROR, tts_tag(), "[ERROR] Fail to get screen reader");
327                 } else {
328                         SLOG(LOG_INFO, tts_tag(), "[INFO] Success to get screen reader(%d), g_screen_reader(%s), client->mode(%d)", screen_reader, (true == g_screen_reader) ? "True" : "False", client->mode);
329                         g_screen_reader = (bool)screen_reader;
330                 }
331                 if (!(false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode)) {
332                         do {
333                                 ret = tts_dbus_request_finalize(client->uid);
334                                 if (0 != ret) {
335                                         //LCOV_EXCL_START
336                                         if (TTS_ERROR_TIMED_OUT != ret) {
337                                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
338                                                 break;
339                                         } else {
340                                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry finalize");
341                                                 usleep(10000);
342                                                 count++;
343                                                 if (TTS_RETRY_COUNT == count) {
344                                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
345                                                         break;
346                                                 }
347                                         }
348                                         //LCOV_EXCL_STOP
349                                 }
350                         } while (0 != ret);
351                 } else {
352                         SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Do not request finalize : g_sr(%d) mode(%d)", g_screen_reader, client->mode);
353                 }
354
355                 client->before_state = client->current_state;
356                 client->current_state = TTS_STATE_CREATED;
357
358         case TTS_STATE_CREATED:
359                 if (NULL != client->conn_timer) {
360                         SLOG(LOG_DEBUG, TAG_TTSC, "Connect Timer is deleted");
361                         ecore_timer_del(client->conn_timer);
362                         client->conn_timer = NULL;
363                 }
364                 /* Free resources */
365                 tts_client_destroy(tts);
366                 break;
367
368         default:
369                 break;
370         }
371
372         if (0 == tts_client_get_size()) {
373                 if (0 != tts_dbus_close_connection()) {
374                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to close connection");
375                 }
376         }
377
378         if (NULL != g_language) {
379                 free(g_language);
380                 g_language = NULL;
381         }
382
383         tts = NULL;
384
385         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
386
387         return TTS_ERROR_NONE;
388 }
389
390 //LCOV_EXCL_START
391 void __tts_screen_reader_changed_cb(bool value)
392 {
393         g_screen_reader = value;
394 }
395 //LCOV_EXCL_STOP
396
397 int tts_set_mode(tts_h tts, tts_mode_e mode)
398 {
399         if (0 != __tts_get_feature_enabled()) {
400                 return TTS_ERROR_NOT_SUPPORTED;
401         }
402
403         SLOG(LOG_INFO, TAG_TTSC, "@@@ Set TTS mode(%d)", mode);
404
405         tts_client_s* client = tts_client_get(tts);
406
407         /* check handle */
408         if (NULL == client) {
409                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not available");
410                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
411                 return TTS_ERROR_INVALID_PARAMETER;
412         }
413
414         /* check state */
415         if (client->current_state != TTS_STATE_CREATED) {
416                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid State: Current state is not 'CREATED'");
417                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
418                 SLOG(LOG_DEBUG, TAG_TTSC, " ");
419                 return TTS_ERROR_INVALID_STATE;
420         }
421
422         if (TTS_MODE_DEFAULT <= mode && mode <= TTS_MODE_INTERRUPT) {
423                 client->mode = mode;
424         } else {
425                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] mode is not valid : %d", mode);
426                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
427                 SLOG(LOG_DEBUG, TAG_TTSC, " ");
428                 return TTS_ERROR_INVALID_PARAMETER;
429         }
430
431         if (TTS_MODE_SCREEN_READER == mode) {
432                 int ret;
433                 int screen_reader;
434                 ret = vconf_get_bool(TTS_ACCESSIBILITY_KEY, &screen_reader);
435                 if (0 != ret) {
436                         SLOG(LOG_ERROR, tts_tag(), "[Config ERROR] Fail to get screen reader");
437                         return TTS_ERROR_OPERATION_FAILED;
438                 }
439                 g_screen_reader = (bool)screen_reader;
440                 tts_config_set_screen_reader_callback(client->uid, __tts_screen_reader_changed_cb);
441         } else {
442                 tts_config_unset_screen_reader_callback(client->uid);
443         }
444
445         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
446
447         return TTS_ERROR_NONE;
448 }
449
450 int tts_get_mode(tts_h tts, tts_mode_e* mode)
451 {
452         if (0 != __tts_get_feature_enabled()) {
453                 return TTS_ERROR_NOT_SUPPORTED;
454         }
455
456         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Get TTS mode");
457
458         tts_client_s* client = tts_client_get(tts);
459
460         /* check handle */
461         if (NULL == client) {
462                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not available");
463                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
464                 SLOG(LOG_DEBUG, TAG_TTSC, " ");
465                 return TTS_ERROR_INVALID_PARAMETER;
466         }
467
468         /* check state */
469         if (client->current_state != TTS_STATE_CREATED) {
470                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid State: Current state is not 'CREATED'");
471                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
472                 SLOG(LOG_DEBUG, TAG_TTSC, " ");
473                 return TTS_ERROR_INVALID_STATE;
474         }
475
476         if (NULL == mode) {
477                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter(mode) is NULL");
478                 return TTS_ERROR_INVALID_PARAMETER;
479         }
480
481         *mode = client->mode;
482
483         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
484         SLOG(LOG_DEBUG, TAG_TTSC, " ");
485
486         return TTS_ERROR_NONE;
487 }
488
489 int tts_set_credential(tts_h tts, const char* credential)
490 {
491         if (0 != __tts_get_feature_enabled()) {
492                 return TTS_ERROR_NOT_SUPPORTED;
493         }
494
495         if (NULL == tts || NULL == credential) {
496                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
497                 return TTS_ERROR_INVALID_PARAMETER;
498         }
499
500         tts_client_s* client = tts_client_get(tts);
501
502         if (NULL == client) {
503                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : A handle is not valid");
504                 return TTS_ERROR_INVALID_PARAMETER;
505         }
506
507         if (TTS_STATE_CREATED != client->current_state && TTS_STATE_READY != client->current_state) {
508                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid (%d).", client->current_state);
509                 return TTS_ERROR_INVALID_STATE;
510         }
511
512         if (NULL != client->credential) {
513                 free(client->credential);
514                 client->credential = NULL;
515         }
516         client->credential = strdup(credential);
517
518         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
519
520         return TTS_ERROR_NONE;
521 }
522
523 //LCOV_EXCL_START
524 int tts_set_server_tts(tts_h tts, const char* credential)
525 {
526         if (0 != __tts_get_feature_enabled()) {
527                 return TTS_ERROR_NOT_SUPPORTED;
528         }
529
530         if (NULL == tts) {
531                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
532                 return TTS_ERROR_INVALID_PARAMETER;
533         }
534
535         tts_client_s* client = tts_client_get(tts);
536
537         if (NULL == client) {
538                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : A handle is not valid");
539                 return TTS_ERROR_INVALID_PARAMETER;
540         }
541
542         if (TTS_STATE_CREATED != client->current_state && TTS_STATE_READY != client->current_state) {
543                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid (%d).", client->current_state);
544                 return TTS_ERROR_INVALID_STATE;
545         }
546
547         if (NULL != client->credential) {
548                 free(client->credential);
549                 client->credential = NULL;
550         }
551
552         client->internal = true;
553
554         char* key = NULL;
555         if (NULL != credential) {
556                 key = strdup("EnableServerTTS");
557                 client->credential = strdup(credential);
558                 if (NULL == client->credential) {
559                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to allocate memory");
560                         if (NULL != key) {
561                                 free(key);
562                                 key = NULL;
563                         }
564                         return TTS_ERROR_OUT_OF_MEMORY;
565                 }
566         } else {
567                 key = strdup("DisableServerTTS");
568         }
569
570         if (NULL == key) {
571                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to allocate memory");
572                 return TTS_ERROR_OUT_OF_MEMORY;
573         }
574
575         int pid = getpid();
576         char* appid = NULL;
577         int ret = app_manager_get_app_id(pid, &appid);
578         if (0 != ret || NULL == appid) {
579                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get appid, ret(%d), pid(%d), appid(%s)", ret, pid, appid);
580                 free(key);
581                 key = NULL;
582                 if (NULL != appid) {
583                         free(appid);
584                         appid = NULL;
585                 }
586                 return TTS_ERROR_OPERATION_FAILED;
587         }
588
589         ret = tts_set_private_data(tts, key, appid);
590         if (0 != ret) {
591                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to set private data, ret(%d), pid(%d), appid(%s)", ret, pid, appid);
592                 free(key);
593                 key = NULL;
594                 free(appid);
595                 appid = NULL;
596                 return ret;
597         }
598
599         free(appid);
600         appid = NULL;
601         free(key);
602         key = NULL;
603
604         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
605
606         return TTS_ERROR_NONE;
607 }
608 // LCOV_EXCL_STOP
609
610 static Eina_Bool __tts_connect_daemon(void *data)
611 {
612         tts_h tts = (tts_h)data;
613         tts_client_s* client = tts_client_get(tts);
614
615         /* check handle */
616         if (NULL == client) {
617                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
618                 return EINA_FALSE;
619         }
620
621         /* Send hello */
622         if (0 != tts_dbus_request_hello(client->uid)) {
623                 return EINA_TRUE;
624         }
625
626         SLOG(LOG_INFO, TAG_TTSC, "@@@ Connect daemon");
627
628         /* do request initialize */
629         int ret = -1;
630         bool credential_needed = false;
631
632         ret = tts_dbus_request_initialize(client->uid, &credential_needed);
633
634         if (TTS_ERROR_ENGINE_NOT_FOUND == ret) {
635                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to initialize : %s", __tts_get_error_code(ret));
636
637                 client->reason = TTS_ERROR_ENGINE_NOT_FOUND;
638                 client->utt_id = -1;
639
640                 ecore_timer_add(0, __tts_notify_error, (void*)client->tts);
641                 client->conn_timer = NULL;
642                 return EINA_FALSE;
643
644         } else if (TTS_ERROR_PERMISSION_DENIED == ret) {
645                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to initialize : %s", __tts_get_error_code(ret));
646
647                 client->reason = TTS_ERROR_PERMISSION_DENIED;
648                 client->utt_id = -1;
649
650                 ecore_timer_add(0, __tts_notify_error, (void*)client->tts);
651                 client->conn_timer = NULL;
652                 return EINA_FALSE;
653
654         } else if (TTS_ERROR_NONE != ret) {
655                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Fail to connection. Retry to connect : %s", __tts_get_error_code(ret));
656                 return EINA_TRUE;
657
658         } else {
659                 /* success to connect tts-daemon */
660                 client->credential_needed = credential_needed;
661                 SLOG(LOG_ERROR, TAG_TTSC, "Supported options : credential(%s)", credential_needed ? "need" : "no need");
662         }
663
664         client->conn_timer = NULL;
665
666         client = tts_client_get(tts);
667         /* check handle */
668         if (NULL == client) {
669                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
670                 return EINA_FALSE;
671         }
672
673         client->before_state = client->current_state;
674         client->current_state = TTS_STATE_READY;
675
676         if (NULL != client->state_changed_cb) {
677                 tts_client_use_callback(client);
678                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
679                 tts_client_not_use_callback(client);
680         } else {
681                 SLOG(LOG_WARN, TAG_TTSC, "State changed callback is NULL");
682         }
683
684         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
685
686         return EINA_FALSE;
687 }
688
689 int tts_prepare(tts_h tts)
690 {
691         if (0 != __tts_get_feature_enabled()) {
692                 return TTS_ERROR_NOT_SUPPORTED;
693         }
694
695         SLOG(LOG_INFO, TAG_TTSC, "@@@ Prepare TTS");
696
697         tts_client_s* client = tts_client_get(tts);
698
699         /* check handle */
700         if (NULL == client) {
701                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not available");
702                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
703                 return TTS_ERROR_INVALID_PARAMETER;
704         }
705
706         /* check state */
707         if (client->current_state != TTS_STATE_CREATED) {
708                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid State: Current state is not 'CREATED'");
709                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
710                 return TTS_ERROR_INVALID_STATE;
711         }
712
713         ecore_thread_main_loop_begin();
714         client->conn_timer = ecore_timer_add(0.02, __tts_connect_daemon, (void*)tts);
715         ecore_thread_main_loop_end();
716
717         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
718
719         return TTS_ERROR_NONE;
720 }
721
722 //LCOV_EXCL_START
723 int tts_prepare_sync(tts_h tts)
724 {
725         if (0 != __tts_get_feature_enabled()) {
726                 return TTS_ERROR_NOT_SUPPORTED;
727         }
728
729         SLOG(LOG_INFO, TAG_TTSC, "@@@ Prepare TTS");
730
731         tts_client_s* client = tts_client_get(tts);
732
733         /* check handle */
734         if (NULL == client) {
735                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not available");
736                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
737                 return TTS_ERROR_INVALID_PARAMETER;
738         }
739
740         /* check state */
741         if (client->current_state != TTS_STATE_CREATED) {
742                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid State: Current state is not 'CREATED'");
743                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
744                 return TTS_ERROR_INVALID_STATE;
745         }
746
747         int cnt = 0;
748         while (EINA_TRUE == __tts_connect_daemon((void*)tts) && TTS_CONNECTION_RETRY_COUNT > cnt) {
749                 cnt++;
750         }
751
752         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
753
754         if (TTS_CONNECTION_RETRY_COUNT == cnt) {
755                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to connect daemon");
756                 return TTS_ERROR_OPERATION_FAILED;
757         }
758
759         return TTS_ERROR_NONE;
760 }
761 //LCOV_EXCL_STOP
762
763 int tts_unprepare(tts_h tts)
764 {
765         if (0 != __tts_get_feature_enabled()) {
766                 return TTS_ERROR_NOT_SUPPORTED;
767         }
768
769         SLOG(LOG_INFO, TAG_TTSC, "@@@ Unprepare TTS");
770
771         tts_client_s* client = tts_client_get(tts);
772
773         /* check handle */
774         if (NULL == client) {
775                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not available");
776                 return TTS_ERROR_INVALID_PARAMETER;
777         }
778
779         /* check state */
780         if (client->current_state != TTS_STATE_READY) {
781                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid State: Current state is not 'READY'");
782                 return TTS_ERROR_INVALID_STATE;
783         }
784
785         int ret = -1;
786         int count = 0;
787         int screen_reader = -1;
788
789         ret = vconf_get_bool(TTS_ACCESSIBILITY_KEY, &screen_reader);
790         if (0 != ret) {
791                 SLOG(LOG_ERROR, tts_tag(), "[ERROR] Fail to get screen reader");
792         } else {
793                 SLOG(LOG_INFO, tts_tag(), "[INFO] Success to get screen reader(%d), g_screen_reader(%s), client->mode(%d)", screen_reader, (true == g_screen_reader) ? "True" : "False", client->mode);
794                 g_screen_reader = (bool)screen_reader;
795         }
796
797         bool is_prepared = false;
798         if (!(false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode)) {
799                 do {
800                         ret = tts_dbus_request_finalize(client->uid);
801                         if (0 != ret) {
802                                 //LCOV_EXCL_START
803                                 if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
804                                         client->current_state = TTS_STATE_CREATED;
805                                         if (0 == tts_prepare_sync(tts)) {
806                                                 is_prepared = true;
807                                                 SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
808                                         }
809                                 } else if (TTS_ERROR_TIMED_OUT != ret) {
810                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
811                                         break;
812                                 } else {
813                                         SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry finalize : %s", __tts_get_error_code(ret));
814                                         usleep(10000);
815                                         count++;
816                                         if (TTS_RETRY_COUNT == count) {
817                                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
818                                                 break;
819                                         }
820                                 }
821                                 //LCOV_EXCL_STOP
822                         }
823                 } while (0 != ret);
824         } else {
825                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Do not request finalize : g_sr(%d) mode(%d)", g_screen_reader, client->mode);
826         }
827
828         client->before_state = client->current_state;
829         client->current_state = TTS_STATE_CREATED;
830
831         if (NULL != client->state_changed_cb) {
832                 tts_client_use_callback(client);
833                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
834                 tts_client_not_use_callback(client);
835                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
836         }
837
838         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
839
840         return TTS_ERROR_NONE;
841 }
842
843 bool __tts_supported_voice_cb(const char* engine_id, const char* language, int type, void* user_data)
844 {
845         tts_h tts = (tts_h)user_data;
846
847         tts_client_s* client = tts_client_get(tts);
848         if (NULL == client) {
849                 SLOG(LOG_ERROR, TAG_TTSC, "[WARNING] A handle is not valid");
850                 return false;
851         }
852
853         /* call callback function */
854         if (NULL != client->supported_voice_cb) {
855                 return client->supported_voice_cb(tts, language, type, client->supported_voice_user_data);
856         } else {
857                 SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of supported voice");
858         }
859
860         return false;
861 }
862
863 int tts_foreach_supported_voices(tts_h tts, tts_supported_voice_cb callback, void* user_data)
864 {
865         if (0 != __tts_get_feature_enabled()) {
866                 return TTS_ERROR_NOT_SUPPORTED;
867         }
868
869         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Foreach supported voices");
870
871         if (NULL == tts || NULL == callback) {
872                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
873                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
874                 return TTS_ERROR_INVALID_PARAMETER;
875         }
876
877         tts_client_s* client = tts_client_get(tts);
878
879         /* check handle */
880         if (NULL == client) {
881                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
882                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
883                 return TTS_ERROR_INVALID_PARAMETER;
884         }
885
886         int ret = 0;
887         char* current_engine = NULL;
888         ret = tts_config_mgr_get_engine(&current_engine);
889         if (0 != ret) {
890                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get current engine : %d", ret);
891                 return __tts_convert_config_error_code(ret);
892         }
893
894         client->supported_voice_cb = callback;
895         client->supported_voice_user_data = user_data;
896
897         ret = tts_config_mgr_get_voice_list(current_engine, __tts_supported_voice_cb, client->tts);
898
899         if (NULL != current_engine) {
900                 free(current_engine);
901                 current_engine = NULL;
902         }
903
904         client->supported_voice_cb = NULL;
905         client->supported_voice_user_data = NULL;
906
907         if (0 != ret) {
908                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Result : %d", ret);
909                 ret = TTS_ERROR_OPERATION_FAILED;
910         }
911
912         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
913
914         return ret;
915 }
916
917 int tts_get_default_voice(tts_h tts, char** lang, int* vctype)
918 {
919         if (0 != __tts_get_feature_enabled()) {
920                 return TTS_ERROR_NOT_SUPPORTED;
921         }
922
923         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Get default voice");
924
925         if (NULL == tts) {
926                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
927                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
928                 return TTS_ERROR_INVALID_PARAMETER;
929
930         }
931         tts_client_s* client = tts_client_get(tts);
932
933         if (NULL == client) {
934                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
935                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
936                 return TTS_ERROR_INVALID_PARAMETER;
937         }
938
939         /* Request call remote method */
940         int ret = 0;
941         ret = tts_config_mgr_get_voice(lang, vctype);
942         if (0 != ret) {
943                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %d", ret);
944                 return __tts_convert_config_error_code(ret);
945         } else {
946                 SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] Default language(%s), type(%d)", *lang, *vctype);
947         }
948
949         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
950
951         return ret;
952 }
953
954 int tts_get_max_text_size(tts_h tts, unsigned int* size)
955 {
956         if (0 != __tts_get_feature_enabled()) {
957                 return TTS_ERROR_NOT_SUPPORTED;
958         }
959
960         if (NULL == tts || NULL == size) {
961                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get max text count : Input parameter is null");
962                 return TTS_ERROR_INVALID_PARAMETER;
963         }
964
965         tts_client_s* client = tts_client_get(tts);
966
967         if (NULL == client) {
968                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get max text count : A handle is not valid");
969                 return TTS_ERROR_INVALID_PARAMETER;
970         }
971
972         if (TTS_STATE_READY != client->current_state) {
973                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get max text count : Current state is NOT 'READY'.");
974                 return TTS_ERROR_INVALID_STATE;
975         }
976
977         if (0 != tts_config_mgr_get_max_text_size(size)) {
978                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get max text size");
979                 return TTS_ERROR_INVALID_PARAMETER;
980         }
981
982         g_max_text_size = (int)*size;
983
984         SLOG(LOG_DEBUG, TAG_TTSC, "Get max text count : %d", *size);
985         return TTS_ERROR_NONE;
986 }
987
988 int tts_get_state(tts_h tts, tts_state_e* state)
989 {
990         if (0 != __tts_get_feature_enabled()) {
991                 return TTS_ERROR_NOT_SUPPORTED;
992         }
993
994         if (NULL == tts || NULL == state) {
995                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : Input parameter is null");
996                 return TTS_ERROR_INVALID_PARAMETER;
997         }
998
999         tts_client_s* client = tts_client_get(tts);
1000
1001         if (NULL == client) {
1002                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : A handle is not valid");
1003                 return TTS_ERROR_INVALID_PARAMETER;
1004         }
1005
1006         *state = client->current_state;
1007
1008         switch (*state) {
1009         case TTS_STATE_CREATED: SLOG(LOG_DEBUG, TAG_TTSC, "Current state is 'Created'");        break;
1010         case TTS_STATE_READY:   SLOG(LOG_DEBUG, TAG_TTSC, "Current state is 'Ready'");          break;
1011         case TTS_STATE_PLAYING: SLOG(LOG_DEBUG, TAG_TTSC, "Current state is 'Playing'");        break;
1012         case TTS_STATE_PAUSED:  SLOG(LOG_DEBUG, TAG_TTSC, "Current state is 'Paused'");         break;
1013         default:                SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid value");             break;
1014         }
1015
1016         return TTS_ERROR_NONE;
1017 }
1018
1019 int tts_get_speed_range(tts_h tts, int* min, int* normal, int* max)
1020 {
1021         if (0 != __tts_get_feature_enabled()) {
1022                 return TTS_ERROR_NOT_SUPPORTED;
1023         }
1024
1025         if (NULL == tts || NULL == min || NULL == normal || NULL == max) {
1026                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
1027                 return TTS_ERROR_INVALID_PARAMETER;
1028         }
1029
1030         tts_client_s* client = tts_client_get(tts);
1031
1032         if (NULL == client) {
1033                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : A handle is not valid");
1034                 return TTS_ERROR_INVALID_PARAMETER;
1035         }
1036
1037         *min = TTS_SPEED_MIN;
1038         *normal = TTS_SPEED_NORMAL;
1039         *max = TTS_SPEED_MAX;
1040
1041         return TTS_ERROR_NONE;
1042 }
1043
1044 int tts_get_error_message(tts_h tts, char** err_msg)
1045 {
1046         if (0 != __tts_get_feature_enabled()) {
1047                 return TTS_ERROR_NOT_SUPPORTED;
1048         }
1049
1050         if (NULL == tts || NULL == err_msg) {
1051                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
1052                 return TTS_ERROR_INVALID_PARAMETER;
1053         }
1054
1055         tts_client_s* client = tts_client_get(tts);
1056
1057         if (NULL == client) {
1058                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Get state : A handle is not valid");
1059                 return TTS_ERROR_INVALID_PARAMETER;
1060         }
1061
1062         if (NULL != client->err_msg) {
1063                 *err_msg = strdup(client->err_msg);
1064                 SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Error msg (%s)", *err_msg);
1065         } else {
1066                 *err_msg = NULL;
1067                 SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Error msg (NULL)");
1068         }
1069
1070         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1071
1072         return TTS_ERROR_NONE;
1073 }
1074
1075 int tts_add_text(tts_h tts, const char* text, const char* language, int voice_type, int speed, int* utt_id)
1076 {
1077         SLOG(LOG_INFO, TAG_TTSC, "[DEBUG] Add text: text(%s), language(%s), type(%d)", (NULL == text) ? "NULL" : text, (NULL == language) ? "NULL" : language, voice_type);
1078
1079         if (0 != __tts_get_feature_enabled()) {
1080                 return TTS_ERROR_NOT_SUPPORTED;
1081         }
1082
1083         if (speed < 0) {
1084                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Speed should not be negative(%d)", speed);
1085                 return TTS_ERROR_INVALID_PARAMETER;
1086         }
1087
1088         if (voice_type < 0) {
1089                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Voice type should not be negative(%d)", voice_type);
1090                 return TTS_ERROR_INVALID_PARAMETER;
1091         }
1092
1093         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Add text");
1094
1095         if (NULL == tts || NULL == utt_id) {
1096                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null");
1097                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1098                 return TTS_ERROR_INVALID_PARAMETER;
1099         }
1100
1101         tts_client_s* client = tts_client_get(tts);
1102
1103         if (NULL == client) {
1104                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1105                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1106                 return TTS_ERROR_INVALID_PARAMETER;
1107         }
1108
1109         if (TTS_STATE_CREATED == client->current_state) {
1110                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Current state is 'CREATED'.");
1111                 return TTS_ERROR_INVALID_STATE;
1112         }
1113
1114         if (-1 == g_max_text_size) {
1115                 SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] g_max_text_size is %d", g_max_text_size);
1116                 if (0 != tts_config_mgr_get_max_text_size((unsigned int*)&g_max_text_size)) {
1117                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to get max text size");
1118                         return TTS_ERROR_INVALID_PARAMETER;
1119                 }
1120         }
1121
1122         if (0 == g_max_text_size) {
1123                 if (strlen(text) <= 0) {
1124                         SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] Max Text Size is %d", g_max_text_size);
1125                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input text size is invalid. (max text size is unlimited.)");
1126                         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1127                         return TTS_ERROR_INVALID_PARAMETER;
1128                 }
1129         } else {
1130                 SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] g_max_text_size is %d", g_max_text_size);
1131                 if (g_max_text_size < strlen(text) || strlen(text) <= 0) {
1132                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input text size is invalid.");
1133                         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1134                         return TTS_ERROR_INVALID_PARAMETER;
1135                 }
1136         }
1137
1138         if (TTS_SPEED_AUTO > speed || TTS_SPEED_MAX < speed) {
1139                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] speed value(%d) is invalid.", speed);
1140                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1141                 return TTS_ERROR_INVALID_PARAMETER;
1142         }
1143
1144         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1145                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1146                 return TTS_ERROR_INVALID_STATE;
1147         }
1148
1149         if (true == client->credential_needed && NULL == client->credential) {
1150                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Do not have app credential for this engine");
1151                 return TTS_ERROR_PERMISSION_DENIED;
1152         }
1153
1154         /* check valid utf8 */
1155         bool valid = false;
1156
1157         DBusError err;
1158         dbus_error_init(&err);
1159
1160         valid = dbus_validate_utf8(text, &err);
1161         if (dbus_error_is_set(&err)) {
1162                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Dbus Error(%s), text(%s)", err.message, text);
1163                 dbus_error_free(&err);
1164                 return TTS_ERROR_INVALID_PARAMETER;
1165         }
1166
1167         if (valid != true) {
1168                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Text is invalid - '%s'", text);
1169                 return TTS_ERROR_INVALID_PARAMETER;
1170         }
1171         SLOG(LOG_DEBUG, TAG_TTSC, "Text is valid - text is '%s'", text);
1172
1173         /* save texts for repetition */
1174         if (NULL != client->text_repeat) {
1175                 free(client->text_repeat);
1176                 client->text_repeat = NULL;
1177         }
1178
1179         client->text_repeat = strdup(text);
1180
1181         if (NULL != g_language) {
1182                 free(g_language);
1183                 g_language = NULL;
1184         }
1185         if (NULL == language)
1186                 g_language = NULL;
1187         else
1188                 g_language = strdup(language);
1189
1190         g_voice_type = voice_type;
1191         g_speed = speed;
1192
1193         SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] repeat: text(%s), language(%s), voice type(%d), speed(%d)", client->text_repeat, g_language, g_voice_type, g_speed);
1194
1195         /* change default language value */
1196         char* temp = NULL;
1197
1198         if (NULL == language)
1199                 temp = strdup("default");
1200         else
1201                 temp = strdup(language);
1202
1203         client->current_utt_id++;
1204         if (client->current_utt_id == 10000) {
1205                 client->current_utt_id = 1;
1206         }
1207
1208         /* do request */
1209         int ret = -1;
1210         int count = 0;
1211         bool is_prepared = false;
1212         while (0 != ret) {
1213                 ret = tts_dbus_request_add_text(client->uid, text, temp, voice_type, speed, client->current_utt_id, client->credential);
1214                 if (0 != ret) {
1215                         //LCOV_EXCL_START
1216                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1217                                 client->current_state = TTS_STATE_CREATED;
1218                                 if (0 == tts_prepare_sync(tts)) {
1219                                         is_prepared = true;
1220                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1221                                 }
1222                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1223                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1224                                 break;
1225                         } else {
1226                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry add text : %s", __tts_get_error_code(ret));
1227                                 usleep(10000);
1228                                 count++;
1229                                 if (TTS_RETRY_MIN_COUNT == count) {
1230                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1231                                         break;
1232                                 }
1233                         }
1234                         //LCOV_EXCL_STOP
1235                 } else {
1236                         *utt_id = client->current_utt_id;
1237                 }
1238         }
1239
1240         if (NULL != temp) {
1241                 free(temp);
1242                 temp = NULL;
1243         }
1244
1245         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1246
1247         return ret;
1248 }
1249
1250 //LCOV_EXCL_START
1251 static void __tts_play_async(void *data)
1252 {
1253         tts_h tts = (tts_h)data;
1254         tts_client_s* client = tts_client_get(tts);
1255
1256         /* check handle */
1257         if (NULL == client) {
1258                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1259                 return;
1260         }
1261
1262         int ret = -1;
1263         int count = 0;
1264         bool is_prepared = false;
1265         while (0 != ret) {
1266                 ret = tts_dbus_request_play(client->uid, client->credential);
1267                 if (0 != ret) {
1268                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1269                                 client->current_state = TTS_STATE_CREATED;
1270                                 if (0 == tts_prepare_sync(tts)) {
1271                                         is_prepared = true;
1272                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1273                                 }
1274                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1275                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1276                                 break;
1277                         } else {
1278                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry play : %s", __tts_get_error_code(ret));
1279                                 usleep(10000);
1280                                 count++;
1281                                 if (TTS_RETRY_COUNT == count) {
1282                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1283                                         break;
1284                                 }
1285                         }
1286                 }
1287         }
1288
1289         if (0 != ret) {
1290                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to play tts : %s", __tts_get_error_code(ret));
1291
1292                 client->reason = ret;
1293                 client->utt_id = -1;
1294
1295                 ecore_timer_add(0, __tts_notify_error, client->tts);
1296                 return;
1297         }
1298
1299         client->before_state = client->current_state;
1300         client->current_state = TTS_STATE_PLAYING;
1301
1302         if (NULL != client->state_changed_cb) {
1303                 tts_client_use_callback(client);
1304                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1305                 tts_client_not_use_callback(client);
1306                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1307         }
1308
1309         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1310
1311         return;
1312 }
1313
1314 int tts_play_async(tts_h tts)
1315 {
1316         if (0 != __tts_get_feature_enabled()) {
1317                 return TTS_ERROR_NOT_SUPPORTED;
1318         }
1319
1320         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Play tts");
1321
1322         if (NULL == tts) {
1323                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
1324                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1325                 return TTS_ERROR_INVALID_PARAMETER;
1326         }
1327
1328         tts_client_s* client = tts_client_get(tts);
1329
1330         if (NULL == client) {
1331                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
1332                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1333                 return TTS_ERROR_INVALID_PARAMETER;
1334         }
1335
1336         if (TTS_STATE_PLAYING == client->current_state || TTS_STATE_CREATED == client->current_state) {
1337                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid.");
1338                 return TTS_ERROR_INVALID_STATE;
1339         }
1340
1341         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1342                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1343                 return TTS_ERROR_INVALID_STATE;
1344         }
1345
1346         if (true == client->credential_needed && NULL == client->credential) {
1347                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Do not have app credential for this engine");
1348                 return TTS_ERROR_PERMISSION_DENIED;
1349         }
1350
1351         ecore_main_loop_thread_safe_call_async(__tts_play_async, (void*)tts);
1352
1353         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1354
1355         return TTS_ERROR_NONE;
1356 }
1357 //LCOV_EXCL_STOP
1358 int tts_play(tts_h tts)
1359 {
1360         if (0 != __tts_get_feature_enabled()) {
1361                 return TTS_ERROR_NOT_SUPPORTED;
1362         }
1363
1364         SLOG(LOG_INFO, TAG_TTSC, "@@@ Play tts");
1365
1366         if (NULL == tts) {
1367                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
1368                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1369                 return TTS_ERROR_INVALID_PARAMETER;
1370         }
1371
1372         tts_client_s* client = tts_client_get(tts);
1373
1374         if (NULL == client) {
1375                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
1376                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1377                 SLOG(LOG_DEBUG, TAG_TTSC, " ");
1378                 return TTS_ERROR_INVALID_PARAMETER;
1379         }
1380
1381         if (TTS_STATE_PLAYING == client->current_state || TTS_STATE_CREATED == client->current_state) {
1382                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid.");
1383                 return TTS_ERROR_INVALID_STATE;
1384         }
1385
1386         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1387                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1388                 return TTS_ERROR_INVALID_STATE;
1389         }
1390
1391         if (true == client->credential_needed && NULL == client->credential) {
1392                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Do not have app credential for this engine");
1393                 return TTS_ERROR_PERMISSION_DENIED;
1394         }
1395
1396         int ret = -1;
1397         int count = 0;
1398         bool is_prepared = false;
1399         while (0 != ret) {
1400                 ret = tts_dbus_request_play(client->uid, client->credential);
1401                 if (0 != ret) {
1402                         //LCOV_EXCL_START
1403                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1404                                 client->current_state = TTS_STATE_CREATED;
1405                                 if (0 == tts_prepare_sync(tts)) {
1406                                         is_prepared = true;
1407                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1408                                 }
1409                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1410                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1411                                 return ret;
1412                         } else {
1413                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry play : %s", __tts_get_error_code(ret));
1414                                 usleep(10000);
1415                                 count++;
1416                                 if (TTS_RETRY_COUNT == count) {
1417                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1418                                         return ret;
1419                                 }
1420                         }
1421                         //LCOV_EXCL_STOP
1422                 }
1423         }
1424
1425         client->before_state = client->current_state;
1426         client->current_state = TTS_STATE_PLAYING;
1427
1428         if (NULL != client->state_changed_cb) {
1429                 tts_client_use_callback(client);
1430                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1431                 tts_client_not_use_callback(client);
1432                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1433         }
1434
1435         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1436
1437         return TTS_ERROR_NONE;
1438 }
1439 //LCOV_EXCL_START
1440 static void __tts_stop_async(void *data)
1441 {
1442         tts_h tts = (tts_h)data;
1443         tts_client_s* client = tts_client_get(tts);
1444
1445         /* check handle */
1446         if (NULL == client) {
1447                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1448                 return;
1449         }
1450
1451         int ret = -1;
1452         int count = 0;
1453         bool is_prepared = false;
1454         while (0 != ret) {
1455                 ret = tts_dbus_request_stop(client->uid);
1456                 if (0 != ret) {
1457                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1458                                 client->current_state = TTS_STATE_CREATED;
1459                                 if (0 == tts_prepare_sync(tts)) {
1460                                         is_prepared = true;
1461                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1462                                 }
1463                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1464                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1465                                 break;
1466                         } else {
1467                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry stop : %s", __tts_get_error_code(ret));
1468                                 usleep(10000);
1469                                 count++;
1470                                 if (TTS_RETRY_COUNT == count) {
1471                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1472                                         break;
1473                                 }
1474                         }
1475                 }
1476         }
1477
1478         if (0 != ret) {
1479                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to stop tts : %s", __tts_get_error_code(ret));
1480
1481                 client->reason = ret;
1482                 client->utt_id = -1;
1483
1484                 ecore_timer_add(0, __tts_notify_error, client->tts);
1485                 return;
1486         }
1487
1488         client->before_state = client->current_state;
1489         client->current_state = TTS_STATE_READY;
1490
1491         if (NULL != client->state_changed_cb) {
1492                 tts_client_use_callback(client);
1493                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1494                 tts_client_not_use_callback(client);
1495                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1496         }
1497
1498         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1499
1500         return;
1501 }
1502
1503 int tts_stop_aync(tts_h tts)
1504 {
1505         if (0 != __tts_get_feature_enabled()) {
1506                 return TTS_ERROR_NOT_SUPPORTED;
1507         }
1508
1509         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Stop tts");
1510
1511         if (NULL == tts) {
1512                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1513                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1514                 return TTS_ERROR_INVALID_PARAMETER;
1515         }
1516
1517         tts_client_s* client = tts_client_get(tts);
1518
1519         if (NULL == client) {
1520                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1521                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1522                 return TTS_ERROR_INVALID_PARAMETER;
1523         }
1524
1525         if (TTS_STATE_CREATED == client->current_state) {
1526                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Current state is 'CREATED'.");
1527                 return TTS_ERROR_INVALID_STATE;
1528         }
1529
1530         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1531                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1532                 return TTS_ERROR_INVALID_STATE;
1533         }
1534
1535         ecore_main_loop_thread_safe_call_async(__tts_stop_async, (void*)tts);
1536
1537         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1538
1539         return TTS_ERROR_NONE;
1540 }
1541 //LCOV_EXCL_STOP
1542 int tts_stop(tts_h tts)
1543 {
1544         if (0 != __tts_get_feature_enabled()) {
1545                 return TTS_ERROR_NOT_SUPPORTED;
1546         }
1547
1548         SLOG(LOG_INFO, TAG_TTSC, "@@@ Stop tts");
1549
1550         if (NULL == tts) {
1551                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1552                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1553                 return TTS_ERROR_INVALID_PARAMETER;
1554         }
1555
1556         tts_client_s* client = tts_client_get(tts);
1557
1558         if (NULL == client) {
1559                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1560                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1561                 return TTS_ERROR_INVALID_PARAMETER;
1562         }
1563
1564         if (TTS_STATE_CREATED == client->current_state) {
1565                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Current state is 'CREATED'.");
1566                 return TTS_ERROR_INVALID_STATE;
1567         }
1568
1569         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1570                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1571                 return TTS_ERROR_INVALID_STATE;
1572         }
1573
1574         int ret = -1;
1575         int count = 0;
1576         bool is_prepared = false;
1577         while (0 != ret) {
1578                 ret = tts_dbus_request_stop(client->uid);
1579                 if (0 != ret) {
1580                         //LCOV_EXCL_START
1581                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1582                                 client->current_state = TTS_STATE_CREATED;
1583                                 if (0 == tts_prepare_sync(tts)) {
1584                                         is_prepared = true;
1585                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1586                                 }
1587                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1588                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1589                                 return ret;
1590                         } else {
1591                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry stop : %s", __tts_get_error_code(ret));
1592                                 usleep(10000);
1593                                 count++;
1594                                 if (TTS_RETRY_COUNT == count) {
1595                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1596                                         return ret;
1597                                 }
1598                         }
1599                         //LCOV_EXCL_STOP
1600                 }
1601         }
1602
1603         client->before_state = client->current_state;
1604         client->current_state = TTS_STATE_READY;
1605
1606         if (NULL != client->state_changed_cb) {
1607                 tts_client_use_callback(client);
1608                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1609                 tts_client_not_use_callback(client);
1610                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1611         }
1612
1613         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1614
1615         return TTS_ERROR_NONE;
1616 }
1617 //LCOV_EXCL_START
1618 static void __tts_pause_async(void *data)
1619 {
1620         tts_h tts = (tts_h)data;
1621         tts_client_s* client = tts_client_get(tts);
1622
1623         /* check handle */
1624         if (NULL == client) {
1625                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1626                 return;
1627         }
1628
1629         int ret = -1;
1630         int count = 0;
1631         bool is_prepared = false;
1632         while (0 != ret) {
1633                 ret = tts_dbus_request_pause(client->uid);
1634                 if (0 != ret) {
1635                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1636                                 client->current_state = TTS_STATE_CREATED;
1637                                 if (0 == tts_prepare_sync(tts)) {
1638                                         is_prepared = true;
1639                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1640                                 }
1641                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1642                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1643                                 break;
1644                         } else {
1645                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry pause : %s", __tts_get_error_code(ret));
1646                                 usleep(10000);
1647                                 count++;
1648                                 if (TTS_RETRY_COUNT == count) {
1649                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1650                                         break;
1651                                 }
1652                         }
1653                 }
1654         }
1655
1656         if (0 != ret) {
1657                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to pause tts : %s", __tts_get_error_code(ret));
1658
1659                 client->reason = ret;
1660                 client->utt_id = -1;
1661
1662                 ecore_timer_add(0, __tts_notify_error, client->tts);
1663                 return;
1664         }
1665
1666         client->before_state = client->current_state;
1667         client->current_state = TTS_STATE_PAUSED;
1668
1669         if (NULL != client->state_changed_cb) {
1670                 tts_client_use_callback(client);
1671                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1672                 tts_client_not_use_callback(client);
1673                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1674         }
1675
1676         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1677
1678         return;
1679 }
1680
1681 int tts_pause_async(tts_h tts)
1682 {
1683         if (0 != __tts_get_feature_enabled()) {
1684                 return TTS_ERROR_NOT_SUPPORTED;
1685         }
1686
1687         SLOG(LOG_DEBUG, TAG_TTSC, "@@@ Pause tts");
1688
1689         if (NULL == tts) {
1690                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1691                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1692                 return TTS_ERROR_INVALID_PARAMETER;
1693         }
1694
1695         tts_client_s* client = tts_client_get(tts);
1696
1697         if (NULL == client) {
1698                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1699                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1700                 return TTS_ERROR_INVALID_PARAMETER;
1701         }
1702
1703         if (TTS_STATE_PLAYING != client->current_state) {
1704                 SLOG(LOG_ERROR, TAG_TTSC, "[Error] The Current state is NOT 'playing'. So this request should be not running.");
1705                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1706                 return TTS_ERROR_INVALID_STATE;
1707         }
1708
1709         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1710                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1711                 return TTS_ERROR_INVALID_STATE;
1712         }
1713
1714         ecore_main_loop_thread_safe_call_async(__tts_pause_async, (void*)tts);
1715
1716         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1717
1718         return TTS_ERROR_NONE;
1719 }
1720 //LCOV_EXCL_STOP
1721 int tts_pause(tts_h tts)
1722 {
1723         if (0 != __tts_get_feature_enabled()) {
1724                 return TTS_ERROR_NOT_SUPPORTED;
1725         }
1726
1727         SLOG(LOG_INFO, TAG_TTSC, "@@@ Pause tts");
1728
1729         if (NULL == tts) {
1730                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1731                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1732                 return TTS_ERROR_INVALID_PARAMETER;
1733         }
1734
1735         tts_client_s* client = tts_client_get(tts);
1736
1737         if (NULL == client) {
1738                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1739                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1740                 return TTS_ERROR_INVALID_PARAMETER;
1741         }
1742
1743         if (TTS_STATE_PLAYING != client->current_state) {
1744                 SLOG(LOG_ERROR, TAG_TTSC, "[Error] The Current state is NOT 'playing'. So this request should be not running.");
1745                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1746                 return TTS_ERROR_INVALID_STATE;
1747         }
1748
1749         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
1750                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
1751                 return TTS_ERROR_INVALID_STATE;
1752         }
1753
1754         int ret = -1;
1755         int count = 0;
1756         bool is_prepared = false;
1757         while (0 != ret) {
1758                 ret = tts_dbus_request_pause(client->uid);
1759                 if (0 != ret) {
1760                         //LCOV_EXCL_START
1761                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1762                                 client->current_state = TTS_STATE_CREATED;
1763                                 if (0 == tts_prepare_sync(tts)) {
1764                                         is_prepared = true;
1765                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1766                                 }
1767                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1768                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1769                                 return ret;
1770                         } else {
1771                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry pause : %s", __tts_get_error_code(ret));
1772                                 usleep(10000);
1773                                 count++;
1774                                 if (TTS_RETRY_COUNT == count) {
1775                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1776                                         return ret;
1777                                 }
1778                         }
1779                         //LCOV_EXCL_STOP
1780                 }
1781         }
1782
1783         client->before_state = client->current_state;
1784         client->current_state = TTS_STATE_PAUSED;
1785
1786         if (NULL != client->state_changed_cb) {
1787                 tts_client_use_callback(client);
1788                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
1789                 tts_client_not_use_callback(client);
1790                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
1791         }
1792
1793         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1794
1795         return TTS_ERROR_NONE;
1796 }
1797
1798 int tts_set_private_data(tts_h tts, const char* key, const char* data)
1799 {
1800         if (0 != __tts_get_feature_enabled()) {
1801                 return TTS_ERROR_NOT_SUPPORTED;
1802         }
1803
1804         SLOG(LOG_INFO, TAG_TTSC, "@@@ Set private data, key(%s), data(%s)", key, data);
1805
1806         if (NULL == tts) {
1807                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1808                 return TTS_ERROR_INVALID_PARAMETER;
1809         }
1810
1811         if (NULL == key || NULL == data) {
1812                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid parameter");
1813                 return TTS_ERROR_INVALID_PARAMETER;
1814         }
1815
1816         tts_client_s* client = tts_client_get(tts);
1817
1818         if (NULL == client) {
1819                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1820                 return TTS_ERROR_INVALID_PARAMETER;
1821         }
1822
1823         if (TTS_STATE_READY != client->current_state) {
1824                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid state : Current state is NOT 'READY'");
1825                 return TTS_ERROR_INVALID_STATE;
1826         }
1827
1828         if (true != client->internal && (0 == strcmp(key, "EnableServerTTS") || 0 == strcmp(key, "DisableServerTTS"))) {
1829                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] This is not an internal app");
1830                 return TTS_ERROR_INVALID_PARAMETER;
1831         }
1832
1833         int ret = -1;
1834         int count = 0;
1835         bool is_prepared = false;
1836         while (0 != ret) {
1837                 ret = tts_dbus_request_set_private_data(client->uid, key, data);
1838                 if (0 != ret) {
1839                         //LCOV_EXCL_START
1840                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1841                                 client->current_state = TTS_STATE_CREATED;
1842                                 if (0 == tts_prepare_sync(tts)) {
1843                                         is_prepared = true;
1844                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1845                                 }
1846                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1847                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1848                                 return ret;
1849                         } else {
1850                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry : %s", __tts_get_error_code(ret));
1851                                 usleep(10000);
1852                                 count++;
1853                                 if (TTS_RETRY_COUNT == count) {
1854                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1855                                         return ret;
1856                                 }
1857                         }
1858                         //LCOV_EXCL_STOP
1859                 }
1860         }
1861
1862         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1863
1864         return 0;
1865 }
1866
1867 int tts_get_private_data(tts_h tts, const char* key, char** data)
1868 {
1869         if (0 != __tts_get_feature_enabled()) {
1870                 return TTS_ERROR_NOT_SUPPORTED;
1871         }
1872
1873         SLOG(LOG_INFO, TAG_TTSC, "@@@ Get private data, key(%s)", key);
1874
1875         if (NULL == tts) {
1876                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null");
1877                 return TTS_ERROR_INVALID_PARAMETER;
1878         }
1879
1880         if (NULL == key || NULL == data) {
1881                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid parameter");
1882                 return TTS_ERROR_INVALID_PARAMETER;
1883         }
1884
1885         tts_client_s* client = tts_client_get(tts);
1886
1887         if (NULL == client) {
1888                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid");
1889                 return TTS_ERROR_INVALID_PARAMETER;
1890         }
1891
1892         if (TTS_STATE_READY != client->current_state) {
1893                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Invalid state : Current state is NOT 'READY'");
1894                 return TTS_ERROR_INVALID_STATE;
1895         }
1896
1897         int ret = -1;
1898         int count = 0;
1899         bool is_prepared = false;
1900         while (0 != ret) {
1901                 ret = tts_dbus_request_get_private_data(client->uid, key, data);
1902                 if (0 != ret) {
1903                         //LCOV_EXCL_START
1904                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
1905                                 client->current_state = TTS_STATE_CREATED;
1906                                 if (0 == tts_prepare_sync(tts)) {
1907                                         is_prepared = true;
1908                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
1909                                 }
1910                         } else if (TTS_ERROR_TIMED_OUT != ret) {
1911                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
1912                                 return ret;
1913                         } else {
1914                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry : %s", __tts_get_error_code(ret));
1915                                 usleep(10000);
1916                                 count++;
1917                                 if (TTS_RETRY_COUNT == count) {
1918                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
1919                                         return ret;
1920                                 }
1921                         }
1922                         //LCOV_EXCL_STOP
1923                 }
1924         }
1925
1926         if (0 == strncmp(*data, "NULL", strlen(*data))) {
1927                 free(*data);
1928                 *data = NULL;
1929         }
1930
1931         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
1932
1933         return 0;
1934 }
1935
1936 //LCOV_EXCL_START
1937 static Eina_Bool __tts_notify_error(void *data)
1938 {
1939         tts_h tts = (tts_h)data;
1940
1941         tts_client_s* client = tts_client_get(tts);
1942
1943         /* check handle */
1944         if (NULL == client) {
1945                 SLOG(LOG_WARN, TAG_TTSC, "Fail to notify error msg : A handle is not valid");
1946                 return EINA_FALSE;
1947         }
1948
1949         SLOG(LOG_DEBUG, TAG_TTSC, "Error data : uttid(%d) reason(%s)", client->utt_id, __tts_get_error_code(client->reason));
1950
1951         if (NULL != client->error_cb) {
1952                 SLOG(LOG_DEBUG, TAG_TTSC, "Call callback function of error");
1953                 tts_client_use_callback(client);
1954                 g_err_callback_status = true;
1955                 client->error_cb(client->tts, client->utt_id, client->reason, client->error_user_data);
1956                 g_err_callback_status = false;
1957                 tts_client_not_use_callback(client);
1958         } else {
1959                 SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of error ");
1960         }
1961
1962         return EINA_FALSE;
1963 }
1964
1965 int __tts_cb_error(int uid, tts_error_e reason, int utt_id, char* err_msg)
1966 {
1967         if (-1 == uid) {
1968                 GList* client_list = NULL;
1969                 client_list = tts_client_get_client_list();
1970
1971                 GList *iter = NULL;
1972                 tts_client_s *data = NULL;
1973
1974                 if (g_list_length(client_list) > 0) {
1975                         /* Get a first item */
1976                         iter = g_list_first(client_list);
1977
1978                         while (NULL != iter) {
1979                                 data = iter->data;
1980
1981                                 data->utt_id = utt_id;
1982                                 data->reason = reason;
1983                                 if (NULL != data->err_msg) {
1984                                         free(data->err_msg);
1985                                         data->err_msg = NULL;
1986                                 }
1987                                 if (NULL != err_msg)
1988                                         data->err_msg = strdup(err_msg);
1989
1990                                 /* call callback function */
1991                                 if (NULL != data->error_cb) {
1992                                         ecore_timer_add(0, __tts_notify_error, data->tts);
1993                                 } else {
1994                                         SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of error ");
1995                                 }
1996
1997                                 if (TTS_ERROR_SERVICE_RESET == reason) {
1998                                         SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Service Reset");
1999
2000                                         data->current_state = TTS_STATE_CREATED;
2001                                         if (0 != tts_prepare(data->tts)) {
2002                                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to prepare");
2003                                         }
2004                                 }
2005
2006                                 /* Next item */
2007                                 iter = g_list_next(iter);
2008                         }
2009                 }
2010         } else {
2011                 tts_client_s* client = tts_client_get_by_uid(uid);
2012
2013                 if (NULL == client) {
2014                         SLOG(LOG_WARN, TAG_TTSC, "[WARNING] A handle is not valid");
2015                         return TTS_ERROR_INVALID_PARAMETER;
2016                 }
2017
2018                 client->utt_id = utt_id;
2019                 client->reason = reason;
2020                 if (NULL != client->err_msg) {
2021                         free(client->err_msg);
2022                         client->err_msg = NULL;
2023                 }
2024                 if (NULL != err_msg)
2025                         client->err_msg = strdup(err_msg);
2026
2027                 /* call callback function */
2028                 if (NULL != client->error_cb) {
2029                         ecore_timer_add(0, __tts_notify_error, client->tts);
2030                 } else {
2031                         SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of error ");
2032                 }
2033
2034                 if (TTS_ERROR_SERVICE_RESET == reason) {
2035                         SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Service Reset");
2036
2037                         client->current_state = TTS_STATE_CREATED;
2038                         if (0 != tts_prepare(client->tts)) {
2039                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to prepare");
2040                         }
2041                 }
2042         }
2043
2044         return 0;
2045 }
2046
2047 static Eina_Bool __tts_notify_state_changed(void *data)
2048 {
2049         tts_h tts = (tts_h)data;
2050
2051         tts_client_s* client = tts_client_get(tts);
2052
2053         /* check handle */
2054         if (NULL == client) {
2055                 SLOG(LOG_WARN, TAG_TTSC, "Fail to notify state changed : A handle is not valid");
2056                 return EINA_FALSE;
2057         }
2058
2059         if (NULL != client->state_changed_cb) {
2060                 tts_client_use_callback(client);
2061                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
2062                 tts_client_not_use_callback(client);
2063                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called : pre(%d) cur(%d)", client->before_state, client->current_state);
2064         } else {
2065                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] State changed callback is null");
2066         }
2067
2068         return EINA_FALSE;
2069 }
2070
2071 int __tts_cb_set_state(int uid, int state)
2072 {
2073         tts_client_s* client = tts_client_get_by_uid(uid);
2074         if (NULL == client) {
2075                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] The handle is not valid");
2076                 return -1;
2077         }
2078
2079         tts_state_e state_from_daemon = (tts_state_e)state;
2080
2081         if (client->current_state == state_from_daemon) {
2082                 SLOG(LOG_DEBUG, TAG_TTSC, "Current state has already been %d", client->current_state);
2083                 return 0;
2084         }
2085
2086         if (NULL != client->state_changed_cb) {
2087                 ecore_timer_add(0, __tts_notify_state_changed, client->tts);
2088         } else {
2089                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] State changed callback is null");
2090         }
2091
2092         client->before_state = client->current_state;
2093         client->current_state = state_from_daemon;
2094
2095         return 0;
2096 }
2097 //LCOV_EXCL_STOP
2098
2099 int __tts_cb_utt_started(int uid, int utt_id)
2100 {
2101         tts_client_s* client = tts_client_get_by_uid(uid);
2102
2103         if (NULL == client) {
2104                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] A handle is not valid");
2105                 return TTS_ERROR_INVALID_PARAMETER;
2106         }
2107
2108         SLOG(LOG_INFO, TAG_TTSC, "utterance started : utt id(%d) ", utt_id);
2109
2110         client->utt_id = utt_id;
2111
2112         /* call callback function */
2113         if (NULL != client->utt_started_cb) {
2114                 SLOG(LOG_DEBUG, TAG_TTSC, "Call callback function of utterance started ");
2115                 tts_client_use_callback(client);
2116                 client->utt_started_cb(client->tts, client->utt_id, client->utt_started_user_data);
2117                 tts_client_not_use_callback(client);
2118         } else {
2119                 SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of utterance started ");
2120         }
2121
2122         return 0;
2123 }
2124
2125 int __tts_cb_utt_completed(int uid, int utt_id)
2126 {
2127         tts_client_s* client = tts_client_get_by_uid(uid);
2128
2129         if (NULL == client) {
2130                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] A handle is not valid");
2131                 return TTS_ERROR_INVALID_PARAMETER;
2132         }
2133
2134         SLOG(LOG_INFO, TAG_TTSC, "utterance completed : uttid(%d) ", utt_id);
2135
2136         client->utt_id = utt_id;
2137
2138         /* call callback function */
2139         if (NULL != client->utt_completeted_cb) {
2140                 SLOG(LOG_DEBUG, TAG_TTSC, "Call callback function of utterance completed ");
2141                 tts_client_use_callback(client);
2142                 client->utt_completeted_cb(client->tts, client->utt_id, client->utt_completed_user_data);
2143                 tts_client_not_use_callback(client);
2144         } else {
2145                 SLOG(LOG_WARN, TAG_TTSC, "No registered callback function of utterance completed ");
2146         }
2147
2148         return 0;
2149 }
2150
2151 int tts_set_state_changed_cb(tts_h tts, tts_state_changed_cb callback, void* user_data)
2152 {
2153         if (0 != __tts_get_feature_enabled()) {
2154                 return TTS_ERROR_NOT_SUPPORTED;
2155         }
2156
2157         if (NULL == tts || NULL == callback) {
2158                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set state changed cb : Input parameter is null");
2159                 return TTS_ERROR_INVALID_PARAMETER;
2160         }
2161
2162         tts_client_s* client = tts_client_get(tts);
2163
2164         if (NULL == client) {
2165                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set state changed cb : A handle is not valid");
2166                 return TTS_ERROR_INVALID_PARAMETER;
2167         }
2168
2169         if (TTS_STATE_CREATED != client->current_state) {
2170                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set state changed cb : Current state is not 'Created'.");
2171                 return TTS_ERROR_INVALID_STATE;
2172         }
2173
2174         client->state_changed_cb = callback;
2175         client->state_changed_user_data = user_data;
2176
2177         SLOG(LOG_INFO, TAG_TTSC, "[SUCCESS] Set state changed cb");
2178
2179         return 0;
2180 }
2181
2182 int tts_unset_state_changed_cb(tts_h tts)
2183 {
2184         if (0 != __tts_get_feature_enabled()) {
2185                 return TTS_ERROR_NOT_SUPPORTED;
2186         }
2187
2188         if (NULL == tts) {
2189                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset state changed cb : Input parameter is null");
2190                 return TTS_ERROR_INVALID_PARAMETER;
2191         }
2192
2193         tts_client_s* client = tts_client_get(tts);
2194
2195         if (NULL == client) {
2196                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset state changed cb : A handle is not valid");
2197                 return TTS_ERROR_INVALID_PARAMETER;
2198         }
2199
2200         if (TTS_STATE_CREATED != client->current_state) {
2201                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset state changed cb : Current state is not 'Created'.");
2202                 return TTS_ERROR_INVALID_STATE;
2203         }
2204
2205         client->state_changed_cb = NULL;
2206         client->state_changed_user_data = NULL;
2207
2208         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset state changed cb");
2209
2210         return 0;
2211 }
2212
2213 int tts_set_utterance_started_cb(tts_h tts, tts_utterance_started_cb callback, void* user_data)
2214 {
2215         if (0 != __tts_get_feature_enabled()) {
2216                 return TTS_ERROR_NOT_SUPPORTED;
2217         }
2218
2219         if (NULL == tts || NULL == callback) {
2220                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt started cb : Input parameter is null");
2221                 return TTS_ERROR_INVALID_PARAMETER;
2222         }
2223
2224         tts_client_s* client = tts_client_get(tts);
2225
2226         if (NULL == client) {
2227                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt started cb : A handle is not valid");
2228                 return TTS_ERROR_INVALID_PARAMETER;
2229         }
2230
2231         if (TTS_STATE_CREATED != client->current_state) {
2232                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt started cb : Current state is not 'Created'.");
2233                 return TTS_ERROR_INVALID_STATE;
2234         }
2235
2236         client->utt_started_cb = callback;
2237         client->utt_started_user_data = user_data;
2238
2239         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Set utt started cb");
2240
2241         return 0;
2242 }
2243
2244 int tts_unset_utterance_started_cb(tts_h tts)
2245 {
2246         if (0 != __tts_get_feature_enabled()) {
2247                 return TTS_ERROR_NOT_SUPPORTED;
2248         }
2249
2250         if (NULL == tts) {
2251                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt started cb : Input parameter is null");
2252                 return TTS_ERROR_INVALID_PARAMETER;
2253         }
2254
2255         tts_client_s* client = tts_client_get(tts);
2256
2257         if (NULL == client) {
2258                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt started cb : A handle is not valid");
2259                 return TTS_ERROR_INVALID_PARAMETER;
2260         }
2261
2262         if (TTS_STATE_CREATED != client->current_state) {
2263                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt started cb : Current state is not 'Created'.");
2264                 return TTS_ERROR_INVALID_STATE;
2265         }
2266
2267         client->utt_started_cb = NULL;
2268         client->utt_started_user_data = NULL;
2269
2270         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset utt started cb");
2271
2272         return 0;
2273 }
2274
2275 int tts_set_utterance_completed_cb(tts_h tts, tts_utterance_completed_cb callback, void* user_data)
2276 {
2277         if (0 != __tts_get_feature_enabled()) {
2278                 return TTS_ERROR_NOT_SUPPORTED;
2279         }
2280
2281         if (NULL == tts || NULL == callback) {
2282                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt completed cb : Input parameter is null");
2283                 return TTS_ERROR_INVALID_PARAMETER;
2284         }
2285
2286         tts_client_s* client = tts_client_get(tts);
2287
2288         if (NULL == client) {
2289                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt completed cb : A handle is not valid");
2290                 return TTS_ERROR_INVALID_PARAMETER;
2291         }
2292
2293         if (TTS_STATE_CREATED != client->current_state) {
2294                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set utt completed cb : Current state is not 'Created'.");
2295                 return TTS_ERROR_INVALID_STATE;
2296         }
2297
2298         client->utt_completeted_cb = callback;
2299         client->utt_completed_user_data = user_data;
2300
2301         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Set utt completed cb");
2302
2303         return 0;
2304 }
2305
2306 int tts_unset_utterance_completed_cb(tts_h tts)
2307 {
2308         if (0 != __tts_get_feature_enabled()) {
2309                 return TTS_ERROR_NOT_SUPPORTED;
2310         }
2311
2312         if (NULL == tts) {
2313                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt completed cb : Input parameter is null");
2314                 return TTS_ERROR_INVALID_PARAMETER;
2315         }
2316
2317         tts_client_s* client = tts_client_get(tts);
2318
2319         if (NULL == client) {
2320                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt completed cb : A handle is not valid");
2321                 return TTS_ERROR_INVALID_PARAMETER;
2322         }
2323
2324         if (TTS_STATE_CREATED != client->current_state) {
2325                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset utt completed cb : Current state is not 'Created'.");
2326                 return TTS_ERROR_INVALID_STATE;
2327         }
2328
2329         client->utt_completeted_cb = NULL;
2330         client->utt_completed_user_data = NULL;
2331
2332         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset utt completed cb");
2333         return 0;
2334 }
2335
2336 int tts_set_error_cb(tts_h tts, tts_error_cb callback, void* user_data)
2337 {
2338         if (0 != __tts_get_feature_enabled()) {
2339                 return TTS_ERROR_NOT_SUPPORTED;
2340         }
2341
2342         if (NULL == tts || NULL == callback) {
2343                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set error cb : Input parameter is null");
2344                 return TTS_ERROR_INVALID_PARAMETER;
2345         }
2346
2347         tts_client_s* client = tts_client_get(tts);
2348
2349         if (NULL == client) {
2350                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set error cb : A handle is not valid");
2351                 return TTS_ERROR_INVALID_PARAMETER;
2352         }
2353
2354         if (TTS_STATE_CREATED != client->current_state) {
2355                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set error cb : Current state is not 'Created'.");
2356                 return TTS_ERROR_INVALID_STATE;
2357         }
2358
2359         client->error_cb = callback;
2360         client->error_user_data = user_data;
2361
2362         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Set error cb");
2363
2364         return 0;
2365 }
2366
2367 int tts_unset_error_cb(tts_h tts)
2368 {
2369         if (0 != __tts_get_feature_enabled()) {
2370                 return TTS_ERROR_NOT_SUPPORTED;
2371         }
2372
2373         if (NULL == tts) {
2374                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset error cb : Input parameter is null");
2375                 return TTS_ERROR_INVALID_PARAMETER;
2376         }
2377
2378         tts_client_s* client = tts_client_get(tts);
2379
2380         if (NULL == client) {
2381                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset error cb : A handle is not valid");
2382                 return TTS_ERROR_INVALID_PARAMETER;
2383         }
2384
2385         if (TTS_STATE_CREATED != client->current_state) {
2386                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset error cb : Current state is not 'Created'.");
2387                 return TTS_ERROR_INVALID_STATE;
2388         }
2389
2390         client->error_cb = NULL;
2391         client->error_user_data = NULL;
2392
2393         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset error cb");
2394
2395         return 0;
2396 }
2397
2398 int tts_set_default_voice_changed_cb(tts_h tts, tts_default_voice_changed_cb callback, void* user_data)
2399 {
2400         if (0 != __tts_get_feature_enabled()) {
2401                 return TTS_ERROR_NOT_SUPPORTED;
2402         }
2403
2404         if (NULL == tts || NULL == callback) {
2405                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set default voice changed cb : Input parameter is null");
2406                 return TTS_ERROR_INVALID_PARAMETER;
2407         }
2408
2409         tts_client_s* client = tts_client_get(tts);
2410
2411         if (NULL == client) {
2412                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set default voice changed cb : A handle is not valid");
2413                 return TTS_ERROR_INVALID_PARAMETER;
2414         }
2415
2416         if (TTS_STATE_CREATED != client->current_state) {
2417                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set default voice changed cb : Current state is not 'Created'.");
2418                 return TTS_ERROR_INVALID_STATE;
2419         }
2420
2421         client->default_voice_changed_cb = callback;
2422         client->default_voice_changed_user_data = user_data;
2423
2424         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Set default voice changed cb");
2425
2426         return 0;
2427 }
2428
2429 int tts_unset_default_voice_changed_cb(tts_h tts)
2430 {
2431         if (0 != __tts_get_feature_enabled()) {
2432                 return TTS_ERROR_NOT_SUPPORTED;
2433         }
2434
2435         if (NULL == tts) {
2436                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset default voice changed cb : Input parameter is null");
2437                 return TTS_ERROR_INVALID_PARAMETER;
2438         }
2439
2440         tts_client_s* client = tts_client_get(tts);
2441
2442         if (NULL == client) {
2443                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset default voice changed cb : A handle is not valid");
2444                 return TTS_ERROR_INVALID_PARAMETER;
2445         }
2446
2447         if (TTS_STATE_CREATED != client->current_state) {
2448                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset default voice changed cb : Current state is not 'Created'.");
2449                 return TTS_ERROR_INVALID_STATE;
2450         }
2451
2452         client->default_voice_changed_cb = NULL;
2453         client->default_voice_changed_user_data = NULL;
2454
2455         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset default voice changed cb");
2456
2457         return 0;
2458 }
2459
2460 int tts_set_engine_changed_cb(tts_h tts, tts_engine_changed_cb callback, void* user_data)
2461 {
2462         if (0 != __tts_get_feature_enabled()) {
2463                 return TTS_ERROR_NOT_SUPPORTED;
2464         }
2465
2466         if (NULL == tts || NULL == callback) {
2467                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set engine changed cb : Input parameter is null");
2468                 return TTS_ERROR_INVALID_PARAMETER;
2469         }
2470
2471         tts_client_s* client = tts_client_get(tts);
2472
2473         if (NULL == client) {
2474                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set engine changed cb : A handle is not valid");
2475                 return TTS_ERROR_INVALID_PARAMETER;
2476         }
2477
2478         if (TTS_STATE_CREATED != client->current_state) {
2479                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Set engine changed cb : Current state is not 'Created'.");
2480                 return TTS_ERROR_INVALID_STATE;
2481         }
2482
2483         client->engine_changed_cb = callback;
2484         client->engine_changed_user_data = user_data;
2485
2486         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Set engine changed cb");
2487
2488         return 0;
2489 }
2490
2491 int tts_unset_engine_changed_cb(tts_h tts)
2492 {
2493         if (0 != __tts_get_feature_enabled()) {
2494                 return TTS_ERROR_NOT_SUPPORTED;
2495         }
2496
2497         if (NULL == tts) {
2498                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset engine changed cb : Input parameter is null");
2499                 return TTS_ERROR_INVALID_PARAMETER;
2500         }
2501
2502         tts_client_s* client = tts_client_get(tts);
2503
2504         if (NULL == client) {
2505                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset engine changed cb : A handle is not valid");
2506                 return TTS_ERROR_INVALID_PARAMETER;
2507         }
2508
2509         if (TTS_STATE_CREATED != client->current_state) {
2510                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Unset engine changed cb : Current state is not 'Created'.");
2511                 return TTS_ERROR_INVALID_STATE;
2512         }
2513
2514         client->engine_changed_cb = NULL;
2515         client->engine_changed_user_data = NULL;
2516
2517         SLOG(LOG_DEBUG, TAG_TTSC, "[SUCCESS] Unset engine changed cb");
2518
2519         return 0;
2520 }
2521
2522 //LCOV_EXCL_START
2523 int tts_add_pcm(tts_h tts, int event, const void* data, unsigned int data_size, int audio_type, int rate)
2524 {
2525         if (0 != __tts_get_feature_enabled()) {
2526                 return TTS_ERROR_NOT_SUPPORTED;
2527         }
2528
2529         SLOG(LOG_INFO, TAG_TTSC, "@@@ Add pcm tts");
2530
2531         if (NULL == tts) {
2532                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
2533                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2534                 return TTS_ERROR_INVALID_PARAMETER;
2535         }
2536
2537         tts_client_s* client = tts_client_get(tts);
2538
2539         if (NULL == client) {
2540                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
2541                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2542                 return TTS_ERROR_INVALID_PARAMETER;
2543         }
2544
2545         if (TTS_STATE_CREATED == client->current_state) {
2546                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid.");
2547                 return TTS_ERROR_INVALID_STATE;
2548         }
2549
2550         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
2551                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
2552                 return TTS_ERROR_INVALID_STATE;
2553         }
2554
2555         int ret = -1;
2556         int count = 0;
2557         bool is_prepared = false;
2558         while (0 != ret) {
2559                 ret = tts_dbus_request_add_pcm(client->uid, event, data, data_size, audio_type, rate);
2560                 if (0 != ret) {
2561                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
2562                                 client->current_state = TTS_STATE_CREATED;
2563                                 if (0 == tts_prepare_sync(tts)) {
2564                                         is_prepared = true;
2565                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
2566                                 }
2567                         } else if (TTS_ERROR_TIMED_OUT != ret) {
2568                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
2569                                 return ret;
2570                         } else {
2571                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry add pcm : %s", __tts_get_error_code(ret));
2572                                 usleep(10000);
2573                                 count++;
2574                                 if (TTS_RETRY_COUNT == count) {
2575                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
2576                                         return ret;
2577                                 }
2578                         }
2579                 }
2580         }
2581
2582         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2583
2584         return TTS_ERROR_NONE;
2585 }
2586
2587 int tts_play_pcm(tts_h tts)
2588 {
2589         if (0 != __tts_get_feature_enabled()) {
2590                 return TTS_ERROR_NOT_SUPPORTED;
2591         }
2592
2593         SLOG(LOG_INFO, TAG_TTSC, "@@@ Play pcm tts");
2594
2595         if (NULL == tts) {
2596                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
2597                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2598                 return TTS_ERROR_INVALID_PARAMETER;
2599         }
2600
2601         tts_client_s* client = tts_client_get(tts);
2602
2603         if (NULL == client) {
2604                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
2605                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2606                 return TTS_ERROR_INVALID_PARAMETER;
2607         }
2608
2609         if (TTS_STATE_PLAYING == client->current_state || TTS_STATE_CREATED == client->current_state) {
2610                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid.");
2611                 return TTS_ERROR_INVALID_STATE;
2612         }
2613
2614         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
2615                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
2616                 return TTS_ERROR_INVALID_STATE;
2617         }
2618
2619         int ret = -1;
2620         int count = 0;
2621         bool is_prepared = false;
2622         while (0 != ret) {
2623                 ret = tts_dbus_request_play_pcm(client->uid);
2624                 if (0 != ret) {
2625                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
2626                                 client->current_state = TTS_STATE_CREATED;
2627                                 if (0 == tts_prepare_sync(tts)) {
2628                                         is_prepared = true;
2629                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
2630                                 }
2631                         } else if (TTS_ERROR_TIMED_OUT != ret) {
2632                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
2633                                 return ret;
2634                         } else {
2635                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry play pcm : %s", __tts_get_error_code(ret));
2636                                 usleep(10000);
2637                                 count++;
2638                                 if (TTS_RETRY_COUNT == count) {
2639                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
2640                                         return ret;
2641                                 }
2642                         }
2643                 }
2644         }
2645
2646         client->before_state = client->current_state;
2647         client->current_state = TTS_STATE_PLAYING;
2648
2649         if (NULL != client->state_changed_cb) {
2650                 tts_client_use_callback(client);
2651                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
2652                 tts_client_not_use_callback(client);
2653                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
2654         }
2655
2656         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2657
2658         return TTS_ERROR_NONE;
2659 }
2660
2661 int tts_stop_pcm(tts_h tts)
2662 {
2663         if (0 != __tts_get_feature_enabled()) {
2664                 return TTS_ERROR_NOT_SUPPORTED;
2665         }
2666
2667         SLOG(LOG_INFO, TAG_TTSC, "@@@ Stop pcm tts");
2668
2669         if (NULL == tts) {
2670                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
2671                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2672                 return TTS_ERROR_INVALID_PARAMETER;
2673         }
2674
2675         tts_client_s* client = tts_client_get(tts);
2676
2677         if (NULL == client) {
2678                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
2679                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2680                 return TTS_ERROR_INVALID_PARAMETER;
2681         }
2682
2683         if (TTS_STATE_CREATED == client->current_state) {
2684                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid.");
2685                 return TTS_ERROR_INVALID_STATE;
2686         }
2687
2688         if (false == g_screen_reader && TTS_MODE_SCREEN_READER == client->mode) {
2689                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] Screen reader option is NOT available. Ignore this request");
2690                 return TTS_ERROR_INVALID_STATE;
2691         }
2692
2693         int ret = -1;
2694         int count = 0;
2695         bool is_prepared = false;
2696         while (0 != ret) {
2697                 ret = tts_dbus_request_stop_pcm(client->uid);
2698                 if (0 != ret) {
2699                         if (TTS_ERROR_INVALID_PARAMETER == ret && false == is_prepared) {
2700                                 client->current_state = TTS_STATE_CREATED;
2701                                 if (0 == tts_prepare_sync(tts)) {
2702                                         is_prepared = true;
2703                                         SLOG(LOG_INFO, TAG_TTSC, "[INFO] Success tts_prepare_sync");
2704                                 }
2705                         } else if (TTS_ERROR_TIMED_OUT != ret) {
2706                                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] result : %s", __tts_get_error_code(ret));
2707                                 return ret;
2708                         } else {
2709                                 SLOG(LOG_WARN, TAG_TTSC, "[WARNING] retry stop pcm : %s", __tts_get_error_code(ret));
2710                                 usleep(10000);
2711                                 count++;
2712                                 if (TTS_RETRY_COUNT == count) {
2713                                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to request");
2714                                         return ret;
2715                                 }
2716                         }
2717                 }
2718         }
2719
2720         client->before_state = client->current_state;
2721         client->current_state = TTS_STATE_READY;
2722
2723         if (NULL != client->state_changed_cb) {
2724                 tts_client_use_callback(client);
2725                 client->state_changed_cb(client->tts, client->before_state, client->current_state, client->state_changed_user_data);
2726                 tts_client_not_use_callback(client);
2727                 SLOG(LOG_DEBUG, TAG_TTSC, "State changed callback is called");
2728         }
2729
2730         SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2731
2732         return TTS_ERROR_NONE;
2733 }
2734 //LCOV_EXCL_STOP
2735
2736 int tts_repeat(tts_h tts, char** text_repeat, int* utt_id)
2737 {
2738         if (0 != __tts_get_feature_enabled()) {
2739                 return TTS_ERROR_NOT_SUPPORTED;
2740         }
2741
2742         SLOG(LOG_INFO, TAG_TTSC, "@@@ Repeat TTS");
2743
2744         if (NULL == tts) {
2745                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input handle is null.");
2746                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2747                 return TTS_ERROR_INVALID_PARAMETER;
2748         }
2749
2750         if (NULL == text_repeat || NULL == utt_id) {
2751                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Input parameter is null.");
2752                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2753                 return TTS_ERROR_INVALID_PARAMETER;
2754         }
2755
2756         *text_repeat = NULL;
2757         *utt_id = -1;
2758
2759         tts_client_s* client = tts_client_get(tts);
2760
2761         if (NULL == client) {
2762                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] A handle is not valid.");
2763                 SLOG(LOG_DEBUG, TAG_TTSC, "@@@");
2764                 return TTS_ERROR_INVALID_PARAMETER;
2765         }
2766
2767         if (TTS_STATE_READY != client->current_state) {
2768                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] The current state is invalid. (%d)", client->current_state);
2769                 return TTS_ERROR_INVALID_STATE;
2770         }
2771
2772         /* Clear the legacy and Add texts to be played repeatedly */
2773         int ret = -1;
2774         ret = tts_stop(tts);
2775         if (TTS_ERROR_NONE != ret) {
2776                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to clear the legacy");
2777                 return ret;
2778         }
2779
2780         if (NULL != client->text_repeat) {
2781                 char* tmp_text = strdup(client->text_repeat);
2782                 char* tmp_lang = NULL;
2783                 if (NULL != g_language) {
2784                         tmp_lang = strdup(g_language);
2785                 }
2786                 ret = tts_add_text(tts, tmp_text, tmp_lang, g_voice_type, g_speed, utt_id);
2787                 if (TTS_ERROR_NONE != ret) {
2788                         SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to add texts for repetition.");
2789                         if (NULL != tmp_text) {
2790                                 free(tmp_text);
2791                                 tmp_text = NULL;
2792                         }
2793                         if (NULL != tmp_lang) {
2794                                 free(tmp_lang);
2795                                 tmp_lang = NULL;
2796                         }
2797                         return ret;
2798                 }
2799                 *text_repeat = strdup(client->text_repeat);
2800                 SLOG(LOG_DEBUG, TAG_TTSC, "[DEBUG] text to repeat(%s), utt_id(%d)", *text_repeat, *utt_id);
2801                 if (NULL != tmp_text) {
2802                         free(tmp_text);
2803                         tmp_text = NULL;
2804                 }
2805                 if (NULL != tmp_lang) {
2806                         free(tmp_lang);
2807                         tmp_lang = NULL;
2808                 }
2809         } else {
2810                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] There is no previous added texts. Please add texts");
2811                 return TTS_ERROR_OPERATION_FAILED;
2812         }
2813
2814         /* Play added texts */
2815         ret = tts_play(tts);
2816         if (TTS_ERROR_NONE != ret) {
2817                 SLOG(LOG_ERROR, TAG_TTSC, "[ERROR] Fail to play texts for repetition.");
2818                 if (NULL != *text_repeat) {
2819                         free(*text_repeat);
2820                         *text_repeat = NULL;
2821                 }
2822                 *utt_id = -1;
2823                 return ret;
2824         }
2825
2826         return TTS_ERROR_NONE;
2827 }