Add -ldl to link library libdl.so.
[platform/core/uifw/tts.git] / server / ttsd_data.cpp
1 /*
2 *  Copyright (c) 2011 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 "ttsd_main.h"
16 #include "ttsd_data.h"
17
18 using namespace std;
19
20 static vector<app_data_s> g_app_list;
21
22 static vector<setting_app_data_s> g_setting_list;
23
24 static bool g_mutex_state = false;
25
26 /*
27 * functions for debug
28 */
29
30 int __data_show_list()
31 {
32         int vsize = g_app_list.size();
33
34         SLOG(LOG_DEBUG, TAG_TTSD, "----- client list -----");
35
36         for (int i=0; i<vsize; i++) {
37                 SLOG(LOG_DEBUG, TAG_TTSD, "[%dth] pid(%d), uid(%d), state(%d) \n", i, g_app_list[i].pid, g_app_list[i].uid, g_app_list[i].state );
38         }
39
40         if (0 == vsize) {
41                 SLOG(LOG_DEBUG, TAG_TTSD, "No Client \n");
42         }
43
44         SLOG(LOG_DEBUG, TAG_TTSD, "-----------------------");
45
46         SLOG(LOG_DEBUG, TAG_TTSD, "----- setting client list -----");
47
48         vsize = g_setting_list.size();
49
50         for (int i=0; i<vsize; i++) {
51                 SLOG(LOG_DEBUG, TAG_TTSD, "[%dth] pid(%d)", i, g_setting_list[i].pid );
52         }
53
54         if (0 == vsize) {
55                 SLOG(LOG_DEBUG, TAG_TTSD, "No Setting Client");
56         }
57
58         SLOG(LOG_DEBUG, TAG_TTSD, "--------------------------------");
59
60         return TTSD_ERROR_NONE;
61 }
62
63 int __data_show_sound_list(int index)
64 {
65         SLOG(LOG_DEBUG, TAG_TTSD, "----- Sound list -----");
66         
67         unsigned int i;
68         for (i=0 ; i < g_app_list[index].m_wav_data.size() ; i++) {
69                 SLOG(LOG_DEBUG, TAG_TTSD, "[%dth] data size(%ld), uttid(%d), type(%d) \n", 
70                         i+1, g_app_list[index].m_wav_data[i].data_size, g_app_list[index].m_wav_data[i].utt_id, g_app_list[index].m_wav_data[i].audio_type );
71         }
72
73         if (i == 0) {
74                 SLOG(LOG_DEBUG, TAG_TTSD, "No Sound Data \n");
75         }
76
77         SLOG(LOG_DEBUG, TAG_TTSD, "----------------------");
78         return TTSD_ERROR_NONE;
79 }
80
81 int __data_show_text_list(int index)
82 {
83         SLOG(LOG_DEBUG, TAG_TTSD, "----- Text list -----");
84
85         unsigned int i;
86         for (i=0 ; i< g_app_list[index].m_speak_data.size() ; i++) {
87                 SLOG(LOG_DEBUG, TAG_TTSD, "[%dth] lang(%s), vctype(%d), speed(%d), uttid(%d), text(%s) \n", 
88                                 i+1, g_app_list[index].m_speak_data[i].lang, g_app_list[index].m_speak_data[i].vctype, g_app_list[index].m_speak_data[i].speed,
89                                 g_app_list[index].m_speak_data[i].utt_id, g_app_list[index].m_speak_data[i].text );     
90         }
91
92         if (0 == i) {
93                 SLOG(LOG_DEBUG, TAG_TTSD, "No Text Data \n");
94         }
95
96         SLOG(LOG_DEBUG, TAG_TTSD, "---------------------");
97         return TTSD_ERROR_NONE;
98 }
99
100
101 /*
102 * ttsd data functions
103 */
104
105 int ttsd_data_new_client(int pid, int uid)
106 {
107         if( -1 != ttsd_data_is_client(uid) ) {
108                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_new_client() : uid is not valid (%d)\n", uid);        
109                 return TTSD_ERROR_INVALID_PARAMETER;
110         }
111
112         app_data_s app;
113         app.pid = pid;
114         app.uid = uid;
115         app.utt_id_stopped = 0;
116         app.state = APP_STATE_READY;
117
118         g_app_list.insert( g_app_list.end(), app);
119
120 #ifdef DATA_DEBUG
121         __data_show_list();
122 #endif 
123         return TTSD_ERROR_NONE;
124 }
125
126 int ttsd_data_delete_client(int uid)
127 {
128         int index = 0;
129
130         index = ttsd_data_is_client(uid);
131         
132         if (index < 0) {
133                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_delete_client() : uid is not valid (%d)\n", uid);     
134                 return -1;
135         }
136
137         if (0 != ttsd_data_clear_data(uid)) {
138                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] fail ttsd_data_clear_data()\n");
139                 return -1;
140         }
141
142         g_app_list.erase(g_app_list.begin()+index);
143
144 #ifdef DATA_DEBUG
145         __data_show_list();
146 #endif 
147         return TTSD_ERROR_NONE;
148 }
149
150 int ttsd_data_is_client(int uid)
151 {
152         int vsize = g_app_list.size();
153
154         for (int i=0; i<vsize; i++) {
155                 if(g_app_list[i].uid == uid) {
156                         return i;               
157                 }
158         }
159
160         return -1;
161 }
162
163 int ttsd_data_get_client_count()
164 {
165         return g_app_list.size() + g_setting_list.size();
166 }
167
168 int ttsd_data_get_pid(int uid)
169 {
170         int index;
171
172         index = ttsd_data_is_client(uid);
173         
174         if (index < 0)  {
175                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_delete_client() : uid is not valid (%d)\n", uid);     
176                 return TTSD_ERROR_INVALID_PARAMETER;
177         }
178
179         return g_app_list[index].pid;
180 }
181
182 int ttsd_data_get_speak_data_size(int uid)
183 {
184         int index = 0;
185         index = ttsd_data_is_client(uid);
186         
187         if (index < 0) {
188                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_get_speak_data_size() : uid is not valid (%d)\n", uid);       
189                 return TTSD_ERROR_INVALID_PARAMETER;
190         }
191
192         int size = g_app_list[index].m_speak_data.size();
193         return size;
194 }
195
196 int ttsd_data_add_speak_data(int uid, speak_data_s data)
197 {
198         int index = 0;
199         index = ttsd_data_is_client(uid);
200
201         if (index < 0) {
202                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_add_speak_data() : uid is not valid (%d)\n", uid);    
203                 return TTSD_ERROR_INVALID_PARAMETER;
204         }
205         
206         g_app_list[index].m_speak_data.insert(g_app_list[index].m_speak_data.end(), data);
207
208         if (1 == data.utt_id)
209                 g_app_list[index].utt_id_stopped = 0;
210
211 #ifdef DATA_DEBUG
212         __data_show_text_list(index);
213 #endif 
214         return TTSD_ERROR_NONE;
215 }
216
217 int ttsd_data_get_speak_data(int uid, speak_data_s* data)
218 {
219         int index = 0;
220         index = ttsd_data_is_client(uid);
221
222         if (index < 0) {
223                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_get_speak_data() : uid is not valid(%d)\n", uid);     
224                 return TTSD_ERROR_INVALID_PARAMETER;
225         }
226
227         if (0 == g_app_list[index].m_speak_data.size()) {
228                 SLOG(LOG_WARN, TAG_TTSD, "[DATA WARNING] There is no speak data\n"); 
229                 return -1;
230         }
231
232         data->lang = g_strdup(g_app_list[index].m_speak_data[0].lang);
233         data->vctype = g_app_list[index].m_speak_data[0].vctype;
234         data->speed = g_app_list[index].m_speak_data[0].speed;
235
236         data->text = g_app_list[index].m_speak_data[0].text;
237         data->utt_id = g_app_list[index].m_speak_data[0].utt_id;
238
239         g_app_list[index].m_speak_data.erase(g_app_list[index].m_speak_data.begin());
240
241 #ifdef DATA_DEBUG
242         __data_show_text_list(index);
243 #endif 
244         return TTSD_ERROR_NONE;
245 }
246
247 int ttsd_data_add_sound_data(int uid, sound_data_s data)
248 {
249         int index = 0;
250         index = ttsd_data_is_client(uid);
251
252         if(index < 0) {
253                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_add_sound_data() : uid is not valid (%d)\n", uid);    
254                 return TTSD_ERROR_INVALID_PARAMETER;
255         }
256
257         g_app_list[index].m_wav_data.insert(g_app_list[index].m_wav_data.end(), data);
258
259 #ifdef DATA_DEBUG
260         __data_show_sound_list(index);
261 #endif 
262         return TTSD_ERROR_NONE;
263 }
264
265 int ttsd_data_get_sound_data(int uid, sound_data_s* data)
266 {
267         int index = 0;
268         index = ttsd_data_is_client(uid);
269
270         if (index < 0)  {
271                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_get_sound_data() : uid is not valid (%d)\n", uid);    
272                 return TTSD_ERROR_INVALID_PARAMETER;
273         }
274
275         if (0 == g_app_list[index].m_wav_data.size()) {
276                 SLOG(LOG_WARN, TAG_TTSD, "[DATA WARNING] There is no wav data\n"); 
277                 return -1;
278         }
279
280         data->data = g_app_list[index].m_wav_data[0].data;
281         data->data_size = g_app_list[index].m_wav_data[0].data_size;
282         data->utt_id = g_app_list[index].m_wav_data[0].utt_id;
283         data->audio_type = g_app_list[index].m_wav_data[0].audio_type;
284         data->rate = g_app_list[index].m_wav_data[0].rate;
285         data->channels = g_app_list[index].m_wav_data[0].channels;
286         data->event = g_app_list[index].m_wav_data[0].event;
287
288         g_app_list[index].m_wav_data.erase(g_app_list[index].m_wav_data.begin());
289
290 #ifdef DATA_DEBUG
291         __data_show_sound_list(index);
292 #endif 
293         return TTSD_ERROR_NONE;
294 }
295
296 int ttsd_data_get_sound_data_size(int uid)
297 {
298         int index = 0;
299         index = ttsd_data_is_client(uid);
300
301         if (index < 0)  {
302                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_get_sound_data_size() : uid is not valid (%d)\n", uid);       
303                 return TTSD_ERROR_INVALID_PARAMETER;
304         }
305
306         return g_app_list[index].m_wav_data.size();
307 }
308
309 int ttsd_data_clear_data(int uid)
310 {
311         int index = 0;
312
313         index = ttsd_data_is_client(uid);
314         if (index < 0) {
315                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_clear_data() : uid is not valid (%d)\n", uid);        
316                 return TTSD_ERROR_INVALID_PARAMETER;
317         }
318
319         int removed_last_uttid = -1;
320         /* free allocated data */
321         while(1) {
322                 speak_data_s temp;
323                 if (0 != ttsd_data_get_speak_data(uid, &temp)) {
324                         break;
325                 }
326
327                 if (NULL != temp.text)  free(temp.text);
328                 if (NULL != temp.lang)  free(temp.lang);
329
330                 removed_last_uttid = temp.utt_id;
331         }
332
333         if (-1 != removed_last_uttid) {
334                 g_app_list[index].utt_id_stopped = removed_last_uttid;
335         }
336
337         while(1) {
338                 sound_data_s temp;
339                 if (0 != ttsd_data_get_sound_data(uid, &temp)) {
340                         break;
341                 }
342
343                 if (NULL != temp.data)  free(temp.data);
344         }
345
346         g_app_list[index].m_speak_data.clear();
347         g_app_list[index].m_wav_data.clear();
348
349         return TTSD_ERROR_NONE;
350 }
351
352 int ttsd_data_get_client_state(int uid, app_state_e* state)
353 {
354         int index = 0;
355
356         index = ttsd_data_is_client(uid);
357         if (index < 0)  {
358                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_get_client_state() : uid is not valid (%d)\n", uid);  
359                 return TTSD_ERROR_INVALID_PARAMETER;
360         }
361
362         *state = g_app_list[index].state;
363
364         return TTSD_ERROR_NONE;
365 }
366
367 int ttsd_data_set_client_state(int uid, app_state_e state)
368 {
369         int index = 0;
370
371         index = ttsd_data_is_client(uid);
372         if (index < 0)  {
373                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_set_client_state() : uid is not valid (%d)\n", uid);  
374                 return TTSD_ERROR_INVALID_PARAMETER;
375         }
376
377         if (true == g_mutex_state) {
378                 while(true == g_mutex_state)    {
379                 }
380         }
381         
382         g_mutex_state = true;
383
384         /* The client of playing state of all clients is only one. need to check state. */
385         if (APP_STATE_PLAYING == state) {
386                 int vsize = g_app_list.size();
387                 for (int i=0 ; i<vsize ; i++) {
388                         if(g_app_list[i].state == APP_STATE_PLAYING) {
389                                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_set_client_state() : a playing client has already existed. \n");      
390                                 g_mutex_state = false;
391                                 return -1;
392                         }
393                 }
394         }
395
396         g_app_list[index].state = state;
397
398         g_mutex_state = false;
399
400         return TTSD_ERROR_NONE;
401 }
402
403 int ttsd_data_get_current_playing()
404 {
405         int vsize = g_app_list.size();
406
407         for (int i=0; i<vsize; i++) {
408                 if (APP_STATE_PLAYING == g_app_list[i].state) {
409                         return g_app_list[i].uid;
410                 }
411         }
412
413         SLOG(LOG_DEBUG, TAG_TTSD, "[DATA] NO CURRENT PLAYING !!");      
414
415         return -1;
416 }
417
418 int ttsd_data_foreach_clients(ttsd_data_get_client_cb callback, void* user_data)
419 {
420         if (NULL == callback) {
421                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] input data is NULL!!");
422                 return -1;
423         }
424
425         int vsize = g_app_list.size();
426
427         for (int i=0; i<vsize; i++) {
428                 if (false == callback(g_app_list[i].pid, g_app_list[i].uid, g_app_list[i].state, user_data)) {
429                         break;
430                 }
431         }
432         
433         return 0;
434 }
435
436 bool ttsd_data_is_uttid_valid(int uid, int uttid)
437 {
438         int index = 0;
439
440         index = ttsd_data_is_client(uid);
441         if (index < 0)  {
442                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] ttsd_data_set_client_state() : uid is not valid (%d)\n", uid);  
443                 return TTSD_ERROR_INVALID_PARAMETER;
444         }
445
446         if (uttid < g_app_list[index].utt_id_stopped)
447                 return false;
448
449         return true;
450 }
451
452 int ttsd_data_is_current_playing()
453 {
454         int vsize = g_app_list.size();
455
456         for (int i=0; i<vsize; i++) {
457                 if(g_app_list[i].state == APP_STATE_PLAYING) {
458                         return g_app_list[i].uid;               
459                 }
460         }
461
462         return -1;
463 }
464
465 /*
466 * setting data
467 */
468
469 int ttsd_setting_data_add(int pid)
470 {
471         if (-1 != ttsd_setting_data_is_setting(pid)) {
472                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] pid(%d) is not valid", pid);    
473                 return TTSD_ERROR_INVALID_PARAMETER;
474         }
475
476         setting_app_data_s setting_app;
477         setting_app.pid = pid;
478         
479         g_setting_list.insert(g_setting_list.end(), setting_app);
480
481 #ifdef DATA_DEBUG
482         __data_show_list();
483 #endif 
484         return TTSD_ERROR_NONE;
485
486 }
487
488 int ttsd_setting_data_delete(int pid)
489 {
490         int index = 0;
491
492         index = ttsd_setting_data_is_setting(pid);
493
494         if (index < 0) {
495                 SLOG(LOG_ERROR, TAG_TTSD, "[DATA ERROR] uid is not valid (%d)", pid);   
496                 return -1;
497         }
498
499         g_setting_list.erase(g_setting_list.begin()+index);
500
501 #ifdef DATA_DEBUG
502         __data_show_list();
503 #endif 
504         return TTSD_ERROR_NONE;
505 }
506
507 int ttsd_setting_data_is_setting(int pid)
508 {
509         int vsize = g_setting_list.size();
510
511         for (int i=0; i<vsize; i++) {
512                 if(g_setting_list[i].pid == pid) {
513                         return i;               
514                 }
515         }
516
517         return -1;
518 }