Remove unused code
[platform/core/multimedia/libmedia-thumbnail.git] / server / thumb-server-internal.c
1 /*
2  * media-thumbnail-server
3  *
4  * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Contact: Hyunjun Ko <zzoon.ko@samsung.com>
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  */
21
22 #include "thumb-server-internal.h"
23 #include "media-thumb-util.h"
24 #include "media-thumb-debug.h"
25
26 #include <fcntl.h>
27 #include <unistd.h>
28 #include <dirent.h>
29 #include <stdio.h>
30 #include <string.h>
31 #include <Ecore_Evas.h>
32 #include <vconf.h>
33 #include <grp.h>
34 #include <pwd.h>
35
36 #ifdef LOG_TAG
37 #undef LOG_TAG
38 #endif
39
40 #define LOG_TAG "MEDIA_THUMBNAIL_SERVER"
41 #define THUMB_DEFAULT_WIDTH 320
42 #define THUMB_DEFAULT_HEIGHT 240
43 #define THUMB_BLOCK_SIZE 512
44 #define THUMB_COMM_SOCK_PATH tzplatform_mkpath(TZ_SYS_RUN, "media-server/media_ipc_thumbcomm.socket")
45 #define THUMB_EMPTY_STR ""
46
47 static __thread char **arr_path;
48 static __thread uid_t *arr_uid;
49 static __thread int g_idx = 0;
50 static __thread int g_cur_idx = 0;
51
52 GMainLoop *g_thumb_server_mainloop; // defined in thumb-server.c as extern
53
54 static gboolean __thumb_server_send_msg_to_agent(int msg_type);
55 static void __thumb_daemon_stop_job(void);
56 static int __thumb_daemon_all_extract(uid_t uid);
57 int _thumb_daemon_process_queue_jobs(gpointer data);
58 static gboolean _thumb_server_send_deny_message(int sockfd);
59
60 gboolean _thumb_daemon_start_jobs(gpointer data)
61 {
62         thumb_dbg("");
63         /* Initialize ecore-evas to use evas library */
64         ecore_evas_init();
65
66         __thumb_server_send_msg_to_agent(MS_MSG_THUMB_SERVER_READY);
67
68         return FALSE;
69 }
70
71 void _thumb_daemon_finish_jobs(void)
72 {
73         sqlite3 *sqlite_db_handle = _media_thumb_db_get_handle();
74
75         if (sqlite_db_handle != NULL) {
76                 _media_thumb_db_disconnect();
77                 thumb_dbg("sqlite3 handle is alive. So disconnect to sqlite3");
78         }
79
80         /* Shutdown ecore-evas */
81         ecore_evas_shutdown();
82         g_main_loop_quit(g_thumb_server_mainloop);
83
84         return;
85 }
86
87 int _thumb_daemon_mmc_status(void)
88 {
89         int err = -1;
90         int status = -1;
91
92         err = vconf_get_int(VCONFKEY_SYSMAN_MMC_STATUS, &status);
93         if (err == 0) {
94                 return status;
95         } else if (err == -1) {
96                 thumb_err("vconf_get_int failed : %d", err);
97         } else {
98                 thumb_err("vconf_get_int Unexpected error code: %d", err);
99         }
100
101         return status;
102 }
103
104 void _thumb_daemon_mmc_eject_vconf_cb(void *data)
105 {
106         int err = -1;
107         int status = 0;
108
109         thumb_warn("_thumb_daemon_vconf_cb called");
110
111         err = vconf_get_int(VCONFKEY_SYSMAN_MMC_STATUS, &status);
112         if (err == 0) {
113                 if (status == VCONFKEY_SYSMAN_MMC_REMOVED || status == VCONFKEY_SYSMAN_MMC_INSERTED_NOT_MOUNTED) {
114                         thumb_warn("SD card is ejected or not mounted. So media-thumbnail-server stops jobs to extract all thumbnails");
115
116                         __thumb_daemon_stop_job();
117                 }
118         } else if (err == -1) {
119                 thumb_err("vconf_get_int failed : %d", err);
120         } else {
121                 thumb_err("vconf_get_int Unexpected error code: %d", err);
122         }
123
124         return;
125 }
126
127 void _thumb_daemon_vconf_cb(void *data)
128 {
129         int err = -1;
130         int status = 0;
131
132         thumb_warn("_thumb_daemon_vconf_cb called");
133
134         err = vconf_get_int(VCONFKEY_SYSMAN_MMC_FORMAT, &status);
135         if (err == 0) {
136                 if (status == VCONFKEY_SYSMAN_MMC_FORMAT_COMPLETED) {
137                         thumb_warn("SD card format is completed. So media-thumbnail-server stops jobs to extract all thumbnails");
138
139                         __thumb_daemon_stop_job();
140                 } else {
141                         thumb_dbg("not completed");
142                 }
143         } else if (err == -1) {
144                 thumb_err("vconf_get_int failed : %d", err);
145         } else {
146                 thumb_err("vconf_get_int Unexpected error code: %d", err);
147         }
148
149         return;
150 }
151
152 static void __thumb_daemon_stop_job()
153 {
154         int i = 0;
155         char *path = NULL;
156
157         thumb_warn("There are %d jobs in the queue. But all jobs will be stopped", g_idx - g_cur_idx);
158
159         for (i = g_cur_idx; i < g_idx; i++) {
160                 path = arr_path[g_cur_idx++];
161                 SAFE_FREE(path);
162         }
163
164         return;
165 }
166
167 int _thumb_daemon_process_job(thumbMsg *req_msg, thumbMsg *res_msg)
168 {
169         int err = MS_MEDIA_ERR_NONE;
170
171         err = _media_thumb_process(req_msg, res_msg);
172         if (err != MS_MEDIA_ERR_NONE) {
173                 if (req_msg->msg_type == THUMB_REQUEST_SAVE_FILE) {
174                         thumb_err("_media_thumb_process is failed: %d", err);
175                         res_msg->status = THUMB_FAIL;
176                 } else {
177                         if (err != MS_MEDIA_ERR_FILE_NOT_EXIST) {
178                                 thumb_warn("_media_thumb_process is failed: %d, So use default thumb", err);
179                                 res_msg->status = THUMB_SUCCESS;
180                         } else {
181                                 thumb_warn("_media_thumb_process is failed: %d, (file not exist) ", err);
182                                 res_msg->status = THUMB_FAIL;
183                         }
184                 }
185         } else {
186                 res_msg->status = THUMB_SUCCESS;
187         }
188
189         return err;
190 }
191
192 static int __thumb_daemon_process_job_raw(thumbMsg *req_msg, thumbMsg *res_msg)
193 {
194         int err = MS_MEDIA_ERR_NONE;
195
196         err = _media_thumb_process_raw(req_msg, res_msg);
197         if (err != MS_MEDIA_ERR_NONE) {
198                 thumb_warn("_media_thumb_process is failed: %d", err);
199                 res_msg->status = THUMB_FAIL;
200         } else {
201                 res_msg->status = THUMB_SUCCESS;
202         }
203
204         return err;
205 }
206
207 static int __thumb_daemon_all_extract(uid_t uid)
208 {
209         int err = MS_MEDIA_ERR_NONE;
210         char query_string[MAX_PATH_SIZE + 1] = { 0, };
211         char path[MAX_PATH_SIZE + 1] = { 0, };
212         sqlite3 *sqlite_db_handle = NULL;
213         sqlite3_stmt *sqlite_stmt = NULL;
214
215         err = _media_thumb_db_connect(uid);
216         if (err != MS_MEDIA_ERR_NONE) {
217                 thumb_err("_media_thumb_db_connect failed: %d", err);
218                 return err;
219         }
220
221         sqlite_db_handle = _media_thumb_db_get_handle();
222         if (sqlite_db_handle == NULL) {
223                 thumb_err("sqlite handle is NULL");
224                 return MS_MEDIA_ERR_INTERNAL;
225         }
226
227         if (_thumb_daemon_mmc_status() == VCONFKEY_SYSMAN_MMC_MOUNTED) {
228                 snprintf(query_string, sizeof(query_string), SELECT_PATH_FROM_UNEXTRACTED_THUMB_MEDIA);
229         } else {
230                 snprintf(query_string, sizeof(query_string), SELECT_PATH_FROM_UNEXTRACTED_THUMB_INTERNAL_MEDIA);
231         }
232
233         thumb_warn("Query: %s", query_string);
234
235         err = sqlite3_prepare_v2(sqlite_db_handle, query_string, strlen(query_string), &sqlite_stmt, NULL);
236         if (SQLITE_OK != err) {
237                 thumb_err("prepare error [%s]", sqlite3_errmsg(sqlite_db_handle));
238                 _media_thumb_db_disconnect();
239                 return MS_MEDIA_ERR_INTERNAL;
240         }
241
242         while (1) {
243                 err = sqlite3_step(sqlite_stmt);
244                 if (err != SQLITE_ROW) {
245                         thumb_dbg("end of row [%s]", sqlite3_errmsg(sqlite_db_handle));
246                         break;
247                 }
248
249                 strncpy(path, (const char *)sqlite3_column_text(sqlite_stmt, 0), sizeof(path));
250                 path[sizeof(path) - 1] = '\0';
251
252                 thumb_dbg_slog("Path : %s", path);
253
254                 if (g_idx == 0) {
255                         arr_path = (char**)malloc(sizeof(char*));
256                         arr_uid = (uid_t*)malloc(sizeof(uid_t));
257                 } else {
258                         arr_path = (char**)realloc(arr_path, (g_idx + 1) * sizeof(char*));
259                         arr_uid = (uid_t*)realloc(arr_uid, (g_idx + 1) * sizeof(uid_t));
260                 }
261                 arr_uid[g_idx] = uid;
262                 arr_path[g_idx++] = strdup(path);
263         }
264
265         sqlite3_finalize(sqlite_stmt);
266         _media_thumb_db_disconnect();
267
268         return MS_MEDIA_ERR_NONE;
269 }
270
271 int _thumb_daemon_process_queue_jobs(gpointer data)
272 {
273         int err = MS_MEDIA_ERR_NONE;
274         char *path = NULL;
275         uid_t uid = NULL;
276
277         if (g_cur_idx < g_idx) {
278                 thumb_warn("There are %d jobs in the queue", g_idx - g_cur_idx);
279                 thumb_dbg("Current idx : [%d]", g_cur_idx);
280                 uid = arr_uid[g_cur_idx];
281                 path = arr_path[g_cur_idx++];
282
283                 thumbMsg recv_msg, res_msg;
284                 memset(&recv_msg, 0x00, sizeof(thumbMsg));
285                 memset(&res_msg, 0x00, sizeof(thumbMsg));
286
287                 recv_msg.msg_type = THUMB_REQUEST_DB_INSERT;
288                 recv_msg.uid = uid;
289                 strncpy(recv_msg.org_path, path, sizeof(recv_msg.org_path));
290                 recv_msg.org_path[sizeof(recv_msg.org_path) - 1] = '\0';
291
292                 err = _thumb_daemon_process_job(&recv_msg, &res_msg);
293                 if (err == MS_MEDIA_ERR_FILE_NOT_EXIST) {
294                         thumb_err("Thumbnail processing is failed : %d", err);
295                 } else {
296                         if (res_msg.status == THUMB_SUCCESS) {
297
298                                 err = _media_thumb_db_connect(uid);
299                                 if (err != MS_MEDIA_ERR_NONE) {
300                                         thumb_err("_media_thumb_mb_svc_connect failed: %d", err);
301                                         return TRUE;
302                                 }
303
304                                 /* Need to update DB once generating thumb is done */
305                                 err = _media_thumb_update_db(recv_msg.org_path,
306                                                                                         res_msg.dst_path,
307                                                                                         res_msg.origin_width,
308                                                                                         res_msg.origin_height,
309                                                                                         uid);
310                                 if (err != MS_MEDIA_ERR_NONE) {
311                                         thumb_err("_media_thumb_update_db failed : %d", err);
312                                 }
313
314                                 _media_thumb_db_disconnect();
315                         }
316                 }
317
318                 SAFE_FREE(path);
319         } else {
320                 g_cur_idx = 0;
321                 g_idx = 0;
322                 thumb_warn("Deleting array");
323                 SAFE_FREE(arr_path);
324                 SAFE_FREE(arr_uid);
325                 //_media_thumb_db_disconnect();
326
327                 __thumb_server_send_msg_to_agent(MS_MSG_THUMB_EXTRACT_ALL_DONE); // MS_MSG_THUMB_EXTRACT_ALL_DONE
328
329                 return FALSE;
330         }
331
332         return TRUE;
333 }
334
335 gboolean _thumb_server_read_socket(GIOChannel *src,
336                                                                         GIOCondition condition,
337                                                                         gpointer data)
338 {
339         struct sockaddr_un client_addr;
340         unsigned int client_addr_len;
341         thumbMsg recv_msg;
342         thumbMsg res_msg;
343         ms_peer_credentials credentials;
344
345         int sock = -1;
346         int client_sock = -1;
347
348         memset((void *)&recv_msg, 0, sizeof(recv_msg));
349         memset((void *)&res_msg, 0, sizeof(res_msg));
350         memset((void *)&credentials, 0, sizeof(credentials));
351
352         sock = g_io_channel_unix_get_fd(src);
353         if (sock < 0) {
354                 thumb_err("sock fd is invalid!");
355                 return TRUE;
356         }
357
358         client_addr_len = sizeof(client_addr);
359
360         if ((client_sock = accept(sock, (struct sockaddr*)&client_addr, &client_addr_len)) < 0) {
361                 thumb_stderror("accept failed : %s");
362                 return TRUE;
363         }
364
365         if (ms_cynara_receive_untrusted_message_thumb(client_sock, &recv_msg, &credentials) != MS_MEDIA_ERR_NONE) {
366                 thumb_err("ms_cynara_receive_untrusted_message_thumb failed");
367                 close(client_sock);
368                 return FALSE;
369         }
370
371         if (recv_msg.msg_type != THUMB_REQUEST_KILL_SERVER) {
372                 if (ms_cynara_check(&credentials, MEDIA_STORAGE_PRIVILEGE) != MS_MEDIA_ERR_NONE) {
373                         thumb_err("Cynara denied access to process request");
374                         _thumb_server_send_deny_message(client_sock);
375                         close(client_sock);
376                         return TRUE;
377                 }
378         }
379
380         SAFE_FREE(credentials.smack);
381         SAFE_FREE(credentials.uid);
382
383         thumb_warn_slog("Received [%d] %s(%d) from PID(%d)", recv_msg.msg_type, recv_msg.org_path, strlen(recv_msg.org_path), recv_msg.pid);
384
385         if (recv_msg.msg_type == THUMB_REQUEST_ALL_MEDIA) {
386                 thumb_dbg("All thumbnails are being extracted now");
387                 __thumb_daemon_all_extract(recv_msg.uid);
388                 g_idle_add(_thumb_daemon_process_queue_jobs, NULL);
389         } else if (recv_msg.msg_type == THUMB_REQUEST_RAW_DATA) {
390                 __thumb_daemon_process_job_raw(&recv_msg, &res_msg);
391         } else if (recv_msg.msg_type == THUMB_REQUEST_KILL_SERVER) {
392                 thumb_warn("received KILL msg from thumbnail agent.");
393         } else {
394                 _thumb_daemon_process_job(&recv_msg, &res_msg);
395         }
396
397         if (res_msg.msg_type == 0)
398                 res_msg.msg_type = recv_msg.msg_type;
399         res_msg.request_id = recv_msg.request_id;
400         strncpy(res_msg.org_path, recv_msg.org_path, recv_msg.origin_path_size);
401         res_msg.origin_path_size = recv_msg.origin_path_size;
402         if (res_msg.msg_type != THUMB_RESPONSE_RAW_DATA) {
403                 res_msg.dest_path_size = strlen(res_msg.dst_path)+1;
404                 res_msg.thumb_size = 0;
405         } else {
406                 res_msg.dest_path_size = 1;
407                 res_msg.dst_path[0] = '\0';
408         }
409
410         int buf_size = 0;
411         int sending_block = 0;
412         int block_size = sizeof(res_msg) - MAX_FILEPATH_LEN*2 - sizeof(unsigned char *);
413         unsigned char *buf = NULL;
414         _media_thumb_set_buffer(&res_msg, &buf, &buf_size);
415
416         while (buf_size > 0) {
417                 if (buf_size < THUMB_BLOCK_SIZE) {
418                         block_size = buf_size;
419                 }
420                 if (send(client_sock, buf+sending_block, block_size, 0) != block_size) {
421                         thumb_stderror("sendto failed : %s");
422                 }
423                 sending_block += block_size;
424                 buf_size -= block_size;
425                 if (block_size < THUMB_BLOCK_SIZE) {
426                         block_size = THUMB_BLOCK_SIZE;
427                 }
428         }
429         if (buf_size == 0) {
430                 thumb_dbg_slog("Sent data(%d) from %s", res_msg.thumb_size, res_msg.org_path);
431         }
432         SAFE_FREE(buf);
433         SAFE_FREE(res_msg.thumb_data);
434
435         if (recv_msg.msg_type == THUMB_REQUEST_KILL_SERVER) {
436                 thumb_warn("Shutting down...");
437                 g_main_loop_quit(g_thumb_server_mainloop);
438         }
439
440         close(client_sock);
441
442         return TRUE;
443 }
444
445 static gboolean __thumb_server_send_msg_to_agent(int msg_type)
446 {
447         int sock;
448         ms_sock_info_s sock_info;
449         struct sockaddr_un serv_addr;
450         ms_thumb_server_msg send_msg;
451         sock_info.port = MS_THUMB_COMM_PORT;
452
453         if (ms_ipc_create_client_socket(MS_TIMEOUT_SEC_10, &sock_info) < 0) {
454                 thumb_err("ms_ipc_create_server_socket failed");
455                 return FALSE;
456         }
457
458         memset(&serv_addr, 0, sizeof(serv_addr));
459
460         sock = sock_info.sock_fd;
461         serv_addr.sun_family = AF_UNIX;
462         strncpy(serv_addr.sun_path, THUMB_COMM_SOCK_PATH, strlen(THUMB_COMM_SOCK_PATH));
463
464
465         /* Connecting to the thumbnail server */
466         if (connect(sock, (struct sockaddr*)&serv_addr, sizeof(serv_addr)) < 0) {
467                 thumb_stderror("connect");
468                 ms_ipc_delete_client_socket(&sock_info);
469                 return MS_MEDIA_ERR_SOCKET_CONN;
470         }
471
472         send_msg.msg_type = msg_type;
473
474         if (send(sock, &send_msg, sizeof(ms_thumb_server_msg), 0) != sizeof(ms_thumb_server_msg)) {
475                 thumb_stderror("sendto failed");
476                 ms_ipc_delete_client_socket(&sock_info);
477                 return FALSE;
478         }
479
480         thumb_dbg("Sending msg to thumbnail agent[%d] is successful", send_msg.msg_type);
481
482         ms_ipc_delete_client_socket(&sock_info);
483
484         return TRUE;
485 }
486
487 static gboolean _thumb_server_send_deny_message(int sockfd)
488 {
489         thumbMsg msg = {0};
490         int bytes_to_send = sizeof(msg) - sizeof(msg.org_path) - sizeof(msg.dst_path);
491
492         msg.msg_type = THUMB_RESPONSE;
493         msg.status = THUMB_FAIL;
494
495         if (send(sockfd, &msg, bytes_to_send, 0) != bytes_to_send) {
496                 thumb_stderror("send failed");
497                 return FALSE;
498         }
499
500         return TRUE;
501 }
502
503 gboolean _thumb_server_prepare_socket(int *sock_fd)
504 {
505         int sock;
506         unsigned short serv_port;
507
508         thumbMsg recv_msg;
509         thumbMsg res_msg;
510
511         memset((void *)&recv_msg, 0, sizeof(recv_msg));
512         memset((void *)&res_msg, 0, sizeof(res_msg));
513         serv_port = MS_THUMB_DAEMON_PORT;
514
515         if (ms_ipc_create_server_socket(serv_port, &sock) < 0) {
516                 thumb_err("ms_ipc_create_server_socket failed");
517                 return FALSE;
518         }
519
520         if (ms_cynara_enable_credentials_passing(sock) != MS_MEDIA_ERR_NONE) {
521                 thumb_err("ms_cynara_enable_credentials_passing failed");
522                 close(sock);
523                 return FALSE;
524         }
525
526         *sock_fd = sock;
527
528         return TRUE;
529 }
530
531 int _thumbnail_get_data(const char *origin_path,
532                                                 media_thumb_format format,
533                                                 char *thumb_path,
534                                                 unsigned char **data,
535                                                 int *size,
536                                                 int *width,
537                                                 int *height,
538                                                 int *origin_width,
539                                                 int *origin_height,
540                                                 int *alpha,
541                                                 bool *is_saved)
542 {
543         int err = MS_MEDIA_ERR_NONE;
544         int thumb_width = -1;
545         int thumb_height = -1;
546
547         if (origin_path == NULL || size == NULL
548                         || width == NULL || height == NULL) {
549                 thumb_err("Invalid parameter");
550                 return MS_MEDIA_ERR_INVALID_PARAMETER;
551         }
552
553         if (format < MEDIA_THUMB_BGRA || format > MEDIA_THUMB_RGB888) {
554                 thumb_err("parameter format is invalid");
555                 return MS_MEDIA_ERR_INVALID_PARAMETER;
556         }
557
558         if (!g_file_test
559                 (origin_path, G_FILE_TEST_EXISTS | G_FILE_TEST_IS_REGULAR)) {
560                         thumb_err("Original path (%s) does not exist", origin_path);
561                         return MS_MEDIA_ERR_INVALID_PARAMETER;
562         }
563
564         thumb_dbg("Origin path : %s", origin_path);
565
566         int file_type = THUMB_NONE_TYPE;
567         media_thumb_info thumb_info = {0,};
568         file_type = _media_thumb_get_file_type(origin_path);
569         thumb_width = *width;
570         thumb_height = *height;
571         if (thumb_width == 0 || thumb_height == 0) {
572                 thumb_width = THUMB_DEFAULT_WIDTH;
573                 thumb_height = THUMB_DEFAULT_HEIGHT;
574         }
575
576         thumb_info.is_raw = FALSE;
577
578         if (file_type == THUMB_IMAGE_TYPE) {
579                 err = _media_thumb_image(origin_path, thumb_path, thumb_width, thumb_height, format, &thumb_info);
580                 if (err != MS_MEDIA_ERR_NONE) {
581                         thumb_err("_media_thumb_image failed");
582                         return err;
583                 }
584         } else if (file_type == THUMB_VIDEO_TYPE) {
585                 err = _media_thumb_video(origin_path, thumb_width, thumb_height, format, &thumb_info);
586                 if (err != MS_MEDIA_ERR_NONE) {
587                         thumb_err("_media_thumb_image failed");
588                         return err;
589                 }
590         } else {
591                 thumb_err("invalid file type");
592                 return MS_MEDIA_ERR_INVALID_PARAMETER;
593         }
594
595         if (size) *size = thumb_info.size;
596         if (width) *width = thumb_info.width;
597         if (height) *height = thumb_info.height;
598         *data = thumb_info.data;
599         if (origin_width) *origin_width = thumb_info.origin_width;
600         if (origin_height) *origin_height = thumb_info.origin_height;
601         if (alpha) *alpha = thumb_info.alpha;
602         if (is_saved) *is_saved = thumb_info.is_saved;
603
604         thumb_dbg("Thumb data is generated successfully (Size:%d, W:%d, H:%d) 0x%x", *size, *width, *height, *data);
605
606         return MS_MEDIA_ERR_NONE;
607 }
608
609 int _thumbnail_get_raw_data(const char *origin_path,
610                                                 media_thumb_format format,
611                                                 int *width,
612                                                 int *height,
613                                                 unsigned char **data,
614                                                 int *size)
615 {
616         int err = MS_MEDIA_ERR_NONE;
617         int thumb_width = -1;
618         int thumb_height = -1;
619         const char * thumb_path = NULL;
620
621         if (origin_path == NULL || *width <= 0 || *height <= 0) {
622                 thumb_err("Invalid parameter");
623                 return MS_MEDIA_ERR_INVALID_PARAMETER;
624         }
625
626         if (format < MEDIA_THUMB_BGRA || format > MEDIA_THUMB_RGB888) {
627                 thumb_err("parameter format is invalid");
628                 return MS_MEDIA_ERR_INVALID_PARAMETER;
629         }
630
631         if (!g_file_test(origin_path, G_FILE_TEST_EXISTS | G_FILE_TEST_IS_REGULAR)) {
632                 thumb_err("Original path (%s) does not exist", origin_path);
633                 return MS_MEDIA_ERR_INVALID_PARAMETER;
634         }
635
636         int file_type = THUMB_NONE_TYPE;
637         media_thumb_info thumb_info = {0,};
638         file_type = _media_thumb_get_file_type(origin_path);
639         thumb_width = *width;
640         thumb_height = *height;
641         thumb_info.is_raw = TRUE;
642
643         if (file_type == THUMB_IMAGE_TYPE) {
644                 err = _media_thumb_image(origin_path, thumb_path, thumb_width, thumb_height, format, &thumb_info);
645                 if (err != MS_MEDIA_ERR_NONE) {
646                         thumb_err("_media_thumb_image failed");
647                         return err;
648                 }
649         } else if (file_type == THUMB_VIDEO_TYPE) {
650                 err = _media_thumb_video(origin_path, thumb_width, thumb_height, format, &thumb_info);
651                 if (err != MS_MEDIA_ERR_NONE) {
652                         thumb_err("_media_thumb_image failed");
653                         return err;
654                 }
655         } else {
656                 thumb_err("invalid file type");
657                 return MS_MEDIA_ERR_INVALID_PARAMETER;
658         }
659
660         if (size) *size = thumb_info.size;
661         *data = thumb_info.data;
662         *width = thumb_info.width;
663         *height = thumb_info.height;
664
665         return MS_MEDIA_ERR_NONE;
666 }
667
668 int _media_thumb_process(thumbMsg *req_msg, thumbMsg *res_msg)
669 {
670         int err = MS_MEDIA_ERR_NONE;
671         unsigned char *data = NULL;
672         int thumb_size = 0;
673         int thumb_w = 0;
674         int thumb_h = 0;
675         int origin_w = 0;
676         int origin_h = 0;
677         int max_length = 0;
678         char *thumb_path = NULL;
679         int need_update_db = 0;
680         int alpha = 0;
681         bool is_saved = FALSE;
682
683         if (req_msg == NULL || res_msg == NULL) {
684                 thumb_err("Invalid msg!");
685                 return MS_MEDIA_ERR_INVALID_PARAMETER;
686         }
687
688         int msg_type = req_msg->msg_type;
689         const char *origin_path = req_msg->org_path;
690
691         media_thumb_format thumb_format = MEDIA_THUMB_BGRA;
692         thumb_w = req_msg->thumb_width;
693         thumb_h = req_msg->thumb_height;
694         thumb_path = res_msg->dst_path;
695         thumb_path[0] = '\0';
696         max_length = sizeof(res_msg->dst_path) -1;
697
698         if (!g_file_test(origin_path, G_FILE_TEST_EXISTS | G_FILE_TEST_IS_REGULAR)) {
699                 thumb_err("origin_path does not exist in file system.");
700                 return MS_MEDIA_ERR_FILE_NOT_EXIST;
701         }
702
703         err = _media_thumb_db_connect(req_msg->uid);
704         if (err != MS_MEDIA_ERR_NONE) {
705                 thumb_err("_media_thumb_mb_svc_connect failed: %d", err);
706                 return err;
707         }
708
709         if (msg_type == THUMB_REQUEST_DB_INSERT) {
710                 err = _media_thumb_get_thumb_from_db_with_size(origin_path, thumb_path, max_length, &need_update_db, &origin_w, &origin_h);
711                 if (err == MS_MEDIA_ERR_NONE) {
712                         res_msg->origin_width = origin_w;
713                         res_msg->origin_height = origin_h;
714                         _media_thumb_db_disconnect();
715                         return MS_MEDIA_ERR_NONE;
716                 } else {
717                         if (strlen(thumb_path) == 0) {
718                                 err = _media_thumb_get_hash_name(origin_path, thumb_path, max_length, req_msg->uid);
719                                 if (err != MS_MEDIA_ERR_NONE) {
720                                         thumb_err("_media_thumb_get_hash_name failed - %d", err);
721                                         strncpy(thumb_path, THUMB_EMPTY_STR, max_length);
722                                         _media_thumb_db_disconnect();
723                                         return err;
724                                 }
725
726                                 thumb_path[strlen(thumb_path)] = '\0';
727                         }
728                 }
729
730         } else if (msg_type == THUMB_REQUEST_SAVE_FILE) {
731                 strncpy(thumb_path, req_msg->dst_path, max_length);
732
733         } else if (msg_type == THUMB_REQUEST_ALL_MEDIA) {
734                 err = _media_thumb_get_hash_name(origin_path, thumb_path, max_length, req_msg->uid);
735                 if (err != MS_MEDIA_ERR_NONE) {
736                         thumb_err("_media_thumb_get_hash_name failed - %d", err);
737                         strncpy(thumb_path, THUMB_EMPTY_STR, max_length);
738                         _media_thumb_db_disconnect();
739                         return err;
740                 }
741
742                 thumb_path[strlen(thumb_path)] = '\0';
743         }
744
745         thumb_dbg_slog("Thumb path : %s", thumb_path);
746
747         if (g_file_test(thumb_path, G_FILE_TEST_EXISTS | G_FILE_TEST_IS_REGULAR)) {
748                 thumb_warn("thumb path already exists in file system.. remove the existed file");
749                 _media_thumb_remove_file(thumb_path);
750         }
751
752         err = _thumbnail_get_data(origin_path, thumb_format, thumb_path, &data, &thumb_size, &thumb_w, &thumb_h, &origin_w, &origin_h, &alpha, &is_saved);
753         if (err != MS_MEDIA_ERR_NONE) {
754                 thumb_err("_thumbnail_get_data failed - %d", err);
755                 SAFE_FREE(data);
756                 strncpy(thumb_path, THUMB_EMPTY_STR, max_length);
757
758                 goto DB_UPDATE;
759         }
760
761         res_msg->msg_type = THUMB_RESPONSE;
762         res_msg->thumb_size = thumb_size;
763         res_msg->thumb_width = thumb_w;
764         res_msg->thumb_height = thumb_h;
765         res_msg->origin_width = origin_w;
766         res_msg->origin_height = origin_h;
767
768         /* If the image is transparent PNG format, make png file as thumbnail of this image */
769         if (alpha) {
770                 char file_ext[10];
771                 err = _media_thumb_get_file_ext(origin_path, file_ext, sizeof(file_ext));
772                 if (strncasecmp(file_ext, "png", 3) == 0) {
773                         int len = strlen(thumb_path);
774                         thumb_path[len - 3] = 'p';
775                         thumb_path[len - 2] = 'n';
776                         thumb_path[len - 1] = 'g';
777                 }
778                 thumb_dbg_slog("Thumb path is changed : %s", thumb_path);
779         }
780
781         if (is_saved == FALSE && data != NULL) {
782                 err = _media_thumb_save_to_file_with_evas(data, thumb_w, thumb_h, alpha, thumb_path);
783                 if (err != MS_MEDIA_ERR_NONE) {
784                         thumb_err("save_to_file_with_evas failed - %d", err);
785                         SAFE_FREE(data);
786
787                         if (msg_type == THUMB_REQUEST_DB_INSERT || msg_type == THUMB_REQUEST_ALL_MEDIA) {
788                                 strncpy(thumb_path, THUMB_EMPTY_STR, max_length);
789                         }
790                         _media_thumb_db_disconnect();
791                         return err;
792                 } else {
793                         thumb_dbg("file save success");
794                 }
795         } else {
796                 thumb_dbg("file is already saved");
797         }
798
799         /* fsync */
800         int fd = 0;
801         fd = open(thumb_path, O_WRONLY);
802         if (fd < 0) {
803                 thumb_warn("open failed");
804         } else {
805                 err = fsync(fd);
806                 if (err == -1) {
807                         thumb_warn("fsync failed");
808                 }
809
810                 close(fd);
811         }
812         /* End of fsync */
813
814         SAFE_FREE(data);
815 DB_UPDATE:
816         /* DB update if needed */
817         if (need_update_db == 1) {
818                 err = _media_thumb_update_db(origin_path, thumb_path, res_msg->origin_width, res_msg->origin_height, req_msg->uid);
819                 if (err != MS_MEDIA_ERR_NONE) {
820                         thumb_err("_media_thumb_update_db failed : %d", err);
821                 }
822         }
823
824         _media_thumb_db_disconnect();
825
826         return MS_MEDIA_ERR_NONE;
827 }
828
829 int
830 _media_thumb_process_raw(thumbMsg *req_msg, thumbMsg *res_msg)
831 {
832         int err = MS_MEDIA_ERR_NONE;
833         unsigned char *data = NULL;
834         int thumb_size = 0;
835         int thumb_w = 0;
836         int thumb_h = 0;
837
838         if (req_msg == NULL || res_msg == NULL) {
839                 thumb_err("Invalid msg!");
840                 return MS_MEDIA_ERR_INVALID_PARAMETER;
841         }
842
843         const char *origin_path = req_msg->org_path;
844
845         media_thumb_format thumb_format = MEDIA_THUMB_BGRA;
846         thumb_w = req_msg->thumb_width;
847         thumb_h = req_msg->thumb_height;
848
849         err = _thumbnail_get_raw_data(origin_path, thumb_format, &thumb_w, &thumb_h, &data, &thumb_size);
850
851         if (err != MS_MEDIA_ERR_NONE) {
852                 thumb_err("_thumbnail_get_data failed - %d", err);
853                 SAFE_FREE(data);
854         }
855
856         res_msg->msg_type = THUMB_RESPONSE_RAW_DATA;
857         res_msg->thumb_width = thumb_w;
858         res_msg->thumb_height = thumb_h;
859         res_msg->thumb_size = thumb_size;
860         res_msg->thumb_data = malloc(thumb_size * sizeof(unsigned char));
861         memcpy(res_msg->thumb_data, data, thumb_size);
862
863         SAFE_FREE(data);
864
865         return MS_MEDIA_ERR_NONE;
866 }