Get the module index using muse configure
[platform/core/api/recorder.git] / src / recorder.c
1 /*
2 * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #include <stdio.h>
18 #include <stdlib.h>
19 #include <string.h>
20 #include <camera_internal.h>
21 #include <recorder.h>
22 #include <sound_manager.h>
23 #include <sound_manager_internal.h>
24 #include <storage.h>
25 #include <storage-internal.h>
26 #include <muse_recorder.h>
27 #include <muse_recorder_msg.h>
28 #include <muse_core.h>
29 #include <muse_client.h>
30 #include <recorder_private.h>
31 #include <gio/gio.h>
32 #include <dlog.h>
33 #include <tzplatform_config.h>
34
35 #ifdef LOG_TAG
36 #undef LOG_TAG
37 #endif
38 #define LOG_TAG "TIZEN_N_RECORDER"
39 #define MODULE_NAME "recorder"
40
41 /* for device changed callback */
42 static GMutex g_rec_dev_state_changed_cb_lock;
43 static GList *g_rec_dev_state_changed_cb_list;
44 static int g_rec_dev_state_changed_cb_id;
45 static GDBusConnection *g_rec_dev_state_changed_cb_conn;
46 static guint g_rec_dev_state_changed_cb_subscribe_id;
47 static GMutex g_rec_idle_event_lock;
48
49
50
51 static void __recorder_update_api_waiting(recorder_cb_info_s *cb_info, int api, int value)
52 {
53         if (!cb_info ||
54                 api < 0 || api >= MUSE_RECORDER_API_MAX) {
55                 LOGE("invalid param %p %d", cb_info, api);
56                 return;
57         }
58
59         g_mutex_lock(&(cb_info->api_mutex[api]));
60         cb_info->api_waiting[api] += value;
61         g_mutex_unlock(&(cb_info->api_mutex[api]));
62
63         /*LOGD("api %d, value %d, waiting %d",
64                 api, value, cb_info->api_waiting[api]);*/
65
66         return;
67 }
68
69
70 static void __recorder_device_state_changed_cb(GDBusConnection *connection,
71         const gchar *sender_name, const gchar *object_path, const gchar *interface_name,
72         const gchar *signal_name, GVariant *param, gpointer user_data)
73 {
74         int value = 0;
75         recorder_type_e type = RECORDER_TYPE_AUDIO;
76         recorder_device_state_e state = RECORDER_DEVICE_STATE_IDLE;
77         GList *tmp_list = NULL;
78         recorder_cb_info *info = NULL;
79
80         g_mutex_lock(&g_rec_dev_state_changed_cb_lock);
81
82         if (!g_rec_dev_state_changed_cb_list || !param) {
83                 LOGW("no callback or NULL param %p", param);
84                 goto _DONE;
85         }
86
87         /* get device type and state */
88         g_variant_get(param, "(i)", &value);
89
90         type = value >> 16;
91         state = 0x0000ffff & value;
92
93         LOGD("type %d, state %d", type, state);
94
95         tmp_list = g_rec_dev_state_changed_cb_list;
96
97         do {
98                 info = (recorder_cb_info *)tmp_list->data;
99
100                 if (info) {
101                         if (info->callback) {
102                                 LOGD("start id[%d] callback", info->id);
103                                 ((recorder_device_state_changed_cb)info->callback)(type, state, info->user_data);
104                                 LOGD("returned id[%d] callback", info->id);
105                         } else {
106                                 LOGW("NULL callback for id %d", info->id);
107                         }
108                 }
109
110                 tmp_list = tmp_list->next;
111         } while (tmp_list);
112
113 _DONE:
114         g_mutex_unlock(&g_rec_dev_state_changed_cb_lock);
115
116         return;
117 }
118
119
120 static int _recorder_import_tbm_key(tbm_bufmgr bufmgr, unsigned int tbm_key, tbm_bo *bo, tbm_bo_handle *bo_handle)
121 {
122         tbm_bo tmp_bo = NULL;
123         tbm_bo_handle tmp_bo_handle = {NULL, };
124
125         if (bufmgr == NULL || bo == NULL || bo_handle == NULL || tbm_key == 0) {
126                 LOGE("invalid parameter - bufmgr %p, bo %p, bo_handle %p, key %d",
127                      bufmgr, bo, bo_handle, tbm_key);
128                 return false;
129         }
130
131         tmp_bo = tbm_bo_import(bufmgr, tbm_key);
132         if (tmp_bo == NULL) {
133                 LOGE("bo import failed - bufmgr %p, key %d", bufmgr, tbm_key);
134                 return false;
135         }
136
137         tmp_bo_handle = tbm_bo_map(tmp_bo, TBM_DEVICE_CPU, TBM_OPTION_READ);
138         if (tmp_bo_handle.ptr == NULL) {
139                 LOGE("bo map failed %p", tmp_bo);
140                 tbm_bo_unref(tmp_bo);
141                 tmp_bo = NULL;
142                 return false;
143         }
144
145         /* set bo and bo_handle */
146         *bo = tmp_bo;
147         *bo_handle = tmp_bo_handle;
148
149         return true;
150 }
151
152 static void _recorder_release_imported_bo(tbm_bo *bo)
153 {
154         if (bo == NULL || *bo == NULL) {
155                 LOGW("NULL bo");
156                 return;
157         }
158
159         tbm_bo_unmap(*bo);
160         tbm_bo_unref(*bo);
161         *bo = NULL;
162
163         return;
164 }
165
166 static void _recorder_client_user_callback(recorder_cb_info_s *cb_info, char *recv_msg, muse_recorder_event_e event)
167 {
168         if (recv_msg == NULL || event >= MUSE_RECORDER_EVENT_TYPE_NUM) {
169                 LOGE("invalid parameter - recorder msg %p, event %d", recv_msg, event);
170                 return;
171         }
172
173         /*LOGD("get recorder msg %s, event %d", recv_msg, event);*/
174
175         g_mutex_lock(&cb_info->user_cb_mutex[event]);
176
177         if (cb_info->user_cb[event] == NULL) {
178                 if (event != MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM &&
179                         event != MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM) {
180                         g_mutex_unlock(&cb_info->user_cb_mutex[event]);
181                         LOGW("NULL callback for event %d, return here", event);
182                         return;
183                 } else {
184                         LOGW("NULL callback for event %d, NOT return here", event);
185                 }
186         }
187
188         switch (event) {
189         case MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE:
190                 {
191                         int previous = 0;
192                         int current = 0;
193                         int by_policy = 0;
194
195                         muse_recorder_msg_get(previous, recv_msg);
196                         muse_recorder_msg_get(current, recv_msg);
197                         muse_recorder_msg_get(by_policy, recv_msg);
198
199                         ((recorder_state_changed_cb)cb_info->user_cb[event])((recorder_state_e)previous,
200                                 (recorder_state_e)current,
201                                 (bool)by_policy,
202                                 cb_info->user_data[event]);
203                         break;
204                 }
205         case MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED:
206                 {
207                         int type = 0;
208
209                         muse_recorder_msg_get(type, recv_msg);
210
211                         ((recorder_recording_limit_reached_cb)cb_info->user_cb[event])((recorder_recording_limit_type_e)type,
212                                 cb_info->user_data[event]);
213                         break;
214                 }
215         case MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS:
216                 {
217                         int64_t cb_elapsed_time = 0;
218                         int64_t cb_file_size = 0;
219
220                         muse_recorder_msg_get(cb_elapsed_time, recv_msg);
221                         muse_recorder_msg_get(cb_file_size, recv_msg);
222
223                         ((recorder_recording_status_cb)cb_info->user_cb[event])((unsigned long long)cb_elapsed_time,
224                                 (unsigned long long)cb_file_size,
225                                 cb_info->user_data[event]);
226                         break;
227                 }
228         case MUSE_RECORDER_EVENT_TYPE_INTERRUPTED:
229                 {
230                         int policy = 0;
231                         int previous = 0;
232                         int current = 0;
233
234                         muse_recorder_msg_get(policy, recv_msg);
235                         muse_recorder_msg_get(previous, recv_msg);
236                         muse_recorder_msg_get(current, recv_msg);
237
238                         LOGW("INTERRUPTED - policy %d, state %d -> %d", policy, previous, current);
239
240                         ((recorder_interrupted_cb)cb_info->user_cb[event])((recorder_policy_e)policy,
241                                 (recorder_state_e)previous,
242                                 (recorder_state_e)current,
243                                 cb_info->user_data[event]);
244                         break;
245                 }
246         case MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED:
247                 {
248                         int policy = 0;
249                         int state = 0;
250
251                         muse_recorder_msg_get(policy, recv_msg);
252                         muse_recorder_msg_get(state, recv_msg);
253
254                         LOGW("INTERRUPT_STARTED - policy %d, state %d", policy, state);
255
256                         ((recorder_interrupt_started_cb)cb_info->user_cb[event])((recorder_policy_e)policy,
257                                 (recorder_state_e)state, cb_info->user_data[event]);
258                 }
259                 break;
260         case MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM:
261                 {
262                         int tbm_key = 0;
263                         int size = 0;
264                         int format = 0;
265                         int channel = 0;
266                         int timestamp = 0;
267                         tbm_bo bo = NULL;
268                         tbm_bo_handle bo_handle = {.ptr = NULL};
269                         char *send_msg = NULL;
270
271                         muse_recorder_msg_get(tbm_key, recv_msg);
272                         if (tbm_key == 0) {
273                                 LOGE("invalid key");
274                                 break;
275                         }
276
277                         if (cb_info->user_cb[event]) {
278                                 if (_recorder_import_tbm_key(cb_info->bufmgr, tbm_key, &bo, &bo_handle)) {
279                                         muse_recorder_msg_get(size, recv_msg);
280                                         muse_recorder_msg_get(format, recv_msg);
281                                         muse_recorder_msg_get(channel, recv_msg);
282                                         muse_recorder_msg_get(timestamp, recv_msg);
283
284                                         ((recorder_audio_stream_cb)cb_info->user_cb[event])((void *)bo_handle.ptr,
285                                                 size, (audio_sample_type_e)format, channel,
286                                                 (unsigned int)timestamp, cb_info->user_data[event]);
287
288                                         /* release imported bo */
289                                         _recorder_release_imported_bo(&bo);
290                                 } else {
291                                         LOGE("tbm key %d import failed", tbm_key);
292                                 }
293                         }
294
295                         /* return buffer */
296                         send_msg = muse_core_msg_new(MUSE_RECORDER_API_RETURN_BUFFER,
297                                 MUSE_TYPE_INT, "tbm_key", tbm_key, NULL);
298
299                         if (muse_core_msg_send(cb_info->fd, send_msg) <= 0)
300                                 LOGE("sending message failed");
301
302                         muse_core_msg_free(send_msg);
303                         break;
304                 }
305         case MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM:
306                 {
307                         int tbm_key = 0;
308                         int size = 0;
309                         int64_t offset = 0;
310
311                         tbm_bo bo = NULL;
312                         tbm_bo_handle bo_handle = {.ptr = NULL};
313                         char *send_msg = NULL;
314
315                         muse_recorder_msg_get(tbm_key, recv_msg);
316                         if (tbm_key == 0) {
317                                 LOGE("invalid key");
318                                 break;
319                         }
320
321                         if (cb_info->user_cb[event]) {
322                                 if (_recorder_import_tbm_key(cb_info->bufmgr, tbm_key, &bo, &bo_handle)) {
323                                         muse_recorder_msg_get(size, recv_msg);
324                                         muse_recorder_msg_get(offset, recv_msg);
325
326                                         ((recorder_muxed_stream_cb)cb_info->user_cb[event])((void *)bo_handle.ptr,
327                                                 size, (unsigned long long)offset, cb_info->user_data[event]);
328
329                                         /* release imported bo */
330                                         _recorder_release_imported_bo(&bo);
331                                 } else {
332                                         LOGE("tbm key %d import failed", tbm_key);
333                                 }
334                         }
335
336                         /* return buffer */
337                         send_msg = muse_core_msg_new(MUSE_RECORDER_API_RETURN_BUFFER,
338                                 MUSE_TYPE_INT, "tbm_key", tbm_key, NULL);
339                         if (send_msg) {
340                                 if (muse_core_msg_send(cb_info->fd, send_msg) <= 0)
341                                         LOGE("sending message failed");
342
343                                 muse_core_msg_free(send_msg);
344                                 send_msg = NULL;
345                         } else {
346                                 LOGE("failed to create send msg for key %d", tbm_key);
347                         }
348                         break;
349                 }
350         case MUSE_RECORDER_EVENT_TYPE_ERROR:
351                 {
352                         int error = 0;
353                         int current_state = 0;
354
355                         muse_recorder_msg_get(error, recv_msg);
356                         muse_recorder_msg_get(current_state, recv_msg);
357
358                         ((recorder_error_cb)cb_info->user_cb[event])((recorder_error_e)error,
359                                 (recorder_state_e)current_state,
360                                 cb_info->user_data[event]);
361                         break;
362                 }
363         case MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_AUDIO_ENCODER:
364                 {
365                         int codec = 0;
366
367                         muse_recorder_msg_get(codec, recv_msg);
368
369                         if (((recorder_supported_audio_encoder_cb)cb_info->user_cb[event])((recorder_audio_codec_e)codec, cb_info->user_data[event]) == false) {
370                                 cb_info->user_cb[event] = NULL;
371                                 cb_info->user_data[event] = NULL;
372                                 /*LOGD("stop foreach callback for SUPPORTED_AUDIO_ENCODER");*/
373                         }
374                         break;
375                 }
376         case MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_FILE_FORMAT:
377                 {
378                         int format = 0;
379
380                         muse_recorder_msg_get(format, recv_msg);
381
382                         if (((recorder_supported_file_format_cb)cb_info->user_cb[event])((recorder_file_format_e)format, cb_info->user_data[event]) == false) {
383                                 cb_info->user_cb[event] = NULL;
384                                 cb_info->user_data[event] = NULL;
385                                 /*LOGD("stop foreach callback for SUPPORTED_FILE_FORMAT");*/
386                         }
387                         break;
388                 }
389         case MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_ENCODER:
390                 {
391                         int codec = 0;
392
393                         muse_recorder_msg_get(codec, recv_msg);
394
395                         if (((recorder_supported_video_encoder_cb)cb_info->user_cb[event])((recorder_video_codec_e)codec, cb_info->user_data[event]) == false) {
396                                 cb_info->user_cb[event] = NULL;
397                                 cb_info->user_data[event] = NULL;
398                                 /*LOGD("stop foreach callback for SUPPORTED_VIDEO_ENCODER");*/
399                         }
400                         break;
401                 }
402         default: /* MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_RESOLUTION */
403                 {
404                         int width = 0;
405                         int height = 0;
406
407                         muse_recorder_msg_get(width, recv_msg);
408                         muse_recorder_msg_get(height, recv_msg);
409
410                         if (((recorder_supported_video_resolution_cb)cb_info->user_cb[event])(width, height, cb_info->user_data[event]) == false) {
411                                 cb_info->user_cb[event] = NULL;
412                                 cb_info->user_data[event] = NULL;
413                                 /*LOGD("stop foreach callback for SUPPORTED_VIDEO_RESOLUTION");*/
414                         }
415                         break;
416                 }
417         }
418
419         g_mutex_unlock(&cb_info->user_cb_mutex[event]);
420
421         return;
422 }
423
424
425 static gboolean _recorder_idle_event_callback(gpointer data)
426 {
427         recorder_cb_info_s *cb_info = NULL;
428         recorder_idle_event_s *rec_idle_event = (recorder_idle_event_s *)data;
429
430         if (rec_idle_event == NULL) {
431                 LOGE("rec_idle_event is NULL");
432                 return FALSE;
433         }
434
435         /* lock event */
436         g_mutex_lock(&g_rec_idle_event_lock);
437
438         cb_info = rec_idle_event->cb_info;
439         if (cb_info == NULL) {
440                 LOGW("recorder cb_info is NULL. event %p %d", rec_idle_event, rec_idle_event->event);
441                 g_mutex_unlock(&g_rec_idle_event_lock);
442                 goto IDLE_EVENT_CALLBACK_DONE;
443         }
444
445         /* remove event from list */
446         if (cb_info->idle_event_list)
447                 cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)rec_idle_event);
448
449         g_mutex_unlock(&g_rec_idle_event_lock);
450
451         /* user callback */
452         _recorder_client_user_callback(cb_info, rec_idle_event->recv_msg, rec_idle_event->event);
453
454 IDLE_EVENT_CALLBACK_DONE:
455         /* release event */
456         g_free(rec_idle_event);
457         rec_idle_event = NULL;
458
459         return FALSE;
460 }
461
462
463 static void _recorder_deactivate_idle_event_all(recorder_cb_info_s *cb_info)
464 {
465         recorder_idle_event_s *rec_idle_event = NULL;
466         GList *list = NULL;
467
468         if (cb_info == NULL) {
469                 LOGE("cb_info is NULL");
470                 return;
471         }
472
473         g_mutex_lock(&g_rec_idle_event_lock);
474
475         if (cb_info->idle_event_list == NULL) {
476                 LOGD("No event");
477         } else {
478                 list = cb_info->idle_event_list;
479
480                 while (list) {
481                         rec_idle_event = list->data;
482                         list = g_list_next(list);
483
484                         if (!rec_idle_event) {
485                                 LOGW("The event is NULL");
486                                 continue;
487                         }
488
489                         if (g_idle_remove_by_data(rec_idle_event)) {
490                                 LOGW("remove idle event %p done", rec_idle_event);
491
492                                 cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)rec_idle_event);
493
494                                 g_free(rec_idle_event);
495                                 rec_idle_event = NULL;
496
497                                 continue;
498                         }
499
500                         LOGW("set NULL cb_info for event %p %d, it will be freed on idle callback",
501                                 rec_idle_event, rec_idle_event->event);
502
503                         rec_idle_event->cb_info = NULL;
504
505                         cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)rec_idle_event);
506                 }
507
508                 g_list_free(cb_info->idle_event_list);
509                 cb_info->idle_event_list = NULL;
510         }
511
512         g_mutex_unlock(&g_rec_idle_event_lock);
513
514         return;
515 }
516
517
518 static void __recorder_add_msg_to_queue(recorder_cb_info_s *cb_info, int api, int event, int event_class, char *msg)
519 {
520         recorder_message_s *rec_msg = NULL;
521         recorder_msg_handler_info_s *msg_handler_info = NULL;
522
523         if (!cb_info || !msg) {
524                 LOGE("NULL pointer %p %p", cb_info, msg);
525                 return;
526         }
527
528         rec_msg = g_new0(recorder_message_s, 1);
529         if (!rec_msg) {
530                 LOGE("failed to alloc rec_msg for [%s]", msg);
531                 return;
532         }
533
534         rec_msg->api = api;
535         rec_msg->event = event;
536         rec_msg->event_class = event_class;
537
538         strncpy(rec_msg->recv_msg, msg, sizeof(rec_msg->recv_msg) - 1);
539
540         /*LOGD("add recorder message to queue : api %d, event %d, event_class %d", api, event, event_class);*/
541
542         if (event == MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM)
543                 msg_handler_info = &cb_info->audio_stream_cb_info;
544         else if (event == MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM)
545                 msg_handler_info = &cb_info->muxed_stream_cb_info;
546         else
547                 msg_handler_info = &cb_info->msg_handler_info;
548
549         g_mutex_lock(&msg_handler_info->mutex);
550         g_queue_push_tail(msg_handler_info->queue, (gpointer)rec_msg);
551         g_cond_signal(&msg_handler_info->cond);
552         g_mutex_unlock(&msg_handler_info->mutex);
553
554         rec_msg = NULL;
555
556         return;
557 }
558
559
560 static void __recorder_get_api_operation(int api, recorder_cb_info_s *cb_info, char *msg)
561 {
562         if (!cb_info || !msg) {
563                 LOGE("NULL pointer %p %p", cb_info, msg);
564                 return;
565         }
566
567         switch (api) {
568         case MUSE_RECORDER_API_GET_STATE:
569                 {
570                         int get_state = 0;
571                         muse_recorder_msg_get(get_state, msg);
572                         cb_info->get_int_value[_RECORDER_GET_INT_STATE] = get_state;
573                 }
574                 break;
575         case MUSE_RECORDER_API_GET_VIDEO_RESOLUTION:
576                 {
577                         int get_width = 0;
578                         int get_height = 0;
579                         muse_recorder_msg_get(get_width, msg);
580                         muse_recorder_msg_get(get_height, msg);
581                         cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_RESOLUTION] = get_width << 16;
582                         cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_RESOLUTION] |= get_height;
583                 }
584                 break;
585         case MUSE_RECORDER_API_GET_FILE_FORMAT:
586                 {
587                         int get_format = 0;
588                         muse_recorder_msg_get(get_format, msg);
589                         cb_info->get_int_value[_RECORDER_GET_INT_FILE_FORMAT] = get_format;
590                 }
591                 break;
592         case MUSE_RECORDER_API_GET_AUDIO_ENCODER:
593                 {
594                         int get_codec = 0;
595                         muse_recorder_msg_get(get_codec, msg);
596                         cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_ENCODER] = get_codec;
597                 }
598                 break;
599         case MUSE_RECORDER_API_GET_VIDEO_ENCODER:
600                 {
601                         int get_codec = 0;
602                         muse_recorder_msg_get(get_codec, msg);
603                         cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_ENCODER] = get_codec;
604                 }
605                 break;
606         case MUSE_RECORDER_API_ATTR_GET_SIZE_LIMIT:
607                 {
608                         int get_kbyte = 0;
609                         muse_recorder_msg_get(get_kbyte, msg);
610                         cb_info->get_int_value[_RECORDER_GET_INT_SIZE_LIMIT] = get_kbyte;
611                 }
612                 break;
613         case MUSE_RECORDER_API_ATTR_GET_TIME_LIMIT:
614                 {
615                         int get_second = 0;
616                         muse_recorder_msg_get(get_second, msg);
617                         cb_info->get_int_value[_RECORDER_GET_INT_TIME_LIMIT] = get_second;
618                 }
619                 break;
620         case MUSE_RECORDER_API_ATTR_GET_AUDIO_DEVICE:
621                 {
622                         int get_device = 0;
623                         muse_recorder_msg_get(get_device, msg);
624                         cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_DEVICE] = get_device;
625                 }
626                 break;
627         case MUSE_RECORDER_API_ATTR_GET_AUDIO_SAMPLERATE:
628                 {
629                         int get_samplerate = 0;
630                         muse_recorder_msg_get(get_samplerate, msg);
631                         cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_SAMPLERATE] = get_samplerate;
632                 }
633                 break;
634         case MUSE_RECORDER_API_ATTR_GET_AUDIO_ENCODER_BITRATE:
635                 {
636                         int get_bitrate = 0;
637                         muse_recorder_msg_get(get_bitrate, msg);
638                         cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_ENCODER_BITRATE] = get_bitrate;
639                 }
640                 break;
641         case MUSE_RECORDER_API_ATTR_GET_VIDEO_ENCODER_BITRATE:
642                 {
643                         int get_bitrate = 0;
644                         muse_recorder_msg_get(get_bitrate, msg);
645                         cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_ENCODER_BITRATE] = get_bitrate;
646                 }
647                 break;
648         case MUSE_RECORDER_API_ATTR_GET_RECORDING_MOTION_RATE:
649                 {
650                         double get_rate = 0;
651                         muse_recorder_msg_get_double(get_rate, msg);
652                         cb_info->get_double_value[_RECORDER_GET_DOUBLE_RECORDING_MOTION_RATE] = get_rate;
653                 }
654                 break;
655         case MUSE_RECORDER_API_ATTR_GET_AUDIO_CHANNEL:
656                 {
657                         int get_channel_count = 0;
658                         muse_recorder_msg_get(get_channel_count, msg);
659                         cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_CHANNEL] = get_channel_count;
660                 }
661                 break;
662         case MUSE_RECORDER_API_ATTR_GET_ORIENTATION_TAG:
663                 {
664                         int get_orientation = 0;
665                         muse_recorder_msg_get(get_orientation, msg);
666                         cb_info->get_int_value[_RECORDER_GET_INT_ORIENTATION_TAG] = get_orientation;
667                 }
668                 break;
669         case MUSE_RECORDER_API_GET_AUDIO_LEVEL:
670                 {
671                         double get_level = 0.0;
672                         muse_recorder_msg_get_double(get_level, msg);
673                         cb_info->get_double_value[_RECORDER_GET_DOUBLE_AUDIO_LEVEL] = get_level;
674                 }
675                 break;
676         case MUSE_RECORDER_API_GET_FILENAME:
677                 {
678                         char get_filename[MUSE_RECORDER_MSG_MAX_LENGTH] = {'\0',};
679                         muse_recorder_msg_get_string(get_filename, msg);
680                         if (cb_info->get_filename) {
681                                 free(cb_info->get_filename);
682                                 cb_info->get_filename = NULL;
683                         }
684                         cb_info->get_filename = strdup(get_filename);
685                 }
686                 break;
687         default:
688                 break;
689         }
690
691         return;
692 }
693
694
695 static void __recorder_process_msg(recorder_cb_info_s *cb_info, char *msg)
696 {
697         int ret = RECORDER_ERROR_NONE;
698         int api = -1;
699         int api_class = -1;
700         int event = -1;
701         int event_class = -1;
702
703         if (!cb_info || !msg) {
704                 LOGE("invalid ptr %p %p", cb_info, msg);
705                 return;
706         }
707
708         /*LOGD("msg [%s]", msg);*/
709
710         if (!muse_recorder_msg_get(api, msg)) {
711                 LOGE("failed to get recorder api");
712                 return;
713         }
714
715         if (api == MUSE_RECORDER_CB_EVENT) {
716                 if (!muse_recorder_msg_get(event, msg) ||
717                         !muse_recorder_msg_get(event_class, msg)) {
718                         LOGE("failed to get event or event_class [%s]", msg);
719                         return;
720                 }
721         } else {
722                 if (!muse_recorder_msg_get(api_class, msg)) {
723                         LOGE("failed to get api_class [%s]", msg);
724                         return;
725                 }
726         }
727
728         if (api_class == MUSE_RECORDER_API_CLASS_IMMEDIATE) {
729                 if (api >= MUSE_RECORDER_API_MAX) {
730                         LOGE("invalid api %d", api);
731                         return;
732                 }
733
734                 if (!muse_recorder_msg_get(ret, msg)) {
735                         LOGE("failed to get recorder ret");
736                         return;
737                 }
738
739                 g_mutex_lock(&cb_info->api_mutex[api]);
740
741                 if (api == MUSE_RECORDER_API_GET_DEVICE_STATE) {
742                         g_atomic_int_set(&cb_info->msg_recv_running, 0);
743                         LOGD("get device state done. close client cb handler");
744                 } else {
745                         switch (api) {
746                         case MUSE_RECORDER_API_CREATE:
747                                 if (ret != RECORDER_ERROR_NONE) {
748                                         g_atomic_int_set(&cb_info->msg_recv_running, 0);
749                                         LOGE("create error 0x%x. closing..", ret);
750                                 }
751                                 break;
752                         case MUSE_RECORDER_API_DESTROY:
753                                 if (ret == RECORDER_ERROR_NONE) {
754                                         g_atomic_int_set(&cb_info->msg_recv_running, 0);
755                                         LOGD("destroy done. closing..");
756                                 }
757                                 break;
758                         default:
759                                 __recorder_get_api_operation(api, cb_info, msg);
760                                 break;
761                         }
762                 }
763
764                 if (cb_info->api_waiting[api] > 0) {
765                         cb_info->api_ret[api] = ret;
766                         cb_info->api_activating[api] = 1;
767
768                         g_cond_signal(&cb_info->api_cond[api]);
769                 } else {
770                         LOGE("no waiting for api [%d]", api);
771                 }
772
773                 g_mutex_unlock(&cb_info->api_mutex[api]);
774         } else if (api_class == MUSE_RECORDER_API_CLASS_THREAD_SUB || api == MUSE_RECORDER_CB_EVENT) {
775                 __recorder_add_msg_to_queue(cb_info, api, event, event_class, msg);
776         } else {
777                 LOGW("unknown recorder api %d and api_class %d", api, api_class);
778         }
779
780         return;
781 }
782
783
784 static void *_recorder_msg_handler_func(gpointer data)
785 {
786         int api = 0;
787         int type = 0;
788         recorder_message_s *rec_msg = NULL;
789         recorder_idle_event_s *rec_idle_event = NULL;
790         recorder_msg_handler_info_s *handler_info = (recorder_msg_handler_info_s *)data;
791         recorder_cb_info_s *cb_info = NULL;
792
793         if (!handler_info || !handler_info->cb_info) {
794                 LOGE("NULL handler %p", handler_info);
795                 return NULL;
796         }
797
798         cb_info = (recorder_cb_info_s *)handler_info->cb_info;
799         type = handler_info->type;
800
801         LOGD("t:%d start", type);
802
803         g_mutex_lock(&handler_info->mutex);
804
805         while (g_atomic_int_get(&handler_info->running)) {
806                 if (g_queue_is_empty(handler_info->queue)) {
807                         /*LOGD("signal wait...");*/
808                         g_cond_wait(&handler_info->cond, &handler_info->mutex);
809                         /*LOGD("signal received");*/
810
811                         if (g_atomic_int_get(&handler_info->running) == 0) {
812                                 LOGD("stop event thread");
813                                 break;
814                         }
815                 }
816
817                 rec_msg = (recorder_message_s *)g_queue_pop_head(handler_info->queue);
818                 g_mutex_unlock(&handler_info->mutex);
819                 if (rec_msg == NULL) {
820                         LOGE("NULL message");
821                         g_mutex_lock(&handler_info->mutex);
822                         continue;
823                 }
824
825                 api = rec_msg->api;
826
827                 if (api < MUSE_RECORDER_API_MAX) {
828                         int ret = 0;
829
830                         g_mutex_lock(&cb_info->api_mutex[api]);
831
832                         if (muse_recorder_msg_get(ret, rec_msg->recv_msg)) {
833                                 if (cb_info->api_waiting[api] > 0) {
834                                         cb_info->api_ret[api] = ret;
835                                         cb_info->api_activating[api] = 1;
836
837                                         /*LOGD("recorder api %d - return 0x%x", ret);*/
838
839                                         g_cond_signal(&cb_info->api_cond[api]);
840                                 } else {
841                                         LOGE("no waiting for api [%d]", api);
842                                 }
843                         } else {
844                                 LOGE("t:%d failed to get ret for api %d, msg %s", type, api, rec_msg->recv_msg);
845                         }
846
847                         g_mutex_unlock(&cb_info->api_mutex[api]);
848                 } else if (api == MUSE_RECORDER_CB_EVENT) {
849                         switch (rec_msg->event_class) {
850                         case MUSE_RECORDER_EVENT_CLASS_THREAD_SUB:
851                                 _recorder_client_user_callback(cb_info, rec_msg->recv_msg, rec_msg->event);
852                                 break;
853                         case MUSE_RECORDER_EVENT_CLASS_THREAD_MAIN:
854                                 rec_idle_event = g_new0(recorder_idle_event_s, 1);
855                                 if (rec_idle_event == NULL) {
856                                         LOGE("event alloc failed");
857                                         break;
858                                 }
859
860                                 rec_idle_event->event = rec_msg->event;
861                                 rec_idle_event->cb_info = cb_info;
862
863                                 strncpy(rec_idle_event->recv_msg, rec_msg->recv_msg, sizeof(rec_idle_event->recv_msg) - 1);
864
865                                 /*LOGD("add recorder event[%d, %p] to IDLE", rec_msg->event, rec_idle_event);*/
866
867                                 g_mutex_lock(&g_rec_idle_event_lock);
868                                 cb_info->idle_event_list = g_list_append(cb_info->idle_event_list, (gpointer)rec_idle_event);
869                                 g_mutex_unlock(&g_rec_idle_event_lock);
870
871                                 g_idle_add_full(G_PRIORITY_DEFAULT,
872                                         (GSourceFunc)_recorder_idle_event_callback,
873                                         (gpointer)rec_idle_event,
874                                         NULL);
875                                 break;
876                         default:
877                                 LOGE("unknown event class %d", rec_msg->event_class);
878                                 break;
879                         }
880                 } else {
881                         LOGE("unknown api[%d] message", api);
882                 }
883
884                 g_free(rec_msg);
885                 rec_msg = NULL;
886
887                 g_mutex_lock(&handler_info->mutex);
888         }
889
890         /* remove remained event */
891         while (!g_queue_is_empty(handler_info->queue)) {
892                 rec_msg = (recorder_message_s *)g_queue_pop_head(handler_info->queue);
893                 if (rec_msg) {
894                         LOGD("remove message %p", rec_msg);
895                         free(rec_msg);
896                         rec_msg = NULL;
897                 } else {
898                         LOGW("NULL message");
899                 }
900         }
901
902         g_mutex_unlock(&handler_info->mutex);
903
904         LOGD("return");
905
906         return NULL;
907 }
908
909
910 static void *_recorder_msg_recv_func(gpointer data)
911 {
912         int recv_length = 0;
913         int single_length = 0;
914         int remained_length = 0;
915         char *recv_msg = NULL;
916         char *single_msg = NULL;
917         char *remained_msg = NULL;
918         int num_msg = 0;
919         int cur_pos = 0;
920         int prev_pos = 0;
921         recorder_cb_info_s *cb_info = (recorder_cb_info_s *)data;
922
923         if (cb_info == NULL) {
924                 LOGE("cb_info NULL");
925                 return NULL;
926         }
927
928         LOGD("start");
929
930         single_msg = (char *)malloc(sizeof(char) * MUSE_RECORDER_MSG_MAX_LENGTH);
931         if (single_msg == NULL) {
932                 LOGE("single_msg malloc failed");
933                 goto CB_HANDLER_EXIT;
934         }
935
936         recv_msg = cb_info->recv_msg;
937
938         while (g_atomic_int_get(&cb_info->msg_recv_running)) {
939                 recv_length = muse_core_msg_recv(cb_info->fd, recv_msg, MUSE_MSG_MAX_LENGTH);
940                 if (recv_length <= 0) {
941                         cb_info->is_server_connected = FALSE;
942                         LOGE("receive msg failed - server disconnected");
943                         break;
944                 }
945
946                 recv_msg[recv_length] = '\0';
947
948                 cur_pos = 0;
949                 prev_pos = 0;
950                 num_msg = 0;
951
952                 /*LOGD("recv msg : %s, length : %d", recv_msg, recv_length);*/
953
954                 /* Need to split the combined entering msgs */
955                 for (cur_pos = 0; cur_pos < recv_length; cur_pos++) {
956                         if (recv_msg[cur_pos] == '}') {
957                                 single_length = cur_pos - prev_pos + 1;
958
959                                 if (single_length < MUSE_RECORDER_MSG_MAX_LENGTH) {
960                                         /* check remained msg */
961                                         if (remained_length > 0) {
962                                                 if (remained_msg) {
963                                                         strncpy(single_msg, remained_msg, remained_length);
964                                                         strncpy(single_msg + remained_length, recv_msg + prev_pos, single_length);
965                                                         single_msg[remained_length + single_length] = '\0';
966
967                                                         free(remained_msg);
968                                                         remained_msg = NULL;
969                                                 } else {
970                                                         strncpy(single_msg, recv_msg + prev_pos, single_length);
971                                                         single_msg[single_length] = '\0';
972                                                         LOGE("lost msg [%s], skip...", single_msg);
973                                                 }
974
975                                                 remained_length = 0;
976                                         } else {
977                                                 strncpy(single_msg, recv_msg + prev_pos, single_length);
978                                                 single_msg[single_length] = '\0';
979                                         }
980
981                                         if (single_msg[0] == '{') {
982                                                 num_msg++;
983                                                 /*LOGD("splitted msg : [%s], Index : %d", single_msg, num_msg);*/
984                                                 __recorder_process_msg(cb_info, single_msg);
985                                         } else {
986                                                 LOGE("invalid msg [%s]", single_msg);
987                                         }
988                                 } else {
989                                         LOGE("too long message [len %d] skip...", single_length);
990                                 }
991
992                                 prev_pos = cur_pos + 1;
993                         }
994                 }
995
996                 /* check incompleted message */
997                 if (recv_msg[recv_length - 1] != '}') {
998                         remained_length = recv_length - prev_pos;
999
1000                         LOGW("incompleted message [len %d]", remained_length);
1001
1002                         if (remained_msg) {
1003                                 free(remained_msg);
1004                                 remained_msg = NULL;
1005                         }
1006
1007                         remained_msg = (char *)malloc(remained_length + 1);
1008                         if (remained_msg) {
1009                                 strncpy(remained_msg, recv_msg + prev_pos, remained_length);
1010                                 remained_msg[remained_length] = '\0';
1011                         } else {
1012                                 LOGE("failed to alloc for remained msg");
1013                         }
1014                 } else {
1015                         remained_length = 0;
1016                 }
1017         }
1018
1019         LOGD("client cb exit - server connected %d", cb_info->is_server_connected);
1020
1021         if (!cb_info->is_server_connected) {
1022                 /* send error msg for server disconnection */
1023                 char *error_msg = muse_core_msg_new(MUSE_RECORDER_CB_EVENT,
1024                         MUSE_TYPE_INT, "error", RECORDER_ERROR_SERVICE_DISCONNECTED,
1025                         MUSE_TYPE_INT, "current_state", RECORDER_STATE_NONE,
1026                         NULL);
1027
1028                 if (!error_msg) {
1029                         LOGE("error_msg failed");
1030                         goto CB_HANDLER_EXIT;
1031                 }
1032
1033                 LOGE("add error msg for service disconnection done");
1034
1035                 __recorder_add_msg_to_queue(cb_info,
1036                         MUSE_RECORDER_CB_EVENT,
1037                         MUSE_RECORDER_EVENT_TYPE_ERROR,
1038                         MUSE_RECORDER_EVENT_CLASS_THREAD_MAIN,
1039                         error_msg);
1040
1041                 muse_core_msg_free(error_msg);
1042                 error_msg = NULL;
1043
1044                 LOGE("add error msg for service disconnection done");
1045         }
1046
1047 CB_HANDLER_EXIT:
1048         if (single_msg) {
1049                 free(single_msg);
1050                 single_msg = NULL;
1051         }
1052
1053         if (remained_msg) {
1054                 free(remained_msg);
1055                 remained_msg = NULL;
1056         }
1057
1058         return NULL;
1059 }
1060
1061
1062 static bool __create_msg_handler_thread(recorder_msg_handler_info_s *handler_info,
1063         int type, const char *thread_name, recorder_cb_info_s *cb_info)
1064 {
1065         if (!handler_info || !thread_name || !cb_info) {
1066                 LOGE("t:%d NULL %p %p %p",
1067                         type, handler_info, thread_name, cb_info);
1068                 return false;
1069         }
1070
1071         LOGD("t:%d", type);
1072
1073         handler_info->type = type;
1074         handler_info->queue = g_queue_new();
1075         if (handler_info->queue == NULL) {
1076                 LOGE("t:%d queue failed", type);
1077                 return false;
1078         }
1079
1080         g_mutex_init(&handler_info->mutex);
1081         g_cond_init(&handler_info->cond);
1082
1083         handler_info->cb_info = (void *)cb_info;
1084         g_atomic_int_set(&handler_info->running, 1);
1085
1086         handler_info->thread = g_thread_try_new(thread_name,
1087                 _recorder_msg_handler_func, (gpointer)handler_info, NULL);
1088         if (handler_info->thread == NULL) {
1089                 LOGE("t:%d thread failed", type);
1090
1091                 g_mutex_clear(&handler_info->mutex);
1092                 g_cond_clear(&handler_info->cond);
1093                 g_queue_free(handler_info->queue);
1094                 handler_info->queue = NULL;
1095
1096                 return false;
1097         }
1098
1099         LOGD("t:%d done", type);
1100
1101         return true;
1102 }
1103
1104
1105 static void __destroy_msg_handler_thread(recorder_msg_handler_info_s *handler_info)
1106 {
1107         int type = 0;
1108
1109         if (!handler_info) {
1110                 LOGE("NULL handler");
1111                 return;
1112         }
1113
1114         if (!handler_info->thread) {
1115                 LOGW("thread is not created");
1116                 return;
1117         }
1118
1119         type = handler_info->type;
1120
1121         LOGD("t:%d thread %p", type, handler_info->thread);
1122
1123         g_mutex_lock(&handler_info->mutex);
1124         g_atomic_int_set(&handler_info->running, 0);
1125         g_cond_signal(&handler_info->cond);
1126         g_mutex_unlock(&handler_info->mutex);
1127
1128         g_thread_join(handler_info->thread);
1129         handler_info->thread = NULL;
1130
1131         g_mutex_clear(&handler_info->mutex);
1132         g_cond_clear(&handler_info->cond);
1133         g_queue_free(handler_info->queue);
1134         handler_info->queue = NULL;
1135
1136         LOGD("t:%d done", type);
1137
1138         return;
1139 }
1140
1141
1142 static recorder_cb_info_s *_recorder_client_callback_new(gint sockfd)
1143 {
1144         recorder_cb_info_s *cb_info = NULL;
1145         gint i = 0;
1146
1147         g_return_val_if_fail(sockfd > 0, NULL);
1148
1149         cb_info = g_new0(recorder_cb_info_s, 1);
1150         if (cb_info == NULL) {
1151                 LOGE("cb_info failed");
1152                 goto ErrorExit;
1153         }
1154
1155         cb_info->api_waiting[MUSE_RECORDER_API_CREATE] = 1;
1156
1157         for (i = 0 ; i < MUSE_RECORDER_API_MAX ; i++) {
1158                 g_mutex_init(&cb_info->api_mutex[i]);
1159                 g_cond_init(&cb_info->api_cond[i]);
1160         }
1161
1162         for (i = 0 ; i < MUSE_RECORDER_EVENT_TYPE_NUM ; i++)
1163                 g_mutex_init(&cb_info->user_cb_mutex[i]);
1164
1165         /* message handler thread */
1166         if (!__create_msg_handler_thread(&cb_info->msg_handler_info,
1167                 _RECORDER_MESSAGE_HANDLER_TYPE_GENERAL, "recorder_msg_handler", cb_info)) {
1168                 LOGE("msg_handler_info failed");
1169                 goto ErrorExit;
1170         }
1171
1172         /* message handler thread for audio stream callback */
1173         if (!__create_msg_handler_thread(&cb_info->audio_stream_cb_info,
1174                 _RECORDER_MESSAGE_HANDLER_TYPE_AUDIO_STREAM_CB, "recorder_msg_handler:audio_stream_cb", cb_info)) {
1175                 LOGE("audio_stream_cb_info failed");
1176                 goto ErrorExit;
1177         }
1178
1179         /* message handler thread for muxed stream callback */
1180         if (!__create_msg_handler_thread(&cb_info->muxed_stream_cb_info,
1181                 _RECORDER_MESSAGE_HANDLER_TYPE_MUXED_STREAM_CB, "recorder_msg_handler:muxed_stream_cb", cb_info)) {
1182                 LOGE("muxed_stream_cb_info failed");
1183                 goto ErrorExit;
1184         }
1185
1186         cb_info->fd = sockfd;
1187
1188         /* message receive thread */
1189         g_atomic_int_set(&cb_info->msg_recv_running, 1);
1190         cb_info->msg_recv_thread = g_thread_try_new("recorder_msg_recv",
1191                 _recorder_msg_recv_func, (gpointer)cb_info, NULL);
1192         if (cb_info->msg_recv_thread == NULL) {
1193                 LOGE("message receive thread creation failed");
1194                 goto ErrorExit;
1195         }
1196
1197         cb_info->is_server_connected = TRUE;
1198
1199         return cb_info;
1200
1201 ErrorExit:
1202         if (cb_info) {
1203                 __destroy_msg_handler_thread(&cb_info->msg_handler_info);
1204                 __destroy_msg_handler_thread(&cb_info->audio_stream_cb_info);
1205                 __destroy_msg_handler_thread(&cb_info->muxed_stream_cb_info);
1206
1207                 for (i = 0 ; i < MUSE_RECORDER_EVENT_TYPE_NUM ; i++)
1208                         g_mutex_clear(&cb_info->user_cb_mutex[i]);
1209
1210                 for (i = 0 ; i < MUSE_RECORDER_API_MAX ; i++) {
1211                         g_mutex_clear(&cb_info->api_mutex[i]);
1212                         g_cond_clear(&cb_info->api_cond[i]);
1213                 }
1214
1215                 g_free(cb_info);
1216                 cb_info = NULL;
1217         }
1218
1219         return NULL;
1220 }
1221
1222 static int _recorder_client_wait_for_cb_return(muse_recorder_api_e api, recorder_cb_info_s *cb_info, int time_out)
1223 {
1224         int ret = RECORDER_ERROR_NONE;
1225         gint64 end_time;
1226
1227         /*LOGD("Enter api : %d", api);*/
1228
1229         if (!cb_info->is_server_connected) {
1230                 LOGE("server is disconnected");
1231                 return RECORDER_ERROR_SERVICE_DISCONNECTED;
1232         }
1233
1234         g_mutex_lock(&(cb_info->api_mutex[api]));
1235
1236         if (cb_info->api_activating[api] == 0) {
1237                 if (time_out == RECORDER_CB_NO_TIMEOUT) {
1238                         LOGW("wait for api %d", api);
1239                         g_cond_wait(&(cb_info->api_cond[api]), &(cb_info->api_mutex[api]));
1240                         ret = cb_info->api_ret[api];
1241                         cb_info->api_activating[api] = 0;
1242                         LOGW("api %d returned 0x%x", api, ret);
1243                 } else {
1244                         end_time = g_get_monotonic_time() + time_out * G_TIME_SPAN_SECOND;
1245                         if (g_cond_wait_until(&(cb_info->api_cond[api]), &(cb_info->api_mutex[api]), end_time)) {
1246                                 ret = cb_info->api_ret[api];
1247                                 cb_info->api_activating[api] = 0;
1248                                 /*LOGD("return value : 0x%x", ret);*/
1249                         } else {
1250                                 ret = RECORDER_ERROR_INVALID_OPERATION;
1251                                 LOGE("api %d was TIMED OUT!", api);
1252                         }
1253                 }
1254         } else {
1255                 ret = cb_info->api_ret[api];
1256                 cb_info->api_activating[api] = 0;
1257
1258                 /*LOGD("condition is already checked for the api[%d], return[0x%x]", api, ret);*/
1259         }
1260
1261         if (ret != RECORDER_ERROR_NONE)
1262                 LOGE("ERROR : api %d - ret 0x%x", api, ret);
1263
1264         g_mutex_unlock(&(cb_info->api_mutex[api]));
1265
1266         return ret;
1267 }
1268
1269
1270 static int _recorder_msg_send(int api, recorder_cb_info_s *cb_info, int *ret, int timeout)
1271 {
1272         int send_ret = 0;
1273         char *msg = NULL;
1274
1275         if (!cb_info || !ret) {
1276                 LOGE("invalid pointer for api %d - %p %p", api, cb_info, ret);
1277                 return RECORDER_ERROR_INVALID_PARAMETER;
1278         }
1279
1280         msg = muse_core_msg_new(api, NULL);
1281         if (!msg) {
1282                 LOGE("msg creation failed: api %d", api);
1283                 return RECORDER_ERROR_OUT_OF_MEMORY;
1284         }
1285
1286         /*LOGD("send msg %s", msg);*/
1287
1288         if (cb_info->is_server_connected) {
1289                 __recorder_update_api_waiting(cb_info, api, 1);
1290                 send_ret = muse_core_msg_send(cb_info->fd, msg);
1291         }
1292
1293         if (send_ret < 0) {
1294                 LOGE("message send failed");
1295                 *ret = RECORDER_ERROR_INVALID_OPERATION;
1296         } else {
1297                 *ret = _recorder_client_wait_for_cb_return(api, cb_info, timeout);
1298         }
1299
1300         __recorder_update_api_waiting(cb_info, api, -1);
1301
1302         muse_core_msg_free(msg);
1303
1304         return RECORDER_ERROR_NONE;
1305 }
1306
1307
1308 static int _recorder_msg_send_param1(int api, recorder_cb_info_s *cb_info, int *ret, recorder_msg_param *param)
1309 {
1310         int send_ret = 0;
1311         char *msg = NULL;
1312
1313         if (!cb_info || !ret || !param) {
1314                 LOGE("invalid pointer for api %d - %p %p %p", api, cb_info, ret, param);
1315                 return RECORDER_ERROR_INVALID_PARAMETER;
1316         }
1317
1318         /*LOGD("type %d, name %s", param->type, param->name);*/
1319
1320         switch (param->type) {
1321         case MUSE_TYPE_INT:
1322                 msg = muse_core_msg_new(api, param->type, param->name, param->value.value_INT, NULL);
1323                 break;
1324         case MUSE_TYPE_DOUBLE:
1325                 msg = muse_core_msg_new(api, param->type, param->name, param->value.value_DOUBLE, NULL);
1326                 break;
1327         case MUSE_TYPE_STRING:
1328                 msg = muse_core_msg_new(api, param->type, param->name, param->value.value_STRING, NULL);
1329                 break;
1330         default:
1331                 LOGE("unknown type %d", param->type);
1332                 break;
1333         }
1334
1335         if (!msg) {
1336                 LOGE("msg creation failed: api %d, type %d, param name %s",
1337                         api, param->type, param->name);
1338                 return RECORDER_ERROR_OUT_OF_MEMORY;
1339         }
1340
1341         /*LOGD("send msg %s", msg);*/
1342
1343         if (cb_info->is_server_connected) {
1344                 __recorder_update_api_waiting(cb_info, api, 1);
1345
1346                 send_ret = muse_core_msg_send(cb_info->fd, msg);
1347         }
1348
1349         if (send_ret < 0) {
1350                 LOGE("message send failed");
1351                 *ret = RECORDER_ERROR_INVALID_OPERATION;
1352         } else {
1353                 *ret = _recorder_client_wait_for_cb_return(api, cb_info, RECORDER_CB_TIMEOUT);
1354         }
1355
1356         __recorder_update_api_waiting(cb_info, api, -1);
1357
1358         muse_core_msg_free(msg);
1359
1360         return RECORDER_ERROR_NONE;
1361 }
1362
1363
1364 static void _recorder_client_callback_destroy(recorder_cb_info_s *cb_info)
1365 {
1366         gint i = 0;
1367
1368         g_return_if_fail(cb_info != NULL);
1369
1370         LOGD("MSG receive thread[%p] destroy", cb_info->msg_recv_thread);
1371
1372         g_thread_join(cb_info->msg_recv_thread);
1373         cb_info->msg_recv_thread = NULL;
1374
1375         LOGD("msg_recv thread removed");
1376
1377         __destroy_msg_handler_thread(&cb_info->msg_handler_info);
1378         __destroy_msg_handler_thread(&cb_info->audio_stream_cb_info);
1379         __destroy_msg_handler_thread(&cb_info->muxed_stream_cb_info);
1380
1381         for (i = 0 ; i < MUSE_RECORDER_EVENT_TYPE_NUM ; i++)
1382                 g_mutex_clear(&cb_info->user_cb_mutex[i]);
1383
1384         for (i = 0 ; i < MUSE_RECORDER_API_MAX ; i++) {
1385                 g_mutex_clear(&cb_info->api_mutex[i]);
1386                 g_cond_clear(&cb_info->api_cond[i]);
1387         }
1388
1389         if (cb_info->fd > -1) {
1390                 muse_client_close(cb_info->fd);
1391                 cb_info->fd = -1;
1392         }
1393
1394         if (cb_info->bufmgr) {
1395                 tbm_bufmgr_deinit(cb_info->bufmgr);
1396                 cb_info->bufmgr = NULL;
1397         }
1398         if (cb_info->get_filename) {
1399                 free(cb_info->get_filename);
1400                 cb_info->get_filename = NULL;
1401         }
1402
1403         g_free(cb_info);
1404         cb_info = NULL;
1405
1406         return;
1407 }
1408
1409
1410 static int _recorder_storage_device_supported_cb(int storage_id, storage_type_e type, storage_state_e state, const char *path, void *user_data)
1411 {
1412         char **root_directory = (char **)user_data;
1413
1414         if (root_directory == NULL) {
1415                 LOGE("user data is NULL");
1416                 return false;
1417         }
1418
1419         LOGD("storage id %d, type %d, state %d, path %s",
1420                 storage_id, type, state, path ? path : "NULL");
1421
1422         if (type == STORAGE_TYPE_INTERNAL && path) {
1423                 if (*root_directory) {
1424                         free(*root_directory);
1425                         *root_directory = NULL;
1426                 }
1427
1428                 *root_directory = strdup(path);
1429                 if (*root_directory) {
1430                         LOGD("get root directory %s", *root_directory);
1431                         return false;
1432                 } else {
1433                         LOGE("strdup %s failed", path);
1434                 }
1435         }
1436
1437         return true;
1438 }
1439
1440 static int _recorder_client_get_root_directory(char **root_directory)
1441 {
1442         int ret = STORAGE_ERROR_NONE;
1443
1444         if (root_directory == NULL) {
1445                 LOGE("user data is NULL");
1446                 return false;
1447         }
1448
1449         ret = storage_foreach_device_supported((storage_device_supported_cb)_recorder_storage_device_supported_cb, root_directory);
1450         if (ret != STORAGE_ERROR_NONE) {
1451                 LOGE("storage_foreach_device_supported failed 0x%x", ret);
1452                 return false;
1453         }
1454
1455         return true;
1456 }
1457
1458 static int _recorder_create_common(recorder_h *recorder, muse_recorder_type_e type, camera_h camera)
1459 {
1460         int ret = RECORDER_ERROR_NONE;
1461         int destroy_ret = RECORDER_ERROR_NONE;
1462         int sock_fd = -1;
1463         int module_index = -1;
1464         int send_ret = 0;
1465         char *send_msg = NULL;
1466         char *root_directory = NULL;
1467         intptr_t camera_handle = 0;
1468         intptr_t handle = 0;
1469         tbm_bufmgr bufmgr = NULL;
1470         recorder_cli_s *pc = NULL;
1471         recorder_msg_param param;
1472
1473         LOGD("Enter - type %d", type);
1474
1475         if (recorder == NULL) {
1476                 LOGE("NULL pointer for recorder handle");
1477                 return RECORDER_ERROR_INVALID_PARAMETER;
1478         }
1479
1480         if (type == MUSE_RECORDER_TYPE_VIDEO && camera == NULL) {
1481                 LOGE("NULL pointer for camera handle on video recorder mode");
1482                 return RECORDER_ERROR_INVALID_PARAMETER;
1483         }
1484
1485         bufmgr = tbm_bufmgr_init(-1);
1486         if (bufmgr == NULL) {
1487                 LOGE("get tbm bufmgr failed");
1488                 return RECORDER_ERROR_INVALID_OPERATION;
1489         }
1490
1491         pc = g_new0(recorder_cli_s, 1);
1492         if (pc == NULL) {
1493                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
1494                 goto _ERR_RECORDER_EXIT;
1495         }
1496
1497         sock_fd = muse_client_new();
1498         if (sock_fd < 0) {
1499                 LOGE("muse_client_new failed - returned fd %d", sock_fd);
1500                 ret = RECORDER_ERROR_INVALID_OPERATION;
1501                 goto _ERR_RECORDER_EXIT;
1502         }
1503
1504         if (muse_client_get_module_index(MODULE_NAME, &module_index) != MM_ERROR_NONE) {
1505                 LOGE("muse client get module index failed");
1506                 ret = RECORDER_ERROR_INVALID_OPERATION;
1507                 goto _ERR_RECORDER_EXIT;
1508         }
1509
1510         if (type == MUSE_RECORDER_TYPE_AUDIO) {
1511                 send_msg = muse_core_msg_new(MUSE_RECORDER_API_CREATE,
1512                         MUSE_TYPE_INT, "module", module_index,
1513                         MUSE_TYPE_INT, PARAM_RECORDER_TYPE, MUSE_RECORDER_TYPE_AUDIO,
1514                         MUSE_TYPE_INT, "pid", getpid(),
1515                         NULL);
1516         } else {
1517                 pc->camera = camera;
1518                 camera_handle = (intptr_t)((camera_cli_s *)camera)->remote_handle;
1519                 send_msg = muse_core_msg_new(MUSE_RECORDER_API_CREATE,
1520                         MUSE_TYPE_INT, "module", module_index,
1521                         MUSE_TYPE_INT, PARAM_RECORDER_TYPE, MUSE_RECORDER_TYPE_VIDEO,
1522                         MUSE_TYPE_INT, "pid", getpid(),
1523                         MUSE_TYPE_POINTER, "camera_handle", camera_handle,
1524                         NULL);
1525         }
1526
1527         if (!send_msg) {
1528                 LOGE("NULL msg");
1529                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
1530                 goto _ERR_RECORDER_EXIT;
1531         }
1532
1533         LOGD("sock_fd : %d, msg : %s", sock_fd, send_msg);
1534
1535         send_ret = muse_core_msg_send(sock_fd, send_msg);
1536
1537         muse_core_msg_free(send_msg);
1538         send_msg = NULL;
1539
1540         if (send_ret < 0) {
1541                 LOGE("send msg failed %d", errno);
1542                 ret = RECORDER_ERROR_INVALID_OPERATION;
1543                 goto _ERR_RECORDER_EXIT;
1544         }
1545
1546         pc->cb_info = _recorder_client_callback_new(sock_fd);
1547         if (pc->cb_info == NULL) {
1548                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
1549                 goto _ERR_RECORDER_EXIT;
1550         }
1551
1552         sock_fd = -1;
1553
1554         ret = _recorder_client_wait_for_cb_return(MUSE_RECORDER_API_CREATE, pc->cb_info, RECORDER_CB_TIMEOUT);
1555
1556         pc->cb_info->api_waiting[MUSE_RECORDER_API_CREATE] = 0;
1557
1558         if (ret != RECORDER_ERROR_NONE) {
1559                 LOGE("API_CREATE failed 0x%x", ret);
1560                 goto _ERR_RECORDER_EXIT;
1561         }
1562
1563         muse_recorder_msg_get_pointer(handle, pc->cb_info->recv_msg);
1564         if (handle == 0) {
1565                 LOGE("Receiving Handle Failed!!");
1566                 ret = RECORDER_ERROR_INVALID_OPERATION;
1567                 goto _ERR_RECORDER_AFTER_CREATE;
1568         }
1569
1570         if (!_recorder_client_get_root_directory(&root_directory) || root_directory == NULL) {
1571                 LOGE("failed to get root directory of internal storage");
1572                 ret = RECORDER_ERROR_INVALID_OPERATION;
1573                 goto _ERR_RECORDER_AFTER_CREATE;
1574         }
1575
1576         LOGD("root directory [%s]", root_directory);
1577
1578         RECORDER_MSG_PARAM_SET(param, STRING, root_directory);
1579
1580         _recorder_msg_send_param1(MUSE_RECORDER_API_ATTR_SET_ROOT_DIRECTORY, pc->cb_info, &ret, &param);
1581
1582         if (ret != RECORDER_ERROR_NONE) {
1583                 LOGE("failed to set root directory %s", root_directory);
1584                 ret = RECORDER_ERROR_INVALID_OPERATION;
1585                 goto _ERR_RECORDER_AFTER_CREATE;
1586         }
1587
1588         free(root_directory);
1589         root_directory = NULL;
1590
1591         pc->remote_handle = handle;
1592         pc->cb_info->bufmgr = bufmgr;
1593
1594         LOGD("recorder[type %d] %p create success : remote handle 0x%td",
1595                 type, pc, pc->remote_handle);
1596
1597         *recorder = (recorder_h)pc;
1598
1599         LOGD("done");
1600
1601         return RECORDER_ERROR_NONE;
1602
1603 _ERR_RECORDER_AFTER_CREATE:
1604         _recorder_msg_send(MUSE_RECORDER_API_DESTROY, pc->cb_info, &destroy_ret, RECORDER_CB_TIMEOUT);
1605         LOGE("destroy return 0x%x", destroy_ret);
1606
1607 _ERR_RECORDER_EXIT:
1608         tbm_bufmgr_deinit(bufmgr);
1609         bufmgr = NULL;
1610
1611         if (root_directory) {
1612                 free(root_directory);
1613                 root_directory = NULL;
1614         }
1615
1616         if (sock_fd > -1) {
1617                 muse_client_close(sock_fd);
1618                 sock_fd = -1;
1619         }
1620
1621         if (pc) {
1622                 if (pc->cb_info) {
1623                         _recorder_client_callback_destroy(pc->cb_info);
1624                         pc->cb_info = NULL;
1625                 }
1626                 g_free(pc);
1627                 pc = NULL;
1628         }
1629
1630         return ret;
1631 }
1632
1633
1634 int recorder_create_videorecorder(camera_h camera, recorder_h *recorder)
1635 {
1636         return _recorder_create_common(recorder, MUSE_RECORDER_TYPE_VIDEO, camera);
1637 }
1638
1639
1640 int recorder_create_audiorecorder(recorder_h *recorder)
1641 {
1642         return _recorder_create_common(recorder, MUSE_RECORDER_TYPE_AUDIO, NULL);
1643 }
1644
1645
1646 int recorder_get_state(recorder_h recorder, recorder_state_e *state)
1647 {
1648         int ret = RECORDER_ERROR_NONE;
1649         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1650         muse_recorder_api_e api = MUSE_RECORDER_API_GET_STATE;
1651
1652         if (!pc || !pc->cb_info) {
1653                 LOGE("NULL handle");
1654                 return RECORDER_ERROR_INVALID_PARAMETER;
1655         }
1656
1657         if (state == NULL) {
1658                 LOGE("NULL pointer state");
1659                 return RECORDER_ERROR_INVALID_PARAMETER;
1660         }
1661
1662         LOGD("Enter, remote_handle : %td", pc->remote_handle);
1663
1664         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1665
1666         if (ret == RECORDER_ERROR_NONE)
1667                 *state = (recorder_state_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_STATE];
1668
1669         LOGD("ret : 0x%x, state : %d", ret, *state);
1670
1671         return ret;
1672 }
1673
1674
1675 int recorder_destroy(recorder_h recorder)
1676 {
1677         int ret = RECORDER_ERROR_NONE;
1678         muse_recorder_api_e api = MUSE_RECORDER_API_DESTROY;
1679         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1680
1681         if (!pc || !pc->cb_info) {
1682                 LOGE("NULL handle");
1683                 return RECORDER_ERROR_INVALID_PARAMETER;
1684         }
1685
1686         LOGD("ENTER");
1687
1688         if (pc->cb_info->is_server_connected)
1689                 _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1690         else
1691                 LOGW("server disconnected. release resource without send message.");
1692
1693         if (ret == RECORDER_ERROR_NONE) {
1694                 _recorder_deactivate_idle_event_all(pc->cb_info);
1695                 _recorder_client_callback_destroy(pc->cb_info);
1696                 g_free(pc);
1697                 pc = NULL;
1698         }
1699
1700         LOGD("ret : 0x%x", ret);
1701
1702         return ret;
1703 }
1704
1705
1706 int recorder_prepare(recorder_h recorder)
1707 {
1708         int ret = RECORDER_ERROR_NONE;
1709         muse_recorder_api_e api = MUSE_RECORDER_API_PREPARE;
1710         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1711
1712         if (!pc || !pc->cb_info) {
1713                 LOGE("NULL handle");
1714                 return RECORDER_ERROR_INVALID_PARAMETER;
1715         }
1716
1717         LOGD("ENTER");
1718
1719         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1720
1721         LOGD("ret : 0x%x", ret);
1722
1723         if (ret == RECORDER_ERROR_NONE && pc->camera)
1724                 camera_start_evas_rendering(pc->camera);
1725
1726         return ret;
1727 }
1728
1729
1730 int recorder_unprepare(recorder_h recorder)
1731 {
1732         int ret = RECORDER_ERROR_NONE;
1733         muse_recorder_api_e api = MUSE_RECORDER_API_UNPREPARE;
1734         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1735         camera_state_e camera_state = CAMERA_STATE_NONE;
1736
1737         if (!pc || !pc->cb_info) {
1738                 LOGE("NULL handle");
1739                 return RECORDER_ERROR_INVALID_PARAMETER;
1740         }
1741
1742         LOGD("ENTER");
1743
1744         if (pc->camera) {
1745                 ret = camera_get_state(pc->camera, &camera_state);
1746                 if (ret != CAMERA_ERROR_NONE) {
1747                         LOGE("failed to get camera state 0x%x", ret);
1748                         return RECORDER_ERROR_INVALID_OPERATION;
1749                 }
1750
1751                 if (camera_state == CAMERA_STATE_PREVIEW) {
1752                         ret = camera_stop_evas_rendering(pc->camera, false);
1753                         if (ret != CAMERA_ERROR_NONE) {
1754                                 LOGE("camera_stop_evas_rendering failed 0x%x", ret);
1755                                 return RECORDER_ERROR_INVALID_OPERATION;
1756                         }
1757                 }
1758         }
1759
1760         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1761
1762         LOGD("ret : 0x%x", ret);
1763
1764         return ret;
1765 }
1766
1767
1768 int recorder_start(recorder_h recorder)
1769 {
1770         int ret = RECORDER_ERROR_NONE;
1771         muse_recorder_api_e api = MUSE_RECORDER_API_START;
1772         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1773         recorder_state_e current_state = RECORDER_STATE_NONE;
1774
1775         if (!pc || !pc->cb_info) {
1776                 LOGE("NULL handle");
1777                 return RECORDER_ERROR_INVALID_PARAMETER;
1778         }
1779
1780         LOGD("ENTER");
1781
1782         if (pc->camera) {
1783                 ret = recorder_get_state(recorder, &current_state);
1784                 if (ret != RECORDER_ERROR_NONE) {
1785                         LOGE("failed to get current state 0x%x", ret);
1786                         return RECORDER_ERROR_INVALID_OPERATION;
1787                 }
1788
1789                 if (current_state == RECORDER_STATE_READY) {
1790                         ret = camera_stop_evas_rendering(pc->camera, true);
1791                         if (ret != CAMERA_ERROR_NONE) {
1792                                 LOGE("camera_stop_evas_rendering failed 0x%x", ret);
1793                                 return RECORDER_ERROR_INVALID_OPERATION;
1794                         }
1795                 }
1796         }
1797
1798         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_NO_TIMEOUT);
1799
1800         if (pc->camera && current_state == RECORDER_STATE_READY)
1801                 camera_start_evas_rendering(pc->camera);
1802
1803         LOGD("ret : 0x%x", ret);
1804
1805         return ret;
1806 }
1807
1808
1809 int recorder_pause(recorder_h recorder)
1810 {
1811         int ret = RECORDER_ERROR_NONE;
1812         muse_recorder_api_e api = MUSE_RECORDER_API_PAUSE;
1813         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1814
1815         if (!pc || !pc->cb_info) {
1816                 LOGE("NULL handle");
1817                 return RECORDER_ERROR_INVALID_PARAMETER;
1818         }
1819
1820         LOGD("ENTER");
1821
1822         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1823
1824         LOGD("ret : 0x%x", ret);
1825
1826         return ret;
1827 }
1828
1829
1830 int recorder_commit(recorder_h recorder)
1831 {
1832         int ret = RECORDER_ERROR_NONE;
1833         muse_recorder_api_e api = MUSE_RECORDER_API_COMMIT;
1834         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1835         recorder_state_e current_state = RECORDER_STATE_NONE;
1836
1837         if (!pc || !pc->cb_info) {
1838                 LOGE("NULL handle");
1839                 return RECORDER_ERROR_INVALID_PARAMETER;
1840         }
1841
1842         LOGD("ENTER");
1843
1844         if (pc->camera) {
1845                 ret = recorder_get_state(recorder, &current_state);
1846                 if (ret != RECORDER_ERROR_NONE) {
1847                         LOGE("failed to get current state 0x%x", ret);
1848                         return RECORDER_ERROR_INVALID_OPERATION;
1849                 }
1850
1851                 if (current_state >= RECORDER_STATE_RECORDING) {
1852                         ret = camera_stop_evas_rendering(pc->camera, true);
1853                         if (ret != CAMERA_ERROR_NONE) {
1854                                 LOGE("camera_stop_evas_rendering failed 0x%x", ret);
1855                                 return RECORDER_ERROR_INVALID_OPERATION;
1856                         }
1857                 }
1858         }
1859
1860         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1861
1862         if (pc->camera && current_state >= RECORDER_STATE_RECORDING)
1863                 camera_start_evas_rendering(pc->camera);
1864
1865         LOGD("ret : 0x%x", ret);
1866
1867         return ret;
1868 }
1869
1870
1871 int recorder_cancel(recorder_h recorder)
1872 {
1873         int ret = RECORDER_ERROR_NONE;
1874         muse_recorder_api_e api = MUSE_RECORDER_API_CANCEL;
1875         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1876         recorder_state_e current_state = RECORDER_STATE_NONE;
1877
1878         if (!pc || !pc->cb_info) {
1879                 LOGE("NULL handle");
1880                 return RECORDER_ERROR_INVALID_PARAMETER;
1881         }
1882
1883         LOGD("ENTER");
1884
1885         if (pc->camera) {
1886                 ret = recorder_get_state(recorder, &current_state);
1887                 if (ret != RECORDER_ERROR_NONE) {
1888                         LOGE("failed to get current state 0x%x", ret);
1889                         return RECORDER_ERROR_INVALID_OPERATION;
1890                 }
1891
1892                 if (current_state >= RECORDER_STATE_RECORDING) {
1893                         ret = camera_stop_evas_rendering(pc->camera, true);
1894                         if (ret != CAMERA_ERROR_NONE) {
1895                                 LOGE("camera_stop_evas_rendering failed 0x%x", ret);
1896                                 return RECORDER_ERROR_INVALID_OPERATION;
1897                         }
1898                 }
1899         }
1900
1901         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1902
1903         if (pc->camera && current_state >= RECORDER_STATE_RECORDING)
1904                 camera_start_evas_rendering(pc->camera);
1905
1906         LOGD("ret : 0x%x", ret);
1907
1908         return ret;
1909 }
1910
1911
1912 int recorder_set_video_resolution(recorder_h recorder, int width, int height)
1913 {
1914         int ret = RECORDER_ERROR_NONE;
1915         int send_ret = 0;
1916         char *send_msg = NULL;
1917         muse_recorder_api_e api = MUSE_RECORDER_API_SET_VIDEO_RESOLUTION;
1918         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1919
1920         if (!pc || !pc->cb_info) {
1921                 LOGE("NULL handle");
1922                 return RECORDER_ERROR_INVALID_PARAMETER;
1923         }
1924
1925         LOGD("ENTER");
1926
1927         send_msg = muse_core_msg_new(api,
1928                 MUSE_TYPE_INT, "width", width,
1929                 MUSE_TYPE_INT, "height", height,
1930                 NULL);
1931         if (send_msg) {
1932                 if (pc->cb_info->is_server_connected) {
1933                         __recorder_update_api_waiting(pc->cb_info, api, 1);
1934
1935                         send_ret = muse_core_msg_send(pc->cb_info->fd, send_msg);
1936                 }
1937
1938                 if (send_ret < 0) {
1939                         LOGE("message send failed");
1940                         ret = RECORDER_ERROR_INVALID_OPERATION;
1941                 } else {
1942                         ret = _recorder_client_wait_for_cb_return(api, pc->cb_info, RECORDER_CB_TIMEOUT);
1943                 }
1944
1945                 __recorder_update_api_waiting(pc->cb_info, api, -1);
1946
1947                 muse_core_msg_free(send_msg);
1948         } else {
1949                 LOGE("failed to create msg");
1950                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
1951         }
1952
1953         LOGD("ret : 0x%x", ret);
1954
1955         return ret;
1956 }
1957
1958
1959 int recorder_get_video_resolution(recorder_h recorder, int *width, int *height)
1960 {
1961         int ret = RECORDER_ERROR_NONE;
1962         muse_recorder_api_e api = MUSE_RECORDER_API_GET_VIDEO_RESOLUTION;
1963         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1964
1965         if (!pc || !pc->cb_info) {
1966                 LOGE("NULL handle");
1967                 return RECORDER_ERROR_INVALID_PARAMETER;
1968         }
1969
1970         if (!width || !height) {
1971                 LOGE("NULL pointer width = [%p], height = [%p]", width, height);
1972                 return RECORDER_ERROR_INVALID_PARAMETER;
1973         }
1974
1975         LOGD("ENTER");
1976
1977         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
1978
1979         if (ret == RECORDER_ERROR_NONE) {
1980                 *width = pc->cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_RESOLUTION] >> 16;
1981                 *height = (0x0000ffff & pc->cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_RESOLUTION]);
1982         }
1983
1984         LOGD("ret : 0x%x, %dx%d", ret, *width, *height);
1985
1986         return ret;
1987 }
1988
1989
1990 int recorder_foreach_supported_video_resolution(recorder_h recorder,
1991         recorder_supported_video_resolution_cb foreach_cb, void *user_data)
1992 {
1993         int ret = RECORDER_ERROR_NONE;
1994         recorder_cli_s *pc = (recorder_cli_s *)recorder;
1995         muse_recorder_api_e api = MUSE_RECORDER_API_FOREACH_SUPPORTED_VIDEO_RESOLUTION;
1996
1997         if (!pc || !pc->cb_info || foreach_cb == NULL) {
1998                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
1999                 return RECORDER_ERROR_INVALID_PARAMETER;
2000         }
2001
2002         LOGD("Enter, handle :%td", pc->remote_handle);
2003
2004         pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_RESOLUTION] = foreach_cb;
2005         pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_RESOLUTION] = user_data;
2006
2007         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2008
2009         LOGD("ret : 0x%x", ret);
2010
2011         return ret;
2012 }
2013
2014
2015 int recorder_get_audio_level(recorder_h recorder, double *level)
2016 {
2017         int ret = RECORDER_ERROR_NONE;
2018         muse_recorder_api_e api = MUSE_RECORDER_API_GET_AUDIO_LEVEL;
2019         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2020
2021         if (!pc || !pc->cb_info || level == NULL) {
2022                 LOGE("NULL pointer %p %p", pc, level);
2023                 return RECORDER_ERROR_INVALID_PARAMETER;
2024         }
2025
2026         LOGD("ENTER");
2027
2028         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2029
2030         if (ret == RECORDER_ERROR_NONE)
2031                 *level = pc->cb_info->get_double_value[_RECORDER_GET_DOUBLE_AUDIO_LEVEL];
2032
2033         LOGD("ret : 0x%x, level %lf", ret, *level);
2034
2035         return ret;
2036 }
2037
2038
2039 int recorder_set_filename(recorder_h recorder, const char *filename)
2040 {
2041         int ret = RECORDER_ERROR_NONE;
2042         size_t length = 0;
2043         muse_recorder_api_e api = MUSE_RECORDER_API_SET_FILENAME;
2044         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2045         recorder_msg_param param;
2046         char set_filename[RECORDER_FILENAME_MAX] = {'\0',};
2047
2048         if (!pc || !pc->cb_info) {
2049                 LOGE("NULL handle");
2050                 return RECORDER_ERROR_INVALID_PARAMETER;
2051         }
2052
2053         if (filename == NULL) {
2054                 LOGE("filename is NULL");
2055                 return RECORDER_ERROR_INVALID_PARAMETER;
2056         }
2057
2058         LOGD("ENTER [%s]", filename);
2059
2060         length = strlen(filename);
2061
2062         if (length >= RECORDER_FILENAME_MAX - 1) {
2063                 LOGE("too long file name [%zu]", length);
2064                 return RECORDER_ERROR_INVALID_PARAMETER;
2065         }
2066
2067         if (storage_get_origin_internal_path(filename, RECORDER_FILENAME_MAX, set_filename) < 0) {
2068                 /* Cannot convert. Use original path. */
2069                 strncpy(set_filename, filename, length + 1);
2070                 pc->cb_info->is_filename_converted = FALSE;
2071         } else {
2072                 /* Converted. Use converted path. */
2073                 LOGD("Converted filename : %s -> %s", filename, set_filename);
2074                 pc->cb_info->is_filename_converted = TRUE;
2075         }
2076
2077         RECORDER_MSG_PARAM_SET(param, STRING, set_filename);
2078
2079         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2080
2081         LOGD("ret : 0x%x", ret);
2082
2083         return ret;
2084 }
2085
2086
2087 int recorder_get_filename(recorder_h recorder,  char **filename)
2088 {
2089         int ret = RECORDER_ERROR_NONE;
2090         muse_recorder_api_e api = MUSE_RECORDER_API_GET_FILENAME;
2091         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2092         char compat_filename[RECORDER_FILENAME_MAX] = {0, };
2093
2094         if (!pc || !pc->cb_info) {
2095                 LOGE("NULL handle");
2096                 return RECORDER_ERROR_INVALID_PARAMETER;
2097         }
2098
2099         if (filename == NULL) {
2100                 LOGE("filename is NULL");
2101                 return RECORDER_ERROR_INVALID_PARAMETER;
2102         }
2103
2104         LOGD("ENTER");
2105
2106         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2107
2108         if (ret == RECORDER_ERROR_NONE) {
2109                 if (pc->cb_info->is_filename_converted == FALSE ||
2110                         storage_get_compat_internal_path(pc->cb_info->get_filename, RECORDER_FILENAME_MAX, compat_filename) < 0) {
2111                         /* Use original path. */
2112                         *filename = pc->cb_info->get_filename;
2113                 } else {
2114                         /* Converted. Use converted path. */
2115                         LOGD("Converted filename : %s -> %s", pc->cb_info->get_filename, compat_filename);
2116                         *filename = strdup(compat_filename);
2117                         free(pc->cb_info->get_filename);
2118                 }
2119
2120                 pc->cb_info->get_filename = NULL;
2121         }
2122
2123         LOGD("ret : 0x%x, filename : [%s]", ret, (*filename) ? *filename : "NULL");
2124
2125         return ret;
2126 }
2127
2128
2129 int recorder_set_file_format(recorder_h recorder, recorder_file_format_e format)
2130 {
2131         int ret = RECORDER_ERROR_NONE;
2132         int set_format = (int)format;
2133         muse_recorder_api_e api = MUSE_RECORDER_API_SET_FILE_FORMAT;
2134         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2135         recorder_msg_param param;
2136
2137         if (!pc || !pc->cb_info) {
2138                 LOGE("NULL handle");
2139                 return RECORDER_ERROR_INVALID_PARAMETER;
2140         }
2141
2142         LOGD("ENTER, set_format : %d", set_format);
2143
2144         RECORDER_MSG_PARAM_SET(param, INT, set_format);
2145
2146         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2147
2148         LOGD("ret : 0x%x", ret);
2149         return ret;
2150 }
2151
2152
2153 int recorder_get_file_format(recorder_h recorder, recorder_file_format_e *format)
2154 {
2155         int ret = RECORDER_ERROR_NONE;
2156         muse_recorder_api_e api = MUSE_RECORDER_API_GET_FILE_FORMAT;
2157         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2158
2159         if (!pc || !pc->cb_info) {
2160                 LOGE("NULL handle");
2161                 return RECORDER_ERROR_INVALID_PARAMETER;
2162         }
2163
2164         if (format == NULL) {
2165                 LOGE("NULL pointer data");
2166                 return RECORDER_ERROR_INVALID_PARAMETER;
2167         }
2168
2169         LOGD("ENTER");
2170
2171         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2172
2173         if (ret == RECORDER_ERROR_NONE)
2174                 *format = (recorder_file_format_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_FILE_FORMAT];
2175
2176         LOGD("ret : 0x%x, format %d", ret, *format);
2177
2178         return ret;
2179 }
2180
2181
2182 int recorder_set_sound_stream_info(recorder_h recorder, sound_stream_info_h stream_info)
2183 {
2184         int ret = RECORDER_ERROR_NONE;
2185         muse_recorder_api_e api = MUSE_RECORDER_API_SET_SOUND_STREAM_INFO;
2186         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2187         bool is_available = false;
2188         int stream_index = 0;
2189         char *stream_type = NULL;
2190         char *send_msg = NULL;
2191         int send_ret = 0;
2192
2193         if (!pc || !pc->cb_info || stream_info == NULL) {
2194                 LOGE("NULL handle");
2195                 return RECORDER_ERROR_INVALID_PARAMETER;
2196         }
2197
2198         LOGD("ENTER");
2199
2200         ret = sound_manager_is_available_stream_information(stream_info, NATIVE_API_RECORDER, &is_available);
2201         if (ret != SOUND_MANAGER_ERROR_NONE) {
2202                 LOGE("stream info verification failed");
2203                 return RECORDER_ERROR_INVALID_OPERATION;
2204         }
2205
2206         if (is_available == false) {
2207                 LOGE("stream information is not available");
2208                 return RECORDER_ERROR_INVALID_OPERATION;
2209         }
2210
2211         ret = sound_manager_get_type_from_stream_information(stream_info, &stream_type);
2212         ret |= sound_manager_get_index_from_stream_information(stream_info, &stream_index);
2213
2214         LOGD("sound manager return [0x%x]", ret);
2215
2216         if (ret == SOUND_MANAGER_ERROR_NONE) {
2217                 send_msg = muse_core_msg_new(api,
2218                         MUSE_TYPE_STRING, "stream_type", stream_type,
2219                         MUSE_TYPE_INT, "stream_index", stream_index,
2220                         NULL);
2221                 if (send_msg) {
2222                         if (pc->cb_info->is_server_connected) {
2223                                 __recorder_update_api_waiting(pc->cb_info, api, 1);
2224
2225                                 send_ret = muse_core_msg_send(pc->cb_info->fd, send_msg);
2226                         }
2227
2228                         if (send_ret < 0) {
2229                                 LOGE("message send failed");
2230                                 ret = RECORDER_ERROR_INVALID_OPERATION;
2231                         } else {
2232                                 ret = _recorder_client_wait_for_cb_return(api, pc->cb_info, RECORDER_CB_TIMEOUT);
2233                         }
2234
2235                         __recorder_update_api_waiting(pc->cb_info, api, -1);
2236
2237                         muse_core_msg_free(send_msg);
2238                 } else {
2239                         LOGE("failed to create msg");
2240                         ret = RECORDER_ERROR_OUT_OF_MEMORY;
2241                 }
2242         } else {
2243                 ret = RECORDER_ERROR_INVALID_OPERATION;
2244         }
2245
2246         return ret;
2247 }
2248
2249
2250 int recorder_set_state_changed_cb(recorder_h recorder, recorder_state_changed_cb callback, void *user_data)
2251 {
2252         int ret = RECORDER_ERROR_NONE;
2253         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2254         muse_recorder_api_e api = MUSE_RECORDER_API_SET_STATE_CHANGED_CB;
2255
2256         if (!pc || !pc->cb_info || callback == NULL) {
2257                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2258                 return RECORDER_ERROR_INVALID_PARAMETER;
2259         }
2260
2261         LOGD("Enter, handle :%td", pc->remote_handle);
2262
2263         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2264
2265         if (ret == RECORDER_ERROR_NONE) {
2266                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE]);
2267
2268                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE] = callback;
2269                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE] = user_data;
2270
2271                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE]);
2272         }
2273
2274         LOGD("ret : 0x%x", ret);
2275
2276         return ret;
2277 }
2278
2279
2280 int recorder_unset_state_changed_cb(recorder_h recorder)
2281 {
2282         int ret = RECORDER_ERROR_NONE;
2283         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_STATE_CHANGED_CB;
2284         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2285
2286         if (!pc || !pc->cb_info) {
2287                 LOGE("NULL handle");
2288                 return RECORDER_ERROR_INVALID_PARAMETER;
2289         }
2290
2291         LOGD("ENTER");
2292
2293         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2294
2295         if (ret == RECORDER_ERROR_NONE) {
2296                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE]);
2297
2298                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE] = NULL;
2299                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE] = NULL;
2300
2301                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_STATE_CHANGE]);
2302         }
2303
2304         LOGD("ret : 0x%x", ret);
2305
2306         return ret;
2307 }
2308
2309
2310 int recorder_set_interrupted_cb(recorder_h recorder, recorder_interrupted_cb callback, void *user_data)
2311 {
2312         int ret = RECORDER_ERROR_NONE;
2313         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2314         muse_recorder_api_e api = MUSE_RECORDER_API_SET_INTERRUPTED_CB;
2315
2316         if (!pc || !pc->cb_info || callback == NULL) {
2317                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2318                 return RECORDER_ERROR_INVALID_PARAMETER;
2319         }
2320
2321         LOGD("Enter, handle :%td", pc->remote_handle);
2322
2323         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2324
2325         if (ret == RECORDER_ERROR_NONE) {
2326                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED]);
2327
2328                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED] = callback;
2329                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED] = user_data;
2330
2331                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED]);
2332         }
2333
2334         LOGD("ret : 0x%x", ret);
2335
2336         return ret;
2337 }
2338
2339
2340 int recorder_unset_interrupted_cb(recorder_h recorder)
2341 {
2342         int ret = RECORDER_ERROR_NONE;
2343         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_INTERRUPTED_CB;
2344         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2345
2346         if (!pc || !pc->cb_info) {
2347                 LOGE("NULL handle");
2348                 return RECORDER_ERROR_INVALID_PARAMETER;
2349         }
2350
2351         LOGD("ENTER");
2352
2353         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2354
2355         if (ret == RECORDER_ERROR_NONE) {
2356                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED]);
2357
2358                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED] = NULL;
2359                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED] = NULL;
2360
2361                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPTED]);
2362         }
2363
2364         LOGD("ret : 0x%x", ret);
2365
2366         return ret;
2367 }
2368
2369
2370 int recorder_set_interrupt_started_cb(recorder_h recorder, recorder_interrupt_started_cb callback, void *user_data)
2371 {
2372         int ret = RECORDER_ERROR_NONE;
2373         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2374         muse_recorder_api_e api = MUSE_RECORDER_API_SET_INTERRUPT_STARTED_CB;
2375
2376         if (!pc || !pc->cb_info || callback == NULL) {
2377                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2378                 return RECORDER_ERROR_INVALID_PARAMETER;
2379         }
2380
2381         LOGD("Enter, handle :%td", pc->remote_handle);
2382
2383         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2384
2385         if (ret == RECORDER_ERROR_NONE) {
2386                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED]);
2387
2388                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED] = callback;
2389                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED] = user_data;
2390
2391                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED]);
2392         }
2393
2394         LOGD("ret : 0x%x", ret);
2395
2396         return ret;
2397 }
2398
2399
2400 int recorder_unset_interrupt_started_cb(recorder_h recorder)
2401 {
2402         int ret = RECORDER_ERROR_NONE;
2403         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_INTERRUPT_STARTED_CB;
2404         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2405
2406         if (!pc || !pc->cb_info) {
2407                 LOGE("NULL handle");
2408                 return RECORDER_ERROR_INVALID_PARAMETER;
2409         }
2410
2411         LOGD("ENTER");
2412
2413         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2414
2415         if (ret == RECORDER_ERROR_NONE) {
2416                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED]);
2417
2418                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED] = NULL;
2419                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED] = NULL;
2420
2421                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_INTERRUPT_STARTED]);
2422         }
2423
2424         LOGD("ret : 0x%x", ret);
2425
2426         return ret;
2427 }
2428
2429
2430 int recorder_set_audio_stream_cb(recorder_h recorder, recorder_audio_stream_cb callback, void *user_data)
2431 {
2432         int ret = RECORDER_ERROR_NONE;
2433         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2434         muse_recorder_api_e api = MUSE_RECORDER_API_SET_AUDIO_STREAM_CB;
2435
2436         if (!pc || !pc->cb_info || callback == NULL) {
2437                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2438                 return RECORDER_ERROR_INVALID_PARAMETER;
2439         }
2440
2441         LOGD("Enter, handle :%td", pc->remote_handle);
2442
2443         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2444
2445         if (ret == RECORDER_ERROR_NONE) {
2446                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM]);
2447
2448                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM] = callback;
2449                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM] = user_data;
2450
2451                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM]);
2452         }
2453
2454         LOGD("ret : 0x%x", ret);
2455
2456         return ret;
2457 }
2458
2459
2460 int recorder_unset_audio_stream_cb(recorder_h recorder)
2461 {
2462         int ret = RECORDER_ERROR_NONE;
2463         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_AUDIO_STREAM_CB;
2464         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2465
2466         if (!pc || !pc->cb_info) {
2467                 LOGE("NULL handle");
2468                 return RECORDER_ERROR_INVALID_PARAMETER;
2469         }
2470
2471         LOGD("ENTER");
2472
2473         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2474
2475         if (ret == RECORDER_ERROR_NONE) {
2476                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM]);
2477
2478                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM] = NULL;
2479                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM] = NULL;
2480
2481                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_AUDIO_STREAM]);
2482         }
2483
2484         LOGD("ret : 0x%x", ret);
2485
2486         return ret;
2487 }
2488
2489
2490 int recorder_set_muxed_stream_cb(recorder_h recorder, recorder_muxed_stream_cb callback, void *user_data)
2491 {
2492         int ret = RECORDER_ERROR_NONE;
2493         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2494         muse_recorder_api_e api = MUSE_RECORDER_API_SET_MUXED_STREAM_CB;
2495
2496         if (!pc || !pc->cb_info || !callback) {
2497                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2498                 return RECORDER_ERROR_INVALID_PARAMETER;
2499         }
2500
2501         LOGD("Enter, handle :%td", pc->remote_handle);
2502
2503         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2504
2505         if (ret == RECORDER_ERROR_NONE) {
2506                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM]);
2507
2508                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM] = callback;
2509                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM] = user_data;
2510
2511                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM]);
2512         }
2513
2514         LOGD("ret : 0x%x", ret);
2515
2516         return ret;
2517 }
2518
2519
2520 int recorder_unset_muxed_stream_cb(recorder_h recorder)
2521 {
2522         int ret = RECORDER_ERROR_NONE;
2523         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_MUXED_STREAM_CB;
2524         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2525
2526         if (!pc || !pc->cb_info) {
2527                 LOGE("NULL handle");
2528                 return RECORDER_ERROR_INVALID_PARAMETER;
2529         }
2530
2531         LOGD("ENTER");
2532
2533         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2534
2535         if (ret == RECORDER_ERROR_NONE) {
2536                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM]);
2537
2538                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM] = NULL;
2539                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM] = NULL;
2540
2541                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_MUXED_STREAM]);
2542         }
2543
2544         LOGD("ret : 0x%x", ret);
2545
2546         return ret;
2547 }
2548
2549
2550 int recorder_set_error_cb(recorder_h recorder, recorder_error_cb callback, void *user_data)
2551 {
2552         int ret = RECORDER_ERROR_NONE;
2553         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2554         muse_recorder_api_e api = MUSE_RECORDER_API_SET_ERROR_CB;
2555
2556         if (!pc || !pc->cb_info || callback == NULL) {
2557                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2558                 return RECORDER_ERROR_INVALID_PARAMETER;
2559         }
2560
2561         LOGD("Enter, handle :%td", pc->remote_handle);
2562
2563         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2564
2565         if (ret == RECORDER_ERROR_NONE) {
2566                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_ERROR]);
2567
2568                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_ERROR] = callback;
2569                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_ERROR] = user_data;
2570
2571                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_ERROR]);
2572         }
2573
2574         LOGD("ret : 0x%x", ret);
2575
2576         return ret;
2577 }
2578
2579
2580 int recorder_unset_error_cb(recorder_h recorder)
2581 {
2582         int ret = RECORDER_ERROR_NONE;
2583         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_ERROR_CB;
2584         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2585
2586         if (!pc || !pc->cb_info) {
2587                 LOGE("NULL handle");
2588                 return RECORDER_ERROR_INVALID_PARAMETER;
2589         }
2590
2591         LOGD("ENTER");
2592
2593         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2594
2595         if (ret == RECORDER_ERROR_NONE) {
2596                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_ERROR]);
2597
2598                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_ERROR] = NULL;
2599                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_ERROR] = NULL;
2600
2601                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_ERROR]);
2602         }
2603
2604         LOGD("ret : 0x%x", ret);
2605
2606         return ret;
2607 }
2608
2609
2610 int recorder_set_recording_status_cb(recorder_h recorder, recorder_recording_status_cb callback, void *user_data)
2611 {
2612         int ret = RECORDER_ERROR_NONE;
2613         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2614         muse_recorder_api_e api = MUSE_RECORDER_API_SET_RECORDING_STATUS_CB;
2615
2616         if (!pc || !pc->cb_info || callback == NULL) {
2617                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2618                 return RECORDER_ERROR_INVALID_PARAMETER;
2619         }
2620
2621         LOGD("Enter, handle :%td", pc->remote_handle);
2622
2623         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2624
2625         if (ret == RECORDER_ERROR_NONE) {
2626                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS]);
2627
2628                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS] = callback;
2629                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS] = user_data;
2630
2631                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS]);
2632         }
2633
2634         LOGD("ret : 0x%x", ret);
2635
2636         return ret;
2637 }
2638
2639
2640 int recorder_unset_recording_status_cb(recorder_h recorder)
2641 {
2642         int ret = RECORDER_ERROR_NONE;
2643         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_RECORDING_STATUS_CB;
2644         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2645
2646         if (!pc || !pc->cb_info) {
2647                 LOGE("NULL handle");
2648                 return RECORDER_ERROR_INVALID_PARAMETER;
2649         }
2650
2651         LOGD("ENTER");
2652
2653         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2654
2655         if (ret == RECORDER_ERROR_NONE) {
2656                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS]);
2657
2658                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS] = NULL;
2659                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS] = NULL;
2660
2661                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_STATUS]);
2662         }
2663
2664         LOGD("ret : 0x%x", ret);
2665
2666         return ret;
2667 }
2668
2669
2670 int recorder_set_recording_limit_reached_cb(recorder_h recorder, recorder_recording_limit_reached_cb callback, void *user_data)
2671 {
2672         int ret = RECORDER_ERROR_NONE;
2673         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2674         muse_recorder_api_e api = MUSE_RECORDER_API_SET_RECORDING_LIMIT_REACHED_CB;
2675
2676         if (!pc || !pc->cb_info || callback == NULL) {
2677                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2678                 return RECORDER_ERROR_INVALID_PARAMETER;
2679         }
2680
2681         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2682
2683         if (ret == RECORDER_ERROR_NONE) {
2684                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED]);
2685
2686                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED] = callback;
2687                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED] = user_data;
2688
2689                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED]);
2690         }
2691
2692         LOGD("ret : 0x%x", ret);
2693
2694         return ret;
2695 }
2696
2697
2698 int recorder_unset_recording_limit_reached_cb(recorder_h recorder)
2699 {
2700         int ret = RECORDER_ERROR_NONE;
2701         muse_recorder_api_e api = MUSE_RECORDER_API_UNSET_RECORDING_LIMIT_REACHED_CB;
2702         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2703
2704         if (!pc || !pc->cb_info) {
2705                 LOGE("NULL handle");
2706                 return RECORDER_ERROR_INVALID_PARAMETER;
2707         }
2708
2709         LOGD("ENTER");
2710
2711         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2712
2713         if (ret == RECORDER_ERROR_NONE) {
2714                 g_mutex_lock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED]);
2715
2716                 pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED] = NULL;
2717                 pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED] = NULL;
2718
2719                 g_mutex_unlock(&pc->cb_info->user_cb_mutex[MUSE_RECORDER_EVENT_TYPE_RECORDING_LIMITED]);
2720         }
2721
2722         LOGD("ret : 0x%x", ret);
2723
2724         return ret;
2725 }
2726
2727
2728 int recorder_foreach_supported_file_format(recorder_h recorder, recorder_supported_file_format_cb foreach_cb, void *user_data)
2729 {
2730         int ret = RECORDER_ERROR_NONE;
2731         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2732         muse_recorder_api_e api = MUSE_RECORDER_API_FOREACH_SUPPORTED_FILE_FORMAT;
2733
2734         if (!pc || !pc->cb_info || foreach_cb == NULL) {
2735                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
2736                 return RECORDER_ERROR_INVALID_PARAMETER;
2737         }
2738
2739         LOGD("Enter, handle :%td", pc->remote_handle);
2740
2741         pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_FILE_FORMAT] = foreach_cb;
2742         pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_FILE_FORMAT] = user_data;
2743
2744         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2745
2746         LOGD("ret : 0x%x", ret);
2747
2748         return ret;
2749 }
2750
2751
2752 int recorder_attr_set_size_limit(recorder_h recorder, int kbyte)
2753 {
2754         int ret = RECORDER_ERROR_NONE;
2755         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_SIZE_LIMIT;
2756         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2757         recorder_msg_param param;
2758
2759         if (!pc || !pc->cb_info) {
2760                 LOGE("NULL handle");
2761                 return RECORDER_ERROR_INVALID_PARAMETER;
2762         }
2763
2764         LOGD("ENTER");
2765
2766         RECORDER_MSG_PARAM_SET(param, INT, kbyte);
2767
2768         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2769
2770         LOGD("ret : 0x%x", ret);
2771
2772         return ret;
2773 }
2774
2775
2776 int recorder_attr_set_time_limit(recorder_h recorder, int second)
2777 {
2778         int ret = RECORDER_ERROR_NONE;
2779         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_TIME_LIMIT;
2780         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2781         recorder_msg_param param;
2782
2783         if (!pc || !pc->cb_info) {
2784                 LOGE("NULL handle");
2785                 return RECORDER_ERROR_INVALID_PARAMETER;
2786         }
2787
2788         LOGD("ENTER");
2789
2790         RECORDER_MSG_PARAM_SET(param, INT, second);
2791
2792         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2793
2794         LOGD("ret : 0x%x", ret);
2795
2796         return ret;
2797 }
2798
2799
2800 int recorder_attr_set_audio_device(recorder_h recorder, recorder_audio_device_e device)
2801 {
2802         int ret = RECORDER_ERROR_NONE;
2803         int set_device = (int)device;
2804         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_AUDIO_DEVICE;
2805         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2806         recorder_msg_param param;
2807
2808         if (!pc || !pc->cb_info) {
2809                 LOGE("NULL handle");
2810                 return RECORDER_ERROR_INVALID_PARAMETER;
2811         };
2812
2813         LOGD("ENTER");
2814
2815         RECORDER_MSG_PARAM_SET(param, INT, set_device);
2816
2817         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2818
2819         LOGD("ret : 0x%x", ret);
2820
2821         return ret;
2822 }
2823
2824
2825 int recorder_set_audio_encoder(recorder_h recorder, recorder_audio_codec_e codec)
2826 {
2827         int ret = RECORDER_ERROR_NONE;
2828         int set_codec = (int)codec;
2829         muse_recorder_api_e api = MUSE_RECORDER_API_SET_AUDIO_ENCODER;
2830         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2831         recorder_msg_param param;
2832
2833         if (!pc || !pc->cb_info) {
2834                 LOGE("NULL handle");
2835                 return RECORDER_ERROR_INVALID_PARAMETER;
2836         }
2837
2838         LOGD("ENTER");
2839
2840         RECORDER_MSG_PARAM_SET(param, INT, set_codec);
2841
2842         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2843
2844         LOGD("ret : 0x%x", ret);
2845
2846         return ret;
2847 }
2848
2849
2850 int recorder_get_audio_encoder(recorder_h recorder, recorder_audio_codec_e *codec)
2851 {
2852         int ret = RECORDER_ERROR_NONE;
2853         muse_recorder_api_e api = MUSE_RECORDER_API_GET_AUDIO_ENCODER;
2854         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2855
2856         if (!pc || !pc->cb_info) {
2857                 LOGE("NULL handle");
2858                 return RECORDER_ERROR_INVALID_PARAMETER;
2859         }
2860
2861         if (codec == NULL) {
2862                 LOGE("codec is NULL");
2863                 return RECORDER_ERROR_INVALID_PARAMETER;
2864         }
2865
2866         LOGD("ENTER");
2867
2868         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2869
2870         if (ret == RECORDER_ERROR_NONE)
2871                 *codec = (recorder_audio_codec_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_ENCODER];
2872
2873         LOGD("ret : 0x%x, codec %d", ret, *codec);
2874
2875         return ret;
2876 }
2877
2878
2879 int recorder_set_video_encoder(recorder_h recorder, recorder_video_codec_e codec)
2880 {
2881         int ret = RECORDER_ERROR_NONE;
2882         int set_codec = (int)codec;
2883         muse_recorder_api_e api = MUSE_RECORDER_API_SET_VIDEO_ENCODER;
2884         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2885         recorder_msg_param param;
2886
2887         if (!pc || !pc->cb_info) {
2888                 LOGE("NULL handle");
2889                 return RECORDER_ERROR_INVALID_PARAMETER;
2890         }
2891
2892         LOGD("ENTER");
2893
2894         RECORDER_MSG_PARAM_SET(param, INT, set_codec);
2895
2896         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2897
2898         LOGD("ret : 0x%x", ret);
2899
2900         return ret;
2901 }
2902
2903
2904 int recorder_get_video_encoder(recorder_h recorder, recorder_video_codec_e *codec)
2905 {
2906         int ret = RECORDER_ERROR_NONE;
2907         muse_recorder_api_e api = MUSE_RECORDER_API_GET_VIDEO_ENCODER;
2908         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2909
2910         if (!pc || !pc->cb_info) {
2911                 LOGE("NULL handle");
2912                 return RECORDER_ERROR_INVALID_PARAMETER;
2913         }
2914
2915         if (codec == NULL) {
2916                 LOGE("codec is NULL");
2917                 return RECORDER_ERROR_INVALID_PARAMETER;
2918         }
2919
2920         LOGD("ENTER");
2921
2922         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
2923
2924         if (ret == RECORDER_ERROR_NONE)
2925                 *codec = (recorder_video_codec_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_ENCODER];
2926
2927         LOGD("ret : 0x%x, codec %d", ret, *codec);
2928
2929         return ret;
2930 }
2931
2932
2933 int recorder_attr_set_audio_samplerate(recorder_h recorder, int samplerate)
2934 {
2935         int ret = RECORDER_ERROR_NONE;
2936         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_AUDIO_SAMPLERATE;
2937         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2938         recorder_msg_param param;
2939
2940         if (!pc || !pc->cb_info) {
2941                 LOGE("NULL handle");
2942                 return RECORDER_ERROR_INVALID_PARAMETER;
2943         }
2944
2945         LOGD("ENTER, samplerate : %d", samplerate);
2946
2947         RECORDER_MSG_PARAM_SET(param, INT, samplerate);
2948
2949         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2950
2951         LOGD("ret : 0x%x", ret);
2952
2953         return ret;
2954 }
2955
2956
2957 int recorder_attr_set_audio_encoder_bitrate(recorder_h recorder, int bitrate)
2958 {
2959         int ret = RECORDER_ERROR_NONE;
2960         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_AUDIO_ENCODER_BITRATE;
2961         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2962         recorder_msg_param param;
2963
2964         if (!pc || !pc->cb_info) {
2965                 LOGE("NULL handle");
2966                 return RECORDER_ERROR_INVALID_PARAMETER;
2967         }
2968
2969         LOGD("ENTER");
2970
2971         RECORDER_MSG_PARAM_SET(param, INT, bitrate);
2972
2973         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2974
2975         LOGD("ret : 0x%x", ret);
2976
2977         return ret;
2978 }
2979
2980
2981 int recorder_attr_set_video_encoder_bitrate(recorder_h recorder, int bitrate)
2982 {
2983         int ret = RECORDER_ERROR_NONE;
2984         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_VIDEO_ENCODER_BITRATE;
2985         recorder_cli_s *pc = (recorder_cli_s *)recorder;
2986         recorder_msg_param param;
2987
2988         if (!pc || !pc->cb_info) {
2989                 LOGE("NULL handle");
2990                 return RECORDER_ERROR_INVALID_PARAMETER;
2991         }
2992
2993         LOGD("ENTER");
2994
2995         RECORDER_MSG_PARAM_SET(param, INT, bitrate);
2996
2997         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
2998
2999         LOGD("ret : 0x%x", ret);
3000
3001         return ret;
3002 }
3003
3004
3005 int recorder_attr_get_size_limit(recorder_h recorder, int *kbyte)
3006 {
3007         int ret = RECORDER_ERROR_NONE;
3008         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_SIZE_LIMIT;
3009         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3010
3011         if (!pc || !pc->cb_info) {
3012                 LOGE("NULL handle");
3013                 return RECORDER_ERROR_INVALID_PARAMETER;
3014         }
3015
3016         if (kbyte == NULL) {
3017                 LOGE("NULL pointer kbyte");
3018                 return RECORDER_ERROR_INVALID_PARAMETER;
3019         }
3020
3021         LOGD("ENTER");
3022
3023         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3024
3025         if (ret == RECORDER_ERROR_NONE)
3026                 *kbyte = pc->cb_info->get_int_value[_RECORDER_GET_INT_SIZE_LIMIT];
3027
3028         LOGD("ret : 0x%x, %d kbyte", ret, *kbyte);
3029
3030         return ret;
3031 }
3032
3033
3034 int recorder_attr_get_time_limit(recorder_h recorder, int *second)
3035 {
3036         int ret = RECORDER_ERROR_NONE;
3037         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_TIME_LIMIT;
3038         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3039
3040         if (!pc || !pc->cb_info) {
3041                 LOGE("NULL handle");
3042                 return RECORDER_ERROR_INVALID_PARAMETER;
3043         }
3044
3045         if (second == NULL) {
3046                 LOGE("NULL pointer second");
3047                 return RECORDER_ERROR_INVALID_PARAMETER;
3048         }
3049
3050         LOGD("ENTER");
3051
3052         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3053
3054         if (ret == RECORDER_ERROR_NONE)
3055                 *second = pc->cb_info->get_int_value[_RECORDER_GET_INT_TIME_LIMIT];
3056
3057         LOGD("ret : 0x%x, %d second", ret, *second);
3058
3059         return ret;
3060 }
3061
3062
3063 int recorder_attr_get_audio_device(recorder_h recorder, recorder_audio_device_e *device)
3064 {
3065         int ret = RECORDER_ERROR_NONE;
3066         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_AUDIO_DEVICE;
3067         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3068
3069         if (!pc || !pc->cb_info) {
3070                 LOGE("NULL handle");
3071                 return RECORDER_ERROR_INVALID_PARAMETER;
3072         }
3073
3074         if (device == NULL) {
3075                 LOGE("NULL pointer device");
3076                 return RECORDER_ERROR_INVALID_PARAMETER;
3077         }
3078
3079         LOGD("ENTER");
3080
3081         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3082
3083         if (ret == RECORDER_ERROR_NONE)
3084                 *device = (recorder_audio_device_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_DEVICE];
3085
3086         LOGD("ret : 0x%x, device %d", ret, *device);
3087
3088         return ret;
3089 }
3090
3091
3092 int recorder_attr_get_audio_samplerate(recorder_h recorder, int *samplerate)
3093 {
3094         int ret = RECORDER_ERROR_NONE;
3095         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_AUDIO_SAMPLERATE;
3096         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3097
3098         if (!pc || !pc->cb_info) {
3099                 LOGE("NULL handle");
3100                 return RECORDER_ERROR_INVALID_PARAMETER;
3101         }
3102
3103         if (samplerate == NULL) {
3104                 LOGE("NULL pointer handle");
3105                 return RECORDER_ERROR_INVALID_PARAMETER;
3106         }
3107
3108         LOGD("ENTER");
3109
3110         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3111
3112         if (ret == RECORDER_ERROR_NONE)
3113                 *samplerate = pc->cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_SAMPLERATE];
3114
3115         LOGD("ret : 0x%x, samplerate %d", ret, *samplerate);
3116
3117         return ret;
3118 }
3119
3120
3121 int recorder_attr_get_audio_encoder_bitrate(recorder_h recorder, int *bitrate)
3122 {
3123         int ret = RECORDER_ERROR_NONE;
3124         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_AUDIO_ENCODER_BITRATE;
3125         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3126
3127         if (!pc || !pc->cb_info) {
3128                 LOGE("NULL handle");
3129                 return RECORDER_ERROR_INVALID_PARAMETER;
3130         }
3131
3132         if (bitrate == NULL) {
3133                 LOGE("NULL pointer");
3134                 return RECORDER_ERROR_INVALID_PARAMETER;
3135         }
3136
3137         LOGD("ENTER");
3138
3139         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3140
3141         if (ret == RECORDER_ERROR_NONE)
3142                 *bitrate = pc->cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_ENCODER_BITRATE];
3143
3144         LOGD("ret : 0x%x, bitrate %d", ret, *bitrate);
3145
3146         return ret;
3147 }
3148
3149
3150 int recorder_attr_get_video_encoder_bitrate(recorder_h recorder, int *bitrate)
3151 {
3152         int ret = RECORDER_ERROR_NONE;
3153         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_VIDEO_ENCODER_BITRATE;
3154         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3155
3156         if (!pc || !pc->cb_info) {
3157                 LOGE("NULL handle");
3158                 return RECORDER_ERROR_INVALID_PARAMETER;
3159         }
3160
3161         if (bitrate == NULL) {
3162                 LOGE("NULL pointer");
3163                 return RECORDER_ERROR_INVALID_PARAMETER;
3164         }
3165
3166         LOGD("ENTER");
3167
3168         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3169
3170         if (ret == RECORDER_ERROR_NONE)
3171                 *bitrate = pc->cb_info->get_int_value[_RECORDER_GET_INT_VIDEO_ENCODER_BITRATE];
3172
3173         LOGD("ret : 0x%x", ret);
3174
3175         return ret;
3176 }
3177
3178
3179 int recorder_foreach_supported_audio_encoder(recorder_h recorder, recorder_supported_audio_encoder_cb foreach_cb, void *user_data)
3180 {
3181         int ret = RECORDER_ERROR_NONE;
3182         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3183         muse_recorder_api_e api = MUSE_RECORDER_API_FOREACH_SUPPORTED_AUDIO_ENCODER;
3184
3185         if (!pc || !pc->cb_info || foreach_cb == NULL) {
3186                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
3187                 return RECORDER_ERROR_INVALID_PARAMETER;
3188         }
3189
3190         LOGD("Enter, handle :%td", pc->remote_handle);
3191
3192         pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_AUDIO_ENCODER] = foreach_cb;
3193         pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_AUDIO_ENCODER] = user_data;
3194
3195         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3196
3197         LOGD("ret : 0x%x", ret);
3198
3199         return ret;
3200 }
3201
3202
3203 int recorder_foreach_supported_video_encoder(recorder_h recorder, recorder_supported_video_encoder_cb foreach_cb, void *user_data)
3204 {
3205         int ret = RECORDER_ERROR_NONE;
3206         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3207         muse_recorder_api_e api = MUSE_RECORDER_API_FOREACH_SUPPORTED_VIDEO_ENCODER;
3208
3209         if (!pc || !pc->cb_info || foreach_cb == NULL) {
3210                 LOGE("INVALID_PARAMETER(0x%08x)", RECORDER_ERROR_INVALID_PARAMETER);
3211                 return RECORDER_ERROR_INVALID_PARAMETER;
3212         }
3213
3214         LOGD("Enter, handle :%td", pc->remote_handle);
3215
3216         pc->cb_info->user_cb[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_ENCODER] = foreach_cb;
3217         pc->cb_info->user_data[MUSE_RECORDER_EVENT_TYPE_FOREACH_SUPPORTED_VIDEO_ENCODER] = user_data;
3218
3219         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3220
3221         LOGD("ret : 0x%x", ret);
3222
3223         return ret;
3224 }
3225
3226
3227 int recorder_attr_set_mute(recorder_h recorder, bool enable)
3228 {
3229         int ret = RECORDER_ERROR_NONE;
3230         int set_enable = (int)enable;
3231         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_MUTE;
3232         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3233         recorder_msg_param param;
3234
3235         if (!pc || !pc->cb_info) {
3236                 LOGE("NULL handle");
3237                 return RECORDER_ERROR_INVALID_PARAMETER;
3238         }
3239
3240         LOGD("ENTER");
3241
3242         RECORDER_MSG_PARAM_SET(param, INT, set_enable);
3243
3244         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
3245
3246         LOGD("ret : 0x%x", ret);
3247
3248         return ret;
3249 }
3250
3251
3252 bool recorder_attr_is_muted(recorder_h recorder)
3253 {
3254         int ret = false;
3255         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_IS_MUTED;
3256         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3257
3258         if (!pc || !pc->cb_info) {
3259                 LOGE("NULL handle");
3260                 return false;
3261         }
3262
3263         LOGD("ENTER");
3264
3265         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3266
3267         if (ret == RECORDER_ERROR_SERVICE_DISCONNECTED)
3268                 ret = false;
3269
3270         LOGD("ret : %d", ret);
3271
3272         return (bool)ret;
3273 }
3274
3275
3276 int recorder_attr_set_recording_motion_rate(recorder_h recorder, double rate)
3277 {
3278         int ret = RECORDER_ERROR_NONE;
3279         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_RECORDING_MOTION_RATE;
3280         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3281         recorder_msg_param param;
3282
3283         if (!pc || !pc->cb_info) {
3284                 LOGE("NULL handle");
3285                 return RECORDER_ERROR_INVALID_PARAMETER;
3286         }
3287
3288         LOGD("ENTER - %.20lf", rate);
3289
3290         RECORDER_MSG_PARAM_SET(param, DOUBLE, rate);
3291
3292         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
3293
3294         LOGD("ret : 0x%x", ret);
3295
3296         return ret;
3297 }
3298
3299
3300 int recorder_attr_get_recording_motion_rate(recorder_h recorder, double *rate)
3301 {
3302         int ret = RECORDER_ERROR_NONE;
3303         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_RECORDING_MOTION_RATE;
3304         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3305
3306         if (!pc || !pc->cb_info) {
3307                 LOGE("NULL handle");
3308                 return RECORDER_ERROR_INVALID_PARAMETER;
3309         }
3310
3311         if (rate == NULL) {
3312                 LOGE("rate is NULL");
3313                 return RECORDER_ERROR_INVALID_PARAMETER;
3314         }
3315
3316         LOGD("ENTER");
3317
3318         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3319         if (ret == RECORDER_ERROR_NONE)
3320                 *rate = pc->cb_info->get_double_value[_RECORDER_GET_DOUBLE_RECORDING_MOTION_RATE];
3321
3322         LOGD("ret : 0x%x - rate %.20lf", ret, *rate);
3323
3324         return ret;
3325 }
3326
3327
3328 int recorder_attr_set_audio_channel(recorder_h recorder, int channel_count)
3329 {
3330         int ret = RECORDER_ERROR_NONE;
3331         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_AUDIO_CHANNEL;
3332         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3333         recorder_msg_param param;
3334
3335         if (!pc || !pc->cb_info) {
3336                 LOGE("NULL handle");
3337                 return RECORDER_ERROR_INVALID_PARAMETER;
3338         }
3339
3340         LOGD("ENTER");
3341
3342         RECORDER_MSG_PARAM_SET(param, INT, channel_count);
3343
3344         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
3345
3346         LOGD("ret : 0x%x", ret);
3347
3348         return ret;
3349 }
3350
3351
3352 int recorder_attr_get_audio_channel(recorder_h recorder, int *channel_count)
3353 {
3354         int ret = RECORDER_ERROR_NONE;
3355         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_AUDIO_CHANNEL;
3356         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3357
3358         if (!pc || !pc->cb_info) {
3359                 LOGE("NULL handle");
3360                 return RECORDER_ERROR_INVALID_PARAMETER;
3361         }
3362
3363         if (channel_count == NULL) {
3364                 LOGE("channel_count is NULL");
3365                 return RECORDER_ERROR_INVALID_PARAMETER;
3366         }
3367
3368         LOGD("ENTER");
3369
3370         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3371
3372         if (ret == RECORDER_ERROR_NONE)
3373                 *channel_count = pc->cb_info->get_int_value[_RECORDER_GET_INT_AUDIO_CHANNEL];
3374
3375         LOGD("ret : 0x%x, channel count %d", ret, *channel_count);
3376
3377         return ret;
3378 }
3379
3380
3381 int recorder_attr_set_orientation_tag(recorder_h recorder, recorder_rotation_e orientation)
3382 {
3383         int ret = RECORDER_ERROR_NONE;
3384         int set_orientation = (int)orientation;
3385         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_SET_ORIENTATION_TAG;
3386         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3387         recorder_msg_param param;
3388
3389         if (!pc || !pc->cb_info) {
3390                 LOGE("NULL handle");
3391                 return RECORDER_ERROR_INVALID_PARAMETER;
3392         }
3393
3394         LOGD("ENTER");
3395
3396         RECORDER_MSG_PARAM_SET(param, INT, set_orientation);
3397
3398         _recorder_msg_send_param1(api, pc->cb_info, &ret, &param);
3399
3400         LOGD("ret : 0x%x", ret);
3401
3402         return ret;
3403 }
3404
3405
3406 int  recorder_attr_get_orientation_tag(recorder_h recorder, recorder_rotation_e *orientation)
3407 {
3408         int ret = RECORDER_ERROR_NONE;
3409         muse_recorder_api_e api = MUSE_RECORDER_API_ATTR_GET_ORIENTATION_TAG;
3410         recorder_cli_s *pc = (recorder_cli_s *)recorder;
3411
3412         if (!pc || !pc->cb_info) {
3413                 LOGE("NULL handle");
3414                 return RECORDER_ERROR_INVALID_PARAMETER;
3415         }
3416
3417         if (orientation == NULL) {
3418                 LOGE("orientation is NULL");
3419                 return RECORDER_ERROR_INVALID_PARAMETER;
3420         }
3421
3422         LOGD("ENTER");
3423
3424         _recorder_msg_send(api, pc->cb_info, &ret, RECORDER_CB_TIMEOUT);
3425
3426         if (ret == RECORDER_ERROR_NONE)
3427                 *orientation = (recorder_rotation_e)pc->cb_info->get_int_value[_RECORDER_GET_INT_ORIENTATION_TAG];
3428
3429         LOGD("ret : 0x%x, orientation %d", ret, *orientation);
3430
3431         return ret;
3432 }
3433
3434
3435 int recorder_get_device_state(recorder_type_e type, recorder_device_state_e *state)
3436 {
3437         int ret = RECORDER_ERROR_NONE;
3438         int sock_fd = -1;
3439         int module_index = -1;
3440         int get_device_state = 0;
3441         char *send_msg = NULL;
3442         char recv_msg[MUSE_RECORDER_MSG_MAX_LENGTH] = {'\0',};
3443
3444         if (!state) {
3445                 LOGE("NULL pointer");
3446                 return RECORDER_ERROR_INVALID_PARAMETER;
3447         }
3448
3449         LOGD("Enter - type %d", type);
3450
3451         sock_fd = muse_client_new();
3452         if (sock_fd < 0) {
3453                 LOGE("muse_client_new failed - returned fd %d", sock_fd);
3454                 ret = RECORDER_ERROR_INVALID_OPERATION;
3455                 goto _GET_DEVICE_STATE_EXIT;
3456         }
3457
3458         if (muse_client_get_module_index(MODULE_NAME, &module_index) != MM_ERROR_NONE) {
3459                 LOGE("muse client get module index failed");
3460                 ret = RECORDER_ERROR_INVALID_OPERATION;
3461                 goto _GET_DEVICE_STATE_EXIT;
3462         }
3463
3464         send_msg = muse_core_msg_new(MUSE_RECORDER_API_GET_DEVICE_STATE,
3465                 MUSE_TYPE_INT, "module", module_index,
3466                 MUSE_TYPE_INT, PARAM_RECORDER_TYPE, type,
3467                 NULL);
3468         if (!send_msg) {
3469                 LOGE("NULL msg");
3470                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
3471                 goto _GET_DEVICE_STATE_EXIT;
3472         }
3473
3474         LOGD("sock_fd : %d, msg : %s", sock_fd, send_msg);
3475
3476         ret = muse_core_msg_send(sock_fd, send_msg);
3477
3478         muse_core_msg_free(send_msg);
3479         send_msg = NULL;
3480
3481         if (ret < 0) {
3482                 LOGE("send msg failed %d", errno);
3483                 ret = RECORDER_ERROR_INVALID_OPERATION;
3484                 goto _GET_DEVICE_STATE_EXIT;
3485         }
3486
3487         ret = muse_core_msg_recv(sock_fd, recv_msg, MUSE_RECORDER_MSG_MAX_LENGTH);
3488         if (ret <= 0) {
3489                 LOGE("recv msg failed %d", errno);
3490                 ret = RECORDER_ERROR_INVALID_OPERATION;
3491                 goto _GET_DEVICE_STATE_EXIT;
3492         }
3493
3494         if (!muse_recorder_msg_get(ret, recv_msg)) {
3495                 LOGE("failed to get return value from msg [%s]", recv_msg);
3496                 ret = RECORDER_ERROR_INVALID_OPERATION;
3497                 goto _GET_DEVICE_STATE_EXIT;
3498         }
3499
3500         if (ret == RECORDER_ERROR_NONE) {
3501                 if (muse_recorder_msg_get(get_device_state, recv_msg)) {
3502                         *state = (recorder_device_state_e)get_device_state;
3503                         LOGD("device type %d state %d", type, *state);
3504                 } else {
3505                         LOGE("failed to get device state from msg [%s]", recv_msg);
3506                         ret = RECORDER_ERROR_INVALID_OPERATION;
3507                 }
3508         } else {
3509                 LOGE("failed 0x%x", ret);
3510         }
3511
3512 _GET_DEVICE_STATE_EXIT:
3513         if (sock_fd > -1) {
3514                 muse_client_close(sock_fd);
3515                 sock_fd = -1;
3516         }
3517
3518         return ret;
3519 }
3520
3521
3522 int recorder_add_device_state_changed_cb(recorder_device_state_changed_cb callback, void *user_data, int *cb_id)
3523 {
3524         int ret = RECORDER_ERROR_NONE;
3525         recorder_device_state_e state = RECORDER_DEVICE_STATE_IDLE;
3526         recorder_cb_info *info = NULL;
3527
3528         if (!callback || !cb_id) {
3529                 LOGE("invalid pointer %p %p", callback, cb_id);
3530                 return RECORDER_ERROR_INVALID_PARAMETER;
3531         }
3532
3533         g_mutex_lock(&g_rec_dev_state_changed_cb_lock);
3534
3535         /* check recorder support */
3536         ret = recorder_get_device_state(RECORDER_TYPE_AUDIO, &state);
3537         if (ret != RECORDER_ERROR_NONE) {
3538                 LOGE("get device state failed");
3539                 g_mutex_unlock(&g_rec_dev_state_changed_cb_lock);
3540                 return ret;
3541         }
3542
3543         info = g_new0(recorder_cb_info, 1);
3544         if (!info) {
3545                 LOGE("info failed");
3546                 ret = RECORDER_ERROR_OUT_OF_MEMORY;
3547                 goto _DONE;
3548         }
3549
3550         info->id = ++g_rec_dev_state_changed_cb_id;
3551         info->callback = (void *)callback;
3552         info->user_data = user_data;
3553
3554         *cb_id = info->id;
3555
3556         /* subscribe dbus signal for camera state change */
3557         if (!g_rec_dev_state_changed_cb_conn) {
3558                 g_rec_dev_state_changed_cb_conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, NULL);
3559                 if (!g_rec_dev_state_changed_cb_conn) {
3560                         LOGE("failed to get gdbus connection");
3561                         ret = RECORDER_ERROR_INVALID_OPERATION;
3562                         goto _DONE;
3563                 }
3564
3565                 LOGD("subscribe signal %s - %s - %s",
3566                         MM_CAMCORDER_DBUS_OBJECT,
3567                         MM_CAMCORDER_DBUS_INTERFACE_RECORDER,
3568                         MM_CAMCORDER_DBUS_SIGNAL_STATE_CHANGED);
3569
3570                 g_rec_dev_state_changed_cb_subscribe_id = g_dbus_connection_signal_subscribe(g_rec_dev_state_changed_cb_conn,
3571                         NULL, MM_CAMCORDER_DBUS_INTERFACE_RECORDER, MM_CAMCORDER_DBUS_SIGNAL_STATE_CHANGED, MM_CAMCORDER_DBUS_OBJECT, NULL,
3572                         G_DBUS_SIGNAL_FLAGS_NONE, (GDBusSignalCallback)__recorder_device_state_changed_cb, NULL, NULL);
3573                 if (!g_rec_dev_state_changed_cb_subscribe_id) {
3574                         LOGE("failed to get gdbus connection");
3575                         ret = RECORDER_ERROR_INVALID_OPERATION;
3576                         goto _DONE;
3577                 }
3578
3579                 LOGD("signal subscribe id %u", g_rec_dev_state_changed_cb_subscribe_id);
3580         }
3581
3582         g_rec_dev_state_changed_cb_list = g_list_prepend(g_rec_dev_state_changed_cb_list, (gpointer)info);
3583
3584         LOGD("callback id %d", info->id);
3585
3586 _DONE:
3587         if (ret != RECORDER_ERROR_NONE) {
3588                 if (info) {
3589                         g_free(info);
3590                         info = NULL;
3591                 }
3592
3593                 if (g_rec_dev_state_changed_cb_conn) {
3594                         g_object_unref(g_rec_dev_state_changed_cb_conn);
3595                         g_rec_dev_state_changed_cb_conn = NULL;
3596                 }
3597         }
3598
3599         g_mutex_unlock(&g_rec_dev_state_changed_cb_lock);
3600
3601         return ret;
3602 }
3603
3604
3605 int recorder_remove_device_state_changed_cb(int cb_id)
3606 {
3607         int ret = RECORDER_ERROR_NONE;
3608         recorder_device_state_e state = RECORDER_DEVICE_STATE_IDLE;
3609         GList *tmp_list = NULL;
3610         recorder_cb_info *info = NULL;
3611
3612         /* check recorder support */
3613         ret = recorder_get_device_state(RECORDER_TYPE_AUDIO, &state);
3614         if (ret != RECORDER_ERROR_NONE) {
3615                 LOGE("get device state failed");
3616                 return ret;
3617         }
3618
3619         g_mutex_lock(&g_rec_dev_state_changed_cb_lock);
3620
3621         if (!g_rec_dev_state_changed_cb_list) {
3622                 LOGE("there is no callback info");
3623                 ret = RECORDER_ERROR_INVALID_OPERATION;
3624                 goto _DONE;
3625         }
3626
3627         tmp_list = g_rec_dev_state_changed_cb_list;
3628
3629         do {
3630                 info = tmp_list->data;
3631                 tmp_list = tmp_list->next;
3632
3633                 if (!info) {
3634                         LOGW("NULL info");
3635                         continue;
3636                 }
3637
3638                 if (info->id == cb_id) {
3639                         g_rec_dev_state_changed_cb_list = g_list_remove(g_rec_dev_state_changed_cb_list, info);
3640
3641                         g_free(info);
3642                         info = NULL;
3643
3644                         if (!g_rec_dev_state_changed_cb_list) {
3645                                 /* no remained callback */
3646                                 if (g_rec_dev_state_changed_cb_conn) {
3647                                         /* unsubscribe signal */
3648                                         g_dbus_connection_signal_unsubscribe(g_rec_dev_state_changed_cb_conn, g_rec_dev_state_changed_cb_subscribe_id);
3649                                         g_rec_dev_state_changed_cb_subscribe_id = 0;
3650
3651                                         /* unref connection */
3652                                         g_object_unref(g_rec_dev_state_changed_cb_conn);
3653                                         g_rec_dev_state_changed_cb_conn = NULL;
3654                                 }
3655                         }
3656
3657                         LOGD("id %d callback removed", cb_id);
3658                         ret = RECORDER_ERROR_NONE;
3659
3660                         goto _DONE;
3661                 }
3662         } while (tmp_list);
3663
3664         LOGE("id %d callback not found", cb_id);
3665         ret = RECORDER_ERROR_INVALID_PARAMETER;
3666
3667 _DONE:
3668         g_mutex_unlock(&g_rec_dev_state_changed_cb_lock);
3669
3670         return ret;
3671 }