Extend timeout value for recognition processing
[platform/core/uifw/stt.git] / server / sttd_engine_agent.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
15 #include <dlfcn.h>
16 #include <dirent.h>
17
18 #include "stt_defs.h"
19 #include "stt_engine.h"
20 #include "sttd_main.h"
21 #include "sttd_client_data.h"
22 #include "sttd_config.h"
23 #include "sttd_dbus.h"
24 #include "sttd_recorder.h"
25 #include "sttd_engine_agent.h"
26 #include "stt_dlog.h"
27
28
29 #define AUDIO_CREATE_ON_START
30
31 /*
32 * Internal data structure
33 */
34
35 typedef struct _sttengine_info {
36         char*   engine_uuid;
37         char*   engine_path;
38         char*   engine_name;
39         char*   engine_setting_path;
40         bool    use_network;
41
42         bool    is_loaded;
43
44         /* engine base setting */
45         char*   first_lang;
46         bool    silence_detection;
47         bool    support_silence_detection;
48         bool    need_credential;
49 } sttengine_info_s;
50
51 /** stt engine agent init */
52 static bool     g_agent_init;
53
54 static sttengine_info_s* g_engine_info = NULL;
55
56 /** default engine info */
57 static char*    g_default_language = NULL;
58 static bool     g_default_silence_detected;
59
60 /** callback functions */
61 static result_callback g_result_cb = NULL;
62 static result_time_callback g_result_time_cb = NULL;
63 static speech_status_callback g_speech_status_cb = NULL;
64 static error_callback g_error_cb = NULL;
65
66 /** callback functions */
67 static bool __result_time_cb(int index, stte_result_time_event_e event, const char* text,
68                       long start_time, long end_time, void* user_data);
69
70 /*
71 * Internal Interfaces
72 */
73
74 /** get engine info */
75 static int __internal_get_engine_info(stte_request_callback_s *callback, sttengine_info_s** info);
76
77 static int __log_enginelist();
78
79 /*
80 * STT Engine Agent Interfaces
81 */
82 int sttd_engine_agent_init(result_callback result_cb, result_time_callback time_cb,
83                            speech_status_callback speech_status_cb, error_callback error_cb)
84 {
85         /* initialize static data */
86         if (NULL == result_cb || NULL == time_cb || NULL == speech_status_cb || NULL == error_cb) {
87                 SLOG(LOG_ERROR, TAG_STTD, "[Engine agent ERROR] Invalid parameter");
88                 return STTD_ERROR_INVALID_PARAMETER;
89         }
90
91         g_result_cb = result_cb;
92         g_result_time_cb = time_cb;
93         g_speech_status_cb = speech_status_cb;
94         g_error_cb = error_cb;
95
96         g_default_language = NULL;
97
98         if (0 != sttd_config_get_default_language(&(g_default_language))) {
99                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent WARNING] There is No default voice in config");
100                 /* Set default voice */
101                 g_default_language = strdup("en_US");
102         } else {
103                 SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Default language is %s", g_default_language);
104         }
105
106         int temp;
107         if (0 != sttd_config_get_default_silence_detection(&temp)) {
108                 SLOG(LOG_WARN, TAG_STTD, "[Server WARNING] There is no silence detection in config");
109                 g_default_silence_detected = true;
110         } else {
111                 g_default_silence_detected = (bool)temp;
112         }
113
114         g_agent_init = true;
115
116         return 0;
117 }
118
119 int __engine_agent_clear_engine(sttengine_info_s *engine)
120 {
121         if (NULL != engine) {
122                 if (NULL != engine->engine_uuid)        free(engine->engine_uuid);
123                 if (NULL != engine->engine_path)        free(engine->engine_path);
124                 if (NULL != engine->engine_name)        free(engine->engine_name);
125                 if (NULL != engine->engine_setting_path)free(engine->engine_setting_path);
126                 if (NULL != engine->first_lang)         free(engine->first_lang);
127
128                 free(engine);
129                 engine = NULL;
130         }
131
132         return 0;
133 }
134
135 int sttd_engine_agent_release()
136 {
137         if (NULL != g_engine_info) {
138                 if (g_engine_info->is_loaded) {
139                         SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Unload engine");
140
141                         if (0 != stt_engine_deinitialize()) {
142                                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to deinitialize");
143                         }
144
145                         if (0 != stt_engine_unload()) {
146                                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to unload engine");
147                         }
148
149                         if (NULL != g_engine_info->engine_uuid) {
150                                 free(g_engine_info->engine_uuid);
151                                 g_engine_info->engine_uuid = NULL;
152                         }
153
154                         if (NULL != g_engine_info->engine_path) {
155                                 free(g_engine_info->engine_path);
156                                 g_engine_info->engine_path = NULL;
157                         }
158
159                         if (NULL != g_engine_info->engine_name) {
160                                 free(g_engine_info->engine_name);
161                                 g_engine_info->engine_name = NULL;
162                         }
163
164                         if (NULL != g_engine_info->engine_setting_path) {
165                                 free(g_engine_info->engine_setting_path);
166                                 g_engine_info->engine_setting_path = NULL;
167                         }
168
169                         if (NULL != g_engine_info->first_lang) {
170                                 free(g_engine_info->first_lang);
171                                 g_engine_info->first_lang = NULL;
172                         }
173
174                         g_engine_info->is_loaded = false;
175                 }
176
177                 __engine_agent_clear_engine(g_engine_info);
178         }
179
180         g_result_cb = NULL;
181         g_speech_status_cb = NULL;
182         g_error_cb = NULL;
183         g_result_time_cb = NULL;
184
185         g_agent_init = false;
186
187         return 0;
188 }
189
190 static int __internal_get_engine_info(stte_request_callback_s *callback, sttengine_info_s** info)
191 {
192         sttengine_info_s* temp;
193         temp = (sttengine_info_s*)calloc(1, sizeof(sttengine_info_s));
194         if (NULL == temp) {
195                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] fail to allocate memory");
196                 return STTD_ERROR_OUT_OF_MEMORY;
197         }
198
199         if (NULL == callback) {
200                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Invalid engine");
201                 free(temp);
202                 return STTD_ERROR_ENGINE_NOT_FOUND;
203         }
204
205         if (NULL == callback->get_info) {
206                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Invalid engine");
207                 free(temp);
208                 return STTD_ERROR_ENGINE_NOT_FOUND;
209         }
210
211         if (0 != callback->get_info(&(temp->engine_uuid), &(temp->engine_name), &(temp->engine_setting_path), &(temp->use_network))) {
212                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get engine info");
213                 free(temp);
214                 return STTD_ERROR_ENGINE_NOT_FOUND;
215         }
216
217         /* todo - removed? */
218         temp->engine_path = strdup("empty");
219         temp->is_loaded = false;
220
221         SLOG(LOG_DEBUG, TAG_STTD, "----- Valid Engine");
222         SLOG(LOG_DEBUG, TAG_STTD, "Engine uuid : %s", (NULL == temp->engine_uuid) ? "NULL" : temp->engine_uuid);
223         SLOG(LOG_DEBUG, TAG_STTD, "Engine name : %s", (NULL == temp->engine_name) ? "NULL" : temp->engine_name);
224         SLOG(LOG_DEBUG, TAG_STTD, "Engine path : %s", (NULL == temp->engine_path) ? "NULL" : temp->engine_path);
225         SLOG(LOG_DEBUG, TAG_STTD, "Engine setting path : %s", (NULL == temp->engine_setting_path) ? "NULL" : temp->engine_setting_path);
226         SLOG(LOG_DEBUG, TAG_STTD, "Use network : %s", temp->use_network ? "true" : "false");
227         SLOG(LOG_DEBUG, TAG_STTD, "-----");
228         SLOG(LOG_DEBUG, TAG_STTD, "  ");
229
230         *info = temp;
231
232         return STTD_ERROR_NONE;
233 }
234
235 bool __is_engine(const char* filepath)
236 {
237         if (NULL == filepath) {
238                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] No filepath");
239                 return false;
240         }
241
242         if (NULL != g_engine_info) {
243                 if (!strcmp(g_engine_info->engine_path, filepath)) {
244                         return true;
245                 }
246         }
247
248         return false;
249 }
250
251 int __engine_agent_check_engine_unload()
252 {
253         /* Check the count of client to use this engine */
254         if (NULL == g_engine_info) {
255                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] No engine");
256         } else {
257                 if (g_engine_info->is_loaded) {
258                         /* unload engine */
259 #ifndef AUDIO_CREATE_ON_START
260                         SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Destroy recorder");
261                         if (0 != sttd_recorder_destroy())
262                                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
263 #endif
264                         SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Unload engine");
265                         if (0 != stt_engine_deinitialize())
266                                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to deinitialize engine");
267
268                         if (0 != stt_engine_unload())
269                                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to unload engine");
270
271                         g_engine_info->is_loaded = false;
272                 }
273         }
274
275         return 0;
276 }
277
278 int sttd_engine_agent_load_current_engine(stte_request_callback_s *callback)
279 {
280         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
281
282         /* Get current engine info */
283         sttengine_info_s* info;
284         int ret = __internal_get_engine_info(callback, &info);
285         if (0 != ret) {
286                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get engine info");
287                 return ret;
288         } else {
289                 g_engine_info = info;
290         }
291
292         __log_enginelist();
293
294         /* Set default engine */
295         char* cur_engine_uuid = NULL;
296         bool is_default_engine = false;
297
298         /* get current engine from config */
299         if (0 == sttd_config_get_default_engine(&cur_engine_uuid)) {
300                 SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] current engine from config : %s", cur_engine_uuid);
301                 if (NULL != g_engine_info->engine_uuid && NULL != cur_engine_uuid) {
302                         if (!strcmp(g_engine_info->engine_uuid, cur_engine_uuid)) {
303                                 is_default_engine = true;
304                         }
305                 }
306                 if (NULL != cur_engine_uuid) {
307                         free(cur_engine_uuid);
308                         cur_engine_uuid = NULL;
309                 }
310         } else {
311                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent WARNING] There is not current engine from config");
312         }
313
314         if (false == is_default_engine) {
315                 SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Current engine is not Default engine");
316         } else {
317                 SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Current engine is Default engine");
318         }
319
320         /* Load engine */
321         ret = stt_engine_load(g_engine_info->engine_path, callback);
322         if (0 != ret) {
323                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to load engine : path(%s)", g_engine_info->engine_path);
324                 return ret;
325         }
326
327         ret = stt_engine_initialize(false);
328         if (0 != ret) {
329                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to initialize engine : path(%s)", g_engine_info->engine_path);
330                 return ret;
331         }
332
333         ret = stt_engine_set_silence_detection(g_default_silence_detected);
334         if (0 != ret) {
335                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent WARNING] Not support silence detection");
336                 g_engine_info->support_silence_detection = false;
337         } else {
338                 SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Silence detection : %s", g_default_silence_detected ? "true" : "false");
339                 g_engine_info->support_silence_detection = true;
340                 g_engine_info->silence_detection = g_default_silence_detected;
341         }
342
343         /* Set first language */
344         char* tmp_lang = NULL;
345         ret = stt_engine_get_first_language(&tmp_lang);
346         if (0 == ret && NULL != tmp_lang) {
347                 g_engine_info->first_lang = strdup(tmp_lang);
348                 free(tmp_lang);
349         } else {
350                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get first language from engine : %s", g_engine_info->engine_name);
351                 return ret;
352         }
353
354 #ifndef AUDIO_CREATE_ON_START
355         /* Ready recorder */
356         stte_audio_type_e atype;
357         int rate;
358         int channels;
359
360         ret = stt_engine_get_audio_format(&atype, &rate, &channels);
361         if (0 != ret) {
362                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get audio type : %d %s", g_engine_info->engine_name);
363                 return ret;
364         }
365
366         ret = sttd_recorder_create(atype, channels, rate);
367         if (0 != ret) {
368                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to create recorder : %s", g_engine_info->engine_name);
369                 return ret;
370         }
371 #endif
372
373         g_engine_info->is_loaded = true;
374         SECURE_SLOG(LOG_INFO, TAG_STTD, "[Engine Agent SUCCESS] The %s has been loaded !!!", g_engine_info->engine_name);
375
376         return 0;
377 }
378
379 int sttd_engine_agent_unload_current_engine()
380 {
381         if (false == g_agent_init) {
382                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Not Initialized ");
383                 return STTD_ERROR_OPERATION_FAILED;
384         }
385
386         /* Remove client */
387         __engine_agent_check_engine_unload();
388
389         return 0;
390 }
391
392 bool sttd_engine_agent_is_default_engine()
393 {
394                 return true;
395 }
396
397 int sttd_engine_agent_get_engine_list(GSList** engine_list)
398 {
399         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
400
401         SLOG(LOG_DEBUG, TAG_STTD, "--------------------------------------");
402
403         return 0;
404 }
405
406 static int __sttd_engine_agent_check_precondition()
407 {
408         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
409         RETVM_IF(NULL == g_engine_info, STTD_ERROR_INVALID_PARAMETER, "[Engine Agent ERROR] The engine is not valid");
410         RETVM_IF(false == g_engine_info->is_loaded, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not loaded engine");
411         return STTD_ERROR_NONE;
412 }
413
414 int sttd_engine_agent_get_current_engine(char** engine_uuid)
415 {
416         RETVM_IF(NULL == engine_uuid, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Invalid parameter");
417         int tmp = __sttd_engine_agent_check_precondition();
418         if (STTD_ERROR_NONE != tmp)
419                 return tmp;
420
421         *engine_uuid = strdup(g_engine_info->engine_uuid);
422
423         return 0;
424 }
425
426 bool sttd_engine_agent_need_network()
427 {
428         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
429         if (NULL != g_engine_info)
430                 return g_engine_info->use_network;
431
432         return false;
433 }
434
435 int sttd_engine_agent_supported_langs(GSList** lang_list)
436 {
437         RETVM_IF(NULL == lang_list, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
438         int tmp = __sttd_engine_agent_check_precondition();
439         if (STTD_ERROR_NONE != tmp)
440                 return tmp;
441
442         int ret = stt_engine_get_supported_langs(lang_list);
443         if (0 != ret) {
444                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] get language list error(%d)", ret);
445         }
446
447         return ret;
448 }
449
450 int sttd_engine_agent_get_default_lang(char** lang)
451 {
452         RETVM_IF(NULL == lang, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
453         int tmp = __sttd_engine_agent_check_precondition();
454         if (STTD_ERROR_NONE != tmp)
455                 return tmp;
456
457         /* get default language */
458         bool is_valid = false;
459         if (0 != stt_engine_is_valid_language(g_default_language, &is_valid)) {
460                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to check valid language");
461                 return STTD_ERROR_OPERATION_FAILED;
462         }
463
464         if (true == is_valid) {
465                 *lang = strdup(g_default_language);
466         } else
467                 *lang = strdup(g_engine_info->first_lang);
468
469         return 0;
470 }
471
472 int sttd_engine_agent_set_private_data(const char* key, const char* data)
473 {
474         RETVM_IF(NULL == key || NULL == data, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
475         int tmp = __sttd_engine_agent_check_precondition();
476         if (STTD_ERROR_NONE != tmp)
477                 return tmp;
478
479         /* set private data */
480         int ret = -1;
481         ret = stt_engine_set_private_data(key, data);
482         if (0 != ret) {
483                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to set private data");
484         }
485
486         return ret;
487 }
488
489 int sttd_engine_agent_get_private_data(const char* key, char** data)
490 {
491         RETVM_IF(NULL == key || NULL == data, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
492         int tmp = __sttd_engine_agent_check_precondition();
493         if (STTD_ERROR_NONE != tmp)
494                 return tmp;
495
496         /* get default language */
497         int ret = -1;
498         ret = stt_engine_get_private_data(key, data);
499         if (0 != ret) {
500                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get private data");
501         }
502
503         return ret;
504 }
505
506 int sttd_engine_agent_get_option_supported(bool* silence)
507 {
508         RETVM_IF(NULL == silence, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
509         int tmp = __sttd_engine_agent_check_precondition();
510         if (STTD_ERROR_NONE != tmp)
511                 return tmp;
512
513         bool temp = false;
514         if (0 != stt_engine_support_silence(&temp)) {
515                 SLOG(LOG_WARN, TAG_STTD, "[WARNING] Fail to get support silence");
516         }
517
518         *silence = g_engine_info->support_silence_detection;
519         if (temp != *silence) {
520                 SLOG(LOG_WARN, TAG_STTD, "[WARNING] Metadata and Engine spec are different (engine:%d) (meta:%d)", temp, *silence);
521         }
522
523         return 0;
524 }
525
526 int sttd_engine_agent_is_credential_needed(unsigned int uid, bool* credential)
527 {
528         RETVM_IF(NULL == credential, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
529         int tmp = __sttd_engine_agent_check_precondition();
530         if (STTD_ERROR_NONE != tmp)
531                 return tmp;
532
533         bool temp = false;
534         int ret;
535
536         ret = stt_engine_need_app_credential(&temp);
537         if (0 != ret) {
538                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get to support recognition type : %d", ret);
539                 return ret;
540         }
541
542         *credential = temp;
543         return 0;
544 }
545
546 int sttd_engine_agent_is_recognition_type_supported(const char* type, bool* support)
547 {
548         RETVM_IF(NULL == type || NULL == support, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
549         int tmp = __sttd_engine_agent_check_precondition();
550         if (STTD_ERROR_NONE != tmp)
551                 return tmp;
552
553         bool temp = false;
554         int ret;
555
556         ret = stt_engine_support_recognition_type(type, &temp);
557         if (0 != ret) {
558                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get to support recognition type : %d", ret);
559                 return ret;
560         }
561
562         *support = temp;
563
564         return 0;
565 }
566
567 /*
568 * STT Engine Interfaces for client
569 */
570
571 int __set_option(sttengine_info_s* engine, int silence)
572 {
573         if (NULL == engine)
574                 return -1;
575
576         /* Check silence detection */
577         if (engine->support_silence_detection) {
578                 if (2 == silence) {
579                         /* default option set */
580 //                      if (g_default_silence_detected != engine->silence_detection) {
581                                 if (0 != stt_engine_set_silence_detection(g_default_silence_detected)) {
582                                         SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to set silence detection : %s", g_default_silence_detected ? "true" : "false");
583                                 } else {
584                                         engine->silence_detection = g_default_silence_detected;
585                                         SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Set silence detection : %s", g_default_silence_detected ? "true" : "false");
586                                 }
587 //                      }
588                 } else {
589                         if (silence != engine->silence_detection) {
590                                 if (0 != stt_engine_set_silence_detection(silence)) {
591                                         SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to set silence detection : %s", silence ? "true" : "false");
592                                 } else {
593                                         engine->silence_detection = silence;
594                                         SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Set silence detection : %s", silence ? "true" : "false");
595                                 }
596                         }
597                 }
598         }
599
600         return 0;
601 }
602
603 int sttd_engine_agent_recognize_start_engine(unsigned int uid, const char* lang, const char* recognition_type,
604                                       int silence, const char* appid, const char* credential, void* user_param)
605 {
606         RETVM_IF(NULL == lang || NULL == recognition_type, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
607         int tmp = __sttd_engine_agent_check_precondition();
608         if (STTD_ERROR_NONE != tmp)
609                 return tmp;
610
611         if (0 != __set_option(g_engine_info, silence)) {
612                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to set options");
613                 return STTD_ERROR_OPERATION_FAILED;
614         }
615
616         SLOG(LOG_INFO, TAG_STTD, "g_default_language %s", g_default_language);
617
618         int ret;
619         char* temp = NULL;
620         if (0 == strncmp(lang, "default", strlen("default"))) {
621                 bool is_valid = false;
622                 ret = stt_engine_is_valid_language(g_default_language, &is_valid);
623                 if (0 != ret) {
624                         SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to check valid language");
625                         return ret;
626                 }
627
628                 if (true == is_valid) {
629                         temp = strdup(g_default_language);
630                         SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent DEBUG] Default language is %s", temp);
631                 } else {
632                         temp = strdup(g_engine_info->first_lang);
633                         SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent DEBUG] Default language is engine first lang : %s", temp);
634                 }
635         } else {
636                 temp = strdup(lang);
637         }
638
639         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Start engine");
640
641         ret = stt_engine_recognize_start(temp, recognition_type, appid, credential, user_param);
642         if (NULL != temp)       free(temp);
643         if (0 != ret) {
644                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Recognition start error(%d)", ret);
645                 return ret;
646         }
647
648 #ifdef AUDIO_CREATE_ON_START
649         /* Ready recorder */
650         stte_audio_type_e atype;
651         int rate;
652         int channels;
653
654         ret = stt_engine_get_audio_format(&atype, &rate, &channels);
655         if (0 != ret) {
656                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get audio format : %s", g_engine_info->engine_name);
657                 return ret;
658         }
659
660         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Create recorder");
661
662         ret = sttd_recorder_create(atype, channels, rate);
663         if (0 != ret) {
664                 SECURE_SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to create format : %s", g_engine_info->engine_name);
665                 return ret;
666         }
667 #endif
668
669 #if 0
670         SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Start recorder(%d)", uid);
671
672         ret = sttd_recorder_start(uid);
673         if (0 != ret) {
674                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to start recorder : result(%d)", ret);
675                 return ret;
676         }
677
678 #endif
679
680         return 0;
681 }
682
683 int sttd_engine_agent_recognize_start_recorder(unsigned int uid, const char* appid)
684 {
685         int tmp = __sttd_engine_agent_check_precondition();
686         if (STTD_ERROR_NONE != tmp)
687                 return tmp;
688
689         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Start recorder");
690
691         int ret;
692         ret = sttd_recorder_start(uid, appid);
693         if (0 != ret) {
694                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to start recorder : result(%d)", ret);
695                 stt_engine_recognize_cancel();
696                 sttd_recorder_stop();
697                 return ret;
698         }
699
700         return 0;
701 }
702
703 int sttd_engine_agent_recognize_start_file(unsigned int uid, const char* filepath)
704 {
705         int tmp = __sttd_engine_agent_check_precondition();
706         if (STTD_ERROR_NONE != tmp)
707                 return tmp;
708
709         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Start recorder");
710
711         int ret;
712         ret = sttd_recorder_start_file(uid, filepath);
713         if (0 != ret) {
714                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to start recorder : result(%d)", ret);
715                 stt_engine_recognize_cancel();
716                 sttd_recorder_stop_file();
717                 return ret;
718         }
719
720         return 0;
721 }
722
723 int sttd_engine_agent_set_recording_data(const void* data, unsigned int length)
724 {
725         RETVM_IF(NULL == data || 0 == length, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
726         int tmp = __sttd_engine_agent_check_precondition();
727         if (STTD_ERROR_NONE != tmp)
728                 return tmp;
729
730         int ret = stt_engine_set_recording_data(data, length);
731         if (0 != ret) {
732                 SLOG(LOG_WARN, TAG_STTD, "[Engine Agent WARNING] set recording error(%d)", ret);
733         }
734
735         return ret;
736 }
737
738 int sttd_engine_agent_recognize_stop_file()
739 {
740         int tmp = __sttd_engine_agent_check_precondition();
741         if (STTD_ERROR_NONE != tmp)
742                 return tmp;
743
744         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Stop recorder");
745         int ret;
746         ret = sttd_recorder_stop_file();
747         if (0 != ret) {
748                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to stop recorder : result(%d)", ret);
749                 return ret;
750         }
751
752 #ifdef AUDIO_CREATE_ON_START
753         SECURE_SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Destroy recorder");
754         if (0 != sttd_recorder_destroy())
755                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
756 #endif
757
758         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent Success] Stop recorder");
759         return 0;
760 }
761
762 int sttd_engine_agent_recognize_stop_recorder()
763 {
764         int tmp = __sttd_engine_agent_check_precondition();
765         if (STTD_ERROR_NONE != tmp)
766                 return tmp;
767
768         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Stop recorder");
769         int ret;
770         ret = sttd_recorder_stop();
771         if (0 != ret) {
772                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to stop recorder : result(%d)", ret);
773                 return ret;
774         }
775
776 #ifdef AUDIO_CREATE_ON_START
777         SECURE_SLOG(LOG_DEBUG, TAG_STTD, "[Engine Agent] Destroy recorder");
778         if (0 != sttd_recorder_destroy())
779                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
780 #endif
781
782         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent Success] Stop recorder");
783         return 0;
784 }
785
786 int sttd_engine_agent_recognize_stop_engine()
787 {
788         int tmp = __sttd_engine_agent_check_precondition();
789         if (STTD_ERROR_NONE != tmp)
790                 return tmp;
791
792         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Stop engine");
793
794         int ret;
795         ret = stt_engine_recognize_stop();
796         if (0 != ret) {
797                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] stop recognition error(%d)", ret);
798                 return ret;
799         }
800
801         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent Success] Stop engine");
802
803         return 0;
804 }
805
806 int sttd_engine_agent_recognize_cancel()
807 {
808         int tmp = __sttd_engine_agent_check_precondition();
809         if (STTD_ERROR_NONE != tmp)
810                 return tmp;
811
812         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Cancel engine");
813
814         int ret;
815         ret = stt_engine_recognize_cancel();
816         if (0 != ret) {
817                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] cancel recognition error(%d)", ret);
818                 return ret;
819         }
820
821         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Stop recorder");
822
823         ret = sttd_recorder_stop();
824         if (0 != ret) {
825                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to stop recorder : result(%d)", ret);
826                 return ret;
827         }
828
829 #ifdef AUDIO_CREATE_ON_START
830         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Destroy recorder");
831         if (0 != sttd_recorder_destroy())
832                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
833 #endif
834
835         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent Success] Cancel recognition");
836
837         return 0;
838 }
839
840
841 /*
842 * STT Engine Interfaces for configure
843 */
844
845 int sttd_engine_agent_set_default_engine(const char* engine_uuid)
846 {
847         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
848         RETVM_IF(NULL == engine_uuid, STTD_ERROR_INVALID_PARAMETER, "[Engine Agent ERROR] Invalid Parameter");
849
850         __log_enginelist();
851
852         RETVM_IF(NULL == g_engine_info, STTD_ERROR_INVALID_PARAMETER, "[Engine Agent ERROR] The Default engine is not valid");
853
854         SECURE_SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Default engine uuid(%s)", g_engine_info->engine_uuid);
855
856         return 0;
857 }
858
859 int sttd_engine_agent_set_default_language(const char* language)
860 {
861         RETVM_IF(NULL == language, STTD_ERROR_INVALID_PARAMETER,  "[Engine Agent ERROR] Input parameter");
862         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
863
864         if (NULL != g_default_language)
865                 free(g_default_language);
866
867         g_default_language = strdup(language);
868
869         return 0;
870 }
871
872 int sttd_engine_agent_set_silence_detection(bool value)
873 {
874         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
875
876         g_default_silence_detected = value;
877
878         return 0;
879 }
880
881 int sttd_engine_agent_check_app_agreed(const char* appid, bool* result)
882 {
883         int tmp = __sttd_engine_agent_check_precondition();
884         if (STTD_ERROR_NONE != tmp)
885                 return tmp;
886
887         int ret;
888         ret = stt_engine_check_app_agreed(appid, result);
889         if (0 != ret) {
890                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] cancel recognition error(%d)", ret);
891                 return ret;
892         }
893
894
895         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Get engine right : %s", *result ? "true" : "false");
896         return 0;
897 }
898
899 static void __recorder_destroy_by_error_result(void *data)
900 {
901         SLOG(LOG_INFO, TAG_STTD, "[Engine Agent] Destroy recorder");
902         if (0 != sttd_recorder_destroy())
903                 SECURE_SLOG(LOG_WARN, TAG_STTD, "[Engine Agent] Fail to destroy recorder");
904
905         return;
906 }
907
908 int sttd_engine_agent_send_result(stte_result_event_e event, const char* type, const char** result, int result_count,
909                  const char* msg, void* time_info, void *user_data)
910 {
911         int ret = -1;
912         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
913
914         SLOG(LOG_INFO, TAG_STTD, "[Server] === Result time callback ===");
915
916         if (NULL != time_info) {
917                 /* Get the time info */
918                 ret = stt_engine_foreach_result_time(time_info, __result_time_cb, NULL);
919                 if (0 != ret) {
920                         SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] Fail to get time info : %d", ret);
921                         return ret;
922                 }
923         }
924
925         SLOG(LOG_INFO, TAG_STTD, "[Server] ============================");
926
927         ret = g_result_cb(event, type, result, result_count, msg, user_data);
928
929 #ifdef AUDIO_CREATE_ON_START
930         if (event == STTE_RESULT_EVENT_ERROR) {
931                 ecore_main_loop_thread_safe_call_async(__recorder_destroy_by_error_result, NULL);
932         }
933 #endif
934
935         return ret;
936 }
937
938 int sttd_engine_agent_send_error(stte_error_e error, const char* msg)
939 {
940         /* check uid */
941         unsigned int uid = stt_client_get_current_recognition();
942
943         char* err_msg = NULL;
944         int ret = STTD_ERROR_NONE;
945
946
947         if (NULL != msg) {
948                 err_msg = strdup(msg);
949         }
950
951         ret = sttdc_send_error_signal(uid, error, err_msg);
952         if (0 != ret) {
953                 SLOG(LOG_ERROR, TAG_STTD, "[Server ERROR] Fail to send error info.");
954         }
955
956         if (NULL != err_msg) {
957                 free(err_msg);
958                 err_msg = NULL;
959         }
960
961         ret = g_error_cb(error, msg);
962
963         return ret;
964 }
965
966 int sttd_engine_agent_send_speech_status(stte_speech_status_e status, void* user_data)
967 {
968         int ret = STTD_ERROR_NONE;
969         RETVM_IF(false == g_agent_init, STTD_ERROR_OPERATION_FAILED, "[Engine Agent ERROR] Not Initialized");
970
971         ret = g_speech_status_cb(status, user_data);
972         return ret;
973 }
974
975 static bool __result_time_cb(int index, stte_result_time_event_e event, const char* text, long start_time, long end_time, void* user_data)
976 {
977         return g_result_time_cb(index, event, text, start_time, end_time, user_data);
978 }
979
980 /* A function forging */
981 static int __log_enginelist()
982 {
983         if (NULL != g_engine_info) {
984                 SLOG(LOG_DEBUG, TAG_STTD, "------------------ engine -----------------------");
985                 SLOG(LOG_DEBUG, TAG_STTD, "engine uuid : %s", g_engine_info->engine_uuid);
986                 SLOG(LOG_DEBUG, TAG_STTD, "engine name : %s", g_engine_info->engine_name);
987                 SLOG(LOG_DEBUG, TAG_STTD, "engine path : %s", g_engine_info->engine_path);
988                 SLOG(LOG_DEBUG, TAG_STTD, "use network : %s", g_engine_info->use_network ? "true" : "false");
989                 SLOG(LOG_DEBUG, TAG_STTD, "is loaded   : %s", g_engine_info->is_loaded ? "true" : "false");
990                 if (NULL != g_engine_info->first_lang) {
991                         SLOG(LOG_DEBUG, TAG_STTD, "default lang : %s", g_engine_info->first_lang);
992                 }
993                 SLOG(LOG_DEBUG, TAG_STTD, "-------------------------------------------------");
994         } else {
995                 SLOG(LOG_DEBUG, TAG_STTD, "------------------ engine -----------------------");
996                 SLOG(LOG_DEBUG, TAG_STTD, "     No engine");
997                 SLOG(LOG_DEBUG, TAG_STTD, "-------------------------------------------------");
998         }
999
1000         return 0;
1001 }
1002
1003 int sttd_engine_agent_set_audio_type(const char* audio_type)
1004 {
1005         int tmp = __sttd_engine_agent_check_precondition();
1006         if (STTD_ERROR_NONE != tmp)
1007                 return tmp;
1008
1009         SLOG(LOG_INFO, TAG_STTD, "[Server Info] Set audio type(%s)", audio_type);
1010
1011         int ret;
1012         ret = stt_engine_set_audio_type(audio_type);
1013         if (0 != ret) {
1014                 SLOG(LOG_ERROR, TAG_STTD, "[Engine Agent ERROR] set audio type error(%d)", ret);
1015         }
1016         return ret;
1017 }