Merge "Support using wl_surface for legacy_player_test" into tizen
[platform/core/multimedia/libmm-player.git] / src / mm_player_utils.c
1 /*
2  * libmm-player
3  *
4  * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Contact: JongHyuk Choi <jhchoi.choi@samsung.com>, YeJin Cho <cho.yejin@samsung.com>,
7  * Seungbae Shin <seungbae.shin@samsung.com>, YoungHwan An <younghwan_.an@samsung.com>
8  *
9  * Licensed under the Apache License, Version 2.0 (the "License");
10  * you may not use this file except in compliance with the License.
11  * You may obtain a copy of the License at
12  *
13  * http://www.apache.org/licenses/LICENSE-2.0
14  *
15  * Unless required by applicable law or agreed to in writing, software
16  * distributed under the License is distributed on an "AS IS" BASIS,
17  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18  * See the License for the specific language governing permissions and
19  * limitations under the License.
20  *
21  */
22
23 #include <stdio.h>
24 #include <string.h>
25 #include <unistd.h>
26 #include <sys/stat.h>
27 #include <fcntl.h>
28 #include <sys/time.h>
29 #include <netinet/in.h>
30 #include <arpa/inet.h>
31 #include <unicode/ucsdet.h>
32 #include <dlog.h>
33
34 #include "mm_player_utils.h"
35
36 int util_exist_file_path(const char *file_path)
37 {
38         int fd = 0;
39         struct stat stat_results = {0, };
40
41         if (!file_path || !strlen(file_path))
42                 return MM_ERROR_PLAYER_FILE_NOT_FOUND;
43
44         fd = open (file_path, O_RDONLY);
45
46         if (fd < 0)
47         {
48                 LOGE("failed to open file by %s (%d)", strerror(errno), errno);
49
50                 if (EACCES == errno)
51                         return MM_ERROR_PLAYER_PERMISSION_DENIED;
52
53                 return MM_ERROR_PLAYER_FILE_NOT_FOUND;
54         }
55
56         if (fstat(fd, &stat_results) < 0)
57         {
58                 LOGE("failed to get file status");
59         }
60         else if (stat_results.st_size == 0)
61         {
62                 LOGE("file size is zero");
63                 close(fd);
64                 return MM_ERROR_PLAYER_FILE_NOT_FOUND;
65         }
66         else
67         {
68                 LOGW("file size : %lld bytes", (long long)stat_results.st_size);
69         }
70
71         close(fd);
72
73         return MM_ERROR_NONE;
74 }
75
76 bool util_write_file_backup(const char *backup_path, char *data_ptr, int data_size)
77 {
78         FILE *fp = NULL;
79         int wsize = 0;
80
81         fp = fopen(backup_path, "wb");
82         if (!fp)
83                 return FALSE;
84
85         wsize = fwrite(data_ptr, sizeof(char), data_size, fp);
86
87         fclose(fp);
88
89         if (wsize != data_size) {
90                 if (!access(backup_path, R_OK))
91                         remove(backup_path);
92
93                 LOGE("No space to write!\n");
94
95                 return FALSE;
96         }
97
98         return TRUE;
99 }
100
101 bool util_remove_file_backup(const char *backup_path)
102 {
103         if (!backup_path || !strlen(backup_path))
104                 return FALSE;
105
106         int res = access(backup_path, R_OK);
107         if (!res)
108         {
109                 if (remove(backup_path) == -1)
110                         return FALSE;
111         }
112
113         return TRUE;
114 }
115
116 #define DETECTION_PREFIX_SIZE   20
117 int util_is_midi_type_by_mem(void *mem, int size)
118 {
119         const char *p = (const char *)mem;
120
121         if (size < DETECTION_PREFIX_SIZE)
122                 return MM_AUDIO_CODEC_INVALID;
123
124         /* mmf file detection */
125         if (p[0] == 'M' && p[1] == 'M' && p[2] == 'M' && p[3] == 'D') {
126                 LOGD("MM_AUDIO_CODEC_MMF\n");
127                 return MM_AUDIO_CODEC_MMF;
128         }
129
130         /* midi file detection */
131         if (p[0] == 'M' && p[1] == 'T' && p[2] == 'h' && p[3] == 'd') {
132                 LOGD ("MM_AUDIO_CODEC_MIDI, %d\n", MM_AUDIO_CODEC_MIDI);
133                 return MM_AUDIO_CODEC_MIDI;
134         }
135         /* mxmf file detection */
136         if (p[0] == 'X' && p[1] == 'M' && p[2] == 'F' && p[3] == '_') {
137                 LOGD ("MM_AUDIO_CODEC_MXMF\n");
138                 return MM_AUDIO_CODEC_MXMF;
139         }
140
141         /* wave file detection */
142         if (p[0] == 'R' && p[1] == 'I' && p[2] == 'F' && p[3] == 'F' &&
143                 p[8] == 'W' && p[9] == 'A' && p[10] == 'V' && p[11] == 'E' &&
144                 p[12] == 'f' && p[13] == 'm' && p[14] == 't') {
145                 LOGD ("MM_AUDIO_CODEC_WAVE\n");
146                 return MM_AUDIO_CODEC_WAVE;
147         }
148         /* i-melody file detection */
149         if (memcmp(p, "BEGIN:IMELODY", 13) == 0)
150         {
151                 LOGD ("MM_AUDIO_CODEC_IMELODY\n");
152                 return MM_AUDIO_CODEC_IMELODY;
153         }
154
155         return MM_AUDIO_CODEC_INVALID;
156 }
157
158 int util_is_midi_type_by_file(const char *file_path)
159 {
160         struct stat file_attrib;
161         FILE *fp = NULL;
162         char prefix[DETECTION_PREFIX_SIZE] = {0,};
163         int size;
164
165         if (!file_path)
166                 return FALSE;
167
168         fp = fopen(file_path, "r");
169
170         if (!fp)
171         return FALSE;
172
173         memset(&file_attrib, 0, sizeof(file_attrib));
174
175         if (stat(file_path, &file_attrib) != 0)
176         {
177                 fclose(fp);
178                 return FALSE;
179         }
180
181         size = (int) file_attrib.st_size;
182
183         if (size < DETECTION_PREFIX_SIZE)
184         {
185                 fclose(fp);
186                 return FALSE;
187         }
188
189         size = fread(prefix, sizeof(char), DETECTION_PREFIX_SIZE, fp);
190
191         fclose(fp);
192
193         return util_is_midi_type_by_mem(prefix, size);
194 }
195
196 char**
197 util_get_cookie_list ( const char *cookies )
198 {
199         char **cookie_list = NULL;
200         char *temp = NULL;
201         gint i = 0;
202
203         if ( !cookies || !strlen(cookies) )
204                 return NULL;
205
206         SECURE_LOGD("cookies : %d[bytes] - %s \n", strlen(cookies), cookies);
207
208         temp = g_strdup(cookies);
209
210         /* trimming. it works inplace */
211         g_strstrip(temp);
212
213         /* split */
214         cookie_list = g_strsplit(temp, ";", 100);
215
216         for ( i = 0; i < g_strv_length(cookie_list); i++ )
217         {
218                 if (cookie_list[i])
219                 {
220                         if (strlen(cookie_list[i]))
221                         {
222                                 g_strstrip(cookie_list[i]);
223                                 SECURE_LOGD("cookie_list[%d] : %d[bytes] - %s \n", i, strlen(cookie_list[i]), cookie_list[i]);
224                         }
225                         else
226                         {
227                                 cookie_list[i][0]='\0';
228                         }
229                 }
230         }
231
232         if (temp)
233                 g_free (temp);
234         temp=NULL;
235
236         return cookie_list;
237 }
238
239 bool util_check_valid_url ( const char *proxy )
240 {
241         struct in_addr proxy_addr;
242         bool ret = TRUE;
243
244         MMPLAYER_RETURN_VAL_IF_FAIL ( proxy, FALSE );
245         MMPLAYER_RETURN_VAL_IF_FAIL ( strlen(proxy), FALSE );
246
247         if ( inet_aton(proxy, &proxy_addr) != 0 )
248         {
249                 LOGW("invalid proxy is set. \n");
250                 ret = FALSE;
251         }
252
253         return ret;
254 }
255
256 /* check the given path is indicating sdp file */
257 bool
258 util_is_sdp_file ( const char *path )
259 {
260         gboolean ret = FALSE;
261         gchar* uri = NULL;
262
263         MMPLAYER_FENTER();
264
265         MMPLAYER_RETURN_VAL_IF_FAIL ( path, FALSE );
266
267         uri = g_ascii_strdown ( path, -1 );
268
269         if ( uri == NULL)
270         {
271                 return FALSE;
272         }
273
274         /* trimming */
275         g_strstrip( uri );
276
277         /* strlen(".sdp") == 4 */
278         if ( strlen( uri ) <= 4 )
279         {
280                 LOGW ( "path is too short.\n" );
281                 return ret;
282         }
283
284         /* first, check extension name */
285         ret = g_str_has_suffix ( uri, "sdp" );
286
287         /* second, if no suffix is there, check it's contents */
288         if ( ! ret )
289         {
290                 /* FIXIT : do it soon */
291         }
292
293         g_free( uri);
294         uri = NULL;
295
296         return ret;
297 }
298
299 int64_t
300 util_get_time ( void )
301 {
302         struct timeval tv;
303         gettimeofday(&tv,NULL);
304         return (int64_t)tv.tv_sec * 1000000 + tv.tv_usec;
305 }
306
307 int
308 util_get_rank_increase ( const char *factory_class )
309 {
310         gint rank_pri_inc = 20;
311         gint rank_sec_inc = 10;
312         gint ret = 0;
313
314         if ( g_strrstr(factory_class,"Dsp") )
315                 ret = rank_pri_inc;
316         else if ( g_strrstr(factory_class,"HW") )
317                 ret = rank_pri_inc;
318         else if ( g_strrstr(factory_class,"Arm") )
319                 ret = rank_sec_inc;
320
321         return ret;
322 }
323
324 int
325 util_factory_rank_compare(GstPluginFeature *f1, GstPluginFeature *f2)
326 {
327         const gchar *klass;
328         int f1_rank_inc=0, f2_rank_inc=0;
329
330         klass = gst_element_factory_get_klass(GST_ELEMENT_FACTORY(f1));
331         f1_rank_inc = util_get_rank_increase ( klass );
332
333         klass = gst_element_factory_get_klass(GST_ELEMENT_FACTORY(f2));
334         f2_rank_inc = util_get_rank_increase ( klass );
335
336         return (gst_plugin_feature_get_rank(f2)+f2_rank_inc) - (gst_plugin_feature_get_rank(f1)+f1_rank_inc );
337 }
338
339 const char*
340 util_get_charset(const char *file_path)
341 {
342         UCharsetDetector* ucsd;
343         const UCharsetMatch* ucm;
344         UErrorCode status = U_ZERO_ERROR;
345
346         const char* charset = NULL;
347         char *buf = NULL;
348         FILE* fin =0;
349         size_t n_size = 0;
350
351         fin = fopen(file_path, "r");
352         if (!fin)
353         {
354                 SECURE_LOGE("fail to open file %s\n", file_path);
355                 return NULL;
356         }
357
358         ucsd = ucsdet_open( &status );
359         if( U_FAILURE(status) ) {
360                 LOGE("fail to ucsdet_open\n");
361                 goto done;
362         }
363
364         ucsdet_enableInputFilter( ucsd, TRUE );
365
366         buf = g_malloc(1024*1024);
367         if (!buf)
368         {
369                 LOGE("fail to alloc\n");
370                 goto done;
371         }
372
373         n_size = fread( buf, 1, 1024*1024, fin );
374
375         if (!n_size)
376                 goto done;
377
378         ucsdet_setText( ucsd, buf, strlen(buf), &status );
379         if( U_FAILURE(status) ) {
380                 LOGE("fail to ucsdet_setText\n");
381                 goto done;
382         }
383
384         ucm = ucsdet_detect( ucsd, &status );
385         if( U_FAILURE(status) ) {
386                 LOGE("fail to ucsdet_detect\n");
387                 goto done;
388         }
389
390         charset = ucsdet_getName( ucm, &status );
391         if( U_FAILURE(status) ) {
392                 LOGE("fail to ucsdet_getName\n");
393                 goto done;
394         }
395
396         /* CP949 encoding is an extension of the EUC-KR and it is backwards compatible.*/
397         if(charset && !strcmp(charset, "EUC-KR")) {
398                 charset = "CP949";
399         }
400
401 done:
402         if(fin)
403                 fclose(fin);
404
405         if(ucsd)
406                 ucsdet_close( ucsd );
407
408         if (buf)
409                 g_free(buf);
410
411         return charset;
412 }
413
414 int util_get_pixtype(unsigned int fourcc)
415 {
416         int pixtype = MM_PIXEL_FORMAT_INVALID;
417
418     /*
419         char *pfourcc = (char*)&fourcc;
420
421         LOGD("fourcc(%c%c%c%c)",
422                          pfourcc[0], pfourcc[1], pfourcc[2], pfourcc[3]);
423     */
424
425         switch (fourcc) {
426         case GST_MAKE_FOURCC ('S', 'N', '1', '2'):
427         case GST_MAKE_FOURCC ('N', 'V', '1', '2'):
428                 pixtype = MM_PIXEL_FORMAT_NV12;
429                 break;
430         case GST_MAKE_FOURCC ('S', 'T', '1', '2'):
431                 pixtype = MM_PIXEL_FORMAT_NV12T;
432                 break;
433         case GST_MAKE_FOURCC ('S', 'N', '2', '1'):
434         case GST_MAKE_FOURCC ('N', 'V', '2', '1'):
435                 pixtype = MM_PIXEL_FORMAT_NV21;
436                 break;
437         case GST_MAKE_FOURCC ('S', 'U', 'Y', 'V'):
438         case GST_MAKE_FOURCC ('Y', 'U', 'Y', 'V'):
439         case GST_MAKE_FOURCC ('Y', 'U', 'Y', '2'):
440                 pixtype = MM_PIXEL_FORMAT_YUYV;
441                 break;
442         case GST_MAKE_FOURCC ('S', 'Y', 'V', 'Y'):
443         case GST_MAKE_FOURCC ('U', 'Y', 'V', 'Y'):
444                 pixtype = MM_PIXEL_FORMAT_UYVY;
445                 break;
446         case GST_MAKE_FOURCC ('S', '4', '2', '0'):
447         case GST_MAKE_FOURCC ('I', '4', '2', '0'):
448                 pixtype = MM_PIXEL_FORMAT_I420;
449                 break;
450         case GST_MAKE_FOURCC ('Y', 'V', '1', '2'):
451                 pixtype = MM_PIXEL_FORMAT_YV12;
452                 break;
453         case GST_MAKE_FOURCC ('4', '2', '2', 'P'):
454                 pixtype = MM_PIXEL_FORMAT_422P;
455                 break;
456         case GST_MAKE_FOURCC ('R', 'G', 'B', 'P'):
457                 pixtype = MM_PIXEL_FORMAT_RGB565;
458                 break;
459         case GST_MAKE_FOURCC ('R', 'G', 'B', '3'):
460                 pixtype = MM_PIXEL_FORMAT_RGB888;
461                 break;
462         case GST_MAKE_FOURCC ('A', 'R', 'G', 'B'):
463         case GST_MAKE_FOURCC ('x', 'R', 'G', 'B'):
464                 pixtype = MM_PIXEL_FORMAT_ARGB;
465                 break;
466         case GST_MAKE_FOURCC ('B', 'G', 'R', 'A'):
467         case GST_MAKE_FOURCC ('B', 'G', 'R', 'x'):
468         case GST_MAKE_FOURCC ('S', 'R', '3', '2'):
469                 pixtype = MM_PIXEL_FORMAT_RGBA;
470                 break;
471         case GST_MAKE_FOURCC ('J', 'P', 'E', 'G'):
472         case GST_MAKE_FOURCC ('P', 'N', 'G', ' '):
473                 pixtype = MM_PIXEL_FORMAT_ENCODED;
474                 break;
475         case GST_MAKE_FOURCC ('I', 'T', 'L', 'V'):
476                 pixtype = MM_PIXEL_FORMAT_ITLV_JPEG_UYVY;
477                 break;
478         default:
479                 LOGE("Not supported fourcc type(%c%c%c%c)",
480                                fourcc, fourcc>>8, fourcc>>16, fourcc>>24);
481                 pixtype = MM_PIXEL_FORMAT_INVALID;
482                 break;
483         }
484
485         return pixtype;
486 }