4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Jeongmo Yang <jm80.yang@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
22 /*=======================================================================================
24 ========================================================================================*/
29 #include <gst/gstutils.h>
30 #include <gst/gstpad.h>
34 #include "mm_camcorder_internal.h"
37 #include <gst/video/colorbalance.h>
38 #include <gst/video/cameracontrol.h>
39 #include <asm/types.h>
41 #include <system_info.h>
43 /*---------------------------------------------------------------------------------------
44 | GLOBAL VARIABLE DEFINITIONS for internal |
45 ---------------------------------------------------------------------------------------*/
46 int g_mm_camcorder_type = -255;
47 struct sigaction mm_camcorder_int_old_action;
48 struct sigaction mm_camcorder_abrt_old_action;
49 struct sigaction mm_camcorder_segv_old_action;
50 struct sigaction mm_camcorder_term_old_action;
51 struct sigaction mm_camcorder_sys_old_action;
53 /*---------------------------------------------------------------------------------------
54 | LOCAL VARIABLE DEFINITIONS for internal |
55 ---------------------------------------------------------------------------------------*/
56 #define __MMCAMCORDER_CMD_ITERATE_MAX 3
57 #define __MMCAMCORDER_SET_GST_STATE_TIMEOUT 3
58 #define __MMCAMCORDER_SOUND_WAIT_TIMEOUT 3
59 #define __MMCAMCORDER_PATH_CAMERA_RESOURCE "/usr/share/sounds/mm-camcorder/camera_resource"
60 #define __MMCAMCORDER_PATH_RECORDER_RESOURCE "/usr/share/sounds/mm-camcorder/recorder_resource"
63 /*---------------------------------------------------------------------------------------
64 | LOCAL FUNCTION PROTOTYPES: |
65 ---------------------------------------------------------------------------------------*/
66 /* STATIC INTERNAL FUNCTION */
67 static gboolean __mmcamcorder_gstreamer_init(camera_conf * conf);
69 static gboolean __mmcamcorder_handle_gst_error(MMHandleType handle, GstMessage *message, GError *error);
70 static gint __mmcamcorder_gst_handle_stream_error(MMHandleType handle, int code, GstMessage *message);
71 static gint __mmcamcorder_gst_handle_resource_error(MMHandleType handle, int code, GstMessage *message);
72 static gint __mmcamcorder_gst_handle_library_error(MMHandleType handle, int code, GstMessage *message);
73 static gint __mmcamcorder_gst_handle_core_error(MMHandleType handle, int code, GstMessage *message);
74 static gint __mmcamcorder_gst_handle_resource_warning(MMHandleType handle, GstMessage *message , GError *error);
75 static gboolean __mmcamcorder_handle_gst_warning(MMHandleType handle, GstMessage *message, GError *error);
78 #ifdef _MMCAMCORDER_USE_SET_ATTR_CB
79 static gboolean __mmcamcorder_set_attr_to_camsensor_cb(gpointer data);
80 #endif /* _MMCAMCORDER_USE_SET_ATTR_CB */
82 static void __mm_camcorder_signal_handler(int signo);
83 static void _mmcamcorder_constructor() __attribute__((constructor));
85 /*=======================================================================================
86 | FUNCTION DEFINITIONS |
87 =======================================================================================*/
88 /*---------------------------------------------------------------------------------------
89 | GLOBAL FUNCTION DEFINITIONS: |
90 ---------------------------------------------------------------------------------------*/
93 static void __mm_camcorder_signal_handler(int signo)
95 pid_t my_pid = getpid();
96 pid_t vconf_recorder_pid = -1;
97 pid_t vconf_camera_pid = -1;
98 int vconf_flash_state = VCONFKEY_CAMERA_FLASH_STATE_OFF;
100 _mmcam_dbg_warn("start - signo [%d], pid [%d], device type [%d]", signo, my_pid, g_mm_camcorder_type);
102 /* reset vconf key */
103 switch (g_mm_camcorder_type) {
104 case MM_VIDEO_DEVICE_NONE:
105 vconf_get_int(VCONFKEY_RECORDER_PID, (int *)&vconf_recorder_pid);
106 if (my_pid == vconf_recorder_pid) {
107 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_NULL);
108 vconf_set_int(VCONFKEY_RECORDER_PID, -1);
109 _mmcam_dbg_warn("set recorder state NULL");
111 _mmcam_dbg_warn("different pid : my[%d] vconf[%d]", my_pid, vconf_recorder_pid);
114 case MM_VIDEO_DEVICE_CAMERA0:
115 case MM_VIDEO_DEVICE_CAMERA1:
116 vconf_get_int(VCONFKEY_CAMERA_FLASH_STATE, &vconf_flash_state);
117 vconf_get_int(VCONFKEY_CAMERA_PID, (int *)&vconf_camera_pid);
118 if (my_pid == vconf_camera_pid &&
119 vconf_flash_state == VCONFKEY_CAMERA_FLASH_STATE_ON) {
120 vconf_set_int(VCONFKEY_CAMERA_FLASH_STATE, VCONFKEY_CAMERA_FLASH_STATE_OFF);
121 vconf_set_int(VCONFKEY_CAMERA_PID, -1);
122 _mmcam_dbg_warn("set camera flash state OFF");
125 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_NULL);
126 _mmcam_dbg_warn("set camera state NULL");
129 _mmcam_dbg_warn("unknown type [%d]", g_mm_camcorder_type);
133 /* call old signal handler */
136 sigaction(SIGINT, &mm_camcorder_int_old_action, NULL);
140 sigaction(SIGABRT, &mm_camcorder_abrt_old_action, NULL);
144 sigaction(SIGSEGV, &mm_camcorder_segv_old_action, NULL);
148 sigaction(SIGTERM, &mm_camcorder_term_old_action, NULL);
152 sigaction(SIGSYS, &mm_camcorder_sys_old_action, NULL);
159 _mmcam_dbg_warn("done");
165 static void _mmcamcorder_constructor()
167 struct sigaction mm_camcorder_action;
168 mm_camcorder_action.sa_handler = __mm_camcorder_signal_handler;
169 mm_camcorder_action.sa_flags = SA_NOCLDSTOP;
171 _mmcam_dbg_warn("start");
173 sigemptyset(&mm_camcorder_action.sa_mask);
175 sigaction(SIGINT, &mm_camcorder_action, &mm_camcorder_int_old_action);
176 sigaction(SIGABRT, &mm_camcorder_action, &mm_camcorder_abrt_old_action);
177 sigaction(SIGSEGV, &mm_camcorder_action, &mm_camcorder_segv_old_action);
178 sigaction(SIGTERM, &mm_camcorder_action, &mm_camcorder_term_old_action);
179 sigaction(SIGSYS, &mm_camcorder_action, &mm_camcorder_sys_old_action);
181 _mmcam_dbg_warn("done");
187 /* Internal command functions {*/
188 int _mmcamcorder_create(MMHandleType *handle, MMCamPreset *info)
190 int ret = MM_ERROR_NONE;
191 int sys_info_ret = SYSTEM_INFO_ERROR_NONE;
193 int rcmd_fmt_capture = MM_PIXEL_FORMAT_YUYV;
194 int rcmd_fmt_recording = MM_PIXEL_FORMAT_NV12;
195 int rcmd_dpy_rotation = MM_DISPLAY_ROTATION_270;
196 int play_capture_sound = TRUE;
197 int camera_device_count = MM_VIDEO_DEVICE_NUM;
198 int camera_default_flip = MM_FLIP_NONE;
199 int camera_facing_direction = MM_CAMCORDER_CAMERA_FACING_DIRECTION_REAR;
200 int resource_fd = -1;
201 char *err_attr_name = NULL;
202 const char *ConfCtrlFile = NULL;
203 mmf_camcorder_t *hcamcorder = NULL;
204 type_element *EvasSurfaceElement = NULL;
206 _mmcam_dbg_log("Entered");
208 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_INVALID_ARGUMENT);
209 mmf_return_val_if_fail(info, MM_ERROR_CAMCORDER_INVALID_ARGUMENT);
211 /* Create mmf_camcorder_t handle and initialize every variable */
212 hcamcorder = (mmf_camcorder_t *)malloc(sizeof(mmf_camcorder_t));
213 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_LOW_MEMORY);
214 memset(hcamcorder, 0x00, sizeof(mmf_camcorder_t));
217 hcamcorder->type = 0;
218 hcamcorder->state = MM_CAMCORDER_STATE_NONE;
219 hcamcorder->sub_context = NULL;
220 hcamcorder->target_state = MM_CAMCORDER_STATE_NULL;
221 hcamcorder->capture_in_recording = FALSE;
223 pthread_mutex_init(&((hcamcorder->mtsafe).lock), NULL);
224 pthread_cond_init(&((hcamcorder->mtsafe).cond), NULL);
225 pthread_mutex_init(&((hcamcorder->mtsafe).cmd_lock), NULL);
226 pthread_mutex_init(&((hcamcorder->mtsafe).asm_lock), NULL);
227 pthread_mutex_init(&((hcamcorder->mtsafe).state_lock), NULL);
228 pthread_mutex_init(&((hcamcorder->mtsafe).gst_state_lock), NULL);
229 pthread_mutex_init(&((hcamcorder->mtsafe).gst_encode_state_lock), NULL);
230 pthread_mutex_init(&((hcamcorder->mtsafe).message_cb_lock), NULL);
231 pthread_mutex_init(&((hcamcorder->mtsafe).vcapture_cb_lock), NULL);
232 pthread_mutex_init(&((hcamcorder->mtsafe).vstream_cb_lock), NULL);
233 pthread_mutex_init(&((hcamcorder->mtsafe).astream_cb_lock), NULL);
235 pthread_mutex_init(&(hcamcorder->sound_lock), NULL);
236 pthread_cond_init(&(hcamcorder->sound_cond), NULL);
237 pthread_mutex_init(&(hcamcorder->restart_preview_lock), NULL);
239 /* Sound mutex/cond init */
240 pthread_mutex_init(&(hcamcorder->snd_info.open_mutex), NULL);
241 pthread_cond_init(&(hcamcorder->snd_info.open_cond), NULL);
243 /* init for sound thread */
244 pthread_mutex_init(&(hcamcorder->task_thread_lock), NULL);
245 pthread_cond_init(&(hcamcorder->task_thread_cond), NULL);
246 hcamcorder->task_thread_state = _MMCAMCORDER_SOUND_STATE_NONE;
248 /* create task thread */
249 pthread_create(&(hcamcorder->task_thread), NULL, _mmcamcorder_util_task_thread_func, (void *)hcamcorder);
251 /* get root directory */
252 ret = _mmcamcorder_get_root_directory(&hcamcorder->root_directory);
253 if (ret != MM_ERROR_NONE) {
254 goto _ERR_DEFAULT_VALUE_INIT;
257 if (info->videodev_type < MM_VIDEO_DEVICE_NONE ||
258 info->videodev_type >= MM_VIDEO_DEVICE_NUM) {
259 _mmcam_dbg_err("_mmcamcorder_create::video device type is out of range.");
260 ret = MM_ERROR_CAMCORDER_INVALID_ARGUMENT;
261 goto _ERR_DEFAULT_VALUE_INIT;
264 /* set device type */
265 hcamcorder->device_type = info->videodev_type;
266 _mmcam_dbg_warn("Device Type : %d", hcamcorder->device_type);
268 if (hcamcorder->device_type == MM_VIDEO_DEVICE_NONE) {
269 resource_fd = open(__MMCAMCORDER_PATH_RECORDER_RESOURCE, O_RDONLY);
271 resource_fd = open(__MMCAMCORDER_PATH_CAMERA_RESOURCE, O_RDONLY);
274 if (resource_fd < 0) {
275 _mmcam_dbg_log("open error %s : cur %d",strerror(errno),errno);
276 if(errno == EPERM || errno == EACCES) {
277 ret = MM_ERROR_COMMON_INVALID_PERMISSION;
279 ret = MM_ERROR_CAMCORDER_INTERNAL;
281 goto _ERR_DEFAULT_VALUE_INIT;
285 _mmcam_dbg_warn("permission check done");
288 /* Get Camera Configure information from Camcorder INI file */
289 _mmcamcorder_conf_get_info((MMHandleType)hcamcorder, CONFIGURE_TYPE_MAIN, CONFIGURE_MAIN_FILE, &hcamcorder->conf_main);
291 if (!(hcamcorder->conf_main)) {
292 _mmcam_dbg_err( "Failed to get configure(main) info." );
294 ret = MM_ERROR_CAMCORDER_CREATE_CONFIGURE;
295 goto _ERR_AFTER_ASM_REGISTER;
298 hcamcorder->attributes = _mmcamcorder_alloc_attribute((MMHandleType)hcamcorder, info);
299 if (!(hcamcorder->attributes)) {
300 _mmcam_dbg_err("_mmcamcorder_create::alloc attribute error.");
302 ret = MM_ERROR_CAMCORDER_RESOURCE_CREATION;
303 goto _ERR_AFTER_ASM_REGISTER;
306 if (info->videodev_type != MM_VIDEO_DEVICE_NONE) {
307 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
308 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
309 "UseConfCtrl", &UseConfCtrl);
312 int resolution_width = 0;
313 int resolution_height = 0;
314 MMCamAttrsInfo fps_info;
316 _mmcam_dbg_log( "Enable Configure Control system." );
318 switch (info->videodev_type) {
319 case MM_VIDEO_DEVICE_CAMERA0:
320 _mmcamcorder_conf_get_value_string((MMHandleType)hcamcorder, hcamcorder->conf_main,
321 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
322 "ConfCtrlFile0", &ConfCtrlFile);
324 case MM_VIDEO_DEVICE_CAMERA1:
325 _mmcamcorder_conf_get_value_string((MMHandleType)hcamcorder, hcamcorder->conf_main,
326 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
327 "ConfCtrlFile1", &ConfCtrlFile);
330 _mmcam_dbg_err( "Not supported camera type." );
331 ret = MM_ERROR_CAMCORDER_NOT_SUPPORTED;
332 goto _ERR_AFTER_ASM_REGISTER;
335 _mmcam_dbg_log("videodev_type : [%d], ConfCtrlPath : [%s]", info->videodev_type, ConfCtrlFile);
337 _mmcamcorder_conf_get_info((MMHandleType)hcamcorder, CONFIGURE_TYPE_CTRL, ConfCtrlFile, &hcamcorder->conf_ctrl);
339 _mmcamcorder_conf_print_info(&hcamcorder->conf_main);
340 _mmcamcorder_conf_print_info(&hcamcorder->conf_ctrl);
342 if (!(hcamcorder->conf_ctrl)) {
343 _mmcam_dbg_err( "Failed to get configure(control) info." );
344 ret = MM_ERROR_CAMCORDER_CREATE_CONFIGURE;
345 goto _ERR_AFTER_ASM_REGISTER;
348 ret = _mmcamcorder_init_convert_table((MMHandleType)hcamcorder);
349 if (ret != MM_ERROR_NONE) {
350 _mmcam_dbg_warn("converting table initialize error!!");
351 ret = MM_ERROR_CAMCORDER_INTERNAL;
352 goto _ERR_AFTER_ASM_REGISTER;
355 ret = _mmcamcorder_init_attr_from_configure((MMHandleType)hcamcorder, info->videodev_type);
356 if (ret != MM_ERROR_NONE) {
357 _mmcam_dbg_warn("converting table initialize error!!");
358 ret = MM_ERROR_CAMCORDER_INTERNAL;
359 goto _ERR_AFTER_ASM_REGISTER;
362 /* Get device info, recommend preview fmt and display rotation from INI */
363 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
364 CONFIGURE_CATEGORY_CTRL_CAMERA,
365 "RecommendPreviewFormatCapture",
368 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
369 CONFIGURE_CATEGORY_CTRL_CAMERA,
370 "RecommendPreviewFormatRecord",
371 &rcmd_fmt_recording);
373 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
374 CONFIGURE_CATEGORY_CTRL_CAMERA,
375 "RecommendDisplayRotation",
378 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
379 CONFIGURE_CATEGORY_MAIN_CAPTURE,
381 &play_capture_sound);
383 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
384 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
386 &camera_device_count);
388 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
389 CONFIGURE_CATEGORY_CTRL_CAMERA,
391 &camera_facing_direction);
393 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
394 CONFIGURE_CATEGORY_CTRL_EFFECT,
395 "BrightnessStepDenominator",
396 &hcamcorder->brightness_step_denominator);
398 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_ctrl,
399 CONFIGURE_CATEGORY_CTRL_CAPTURE,
401 &hcamcorder->support_zsl_capture);
403 _mmcam_dbg_log("Recommend fmt[cap:%d,rec:%d], dpy rot %d, cap snd %d, dev cnt %d, cam facing dir %d, step denom %d, support zsl %d",
404 rcmd_fmt_capture, rcmd_fmt_recording, rcmd_dpy_rotation,
405 play_capture_sound, camera_device_count, camera_facing_direction,
406 hcamcorder->brightness_step_denominator, hcamcorder->support_zsl_capture);
408 /* Get UseZeroCopyFormat value from INI */
409 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
410 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
412 &(hcamcorder->use_zero_copy_format));
414 /* Get SupportMediaPacketPreviewCb value from INI */
415 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
416 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
417 "SupportMediaPacketPreviewCb",
418 &(hcamcorder->support_media_packet_preview_cb));
420 ret = mm_camcorder_get_attributes((MMHandleType)hcamcorder, NULL,
421 MMCAM_CAMERA_WIDTH, &resolution_width,
422 MMCAM_CAMERA_HEIGHT, &resolution_height,
425 mm_camcorder_get_fps_list_by_resolution((MMHandleType)hcamcorder, resolution_width, resolution_height, &fps_info);
427 _mmcam_dbg_log("UseZeroCopyFormat : %d", hcamcorder->use_zero_copy_format);
428 _mmcam_dbg_log("SupportMediaPacketPreviewCb : %d", hcamcorder->support_media_packet_preview_cb);
429 _mmcam_dbg_log("res : %d X %d, Default FPS by resolution : %d", resolution_width, resolution_height, fps_info.int_array.def);
431 if (camera_facing_direction == 1) {
432 if (rcmd_dpy_rotation == MM_DISPLAY_ROTATION_270 || rcmd_dpy_rotation == MM_DISPLAY_ROTATION_90) {
433 camera_default_flip = MM_FLIP_VERTICAL;
435 camera_default_flip = MM_FLIP_HORIZONTAL;
437 _mmcam_dbg_log("camera_default_flip : [%d]",camera_default_flip);
440 mm_camcorder_set_attributes((MMHandleType)hcamcorder, &err_attr_name,
441 MMCAM_CAMERA_DEVICE_COUNT, camera_device_count,
442 MMCAM_CAMERA_FACING_DIRECTION, camera_facing_direction,
443 MMCAM_RECOMMEND_PREVIEW_FORMAT_FOR_CAPTURE, rcmd_fmt_capture,
444 MMCAM_RECOMMEND_PREVIEW_FORMAT_FOR_RECORDING, rcmd_fmt_recording,
445 MMCAM_RECOMMEND_DISPLAY_ROTATION, rcmd_dpy_rotation,
446 MMCAM_SUPPORT_ZSL_CAPTURE, hcamcorder->support_zsl_capture,
447 MMCAM_SUPPORT_ZERO_COPY_FORMAT, hcamcorder->use_zero_copy_format,
448 MMCAM_SUPPORT_MEDIA_PACKET_PREVIEW_CB, hcamcorder->support_media_packet_preview_cb,
449 MMCAM_CAMERA_FPS, fps_info.int_array.def,
450 MMCAM_DISPLAY_FLIP, camera_default_flip,
451 "capture-sound-enable", play_capture_sound,
454 _mmcam_dbg_err("Set %s FAILED.", err_attr_name);
456 err_attr_name = NULL;
457 ret = MM_ERROR_CAMCORDER_INTERNAL;
458 goto _ERR_AFTER_ASM_REGISTER;
461 /* Get default value of brightness */
462 mm_camcorder_get_attributes((MMHandleType)hcamcorder, &err_attr_name,
463 MMCAM_FILTER_BRIGHTNESS, &hcamcorder->brightness_default,
466 _mmcam_dbg_err("Get brightness FAILED.");
468 err_attr_name = NULL;
469 ret = MM_ERROR_CAMCORDER_INTERNAL;
470 goto _ERR_AFTER_ASM_REGISTER;
472 _mmcam_dbg_log("Default brightness : %d", hcamcorder->brightness_default);
474 _mmcam_dbg_log( "Disable Configure Control system." );
475 hcamcorder->conf_ctrl = NULL;
478 _mmcamcorder_conf_get_value_int((MMHandleType)hcamcorder, hcamcorder->conf_main,
479 CONFIGURE_CATEGORY_MAIN_VIDEO_INPUT,
481 &camera_device_count);
482 mm_camcorder_set_attributes((MMHandleType)hcamcorder, &err_attr_name,
483 MMCAM_CAMERA_DEVICE_COUNT, camera_device_count,
486 _mmcam_dbg_err("Set %s FAILED.", err_attr_name);
488 err_attr_name = NULL;
489 ret = MM_ERROR_CAMCORDER_INTERNAL;
490 goto _ERR_AFTER_ASM_REGISTER;
493 ret = _mmcamcorder_init_attr_from_configure((MMHandleType)hcamcorder, info->videodev_type);
494 if (ret != MM_ERROR_NONE) {
495 _mmcam_dbg_warn("init attribute from configure error : 0x%x", ret);
496 ret = MM_ERROR_CAMCORDER_INTERNAL;
497 goto _ERR_AFTER_ASM_REGISTER;
501 ret = __mmcamcorder_gstreamer_init(hcamcorder->conf_main);
503 _mmcam_dbg_err( "Failed to initialize gstreamer!!" );
504 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
505 goto _ERR_AFTER_ASM_REGISTER;
508 /* Make some attributes as read-only type */
509 _mmcamcorder_lock_readonly_attributes((MMHandleType)hcamcorder);
511 /* Disable attributes in each model */
512 _mmcamcorder_set_disabled_attributes((MMHandleType)hcamcorder);
514 /* Get videosink name for evas surface */
515 _mmcamcorder_conf_get_element((MMHandleType)hcamcorder, hcamcorder->conf_main,
516 CONFIGURE_CATEGORY_MAIN_VIDEO_OUTPUT,
517 "VideosinkElementEvas",
518 &EvasSurfaceElement);
519 if (EvasSurfaceElement) {
521 const char *evassink_name = NULL;
522 mmf_attribute_t *item_evassink_name = NULL;
523 mmf_attrs_t *attrs = (mmf_attrs_t *)MMF_CAMCORDER_ATTRS(hcamcorder);
525 _mmcamcorder_conf_get_value_element_name(EvasSurfaceElement, &evassink_name);
526 mm_attrs_get_index((MMHandleType)attrs, MMCAM_DISPLAY_EVAS_SURFACE_SINK, &attr_index);
527 item_evassink_name = &attrs->items[attr_index];
528 mmf_attribute_set_string(item_evassink_name, evassink_name, strlen(evassink_name));
529 mmf_attribute_commit(item_evassink_name);
531 _mmcam_dbg_log("Evassink name : %s", evassink_name);
534 /* get shutter sound policy */
535 vconf_get_int(VCONFKEY_CAMERA_SHUTTER_SOUND_POLICY, &hcamcorder->shutter_sound_policy);
536 _mmcam_dbg_log("current shutter sound policy : %d", hcamcorder->shutter_sound_policy);
539 sys_info_ret = system_info_get_platform_string("http://tizen.org/system/model_name", &hcamcorder->model_name);
540 if (hcamcorder->model_name) {
541 _mmcam_dbg_log("model name [%s], sys_info_ret 0x%x", hcamcorder->model_name, sys_info_ret);
543 _mmcam_dbg_warn("failed get model name, sys_info_ret 0x%x", sys_info_ret);
546 /* get software version */
547 sys_info_ret = system_info_get_platform_string("http://tizen.org/system/build.string", &hcamcorder->software_version);
548 if (hcamcorder->software_version) {
549 _mmcam_dbg_log("software version [%s], sys_info_ret 0x%d", hcamcorder->software_version, sys_info_ret);
551 _mmcam_dbg_warn("failed get software version, sys_info_ret 0x%x", sys_info_ret);
554 /* Set initial state */
555 _mmcamcorder_set_state((MMHandleType)hcamcorder, MM_CAMCORDER_STATE_NULL);
557 _mmcam_dbg_log("created handle %p", hcamcorder);
559 /* set device type */
560 g_mm_camcorder_type = info->videodev_type;
562 *handle = (MMHandleType)hcamcorder;
564 return MM_ERROR_NONE;
566 _ERR_AFTER_ASM_REGISTER:
568 _ERR_DEFAULT_VALUE_INIT:
569 /* Release lock, cond */
570 pthread_mutex_destroy(&((hcamcorder->mtsafe).lock));
571 pthread_cond_destroy(&((hcamcorder->mtsafe).cond));
572 pthread_mutex_destroy(&((hcamcorder->mtsafe).cmd_lock));
573 pthread_mutex_destroy(&((hcamcorder->mtsafe).asm_lock));
574 pthread_mutex_destroy(&((hcamcorder->mtsafe).state_lock));
575 pthread_mutex_destroy(&((hcamcorder->mtsafe).gst_state_lock));
576 pthread_mutex_destroy(&((hcamcorder->mtsafe).gst_encode_state_lock));
577 pthread_mutex_destroy(&((hcamcorder->mtsafe).message_cb_lock));
578 pthread_mutex_destroy(&((hcamcorder->mtsafe).vcapture_cb_lock));
579 pthread_mutex_destroy(&((hcamcorder->mtsafe).vstream_cb_lock));
580 pthread_mutex_destroy(&((hcamcorder->mtsafe).astream_cb_lock));
582 pthread_mutex_destroy(&(hcamcorder->sound_lock));
583 pthread_cond_destroy(&(hcamcorder->sound_cond));
584 pthread_mutex_destroy(&(hcamcorder->snd_info.open_mutex));
585 pthread_cond_destroy(&(hcamcorder->snd_info.open_cond));
586 pthread_mutex_destroy(&(hcamcorder->restart_preview_lock));
588 if (hcamcorder->conf_ctrl) {
589 _mmcamcorder_conf_release_info(handle, &hcamcorder->conf_ctrl);
592 if (hcamcorder->conf_main) {
593 _mmcamcorder_conf_release_info(handle, &hcamcorder->conf_main);
596 if (hcamcorder->model_name) {
597 free(hcamcorder->model_name);
598 hcamcorder->model_name = NULL;
601 if (hcamcorder->software_version) {
602 free(hcamcorder->software_version);
603 hcamcorder->software_version = NULL;
606 if (hcamcorder->task_thread) {
607 pthread_mutex_lock(&(hcamcorder->task_thread_lock));
608 _mmcam_dbg_log("send signal for task thread exit");
609 hcamcorder->task_thread_state = _MMCAMCORDER_TASK_THREAD_STATE_EXIT;
610 pthread_cond_signal(&(hcamcorder->task_thread_cond));
611 pthread_mutex_unlock(&(hcamcorder->task_thread_lock));
612 pthread_join(hcamcorder->task_thread, NULL);
614 pthread_mutex_destroy(&(hcamcorder->task_thread_lock));
615 pthread_cond_destroy(&(hcamcorder->task_thread_cond));
617 if (hcamcorder->root_directory) {
618 free(hcamcorder->root_directory);
619 hcamcorder->root_directory = NULL;
623 memset(hcamcorder, 0x00, sizeof(mmf_camcorder_t));
630 int _mmcamcorder_destroy(MMHandleType handle)
632 int ret = MM_ERROR_NONE;
633 int state = MM_CAMCORDER_STATE_NONE;
634 int state_FROM = MM_CAMCORDER_STATE_NULL;
636 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
641 _mmcam_dbg_err("Not initialized");
642 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
643 goto _ERR_CAMCORDER_CMD_PRECON;
646 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
647 _mmcam_dbg_err("Another command is running.");
648 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
649 goto _ERR_CAMCORDER_CMD_PRECON;
652 state = _mmcamcorder_get_state(handle);
653 if (state != state_FROM) {
654 _mmcam_dbg_err("Wrong state(%d)", state);
655 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
656 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
659 /* set exit state for sound thread */
660 pthread_mutex_lock(&(hcamcorder->task_thread_lock));
661 _mmcam_dbg_log("send signal for task thread exit");
662 hcamcorder->task_thread_state = _MMCAMCORDER_TASK_THREAD_STATE_EXIT;
663 pthread_cond_signal(&(hcamcorder->task_thread_cond));
664 pthread_mutex_unlock(&(hcamcorder->task_thread_lock));
666 pthread_mutex_lock(&(hcamcorder->sound_lock));
667 while (hcamcorder->capture_sound_count > 0) {
668 struct timespec timeout;
671 gettimeofday(&tv, NULL);
672 timeout.tv_sec = tv.tv_sec + __MMCAMCORDER_SOUND_WAIT_TIMEOUT;
673 timeout.tv_nsec = tv.tv_usec * 1000;
675 _mmcam_dbg_warn("capture_sound_count[%d] is not zero. wait signal...",
676 hcamcorder->capture_sound_count);
678 if (!pthread_cond_timedwait(&(hcamcorder->sound_cond), &(hcamcorder->sound_lock), &timeout)) {
679 _mmcam_dbg_warn("signal received. check again...");
681 hcamcorder->capture_sound_count = 0;
682 _mmcam_dbg_err("capture sound completion wait time out");
686 pthread_mutex_unlock(&(hcamcorder->sound_lock));
688 /* Release SubContext and pipeline */
689 if (hcamcorder->sub_context) {
690 if (hcamcorder->sub_context->element) {
691 _mmcamcorder_destroy_pipeline(handle, hcamcorder->type);
694 _mmcamcorder_dealloc_subcontext(hcamcorder->sub_context);
695 hcamcorder->sub_context = NULL;
698 /* Remove idle function which is not called yet */
699 if (hcamcorder->setting_event_id) {
700 _mmcam_dbg_log("Remove remaining idle function");
701 g_source_remove(hcamcorder->setting_event_id);
702 hcamcorder->setting_event_id = 0;
705 /* check current strobe mode */
706 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
707 pid_t my_pid = getpid();
709 vconf_get_int(VCONFKEY_CAMERA_PID, &camera_pid);
711 if (camera_pid > -1 && my_pid == camera_pid) {
712 int strobe_mode = MM_CAMCORDER_STROBE_MODE_OFF;
714 vconf_set_int(VCONFKEY_CAMERA_PID, -1);
715 _mmcam_dbg_log("reset camera pid");
717 mm_camcorder_get_attributes(handle, NULL,
718 MMCAM_STROBE_MODE, &strobe_mode,
720 if (strobe_mode != MM_CAMCORDER_STROBE_MODE_OFF) {
721 /* set OFF state of vconf key */
722 vconf_set_int(VCONFKEY_CAMERA_FLASH_STATE, VCONFKEY_CAMERA_FLASH_STATE_OFF);
723 _mmcam_dbg_log("reset flash state");
728 /* Remove attributes */
729 if (hcamcorder->attributes) {
730 _mmcamcorder_dealloc_attribute(handle, hcamcorder->attributes);
731 hcamcorder->attributes = 0;
734 /* Remove exif info */
735 if (hcamcorder->exif_info) {
736 mm_exif_destory_exif_info(hcamcorder->exif_info);
737 hcamcorder->exif_info=NULL;
741 /* Release configure info */
742 if (hcamcorder->conf_ctrl) {
743 _mmcamcorder_conf_release_info(handle, &hcamcorder->conf_ctrl);
745 if (hcamcorder->conf_main) {
746 _mmcamcorder_conf_release_info(handle, &hcamcorder->conf_main);
749 /* Remove messages which are not called yet */
750 _mmcamcorder_remove_message_all(handle);
752 /* release model_name */
753 if (hcamcorder->model_name) {
754 free(hcamcorder->model_name);
755 hcamcorder->model_name = NULL;
758 if (hcamcorder->software_version) {
759 free(hcamcorder->software_version);
760 hcamcorder->software_version = NULL;
763 /* join task thread */
764 _mmcam_dbg_log("task thread join");
765 pthread_join(hcamcorder->task_thread, NULL);
767 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
769 /* Release lock, cond */
770 pthread_mutex_destroy(&((hcamcorder->mtsafe).lock));
771 pthread_cond_destroy(&((hcamcorder->mtsafe).cond));
772 pthread_mutex_destroy(&((hcamcorder->mtsafe).cmd_lock));
773 pthread_mutex_destroy(&((hcamcorder->mtsafe).asm_lock));
774 pthread_mutex_destroy(&((hcamcorder->mtsafe).state_lock));
775 pthread_mutex_destroy(&((hcamcorder->mtsafe).gst_state_lock));
776 pthread_mutex_destroy(&((hcamcorder->mtsafe).gst_encode_state_lock));
777 pthread_mutex_destroy(&((hcamcorder->mtsafe).message_cb_lock));
778 pthread_mutex_destroy(&((hcamcorder->mtsafe).vcapture_cb_lock));
779 pthread_mutex_destroy(&((hcamcorder->mtsafe).vstream_cb_lock));
780 pthread_mutex_destroy(&((hcamcorder->mtsafe).astream_cb_lock));
782 pthread_mutex_destroy(&(hcamcorder->sound_lock));
783 pthread_cond_destroy(&(hcamcorder->sound_cond));
784 pthread_mutex_destroy(&(hcamcorder->snd_info.open_mutex));
785 pthread_cond_destroy(&(hcamcorder->snd_info.open_cond));
786 pthread_mutex_destroy(&(hcamcorder->restart_preview_lock));
787 pthread_mutex_destroy(&(hcamcorder->task_thread_lock));
788 pthread_cond_destroy(&(hcamcorder->task_thread_cond));
790 /* Release internal root directory string */
791 if (hcamcorder->root_directory) {
792 free(hcamcorder->root_directory);
793 hcamcorder->root_directory = NULL;
797 memset(hcamcorder, 0x00, sizeof(mmf_camcorder_t));
800 return MM_ERROR_NONE;
802 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
803 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
805 _ERR_CAMCORDER_CMD_PRECON:
807 _mmcam_dbg_err("Destroy fail (type %d, state %d)", hcamcorder->type, state);
810 _mmcam_dbg_err("Destroy fail (ret %x)", ret);
816 int _mmcamcorder_realize(MMHandleType handle)
818 int ret = MM_ERROR_NONE;
819 int state = MM_CAMCORDER_STATE_NONE;
820 int state_FROM = MM_CAMCORDER_STATE_NULL;
821 int state_TO = MM_CAMCORDER_STATE_READY;
822 int display_surface_type = MM_DISPLAY_SURFACE_X;
823 double motion_rate = _MMCAMCORDER_DEFAULT_RECORDING_MOTION_RATE;
824 char *videosink_element_type = NULL;
825 const char *videosink_name = NULL;
827 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
829 /*_mmcam_dbg_log("");*/
832 _mmcam_dbg_err("Not initialized");
833 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
837 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
838 _mmcam_dbg_err("Another command is running.");
839 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
840 goto _ERR_CAMCORDER_CMD_PRECON;
843 state = _mmcamcorder_get_state(handle);
844 if (state != state_FROM) {
845 _mmcam_dbg_err("Wrong state(%d)", state);
846 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
847 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
850 mm_camcorder_get_attributes(handle, NULL,
851 MMCAM_MODE, &hcamcorder->type,
854 /* Get profile mode */
855 _mmcam_dbg_log("Profile mode [%d]", hcamcorder->type);
857 mm_camcorder_get_attributes(handle, NULL,
858 MMCAM_DISPLAY_SURFACE, &display_surface_type,
859 MMCAM_CAMERA_RECORDING_MOTION_RATE, &motion_rate,
862 /* set camera/recorder state to vconf key */
863 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
864 int vconf_camera_state = 0;
866 /* get current camera state of vconf key */
867 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
868 if (vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_OPEN)) {
869 _mmcam_dbg_log("VCONF ERROR %s : cur %d",strerror(errno),errno);
870 if(errno == EPERM || errno == EACCES) {
871 ret = MM_ERROR_COMMON_INVALID_PERMISSION;
872 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
875 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
876 vconf_camera_state, VCONFKEY_CAMERA_STATE_OPEN);
878 int vconf_recorder_state = 0;
880 /* get current recorder state of vconf key */
881 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
882 if (vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_CREATED)) {
883 _mmcam_dbg_log("VCONF ERROR %s : cur %d",strerror(errno),errno);
884 if (errno == EPERM || errno == EACCES) {
885 ret = MM_ERROR_COMMON_INVALID_PERMISSION;
886 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
890 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
891 vconf_recorder_state, VCONFKEY_RECORDER_STATE_CREATED);
894 /* alloc sub context */
895 hcamcorder->sub_context = _mmcamcorder_alloc_subcontext(hcamcorder->type);
896 if(!hcamcorder->sub_context) {
897 ret = MM_ERROR_CAMCORDER_RESOURCE_CREATION;
898 goto _ERR_CAMCORDER_CMD;
901 /* Set basic configure information */
902 if (motion_rate != _MMCAMCORDER_DEFAULT_RECORDING_MOTION_RATE) {
903 hcamcorder->sub_context->is_modified_rate = TRUE;
906 _mmcamcorder_conf_get_value_int(handle, hcamcorder->conf_main,
907 CONFIGURE_CATEGORY_MAIN_CAPTURE,
909 &(hcamcorder->sub_context->bencbin_capture));
910 _mmcam_dbg_warn("UseEncodebin [%d]", hcamcorder->sub_context->bencbin_capture);
912 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
913 /* get dual stream support info */
914 _mmcamcorder_conf_get_value_int(handle, hcamcorder->conf_main,
915 CONFIGURE_CATEGORY_MAIN_RECORD,
917 &(hcamcorder->sub_context->info_video->support_dual_stream));
918 _mmcam_dbg_warn("SupportDualStream [%d]", hcamcorder->sub_context->info_video->support_dual_stream);
921 switch (display_surface_type) {
922 case MM_DISPLAY_SURFACE_X:
923 videosink_element_type = strdup("VideosinkElementX");
925 case MM_DISPLAY_SURFACE_EVAS:
926 videosink_element_type = strdup("VideosinkElementEvas");
928 case MM_DISPLAY_SURFACE_GL:
929 videosink_element_type = strdup("VideosinkElementGL");
931 case MM_DISPLAY_SURFACE_NULL:
932 videosink_element_type = strdup("VideosinkElementNull");
935 videosink_element_type = strdup("VideosinkElementX");
939 /* check string of videosink element */
940 if (videosink_element_type) {
941 _mmcamcorder_conf_get_element(handle, hcamcorder->conf_main,
942 CONFIGURE_CATEGORY_MAIN_VIDEO_OUTPUT,
943 videosink_element_type,
944 &hcamcorder->sub_context->VideosinkElement);
945 free(videosink_element_type);
946 videosink_element_type = NULL;
948 _mmcam_dbg_warn("strdup failed(display_surface_type %d). Use default X type",
949 display_surface_type);
951 _mmcamcorder_conf_get_element(handle, hcamcorder->conf_main,
952 CONFIGURE_CATEGORY_MAIN_VIDEO_OUTPUT,
953 _MMCAMCORDER_DEFAULT_VIDEOSINK_TYPE,
954 &hcamcorder->sub_context->VideosinkElement);
957 _mmcamcorder_conf_get_value_element_name(hcamcorder->sub_context->VideosinkElement, &videosink_name);
958 _mmcam_dbg_log("Videosink name : %s", videosink_name);
960 /* get videoconvert element */
961 _mmcamcorder_conf_get_element(handle, hcamcorder->conf_main,
962 CONFIGURE_CATEGORY_MAIN_VIDEO_OUTPUT,
963 "VideoconvertElement",
964 &hcamcorder->sub_context->VideoconvertElement);
966 _mmcamcorder_conf_get_value_int(handle, hcamcorder->conf_ctrl,
967 CONFIGURE_CATEGORY_CTRL_CAPTURE,
968 "SensorEncodedCapture",
969 &(hcamcorder->sub_context->SensorEncodedCapture));
970 _mmcam_dbg_log("Support sensor encoded capture : %d", hcamcorder->sub_context->SensorEncodedCapture);
972 /* create pipeline */
973 ret = _mmcamcorder_create_pipeline(handle, hcamcorder->type);
974 if (ret != MM_ERROR_NONE) {
975 /* check internal error of gstreamer */
976 if (hcamcorder->error_code != MM_ERROR_NONE) {
977 ret = hcamcorder->error_code;
978 _mmcam_dbg_log("gstreamer error is occurred. return it %x", ret);
981 /* release sub context */
982 _mmcamcorder_dealloc_subcontext(hcamcorder->sub_context);
983 hcamcorder->sub_context = NULL;
984 goto _ERR_CAMCORDER_CMD;
987 /* set command function */
988 ret = _mmcamcorder_set_functions(handle, hcamcorder->type);
989 if (ret != MM_ERROR_NONE) {
990 _mmcamcorder_destroy_pipeline(handle, hcamcorder->type);
991 _mmcamcorder_dealloc_subcontext(hcamcorder->sub_context);
992 hcamcorder->sub_context = NULL;
993 goto _ERR_CAMCORDER_CMD;
996 _mmcamcorder_set_state(handle, state_TO);
998 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1000 return MM_ERROR_NONE;
1003 /* rollback camera state to vconf key */
1004 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1005 int vconf_camera_state = 0;
1007 /* get current camera state of vconf key */
1008 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1009 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_NULL);
1011 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1012 vconf_camera_state, VCONFKEY_CAMERA_STATE_NULL);
1014 int vconf_recorder_state = 0;
1016 /* get current recorder state of vconf key */
1017 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1018 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_NULL);
1020 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1021 vconf_recorder_state, VCONFKEY_RECORDER_STATE_NULL);
1024 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1025 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1027 _ERR_CAMCORDER_CMD_PRECON:
1028 _mmcam_dbg_err("Realize fail (type %d, state %d, ret %x)",
1029 hcamcorder->type, state, ret);
1035 int _mmcamcorder_unrealize(MMHandleType handle)
1037 int ret = MM_ERROR_NONE;
1038 int state = MM_CAMCORDER_STATE_NONE;
1039 int state_FROM = MM_CAMCORDER_STATE_READY;
1040 int state_TO = MM_CAMCORDER_STATE_NULL;
1042 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1047 _mmcam_dbg_err("Not initialized");
1048 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1052 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1053 _mmcam_dbg_err("Another command is running.");
1054 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1055 goto _ERR_CAMCORDER_CMD_PRECON;
1058 state = _mmcamcorder_get_state(handle);
1059 if (state != state_FROM) {
1060 _mmcam_dbg_err("Wrong state(%d)", state);
1061 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1062 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1065 /* Release SubContext */
1066 if (hcamcorder->sub_context) {
1067 /* destroy pipeline */
1068 _mmcamcorder_destroy_pipeline(handle, hcamcorder->type);
1069 /* Deallocate SubContext */
1070 _mmcamcorder_dealloc_subcontext(hcamcorder->sub_context);
1071 hcamcorder->sub_context = NULL;
1074 /* Deinitialize main context member */
1075 hcamcorder->command = NULL;
1078 /* set camera state to vconf key */
1079 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1080 int vconf_camera_state = 0;
1082 /* get current camera state of vconf key */
1083 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1084 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_NULL);
1086 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1087 vconf_camera_state, VCONFKEY_CAMERA_STATE_NULL);
1089 int vconf_recorder_state = 0;
1091 /* get current recorder state of vconf key */
1092 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1093 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_NULL);
1095 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1096 vconf_recorder_state, VCONFKEY_RECORDER_STATE_NULL);
1099 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1101 _mmcamcorder_set_state(handle, state_TO);
1103 return MM_ERROR_NONE;
1105 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1106 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1108 _ERR_CAMCORDER_CMD_PRECON:
1110 _mmcam_dbg_err("Unrealize fail (type %d, state %d, ret %x)",
1111 hcamcorder->type, state, ret);
1116 int _mmcamcorder_start(MMHandleType handle)
1118 int ret = MM_ERROR_NONE;
1119 int state = MM_CAMCORDER_STATE_NONE;
1120 int state_FROM = MM_CAMCORDER_STATE_READY;
1121 int state_TO =MM_CAMCORDER_STATE_PREPARE;
1123 _MMCamcorderSubContext *sc = NULL;
1124 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1129 _mmcam_dbg_err("Not initialized");
1130 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1134 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
1135 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1137 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1138 _mmcam_dbg_err("Another command is running.");
1139 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1140 goto _ERR_CAMCORDER_CMD_PRECON;
1143 state = _mmcamcorder_get_state(handle);
1144 if (state != state_FROM) {
1145 _mmcam_dbg_err("Wrong state(%d)", state);
1146 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1147 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1150 /* initialize error code */
1151 hcamcorder->error_code = MM_ERROR_NONE;
1153 /* set attributes related sensor */
1154 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1155 _mmcamcorder_set_attribute_to_camsensor(handle);
1158 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_PREVIEW_START);
1159 if (ret != MM_ERROR_NONE) {
1160 /* check internal error of gstreamer */
1161 if (hcamcorder->error_code != MM_ERROR_NONE) {
1162 ret = hcamcorder->error_code;
1163 _mmcam_dbg_log("gstreamer error is occurred. return it %x", ret);
1165 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1168 _mmcamcorder_set_state(handle, state_TO);
1170 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1171 int vconf_camera_state = 0;
1173 /* check camera state of vconf key */
1174 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1176 /* set camera state to vconf key */
1177 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_PREVIEW);
1179 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1180 vconf_camera_state, VCONFKEY_CAMERA_STATE_PREVIEW);
1183 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1185 return MM_ERROR_NONE;
1187 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1188 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1190 _ERR_CAMCORDER_CMD_PRECON:
1191 /* check internal error of gstreamer */
1192 if (hcamcorder->error_code != MM_ERROR_NONE) {
1193 ret = hcamcorder->error_code;
1194 hcamcorder->error_code = MM_ERROR_NONE;
1196 _mmcam_dbg_log("gstreamer error is occurred. return it %x", ret);
1199 _mmcam_dbg_err("Start fail (type %d, state %d, ret %x)",
1200 hcamcorder->type, state, ret);
1205 int _mmcamcorder_stop(MMHandleType handle)
1207 int ret = MM_ERROR_NONE;
1208 int state = MM_CAMCORDER_STATE_NONE;
1209 int state_FROM = MM_CAMCORDER_STATE_PREPARE;
1210 int state_TO = MM_CAMCORDER_STATE_READY;
1212 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1217 _mmcam_dbg_err("Not initialized");
1218 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1222 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1223 _mmcam_dbg_err("Another command is running.");
1224 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1225 goto _ERR_CAMCORDER_CMD_PRECON;
1228 state = _mmcamcorder_get_state(handle);
1229 if (state != state_FROM) {
1230 _mmcam_dbg_err("Wrong state(%d)", state);
1231 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1232 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1235 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_PREVIEW_STOP);
1236 if (ret != MM_ERROR_NONE) {
1237 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1240 _mmcamcorder_set_state(handle, state_TO);
1242 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1243 int vconf_camera_state = 0;
1245 /* check camera state of vconf key */
1246 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1248 /* set camera state to vconf key */
1249 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_OPEN);
1251 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1252 vconf_camera_state, VCONFKEY_CAMERA_STATE_OPEN);
1255 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1257 return MM_ERROR_NONE;
1259 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1260 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1262 _ERR_CAMCORDER_CMD_PRECON:
1264 _mmcam_dbg_err("Stop fail (type %d, state %d, ret %x)",
1265 hcamcorder->type, state, ret);
1271 int _mmcamcorder_capture_start(MMHandleType handle)
1273 int ret = MM_ERROR_NONE;
1274 int state = MM_CAMCORDER_STATE_NONE;
1275 int state_FROM_0 = MM_CAMCORDER_STATE_PREPARE;
1276 int state_FROM_1 = MM_CAMCORDER_STATE_RECORDING;
1277 int state_FROM_2 = MM_CAMCORDER_STATE_PAUSED;
1278 int state_TO = MM_CAMCORDER_STATE_CAPTURING;
1280 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1285 _mmcam_dbg_err("Not initialized");
1286 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1290 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1291 _mmcam_dbg_err("Another command is running.");
1292 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1293 goto _ERR_CAMCORDER_CMD_PRECON;
1296 state = _mmcamcorder_get_state(handle);
1297 if (state != state_FROM_0 &&
1298 state != state_FROM_1 &&
1299 state != state_FROM_2) {
1300 _mmcam_dbg_err("Wrong state(%d)", state);
1301 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1302 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1305 /* Handle capture in recording case */
1306 if (state == state_FROM_1 || state == state_FROM_2) {
1307 if (hcamcorder->capture_in_recording == TRUE) {
1308 _mmcam_dbg_err("Capturing in recording (%d)", state);
1309 ret = MM_ERROR_CAMCORDER_DEVICE_BUSY;
1310 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1312 pthread_mutex_lock(&(hcamcorder->task_thread_lock));
1313 if (hcamcorder->task_thread_state == _MMCAMCORDER_TASK_THREAD_STATE_NONE) {
1314 hcamcorder->capture_in_recording = TRUE;
1315 hcamcorder->task_thread_state = _MMCAMCORDER_TASK_THREAD_STATE_CHECK_CAPTURE_IN_RECORDING;
1316 _mmcam_dbg_log("send signal for capture in recording");
1317 pthread_cond_signal(&(hcamcorder->task_thread_cond));
1318 pthread_mutex_unlock(&(hcamcorder->task_thread_lock));
1320 _mmcam_dbg_err("task thread busy : %d", hcamcorder->task_thread_state);
1321 pthread_mutex_unlock(&(hcamcorder->task_thread_lock));
1322 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1323 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1328 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_CAPTURE);
1329 if (ret != MM_ERROR_NONE) {
1330 goto _ERR_CAMCORDER_CMD;
1333 /* Do not change state when recording snapshot capture */
1334 if (state == state_FROM_0) {
1335 _mmcamcorder_set_state(handle, state_TO);
1338 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1340 /* Init break continuous shot attr */
1341 if (mm_camcorder_set_attributes(handle, NULL, "capture-break-cont-shot", 0, NULL) != MM_ERROR_NONE) {
1342 _mmcam_dbg_warn("capture-break-cont-shot set 0 failed");
1345 return MM_ERROR_NONE;
1348 if (hcamcorder->capture_in_recording) {
1349 hcamcorder->capture_in_recording = FALSE;
1352 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1353 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1355 _ERR_CAMCORDER_CMD_PRECON:
1357 _mmcam_dbg_err("Capture start fail (type %d, state %d, ret %x)",
1358 hcamcorder->type, state, ret);
1363 int _mmcamcorder_capture_stop(MMHandleType handle)
1365 int ret = MM_ERROR_NONE;
1366 int state = MM_CAMCORDER_STATE_NONE;
1367 int state_FROM = MM_CAMCORDER_STATE_CAPTURING;
1368 int state_TO = MM_CAMCORDER_STATE_PREPARE;
1369 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1374 _mmcam_dbg_err("Not initialized");
1375 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1379 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1380 _mmcam_dbg_err("Another command is running.");
1381 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1382 goto _ERR_CAMCORDER_CMD_PRECON;
1385 state = _mmcamcorder_get_state(handle);
1386 if (state != state_FROM) {
1387 _mmcam_dbg_err("Wrong state(%d)", state);
1388 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1389 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1392 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_PREVIEW_START);
1393 if (ret != MM_ERROR_NONE) {
1394 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1397 _mmcamcorder_set_state(handle, state_TO);
1399 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1401 return MM_ERROR_NONE;
1403 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1404 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1406 _ERR_CAMCORDER_CMD_PRECON:
1408 _mmcam_dbg_err("Capture stop fail (type %d, state %d, ret %x)",
1409 hcamcorder->type, state, ret);
1414 int _mmcamcorder_record(MMHandleType handle)
1416 int ret = MM_ERROR_NONE;
1417 int state = MM_CAMCORDER_STATE_NONE;
1418 int state_FROM1 = MM_CAMCORDER_STATE_PREPARE;
1419 int state_FROM2 = MM_CAMCORDER_STATE_PAUSED;
1420 int state_TO = MM_CAMCORDER_STATE_RECORDING;
1422 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1427 _mmcam_dbg_err("Not initialized");
1428 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1432 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1433 _mmcam_dbg_err("Another command is running.");
1434 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1435 goto _ERR_CAMCORDER_CMD_PRECON;
1438 state = _mmcamcorder_get_state(handle);
1439 if (state != state_FROM1 && state != state_FROM2) {
1440 _mmcam_dbg_err("Wrong state(%d)", state);
1441 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1442 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1445 /* initialize error code */
1446 hcamcorder->error_code = MM_ERROR_NONE;
1448 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_RECORD);
1449 if (ret != MM_ERROR_NONE) {
1450 /* check internal error of gstreamer */
1451 if (hcamcorder->error_code != MM_ERROR_NONE) {
1452 ret = hcamcorder->error_code;
1453 _mmcam_dbg_log("gstreamer error is occurred. return it %x", ret);
1455 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1458 _mmcamcorder_set_state(handle, state_TO);
1460 /* set camera state to vconf key */
1461 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1462 int vconf_camera_state = 0;
1464 /* get current camera state of vconf key */
1465 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1466 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_RECORDING);
1468 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1469 vconf_camera_state, VCONFKEY_CAMERA_STATE_RECORDING);
1471 int vconf_recorder_state = 0;
1473 /* get current recorder state of vconf key */
1474 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1475 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_RECORDING);
1477 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1478 vconf_recorder_state, VCONFKEY_RECORDER_STATE_RECORDING);
1481 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1483 return MM_ERROR_NONE;
1485 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1486 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1488 _ERR_CAMCORDER_CMD_PRECON:
1489 /* check internal error of gstreamer */
1490 if (hcamcorder->error_code != MM_ERROR_NONE) {
1491 ret = hcamcorder->error_code;
1492 hcamcorder->error_code = MM_ERROR_NONE;
1494 _mmcam_dbg_log("gstreamer error is occurred. return it %x", ret);
1497 _mmcam_dbg_err("Record fail (type %d, state %d, ret %x)",
1498 hcamcorder->type, state, ret);
1504 int _mmcamcorder_pause(MMHandleType handle)
1506 int ret = MM_ERROR_NONE;
1507 int state = MM_CAMCORDER_STATE_NONE;
1508 int state_FROM = MM_CAMCORDER_STATE_RECORDING;
1509 int state_TO = MM_CAMCORDER_STATE_PAUSED;
1511 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1516 _mmcam_dbg_err("Not initialized");
1517 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1521 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1522 _mmcam_dbg_err("Another command is running.");
1523 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1524 goto _ERR_CAMCORDER_CMD_PRECON;
1527 state = _mmcamcorder_get_state(handle);
1528 if (state != state_FROM) {
1529 _mmcam_dbg_err("Wrong state(%d)", state);
1530 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1531 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1534 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_PAUSE);
1535 if (ret != MM_ERROR_NONE) {
1536 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1539 _mmcamcorder_set_state(handle, state_TO);
1541 /* set camera state to vconf key */
1542 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1543 int vconf_camera_state = 0;
1545 /* get current camera state of vconf key */
1546 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1547 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_RECORDING_PAUSE);
1549 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1550 vconf_camera_state, VCONFKEY_CAMERA_STATE_RECORDING_PAUSE);
1552 int vconf_recorder_state = 0;
1554 /* get current recorder state of vconf key */
1555 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1556 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_RECORDING_PAUSE);
1558 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1559 vconf_recorder_state, VCONFKEY_RECORDER_STATE_RECORDING_PAUSE);
1562 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1564 return MM_ERROR_NONE;
1566 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1567 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1569 _ERR_CAMCORDER_CMD_PRECON:
1571 _mmcam_dbg_err("Pause fail (type %d, state %d, ret %x)",
1572 hcamcorder->type, state, ret);
1578 int _mmcamcorder_commit(MMHandleType handle)
1580 int ret = MM_ERROR_NONE;
1581 int state = MM_CAMCORDER_STATE_NONE;
1582 int state_FROM1 = MM_CAMCORDER_STATE_RECORDING;
1583 int state_FROM2 = MM_CAMCORDER_STATE_PAUSED;
1584 int state_TO = MM_CAMCORDER_STATE_PREPARE;
1586 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1591 _mmcam_dbg_err("Not initialized");
1592 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1596 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1597 _mmcam_dbg_err("Another command is running.");
1598 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1599 goto _ERR_CAMCORDER_CMD_PRECON;
1602 state = _mmcamcorder_get_state(handle);
1603 if (state != state_FROM1 && state != state_FROM2) {
1604 _mmcam_dbg_err("Wrong state(%d)", state);
1605 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1606 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1609 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_COMMIT);
1610 if (ret != MM_ERROR_NONE) {
1611 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1614 /* set camera state to vconf key */
1615 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1616 int vconf_camera_state = 0;
1618 /* get current camera state of vconf key */
1619 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1620 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_PREVIEW);
1622 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1623 vconf_camera_state, VCONFKEY_CAMERA_STATE_PREVIEW);
1625 int vconf_recorder_state = 0;
1627 /* get current recorder state of vconf key */
1628 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1629 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_CREATED);
1631 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1632 vconf_recorder_state, VCONFKEY_RECORDER_STATE_CREATED);
1635 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1637 _mmcamcorder_set_state(handle,state_TO);
1639 return MM_ERROR_NONE;
1641 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1642 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1644 _ERR_CAMCORDER_CMD_PRECON:
1646 _mmcam_dbg_err("Commit fail (type %d, state %d, ret %x)",
1647 hcamcorder->type, state, ret);
1653 int _mmcamcorder_cancel(MMHandleType handle)
1655 int ret = MM_ERROR_NONE;
1656 int state = MM_CAMCORDER_STATE_NONE;
1657 int state_FROM1 = MM_CAMCORDER_STATE_RECORDING;
1658 int state_FROM2 = MM_CAMCORDER_STATE_PAUSED;
1659 int state_TO = MM_CAMCORDER_STATE_PREPARE;
1661 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1666 _mmcam_dbg_err("Not initialized");
1667 ret = MM_ERROR_CAMCORDER_NOT_INITIALIZED;
1671 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1672 _mmcam_dbg_err("Another command is running.");
1673 ret = MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1674 goto _ERR_CAMCORDER_CMD_PRECON;
1677 state = _mmcamcorder_get_state(handle);
1678 if (state != state_FROM1 && state != state_FROM2) {
1679 _mmcam_dbg_err("Wrong state(%d)", state);
1680 ret = MM_ERROR_CAMCORDER_INVALID_STATE;
1681 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1684 ret = hcamcorder->command((MMHandleType)hcamcorder, _MMCamcorder_CMD_CANCEL);
1685 if (ret != MM_ERROR_NONE) {
1686 goto _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK;
1689 _mmcamcorder_set_state(handle, state_TO);
1691 /* set camera state to vconf key */
1692 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
1693 int vconf_camera_state = 0;
1695 /* get current camera state of vconf key */
1696 vconf_get_int(VCONFKEY_CAMERA_STATE, &vconf_camera_state);
1697 vconf_set_int(VCONFKEY_CAMERA_STATE, VCONFKEY_CAMERA_STATE_PREVIEW);
1699 _mmcam_dbg_log("VCONFKEY_CAMERA_STATE prev %d -> cur %d",
1700 vconf_camera_state, VCONFKEY_CAMERA_STATE_PREVIEW);
1702 int vconf_recorder_state = 0;
1704 /* get current recorder state of vconf key */
1705 vconf_get_int(VCONFKEY_RECORDER_STATE, &vconf_recorder_state);
1706 vconf_set_int(VCONFKEY_RECORDER_STATE, VCONFKEY_RECORDER_STATE_CREATED);
1708 _mmcam_dbg_log("VCONFKEY_RECORDER_STATE prev %d -> cur %d",
1709 vconf_recorder_state, VCONFKEY_RECORDER_STATE_CREATED);
1712 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1714 return MM_ERROR_NONE;
1716 _ERR_CAMCORDER_CMD_PRECON_AFTER_LOCK:
1717 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1719 _ERR_CAMCORDER_CMD_PRECON:
1721 _mmcam_dbg_err("Cancel fail (type %d, state %d, ret %x)",
1722 hcamcorder->type, state, ret);
1726 /* } Internal command functions */
1729 int _mmcamcorder_commit_async_end(MMHandleType handle)
1733 _mmcam_dbg_warn("_mmcamcorder_commit_async_end : MM_CAMCORDER_STATE_PREPARE");
1734 _mmcamcorder_set_state(handle, MM_CAMCORDER_STATE_PREPARE);
1736 return MM_ERROR_NONE;
1740 int _mmcamcorder_set_message_callback(MMHandleType handle, MMMessageCallback callback, void *user_data)
1742 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1744 _mmcam_dbg_log("%p", hcamcorder);
1746 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1748 if (callback == NULL) {
1749 _mmcam_dbg_warn("Message Callback is disabled, because application sets it to NULL");
1752 if (!_MMCAMCORDER_TRYLOCK_MESSAGE_CALLBACK(hcamcorder)) {
1753 _mmcam_dbg_warn("Application's message callback is running now");
1754 return MM_ERROR_CAMCORDER_INVALID_CONDITION;
1757 /* set message callback to message handle */
1758 hcamcorder->msg_cb = callback;
1759 hcamcorder->msg_cb_param = user_data;
1761 _MMCAMCORDER_UNLOCK_MESSAGE_CALLBACK(hcamcorder);
1763 return MM_ERROR_NONE;
1767 int _mmcamcorder_set_video_stream_callback(MMHandleType handle, mm_camcorder_video_stream_callback callback, void *user_data)
1769 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1771 /*_mmcam_dbg_log("");*/
1773 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1775 if (callback == NULL) {
1776 _mmcam_dbg_warn("Video Stream Callback is disabled, because application sets it to NULL");
1779 if (!_MMCAMCORDER_TRYLOCK_VSTREAM_CALLBACK(hcamcorder)) {
1780 _mmcam_dbg_warn("Application's video stream callback is running now");
1781 return MM_ERROR_CAMCORDER_INVALID_CONDITION;
1784 hcamcorder->vstream_cb = callback;
1785 hcamcorder->vstream_cb_param = user_data;
1787 _MMCAMCORDER_UNLOCK_VSTREAM_CALLBACK(hcamcorder);
1789 return MM_ERROR_NONE;
1793 int _mmcamcorder_set_audio_stream_callback(MMHandleType handle, mm_camcorder_audio_stream_callback callback, void *user_data)
1795 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1799 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1801 if (callback == NULL) {
1802 _mmcam_dbg_warn("Audio Stream Callback is disabled, because application sets it to NULL");
1805 if (!_MMCAMCORDER_TRYLOCK_ASTREAM_CALLBACK(hcamcorder)) {
1806 _mmcam_dbg_warn("Application's audio stream callback is running now");
1807 return MM_ERROR_CAMCORDER_INVALID_CONDITION;
1810 hcamcorder->astream_cb = callback;
1811 hcamcorder->astream_cb_param = user_data;
1813 _MMCAMCORDER_UNLOCK_ASTREAM_CALLBACK(hcamcorder);
1815 return MM_ERROR_NONE;
1819 int _mmcamcorder_set_video_capture_callback(MMHandleType handle, mm_camcorder_video_capture_callback callback, void *user_data)
1821 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1825 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1827 if (callback == NULL) {
1828 _mmcam_dbg_warn("Video Capture Callback is disabled, because application sets it to NULLL");
1831 if (!_MMCAMCORDER_TRYLOCK_VCAPTURE_CALLBACK(hcamcorder)) {
1832 _mmcam_dbg_warn("Application's video capture callback is running now");
1833 return MM_ERROR_CAMCORDER_INVALID_CONDITION;
1836 hcamcorder->vcapture_cb = callback;
1837 hcamcorder->vcapture_cb_param = user_data;
1839 _MMCAMCORDER_UNLOCK_VCAPTURE_CALLBACK(hcamcorder);
1841 return MM_ERROR_NONE;
1844 int _mmcamcorder_get_current_state(MMHandleType handle)
1846 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
1850 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1852 return _mmcamcorder_get_state(handle);
1855 int _mmcamcorder_init_focusing(MMHandleType handle)
1858 int state = MM_CAMCORDER_STATE_NONE;
1859 int focus_mode = MM_CAMCORDER_FOCUS_MODE_NONE;
1860 int af_range = MM_CAMCORDER_AUTO_FOCUS_NORMAL;
1861 int sensor_focus_mode = 0;
1862 int sensor_af_range = 0;
1863 int current_focus_mode = 0;
1864 int current_af_range = 0;
1865 mmf_camcorder_t *hcamcorder = NULL;
1866 _MMCamcorderSubContext *sc = NULL;
1867 GstCameraControl *control = NULL;
1871 hcamcorder = MMF_CAMCORDER(handle);
1872 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1874 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
1875 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1877 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
1878 _mmcam_dbg_err("Another command is running.");
1879 return MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1882 state = _mmcamcorder_get_state(handle);
1884 if (state == MM_CAMCORDER_STATE_CAPTURING ||
1885 state < MM_CAMCORDER_STATE_PREPARE) {
1886 _mmcam_dbg_err( "Not proper state. state[%d]", state );
1887 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1888 return MM_ERROR_CAMCORDER_INVALID_STATE;
1891 if (!GST_IS_CAMERA_CONTROL(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst)) {
1892 _mmcam_dbg_log("Can't cast Video source into camera control.");
1893 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1894 return MM_ERROR_NONE;
1897 control = GST_CAMERA_CONTROL (sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
1898 if (control == NULL) {
1899 _mmcam_dbg_err("cast CAMERA_CONTROL failed");
1900 return MM_ERROR_CAMCORDER_INTERNAL;
1903 ret = gst_camera_control_stop_auto_focus(control);
1905 _mmcam_dbg_err("Auto focusing stop fail.");
1906 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1907 return MM_ERROR_CAMCORDER_DEVICE_IO;
1910 /* Initialize lens position */
1911 mm_camcorder_get_attributes(handle, NULL,
1912 MMCAM_CAMERA_FOCUS_MODE, &focus_mode,
1913 MMCAM_CAMERA_AF_SCAN_RANGE, &af_range,
1915 sensor_af_range = _mmcamcorder_convert_msl_to_sensor(handle, MM_CAM_CAMERA_AF_SCAN_RANGE, af_range);
1916 sensor_focus_mode = _mmcamcorder_convert_msl_to_sensor(handle, MM_CAM_CAMERA_FOCUS_MODE, focus_mode);
1918 gst_camera_control_get_focus(control, ¤t_focus_mode, ¤t_af_range);
1920 if (current_focus_mode != sensor_focus_mode ||
1921 current_af_range != sensor_af_range) {
1922 ret = gst_camera_control_set_focus(control, sensor_focus_mode, sensor_af_range);
1924 _mmcam_dbg_log("No need to init FOCUS [mode:%d, range:%d]", focus_mode, af_range );
1928 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
1931 _mmcam_dbg_log("Lens init success.");
1932 return MM_ERROR_NONE;
1934 _mmcam_dbg_err("Lens init fail.");
1935 return MM_ERROR_CAMCORDER_DEVICE_IO;
1939 int _mmcamcorder_adjust_focus(MMHandleType handle, int direction)
1942 int focus_mode = MM_CAMCORDER_FOCUS_MODE_NONE;
1943 int ret = MM_ERROR_UNKNOWN;
1944 char *err_attr_name = NULL;
1946 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
1947 mmf_return_val_if_fail(direction, MM_ERROR_CAMCORDER_INVALID_ARGUMENT);
1949 /*_mmcam_dbg_log("");*/
1951 if (!_MMCAMCORDER_TRYLOCK_CMD(handle)) {
1952 _mmcam_dbg_err("Another command is running.");
1953 return MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
1956 state = _mmcamcorder_get_state(handle);
1957 if (state == MM_CAMCORDER_STATE_CAPTURING ||
1958 state < MM_CAMCORDER_STATE_PREPARE) {
1959 _mmcam_dbg_err("Not proper state. state[%d]", state);
1960 _MMCAMCORDER_UNLOCK_CMD(handle);
1961 return MM_ERROR_CAMCORDER_INVALID_STATE;
1964 /* TODO : call a auto or manual focus function */
1965 ret = mm_camcorder_get_attributes(handle, &err_attr_name,
1966 MMCAM_CAMERA_FOCUS_MODE, &focus_mode,
1968 if (ret != MM_ERROR_NONE) {
1969 _mmcam_dbg_warn("Get focus-mode fail. (%s:%x)", err_attr_name, ret);
1970 SAFE_FREE (err_attr_name);
1971 _MMCAMCORDER_UNLOCK_CMD(handle);
1975 if (focus_mode == MM_CAMCORDER_FOCUS_MODE_MANUAL) {
1976 ret = _mmcamcorder_adjust_manual_focus(handle, direction);
1977 } else if (focus_mode == MM_CAMCORDER_FOCUS_MODE_AUTO ||
1978 focus_mode == MM_CAMCORDER_FOCUS_MODE_TOUCH_AUTO ||
1979 focus_mode == MM_CAMCORDER_FOCUS_MODE_CONTINUOUS) {
1980 ret = _mmcamcorder_adjust_auto_focus(handle);
1982 _mmcam_dbg_err("It doesn't adjust focus. Focusing mode(%d)", focus_mode);
1983 ret = MM_ERROR_CAMCORDER_NOT_SUPPORTED;
1986 _MMCAMCORDER_UNLOCK_CMD(handle);
1991 int _mmcamcorder_adjust_manual_focus(MMHandleType handle, int direction)
1996 int focus_level = 0;
1997 float unit_level = 0;
1998 GstCameraControl *control = NULL;
1999 _MMCamcorderSubContext *sc = NULL;
2000 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2004 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2005 mmf_return_val_if_fail(_MMFCAMCORDER_FOCUS_TOTAL_LEVEL != 1, MM_ERROR_CAMCORDER_NOT_SUPPORTED);
2006 mmf_return_val_if_fail((direction >= MM_CAMCORDER_MF_LENS_DIR_FORWARD) &&
2007 (direction <= MM_CAMCORDER_MF_LENS_DIR_BACKWARD),
2008 MM_ERROR_CAMCORDER_INVALID_ARGUMENT );
2010 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2011 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2013 if (!GST_IS_CAMERA_CONTROL(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst)) {
2014 _mmcam_dbg_log("Can't cast Video source into camera control.");
2015 return MM_ERROR_NONE;
2018 control = GST_CAMERA_CONTROL (sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
2019 if (control == NULL) {
2020 _mmcam_dbg_err("cast CAMERA_CONTROL failed");
2021 return MM_ERROR_CAMCORDER_INTERNAL;
2024 /* TODO : get max, min level */
2025 if (max_level - min_level + 1 < _MMFCAMCORDER_FOCUS_TOTAL_LEVEL) {
2026 _mmcam_dbg_warn("Total level of manual focus of MMF is greater than that of the camera driver.");
2029 unit_level = ((float)max_level - (float)min_level)/(float)(_MMFCAMCORDER_FOCUS_TOTAL_LEVEL - 1);
2031 if (!gst_camera_control_get_focus_level(control, &cur_level)) {
2032 _mmcam_dbg_err("Can't get current level of manual focus.");
2033 return MM_ERROR_CAMCORDER_DEVICE_IO;
2036 //TODO : adjust unit level value
2037 if (direction == MM_CAMCORDER_MF_LENS_DIR_FORWARD) {
2038 focus_level = cur_level + unit_level;
2039 } else if (direction == MM_CAMCORDER_MF_LENS_DIR_BACKWARD) {
2040 focus_level = cur_level - unit_level;
2043 if (focus_level > max_level) {
2044 focus_level = max_level;
2045 } else if (focus_level < min_level) {
2046 focus_level = min_level;
2049 if (!gst_camera_control_set_focus_level(control, focus_level)) {
2050 _mmcam_dbg_err("Manual focusing fail.");
2051 return MM_ERROR_CAMCORDER_DEVICE_IO;
2054 return MM_ERROR_NONE;
2058 int _mmcamcorder_adjust_auto_focus(MMHandleType handle)
2061 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2062 GstCameraControl *control = NULL;
2063 _MMCamcorderSubContext *sc = NULL;
2065 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2067 /*_mmcam_dbg_log("");*/
2069 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2071 if (!GST_IS_CAMERA_CONTROL(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst)) {
2072 _mmcam_dbg_log("Can't cast Video source into camera control.");
2073 return MM_ERROR_NONE;
2076 control = GST_CAMERA_CONTROL (sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
2079 ret = gst_camera_control_start_auto_focus(control);
2081 _mmcam_dbg_err("cast CAMERA_CONTROL failed");
2086 _mmcam_dbg_log("Auto focusing start success.");
2087 return MM_ERROR_NONE;
2089 _mmcam_dbg_err("Auto focusing start fail.");
2090 return MM_ERROR_CAMCORDER_DEVICE_IO;
2094 int _mmcamcorder_stop_focusing(MMHandleType handle)
2096 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2097 _MMCamcorderSubContext *sc = NULL;
2100 GstCameraControl *control = NULL;
2102 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2104 /*_mmcam_dbg_log("");*/
2106 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2108 if (!_MMCAMCORDER_TRYLOCK_CMD(hcamcorder)) {
2109 _mmcam_dbg_err("Another command is running.");
2110 return MM_ERROR_CAMCORDER_CMD_IS_RUNNING;
2113 state = _mmcamcorder_get_state(handle);
2114 if (state == MM_CAMCORDER_STATE_CAPTURING ||
2115 state < MM_CAMCORDER_STATE_PREPARE) {
2116 _mmcam_dbg_err( "Not proper state. state[%d]", state );
2117 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
2118 return MM_ERROR_CAMCORDER_INVALID_STATE;
2121 if (!GST_IS_CAMERA_CONTROL(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst)) {
2122 _mmcam_dbg_log("Can't cast Video source into camera control.");
2123 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
2124 return MM_ERROR_NONE;
2127 control = GST_CAMERA_CONTROL(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
2129 ret = gst_camera_control_stop_auto_focus(control);
2131 _mmcam_dbg_err("cast CAMERA_CONTROL failed");
2135 _MMCAMCORDER_UNLOCK_CMD(hcamcorder);
2138 _mmcam_dbg_log("Auto focusing stop success.");
2139 return MM_ERROR_NONE;
2141 _mmcam_dbg_err("Auto focusing stop fail.");
2142 return MM_ERROR_CAMCORDER_DEVICE_IO;
2147 /*-----------------------------------------------
2148 | CAMCORDER INTERNAL LOCAL |
2149 -----------------------------------------------*/
2151 __mmcamcorder_gstreamer_init(camera_conf * conf)
2153 static const int max_argc = 10;
2157 gchar **argv = NULL;
2159 gboolean ret = FALSE;
2160 type_string_array *GSTInitOption = NULL;
2162 mmf_return_val_if_fail(conf, FALSE);
2167 argc = malloc(sizeof(int));
2168 argv = malloc(sizeof(gchar *) * max_argc);
2170 if (!argc || !argv) {
2174 memset(argv, 0, sizeof(gchar *) * max_argc);
2178 argv[0] = g_strdup("mmcamcorder");
2181 _mmcamcorder_conf_get_value_string_array(conf,
2182 CONFIGURE_CATEGORY_MAIN_GENERAL,
2185 if (GSTInitOption != NULL && GSTInitOption->value) {
2186 cnt_str = GSTInitOption->count;
2187 for( ; *argc < max_argc && *argc <= cnt_str ; (*argc)++ )
2189 argv[*argc] = g_strdup(GSTInitOption->value[(*argc)-1]);
2193 _mmcam_dbg_log("initializing gstreamer with following parameter[argc:%d]", *argc);
2195 for (i = 0; i < *argc; i++) {
2196 _mmcam_dbg_log("argv[%d] : %s", i, argv[i]);
2199 /* initializing gstreamer */
2200 ret = gst_init_check (argc, &argv, &err);
2202 _mmcam_dbg_err("Could not initialize GStreamer: %s ",
2203 err ? err->message : "unknown error occurred");
2210 for (i = 0; i < *argc; i++) {
2230 _mmcam_dbg_err("failed to initialize gstreamer");
2246 int _mmcamcorder_get_state(MMHandleType handle)
2249 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2251 mmf_return_val_if_fail(hcamcorder, -1);
2253 _MMCAMCORDER_LOCK_STATE(handle);
2255 state = hcamcorder->state;
2256 /*_mmcam_dbg_log("state=%d",state);*/
2258 _MMCAMCORDER_UNLOCK_STATE(handle);
2264 void _mmcamcorder_set_state(MMHandleType handle, int state)
2267 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2268 _MMCamcorderMsgItem msg;
2270 mmf_return_if_fail(hcamcorder);
2272 /*_mmcam_dbg_log("");*/
2274 _MMCAMCORDER_LOCK_STATE(handle);
2276 old_state = hcamcorder->state;
2277 if(old_state != state) {
2278 hcamcorder->state = state;
2279 hcamcorder->target_state = state;
2281 _mmcam_dbg_log("set state[%d] and send state-changed message", state);
2283 msg.id = MM_MESSAGE_CAMCORDER_STATE_CHANGED;
2284 msg.param.state.code = MM_ERROR_NONE;
2285 msg.param.state.previous = old_state;
2286 msg.param.state.current = state;
2288 /*_mmcam_dbg_log("_mmcamcorder_send_message : msg : %p, id:%x", &msg, msg.id);*/
2289 _mmcamcorder_send_message(handle, &msg);
2292 _MMCAMCORDER_UNLOCK_STATE(handle);
2298 int _mmcamcorder_get_async_state(MMHandleType handle)
2301 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2303 _MMCAMCORDER_LOCK_STATE(handle);
2304 state = hcamcorder->target_state;
2306 _MMCAMCORDER_UNLOCK_STATE(handle);
2312 _MMCamcorderSubContext *_mmcamcorder_alloc_subcontext(int type)
2315 _MMCamcorderSubContext *sc = NULL;
2317 /*_mmcam_dbg_log("");*/
2319 /* alloc container */
2320 sc = (_MMCamcorderSubContext *)malloc(sizeof(_MMCamcorderSubContext));
2321 mmf_return_val_if_fail(sc != NULL, NULL);
2324 memset(sc, 0x00, sizeof(_MMCamcorderSubContext));
2326 sc->element_num = _MMCAMCORDER_PIPELINE_ELEMENT_NUM;
2327 sc->encode_element_num = _MMCAMCORDER_ENCODE_PIPELINE_ELEMENT_NUM;
2329 /* alloc info for each mode */
2331 case MM_CAMCORDER_MODE_AUDIO:
2332 sc->info_audio = malloc( sizeof(_MMCamcorderAudioInfo));
2333 if(!sc->info_audio) {
2334 _mmcam_dbg_err("Failed to alloc info structure");
2335 goto ALLOC_SUBCONTEXT_FAILED;
2337 memset(sc->info_audio, 0x00, sizeof(_MMCamcorderAudioInfo));
2339 case MM_CAMCORDER_MODE_VIDEO_CAPTURE:
2341 sc->info_image = malloc( sizeof(_MMCamcorderImageInfo));
2342 if(!sc->info_image) {
2343 _mmcam_dbg_err("Failed to alloc info structure");
2344 goto ALLOC_SUBCONTEXT_FAILED;
2346 memset(sc->info_image, 0x00, sizeof(_MMCamcorderImageInfo));
2348 /* init sound status */
2349 sc->info_image->sound_status = _SOUND_STATUS_INIT;
2351 sc->info_video = malloc( sizeof(_MMCamcorderVideoInfo));
2352 if(!sc->info_video) {
2353 _mmcam_dbg_err("Failed to alloc info structure");
2354 goto ALLOC_SUBCONTEXT_FAILED;
2356 memset(sc->info_video, 0x00, sizeof(_MMCamcorderVideoInfo));
2357 pthread_mutex_init(&(sc->info_video->size_check_lock), NULL);
2361 /* alloc element array */
2362 sc->element = (_MMCamcorderGstElement *)malloc(sizeof(_MMCamcorderGstElement) * sc->element_num);
2364 _mmcam_dbg_err("Failed to alloc element structure");
2365 goto ALLOC_SUBCONTEXT_FAILED;
2368 sc->encode_element = (_MMCamcorderGstElement *)malloc(sizeof(_MMCamcorderGstElement) * sc->encode_element_num);
2369 if(!sc->encode_element) {
2370 _mmcam_dbg_err("Failed to alloc encode element structure");
2371 goto ALLOC_SUBCONTEXT_FAILED;
2374 for (i = 0 ; i < sc->element_num ; i++) {
2375 sc->element[i].id = _MMCAMCORDER_NONE;
2376 sc->element[i].gst = NULL;
2379 for (i = 0 ; i < sc->encode_element_num ; i++) {
2380 sc->encode_element[i].id = _MMCAMCORDER_NONE;
2381 sc->encode_element[i].gst = NULL;
2384 sc->fourcc = 0x80000000;
2385 sc->cam_stability_count = 0;
2386 sc->drop_vframe = 0;
2387 sc->pass_first_vframe = 0;
2388 sc->is_modified_rate = FALSE;
2392 ALLOC_SUBCONTEXT_FAILED:
2394 if (sc->info_audio) {
2395 free(sc->info_audio);
2396 sc->info_audio = NULL;
2398 if (sc->info_image) {
2399 free(sc->info_image);
2400 sc->info_image = NULL;
2402 if (sc->info_video) {
2403 pthread_mutex_destroy(&(sc->info_video->size_check_lock));
2404 free(sc->info_video);
2405 sc->info_video = NULL;
2411 if (sc->encode_element) {
2412 free(sc->encode_element);
2413 sc->encode_element = NULL;
2423 void _mmcamcorder_dealloc_subcontext(_MMCamcorderSubContext *sc)
2429 _mmcam_dbg_log("release element");
2434 if (sc->encode_element) {
2435 _mmcam_dbg_log("release encode_element");
2436 free(sc->encode_element);
2437 sc->encode_element = NULL;
2440 if (sc->info_image) {
2441 _mmcam_dbg_log("release info_image");
2442 free(sc->info_image);
2443 sc->info_image = NULL;
2446 if (sc->info_video) {
2447 _mmcam_dbg_log("release info_video");
2448 if (sc->info_video->filename) {
2449 free(sc->info_video->filename);
2450 sc->info_video->filename = NULL;
2452 pthread_mutex_destroy(&(sc->info_video->size_check_lock));
2453 free(sc->info_video);
2454 sc->info_video = NULL;
2457 if (sc->info_audio) {
2458 _mmcam_dbg_log("release info_audio");
2459 if (sc->info_audio->filename) {
2460 free(sc->info_audio->filename);
2461 sc->info_audio->filename = NULL;
2463 free(sc->info_audio);
2464 sc->info_audio = NULL;
2475 int _mmcamcorder_set_functions(MMHandleType handle, int type)
2477 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2479 /*_mmcam_dbg_log("");*/
2482 case MM_CAMCORDER_MODE_AUDIO:
2483 hcamcorder->command = _mmcamcorder_audio_command;
2485 case MM_CAMCORDER_MODE_VIDEO_CAPTURE:
2487 hcamcorder->command = _mmcamcorder_video_capture_command;
2491 return MM_ERROR_NONE;
2495 gboolean _mmcamcorder_pipeline_cb_message(GstBus *bus, GstMessage *message, gpointer data)
2497 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(data);
2498 _MMCamcorderSubContext *sc = NULL;
2500 mmf_return_val_if_fail(hcamcorder, FALSE);
2501 mmf_return_val_if_fail(message, FALSE);
2502 //_mmcam_dbg_log("message type=(%d)", GST_MESSAGE_TYPE(message));
2504 switch (GST_MESSAGE_TYPE(message)) {
2505 case GST_MESSAGE_UNKNOWN:
2506 _mmcam_dbg_log("GST_MESSAGE_UNKNOWN");
2508 case GST_MESSAGE_EOS:
2510 _mmcam_dbg_log ("Got EOS from element \"%s\".",
2511 GST_STR_NULL(GST_ELEMENT_NAME(GST_MESSAGE_SRC(message))));
2513 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2514 mmf_return_val_if_fail(sc, TRUE);
2516 if (hcamcorder->type != MM_CAMCORDER_MODE_AUDIO) {
2517 mmf_return_val_if_fail(sc->info_video, TRUE);
2518 if (sc->info_video->b_commiting) {
2519 _mmcamcorder_video_handle_eos((MMHandleType)hcamcorder);
2522 mmf_return_val_if_fail(sc->info_audio, TRUE);
2523 if (sc->info_audio->b_commiting) {
2524 _mmcamcorder_audio_handle_eos((MMHandleType)hcamcorder);
2528 sc->bget_eos = TRUE;
2532 case GST_MESSAGE_ERROR:
2536 gst_message_parse_error(message, &err, &debug);
2538 _mmcam_dbg_err ("GSTERR: %s", err->message);
2539 _mmcam_dbg_err ("Error Debug: %s", debug);
2541 __mmcamcorder_handle_gst_error((MMHandleType)hcamcorder, message, err);
2547 case GST_MESSAGE_WARNING:
2551 gst_message_parse_warning (message, &err, &debug);
2553 _mmcam_dbg_warn("GSTWARN: %s", err->message);
2555 __mmcamcorder_handle_gst_warning((MMHandleType)hcamcorder, message, err);
2561 case GST_MESSAGE_INFO:
2562 _mmcam_dbg_log("GST_MESSAGE_INFO");
2564 case GST_MESSAGE_TAG:
2565 _mmcam_dbg_log("GST_MESSAGE_TAG");
2567 case GST_MESSAGE_BUFFERING:
2568 _mmcam_dbg_log("GST_MESSAGE_BUFFERING");
2570 case GST_MESSAGE_STATE_CHANGED:
2572 const GValue *vnewstate;
2574 GstElement *pipeline = NULL;
2576 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2577 if ((sc) && (sc->element)) {
2578 if (sc->element[_MMCAMCORDER_MAIN_PIPE].gst) {
2579 pipeline = sc->element[_MMCAMCORDER_MAIN_PIPE].gst;
2580 if (message->src == (GstObject*)pipeline) {
2581 vnewstate = gst_structure_get_value(gst_message_get_structure(message), "new-state");
2582 newstate = (GstState)vnewstate->data[0].v_int;
2583 _mmcam_dbg_log("GST_MESSAGE_STATE_CHANGED[%s]",gst_element_state_get_name(newstate));
2589 case GST_MESSAGE_STATE_DIRTY:
2590 _mmcam_dbg_log("GST_MESSAGE_STATE_DIRTY");
2592 case GST_MESSAGE_STEP_DONE:
2593 _mmcam_dbg_log("GST_MESSAGE_STEP_DONE");
2595 case GST_MESSAGE_CLOCK_PROVIDE:
2596 _mmcam_dbg_log("GST_MESSAGE_CLOCK_PROVIDE");
2598 case GST_MESSAGE_CLOCK_LOST:
2599 _mmcam_dbg_log("GST_MESSAGE_CLOCK_LOST");
2601 case GST_MESSAGE_NEW_CLOCK:
2603 GstClock *pipe_clock = NULL;
2604 gst_message_parse_new_clock(message, &pipe_clock);
2605 /*_mmcam_dbg_log("GST_MESSAGE_NEW_CLOCK : %s", (clock ? GST_OBJECT_NAME (clock) : "NULL"));*/
2608 case GST_MESSAGE_STRUCTURE_CHANGE:
2609 _mmcam_dbg_log("GST_MESSAGE_STRUCTURE_CHANGE");
2611 case GST_MESSAGE_STREAM_STATUS:
2612 /*_mmcam_dbg_log("GST_MESSAGE_STREAM_STATUS");*/
2614 case GST_MESSAGE_APPLICATION:
2615 _mmcam_dbg_log("GST_MESSAGE_APPLICATION");
2617 case GST_MESSAGE_ELEMENT:
2618 /*_mmcam_dbg_log("GST_MESSAGE_ELEMENT");*/
2620 case GST_MESSAGE_SEGMENT_START:
2621 _mmcam_dbg_log("GST_MESSAGE_SEGMENT_START");
2623 case GST_MESSAGE_SEGMENT_DONE:
2624 _mmcam_dbg_log("GST_MESSAGE_SEGMENT_DONE");
2626 case GST_MESSAGE_DURATION_CHANGED:
2627 _mmcam_dbg_log("GST_MESSAGE_DURATION_CHANGED");
2629 case GST_MESSAGE_LATENCY:
2630 _mmcam_dbg_log("GST_MESSAGE_LATENCY");
2632 case GST_MESSAGE_ASYNC_START:
2633 _mmcam_dbg_log("GST_MESSAGE_ASYNC_START");
2635 case GST_MESSAGE_ASYNC_DONE:
2636 /*_mmcam_dbg_log("GST_MESSAGE_ASYNC_DONE");*/
2638 case GST_MESSAGE_ANY:
2639 _mmcam_dbg_log("GST_MESSAGE_ANY");
2641 case GST_MESSAGE_QOS:
2642 // _mmcam_dbg_log("GST_MESSAGE_QOS");
2645 _mmcam_dbg_log("not handled message type=(%d)", GST_MESSAGE_TYPE(message));
2653 GstBusSyncReply _mmcamcorder_pipeline_bus_sync_callback(GstBus *bus, GstMessage *message, gpointer data)
2655 GstElement *element = NULL;
2657 gchar *debug_info = NULL;
2659 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(data);
2660 _MMCamcorderSubContext *sc = NULL;
2662 mmf_return_val_if_fail(hcamcorder, GST_BUS_PASS);
2663 mmf_return_val_if_fail(message, GST_BUS_PASS);
2665 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2666 mmf_return_val_if_fail(sc, GST_BUS_PASS);
2668 if (GST_MESSAGE_TYPE(message) == GST_MESSAGE_ERROR) {
2669 /* parse error message */
2670 gst_message_parse_error(message, &err, &debug_info);
2673 _mmcam_dbg_err("GST ERROR : %s", debug_info);
2679 _mmcam_dbg_warn("failed to parse error message");
2680 return GST_BUS_PASS;
2683 /* set videosrc element to compare */
2684 element = GST_ELEMENT_CAST(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
2686 /* check domain[RESOURCE] and element[VIDEOSRC] */
2687 if (err->domain == GST_RESOURCE_ERROR &&
2688 GST_ELEMENT_CAST(message->src) == element) {
2689 switch (err->code) {
2690 case GST_RESOURCE_ERROR_BUSY:
2691 _mmcam_dbg_err("Camera device [busy]");
2692 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_BUSY;
2694 case GST_RESOURCE_ERROR_OPEN_WRITE:
2695 _mmcam_dbg_err("Camera device [open failed]");
2696 hcamcorder->error_code = MM_ERROR_COMMON_INVALID_PERMISSION;
2697 //sc->error_code = MM_ERROR_CAMCORDER_DEVICE_OPEN; // SECURITY PART REQUEST PRIVILEGE
2699 case GST_RESOURCE_ERROR_OPEN_READ_WRITE:
2700 _mmcam_dbg_err("Camera device [open failed]");
2701 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_OPEN;
2703 case GST_RESOURCE_ERROR_OPEN_READ:
2704 _mmcam_dbg_err("Camera device [register trouble]");
2705 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_REG_TROUBLE;
2707 case GST_RESOURCE_ERROR_NOT_FOUND:
2708 _mmcam_dbg_err("Camera device [device not found]");
2709 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_NOT_FOUND;
2711 case GST_RESOURCE_ERROR_TOO_LAZY:
2712 _mmcam_dbg_err("Camera device [timeout]");
2713 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_TIMEOUT;
2715 case GST_RESOURCE_ERROR_SETTINGS:
2716 _mmcam_dbg_err("Camera device [not supported]");
2717 hcamcorder->error_code = MM_ERROR_CAMCORDER_NOT_SUPPORTED;
2719 case GST_RESOURCE_ERROR_FAILED:
2720 _mmcam_dbg_err("Camera device [working failed].");
2721 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE_IO;
2724 _mmcam_dbg_err("Camera device [General(%d)]", err->code);
2725 hcamcorder->error_code = MM_ERROR_CAMCORDER_DEVICE;
2729 hcamcorder->error_occurs = TRUE;
2734 /* store error code and drop this message if cmd is running */
2735 if (hcamcorder->error_code != MM_ERROR_NONE) {
2736 _MMCamcorderMsgItem msg;
2738 /* post error to application */
2739 hcamcorder->error_occurs = TRUE;
2740 msg.id = MM_MESSAGE_CAMCORDER_ERROR;
2741 msg.param.code = hcamcorder->error_code;
2742 _mmcamcorder_send_message((MMHandleType)hcamcorder, &msg);
2746 } else if (GST_MESSAGE_TYPE(message) == GST_MESSAGE_ELEMENT) {
2747 _MMCamcorderMsgItem msg;
2749 if (gst_structure_has_name(gst_message_get_structure(message), "avsysvideosrc-AF") ||
2750 gst_structure_has_name(gst_message_get_structure(message), "camerasrc-AF")) {
2751 int focus_state = 0;
2753 gst_structure_get_int(gst_message_get_structure(message), "focus-state", &focus_state);
2754 _mmcam_dbg_log("Focus State:%d", focus_state);
2756 msg.id = MM_MESSAGE_CAMCORDER_FOCUS_CHANGED;
2757 msg.param.code = focus_state;
2758 _mmcamcorder_send_message((MMHandleType)hcamcorder, &msg);
2761 } else if (gst_structure_has_name(gst_message_get_structure(message), "camerasrc-HDR")) {
2765 if (gst_structure_get_int(gst_message_get_structure(message), "progress", &progress)) {
2766 gst_structure_get_int(gst_message_get_structure(message), "status", &status);
2767 _mmcam_dbg_log("HDR progress %d percent, status %d", progress, status);
2769 msg.id = MM_MESSAGE_CAMCORDER_HDR_PROGRESS;
2770 msg.param.code = progress;
2771 _mmcamcorder_send_message((MMHandleType)hcamcorder, &msg);
2775 } else if (gst_structure_has_name(gst_message_get_structure(message), "camerasrc-FD")) {
2777 const GValue *g_value = gst_structure_get_value(gst_message_get_structure(message), "face-info");;
2778 GstCameraControlFaceDetectInfo *fd_info = NULL;
2779 MMCamFaceDetectInfo *cam_fd_info = NULL;
2782 fd_info = (GstCameraControlFaceDetectInfo *)g_value_get_pointer(g_value);
2785 if (fd_info == NULL) {
2786 _mmcam_dbg_warn("fd_info is NULL");
2790 cam_fd_info = (MMCamFaceDetectInfo *)malloc(sizeof(MMCamFaceDetectInfo));
2791 if (cam_fd_info == NULL) {
2792 _mmcam_dbg_warn("cam_fd_info alloc failed");
2800 /* set total face count */
2801 cam_fd_info->num_of_faces = fd_info->num_of_faces;
2803 if (cam_fd_info->num_of_faces > 0) {
2804 cam_fd_info->face_info = (MMCamFaceInfo *)malloc(sizeof(MMCamFaceInfo) * cam_fd_info->num_of_faces);
2805 if (cam_fd_info->face_info) {
2806 /* set information of each face */
2807 for (i = 0 ; i < fd_info->num_of_faces ; i++) {
2808 cam_fd_info->face_info[i].id = fd_info->face_info[i].id;
2809 cam_fd_info->face_info[i].score = fd_info->face_info[i].score;
2810 cam_fd_info->face_info[i].rect.x = fd_info->face_info[i].rect.x;
2811 cam_fd_info->face_info[i].rect.y = fd_info->face_info[i].rect.y;
2812 cam_fd_info->face_info[i].rect.width = fd_info->face_info[i].rect.width;
2813 cam_fd_info->face_info[i].rect.height = fd_info->face_info[i].rect.height;
2815 _mmcam_dbg_log("id %d, score %d, [%d,%d,%dx%d]",
2816 fd_info->face_info[i].id,
2817 fd_info->face_info[i].score,
2818 fd_info->face_info[i].rect.x,
2819 fd_info->face_info[i].rect.y,
2820 fd_info->face_info[i].rect.width,
2821 fd_info->face_info[i].rect.height);
2825 _mmcam_dbg_warn("MMCamFaceInfo alloc failed");
2827 /* free allocated memory that is not sent */
2832 cam_fd_info->face_info = NULL;
2836 /* send message - cam_fd_info should be freed by application */
2837 msg.id = MM_MESSAGE_CAMCORDER_FACE_DETECT_INFO;
2838 msg.param.data = cam_fd_info;
2839 msg.param.size = sizeof(MMCamFaceDetectInfo);
2842 _mmcamcorder_send_message((MMHandleType)hcamcorder, &msg);
2845 /* free fd_info allocated by plugin */
2850 } else if (gst_structure_has_name(gst_message_get_structure(message), "camerasrc-Capture")) {
2851 int capture_done = FALSE;
2853 if (gst_structure_get_int(gst_message_get_structure(message), "capture-done", &capture_done)) {
2854 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2855 if (sc && sc->info_image) {
2856 /* play capture sound */
2857 _mmcamcorder_sound_solo_play((MMHandleType)hcamcorder, _MMCAMCORDER_FILEPATH_CAPTURE_SND, FALSE);
2865 return GST_BUS_PASS;
2867 gst_message_unref(message);
2870 return GST_BUS_DROP;
2874 GstBusSyncReply _mmcamcorder_audio_pipeline_bus_sync_callback(GstBus *bus, GstMessage *message, gpointer data)
2876 GstElement *element = NULL;
2878 gchar *debug_info = NULL;
2880 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(data);
2881 _MMCamcorderSubContext *sc = NULL;
2883 mmf_return_val_if_fail(hcamcorder, GST_BUS_PASS);
2884 mmf_return_val_if_fail(message, GST_BUS_PASS);
2886 sc = MMF_CAMCORDER_SUBCONTEXT(hcamcorder);
2887 mmf_return_val_if_fail(sc, GST_BUS_PASS);
2889 if (GST_MESSAGE_TYPE(message) == GST_MESSAGE_ERROR) {
2890 /* parse error message */
2891 gst_message_parse_error(message, &err, &debug_info);
2894 _mmcam_dbg_err("GST ERROR : %s", debug_info);
2900 _mmcam_dbg_warn("failed to parse error message");
2901 return GST_BUS_PASS;
2904 /* set videosrc element to compare */
2905 element = GST_ELEMENT_CAST(sc->encode_element[_MMCAMCORDER_AUDIOSRC_SRC].gst);
2907 /* check domain[RESOURCE] and element[VIDEOSRC] */
2908 if (err->domain == GST_RESOURCE_ERROR &&
2909 GST_ELEMENT_CAST(message->src) == element) {
2910 _MMCamcorderMsgItem msg;
2911 switch (err->code) {
2912 case GST_RESOURCE_ERROR_OPEN_READ_WRITE:
2913 case GST_RESOURCE_ERROR_OPEN_WRITE:
2914 _mmcam_dbg_err("audio device [open failed]");
2915 hcamcorder->error_code = MM_ERROR_COMMON_INVALID_PERMISSION;
2916 /* post error to application */
2917 hcamcorder->error_occurs = TRUE;
2918 msg.id = MM_MESSAGE_CAMCORDER_ERROR;
2919 msg.param.code = hcamcorder->error_code;
2920 _mmcam_dbg_err(" error : sc->error_occurs %d", hcamcorder->error_occurs);
2922 _mmcamcorder_send_message((MMHandleType)hcamcorder, &msg);
2923 gst_message_unref(message);
2925 return GST_BUS_DROP;
2935 return GST_BUS_PASS;
2939 int _mmcamcorder_create_pipeline(MMHandleType handle, int type)
2941 int ret = MM_ERROR_NONE;
2942 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
2943 _MMCamcorderSubContext *sc = NULL;
2944 GstElement *pipeline = NULL;
2946 _mmcam_dbg_log("handle : %x, type : %d", handle, type);
2948 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2950 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
2951 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
2954 case MM_CAMCORDER_MODE_AUDIO:
2955 ret = _mmcamcorder_create_audio_pipeline(handle);
2956 if (ret != MM_ERROR_NONE) {
2960 case MM_CAMCORDER_MODE_VIDEO_CAPTURE:
2962 ret = _mmcamcorder_create_preview_pipeline(handle);
2963 if (ret != MM_ERROR_NONE) {
2967 /* connect capture signal */
2968 if (!sc->bencbin_capture) {
2969 ret = _mmcamcorder_connect_capture_signal(handle);
2970 if (ret != MM_ERROR_NONE) {
2977 pipeline = sc->element[_MMCAMCORDER_MAIN_PIPE].gst;
2978 if (type != MM_CAMCORDER_MODE_AUDIO) {
2979 ret = _mmcamcorder_gst_set_state(handle, pipeline, GST_STATE_READY);
2981 #ifdef _MMCAMCORDER_GET_DEVICE_INFO
2982 if (!_mmcamcorder_get_device_info(handle)) {
2983 _mmcam_dbg_err("Getting device information error!!");
2987 _mmcam_dbg_log("ret[%x]", ret);
2988 if (ret != MM_ERROR_NONE) {
2989 _mmcam_dbg_err("error : destroy pipeline");
2990 _mmcamcorder_destroy_pipeline(handle, hcamcorder->type);
2997 void _mmcamcorder_destroy_pipeline(MMHandleType handle, int type)
2999 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3000 _MMCamcorderSubContext *sc = NULL;
3002 int element_num = 0;
3003 _MMCamcorderGstElement *element = NULL;
3006 mmf_return_if_fail(hcamcorder);
3008 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3009 mmf_return_if_fail(sc);
3013 /* Inside each pipeline destroy function, Set GST_STATE_NULL to Main pipeline */
3015 case MM_CAMCORDER_MODE_VIDEO_CAPTURE:
3016 element = sc->element;
3017 element_num = sc->element_num;
3018 bus = gst_pipeline_get_bus(GST_PIPELINE(sc->element[_MMCAMCORDER_MAIN_PIPE].gst));
3019 _mmcamcorder_destroy_video_capture_pipeline(handle);
3021 case MM_CAMCORDER_MODE_AUDIO:
3022 element = sc->encode_element;
3023 element_num = sc->encode_element_num;
3024 bus = gst_pipeline_get_bus(GST_PIPELINE(sc->encode_element[_MMCAMCORDER_ENCODE_MAIN_PIPE].gst));
3025 _mmcamcorder_destroy_audio_pipeline(handle);
3028 _mmcam_dbg_err("unknown type %d", type);
3032 _mmcam_dbg_log("Pipeline clear!!");
3034 /* Remove pipeline message callback */
3035 if (hcamcorder->pipeline_cb_event_id > 0) {
3036 g_source_remove(hcamcorder->pipeline_cb_event_id);
3037 hcamcorder->pipeline_cb_event_id = 0;
3040 /* Remove remained message in bus */
3042 GstMessage *gst_msg = NULL;
3043 while ((gst_msg = gst_bus_pop(bus)) != NULL) {
3044 _mmcamcorder_pipeline_cb_message(bus, gst_msg, (gpointer)hcamcorder);
3045 gst_message_unref( gst_msg );
3048 gst_object_unref( bus );
3052 /* checking unreleased element */
3053 for (i = 0 ; i < element_num ; i++ ) {
3054 if (element[i].gst) {
3055 if (GST_IS_ELEMENT(element[i].gst)) {
3056 _mmcam_dbg_warn("Still alive element - ID[%d], name [%s], ref count[%d], status[%s]",
3058 GST_OBJECT_NAME(element[i].gst),
3059 GST_OBJECT_REFCOUNT(element[i].gst),
3060 gst_element_state_get_name(GST_STATE(element[i].gst)));
3061 g_object_weak_unref(G_OBJECT(element[i].gst), (GWeakNotify)_mmcamcorder_element_release_noti, sc);
3063 _mmcam_dbg_warn("The element[%d] is still aliving, check it", element[i].id);
3066 element[i].id = _MMCAMCORDER_NONE;
3067 element[i].gst = NULL;
3075 int _mmcamcorder_gst_set_state_async(MMHandleType handle, GstElement *pipeline, GstState target_state)
3077 GstStateChangeReturn setChangeReturn = GST_STATE_CHANGE_FAILURE;
3079 _MMCAMCORDER_LOCK_GST_STATE(handle);
3080 setChangeReturn = gst_element_set_state(pipeline, target_state);
3081 _MMCAMCORDER_UNLOCK_GST_STATE(handle);
3083 return setChangeReturn;
3087 #ifdef _MMCAMCORDER_USE_SET_ATTR_CB
3088 static gboolean __mmcamcorder_set_attr_to_camsensor_cb(gpointer data)
3090 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(data);
3092 mmf_return_val_if_fail(hcamcorder, FALSE);
3096 _mmcamcorder_set_attribute_to_camsensor((MMHandleType)hcamcorder);
3099 hcamcorder->setting_event_id = 0;
3101 _mmcam_dbg_log("Done");
3106 #endif /* _MMCAMCORDER_USE_SET_ATTR_CB */
3109 int _mmcamcorder_gst_set_state(MMHandleType handle, GstElement *pipeline, GstState target_state)
3112 _MMCamcorderSubContext *sc = NULL;
3113 GstState pipeline_state = GST_STATE_VOID_PENDING;
3114 GstStateChangeReturn setChangeReturn = GST_STATE_CHANGE_FAILURE;
3115 GstStateChangeReturn getChangeReturn = GST_STATE_CHANGE_FAILURE;
3116 GstClockTime get_timeout = __MMCAMCORDER_SET_GST_STATE_TIMEOUT * GST_SECOND;
3117 pthread_mutex_t *state_lock = NULL;
3119 mmf_return_val_if_fail(handle, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3120 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3121 mmf_return_val_if_fail(sc && sc->element, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3123 if (sc->element[_MMCAMCORDER_MAIN_PIPE].gst == pipeline) {
3124 _mmcam_dbg_log("Set state to %d - PREVIEW PIPELINE", target_state);
3125 state_lock = &_MMCAMCORDER_GET_GST_STATE_LOCK(handle);
3127 _mmcam_dbg_log("Set state to %d - ENDODE PIPELINE", target_state);
3128 state_lock = &_MMCAMCORDER_GET_GST_ENCODE_STATE_LOCK(handle);
3131 pthread_mutex_lock(state_lock);
3133 for (k = 0; k < _MMCAMCORDER_STATE_SET_COUNT; k++) {
3134 setChangeReturn = gst_element_set_state(pipeline, target_state);
3135 _mmcam_dbg_log("gst_element_set_state[%d] return %d",
3136 target_state, setChangeReturn);
3137 if (setChangeReturn != GST_STATE_CHANGE_FAILURE) {
3138 getChangeReturn = gst_element_get_state(pipeline, &pipeline_state, NULL, get_timeout);
3139 switch (getChangeReturn) {
3140 case GST_STATE_CHANGE_NO_PREROLL:
3141 _mmcam_dbg_log("status=GST_STATE_CHANGE_NO_PREROLL.");
3142 case GST_STATE_CHANGE_SUCCESS:
3143 /* if we reached the final target state, exit */
3144 if (pipeline_state == target_state) {
3145 _mmcam_dbg_log("Set state to %d - DONE", target_state);
3146 pthread_mutex_unlock(state_lock);
3147 return MM_ERROR_NONE;
3150 case GST_STATE_CHANGE_ASYNC:
3151 _mmcam_dbg_log("status=GST_STATE_CHANGE_ASYNC.");
3154 pthread_mutex_unlock(state_lock);
3155 _mmcam_dbg_log("status=GST_STATE_CHANGE_FAILURE.");
3156 return MM_ERROR_CAMCORDER_GST_STATECHANGE;
3159 pthread_mutex_unlock(state_lock);
3161 _mmcam_dbg_err("timeout of gst_element_get_state()!!");
3163 return MM_ERROR_CAMCORDER_RESPONSE_TIMEOUT;
3166 usleep(_MMCAMCORDER_STATE_CHECK_INTERVAL);
3169 pthread_mutex_unlock(state_lock);
3171 _mmcam_dbg_err("Failure. gst_element_set_state timeout!!");
3173 return MM_ERROR_CAMCORDER_RESPONSE_TIMEOUT;
3177 /* For performance check */
3178 int _mmcamcorder_video_current_framerate(MMHandleType handle)
3180 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3181 _MMCamcorderSubContext *sc = NULL;
3183 mmf_return_val_if_fail(hcamcorder, -1);
3185 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3186 mmf_return_val_if_fail(sc, -1);
3188 return sc->kpi.current_fps;
3192 int _mmcamcorder_video_average_framerate(MMHandleType handle)
3194 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3195 _MMCamcorderSubContext *sc = NULL;
3197 mmf_return_val_if_fail(hcamcorder, -1);
3199 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3200 mmf_return_val_if_fail(sc, -1);
3202 return sc->kpi.average_fps;
3206 void _mmcamcorder_video_current_framerate_init(MMHandleType handle)
3208 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3209 _MMCamcorderSubContext *sc = NULL;
3211 mmf_return_if_fail(hcamcorder);
3213 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3214 mmf_return_if_fail(sc);
3216 memset(&(sc->kpi), 0x00, sizeof(_MMCamcorderKPIMeasure));
3222 static gboolean __mmcamcorder_handle_gst_error(MMHandleType handle, GstMessage *message, GError *error)
3224 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3225 _MMCamcorderMsgItem msg;
3226 gchar *msg_src_element;
3227 _MMCamcorderSubContext *sc = NULL;
3229 return_val_if_fail(hcamcorder, FALSE);
3230 return_val_if_fail(error, FALSE);
3231 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3232 mmf_return_val_if_fail(sc, FALSE);
3236 /* filtering filesink related errors */
3237 if (hcamcorder->state == MM_CAMCORDER_STATE_RECORDING &&
3238 (error->code == GST_RESOURCE_ERROR_WRITE || error->code == GST_RESOURCE_ERROR_SEEK)) {
3239 if (sc->ferror_count == 2 && sc->ferror_send == FALSE) {
3240 sc->ferror_send = TRUE;
3241 msg.param.code = __mmcamcorder_gst_handle_resource_error(handle, error->code, message);
3244 _mmcam_dbg_warn("Skip error");
3249 if (error->domain == GST_CORE_ERROR) {
3250 msg.param.code = __mmcamcorder_gst_handle_core_error(handle, error->code, message);
3251 } else if (error->domain == GST_LIBRARY_ERROR) {
3252 msg.param.code = __mmcamcorder_gst_handle_library_error(handle, error->code, message);
3253 } else if (error->domain == GST_RESOURCE_ERROR) {
3254 msg.param.code = __mmcamcorder_gst_handle_resource_error(handle, error->code, message);
3255 } else if (error->domain == GST_STREAM_ERROR) {
3256 msg.param.code = __mmcamcorder_gst_handle_stream_error(handle, error->code, message);
3258 _mmcam_dbg_warn("This error domain is not defined.");
3260 /* we treat system error as an internal error */
3261 msg.param.code = MM_ERROR_CAMCORDER_INTERNAL;
3265 msg_src_element = GST_ELEMENT_NAME(GST_ELEMENT_CAST(message->src));
3266 _mmcam_dbg_err("-Msg src : [%s] Domain : [%s] Error : [%s] Code : [%d] is tranlated to error code : [0x%x]",
3267 msg_src_element, g_quark_to_string (error->domain), error->message, error->code, msg.param.code);
3269 _mmcam_dbg_err("Domain : [%s] Error : [%s] Code : [%d] is tranlated to error code : [0x%x]",
3270 g_quark_to_string (error->domain), error->message, error->code, msg.param.code);
3273 #ifdef _MMCAMCORDER_SKIP_GST_FLOW_ERROR
3274 /* Check whether send this error to application */
3275 if (msg.param.code == MM_ERROR_CAMCORDER_GST_FLOW_ERROR) {
3276 _mmcam_dbg_log("We got the error. But skip it.");
3279 #endif /* _MMCAMCORDER_SKIP_GST_FLOW_ERROR */
3281 /* post error to application */
3282 hcamcorder->error_occurs = TRUE;
3283 msg.id = MM_MESSAGE_CAMCORDER_ERROR;
3284 _mmcamcorder_send_message(handle, &msg);
3290 static gint __mmcamcorder_gst_handle_core_error(MMHandleType handle, int code, GstMessage *message)
3292 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3293 _MMCamcorderSubContext *sc = NULL;
3294 GstElement *element = NULL;
3298 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3300 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3301 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3303 /* Specific plugin - video encoder plugin */
3304 element = GST_ELEMENT_CAST(sc->encode_element[_MMCAMCORDER_ENCSINK_VENC].gst);
3306 if (GST_ELEMENT_CAST(message->src) == element) {
3307 if (code == GST_CORE_ERROR_NEGOTIATION) {
3308 return MM_ERROR_CAMCORDER_GST_NEGOTIATION;
3310 return MM_ERROR_CAMCORDER_ENCODER;
3317 case GST_CORE_ERROR_STATE_CHANGE:
3318 return MM_ERROR_CAMCORDER_GST_STATECHANGE;
3319 case GST_CORE_ERROR_NEGOTIATION:
3320 return MM_ERROR_CAMCORDER_GST_NEGOTIATION;
3321 case GST_CORE_ERROR_MISSING_PLUGIN:
3322 case GST_CORE_ERROR_SEEK:
3323 case GST_CORE_ERROR_NOT_IMPLEMENTED:
3324 case GST_CORE_ERROR_FAILED:
3325 case GST_CORE_ERROR_TOO_LAZY:
3326 case GST_CORE_ERROR_PAD:
3327 case GST_CORE_ERROR_THREAD:
3328 case GST_CORE_ERROR_EVENT:
3329 case GST_CORE_ERROR_CAPS:
3330 case GST_CORE_ERROR_TAG:
3331 case GST_CORE_ERROR_CLOCK:
3332 case GST_CORE_ERROR_DISABLED:
3334 return MM_ERROR_CAMCORDER_GST_CORE;
3339 static gint __mmcamcorder_gst_handle_library_error(MMHandleType handle, int code, GstMessage *message)
3341 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3342 return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3346 /* Specific plugin - NONE */
3350 case GST_LIBRARY_ERROR_FAILED:
3351 case GST_LIBRARY_ERROR_TOO_LAZY:
3352 case GST_LIBRARY_ERROR_INIT:
3353 case GST_LIBRARY_ERROR_SHUTDOWN:
3354 case GST_LIBRARY_ERROR_SETTINGS:
3355 case GST_LIBRARY_ERROR_ENCODE:
3357 _mmcam_dbg_err("Library error(%d)", code);
3358 return MM_ERROR_CAMCORDER_GST_LIBRARY;
3363 static gint __mmcamcorder_gst_handle_resource_error(MMHandleType handle, int code, GstMessage *message)
3365 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3366 _MMCamcorderSubContext *sc = NULL;
3367 GstElement *element = NULL;
3369 mmf_return_val_if_fail(hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3371 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3372 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3376 /* Specific plugin */
3378 element = GST_ELEMENT_CAST(sc->element[_MMCAMCORDER_VIDEOSINK_SINK].gst);
3379 if (GST_ELEMENT_CAST(message->src) == element) {
3380 if (code == GST_RESOURCE_ERROR_WRITE) {
3381 _mmcam_dbg_err("Display device [Off]");
3382 return MM_ERROR_CAMCORDER_DISPLAY_DEVICE_OFF;
3384 _mmcam_dbg_err("Display device [General(%d)]", code);
3389 element = GST_ELEMENT_CAST(sc->encode_element[_MMCAMCORDER_ENCSINK_VENC].gst);
3390 if (GST_ELEMENT_CAST(message->src) == element) {
3391 if (code == GST_RESOURCE_ERROR_FAILED) {
3392 _mmcam_dbg_err("Encoder [Resource error]");
3393 return MM_ERROR_CAMCORDER_ENCODER_BUFFER;
3395 _mmcam_dbg_err("Encoder [General(%d)]", code);
3396 return MM_ERROR_CAMCORDER_ENCODER;
3402 case GST_RESOURCE_ERROR_WRITE:
3403 _mmcam_dbg_err("File write error");
3404 return MM_ERROR_FILE_WRITE;
3405 case GST_RESOURCE_ERROR_NO_SPACE_LEFT:
3406 _mmcam_dbg_err("No left space");
3407 return MM_MESSAGE_CAMCORDER_NO_FREE_SPACE;
3408 case GST_RESOURCE_ERROR_OPEN_WRITE:
3409 _mmcam_dbg_err("Out of storage");
3410 return MM_ERROR_OUT_OF_STORAGE;
3411 case GST_RESOURCE_ERROR_SEEK:
3412 _mmcam_dbg_err("File read(seek)");
3413 return MM_ERROR_FILE_READ;
3414 case GST_RESOURCE_ERROR_NOT_FOUND:
3415 case GST_RESOURCE_ERROR_FAILED:
3416 case GST_RESOURCE_ERROR_TOO_LAZY:
3417 case GST_RESOURCE_ERROR_BUSY:
3418 case GST_RESOURCE_ERROR_OPEN_READ:
3419 case GST_RESOURCE_ERROR_OPEN_READ_WRITE:
3420 case GST_RESOURCE_ERROR_CLOSE:
3421 case GST_RESOURCE_ERROR_READ:
3422 case GST_RESOURCE_ERROR_SYNC:
3423 case GST_RESOURCE_ERROR_SETTINGS:
3425 _mmcam_dbg_err("Resource error(%d)", code);
3426 return MM_ERROR_CAMCORDER_GST_RESOURCE;
3431 static gint __mmcamcorder_gst_handle_stream_error(MMHandleType handle, int code, GstMessage *message)
3433 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3434 _MMCamcorderSubContext *sc = NULL;
3435 GstElement *element =NULL;
3437 mmf_return_val_if_fail( hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED );
3439 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3440 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3444 /* Specific plugin */
3446 element = GST_ELEMENT_CAST(sc->encode_element[_MMCAMCORDER_ENCSINK_VENC].gst);
3447 if (GST_ELEMENT_CAST(message->src) == element) {
3449 case GST_STREAM_ERROR_WRONG_TYPE:
3450 _mmcam_dbg_err("Video encoder [wrong stream type]");
3451 return MM_ERROR_CAMCORDER_ENCODER_WRONG_TYPE;
3452 case GST_STREAM_ERROR_ENCODE:
3453 _mmcam_dbg_err("Video encoder [encode error]");
3454 return MM_ERROR_CAMCORDER_ENCODER_WORKING;
3455 case GST_STREAM_ERROR_FAILED:
3456 _mmcam_dbg_err("Video encoder [stream failed]");
3457 return MM_ERROR_CAMCORDER_ENCODER_WORKING;
3459 _mmcam_dbg_err("Video encoder [General(%d)]", code);
3460 return MM_ERROR_CAMCORDER_ENCODER;
3464 /* General plugin */
3466 case GST_STREAM_ERROR_FORMAT:
3467 _mmcam_dbg_err("General [negotiation error(%d)]", code);
3468 return MM_ERROR_CAMCORDER_GST_NEGOTIATION;
3469 case GST_STREAM_ERROR_FAILED:
3470 _mmcam_dbg_err("General [flow error(%d)]", code);
3471 return MM_ERROR_CAMCORDER_GST_FLOW_ERROR;
3472 case GST_STREAM_ERROR_TYPE_NOT_FOUND:
3473 case GST_STREAM_ERROR_DECODE:
3474 case GST_STREAM_ERROR_CODEC_NOT_FOUND:
3475 case GST_STREAM_ERROR_NOT_IMPLEMENTED:
3476 case GST_STREAM_ERROR_TOO_LAZY:
3477 case GST_STREAM_ERROR_ENCODE:
3478 case GST_STREAM_ERROR_DEMUX:
3479 case GST_STREAM_ERROR_MUX:
3480 case GST_STREAM_ERROR_DECRYPT:
3481 case GST_STREAM_ERROR_DECRYPT_NOKEY:
3482 case GST_STREAM_ERROR_WRONG_TYPE:
3484 _mmcam_dbg_err("General [error(%d)]", code);
3485 return MM_ERROR_CAMCORDER_GST_STREAM;
3490 static gboolean __mmcamcorder_handle_gst_warning (MMHandleType handle, GstMessage *message, GError *error)
3492 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3493 gchar *debug = NULL;
3496 return_val_if_fail(hcamcorder, FALSE);
3497 return_val_if_fail(error, FALSE);
3501 gst_message_parse_warning(message, &err, &debug);
3503 if (error->domain == GST_CORE_ERROR) {
3504 _mmcam_dbg_warn("GST warning: GST_CORE domain");
3505 } else if (error->domain == GST_LIBRARY_ERROR) {
3506 _mmcam_dbg_warn("GST warning: GST_LIBRARY domain");
3507 } else if (error->domain == GST_RESOURCE_ERROR) {
3508 _mmcam_dbg_warn("GST warning: GST_RESOURCE domain");
3509 __mmcamcorder_gst_handle_resource_warning(handle, message, error);
3510 } else if (error->domain == GST_STREAM_ERROR ) {
3511 _mmcam_dbg_warn("GST warning: GST_STREAM domain");
3513 _mmcam_dbg_warn("This error domain(%d) is not defined.", error->domain);
3520 if (debug != NULL) {
3521 _mmcam_dbg_err ("Debug: %s", debug);
3530 static gint __mmcamcorder_gst_handle_resource_warning(MMHandleType handle, GstMessage *message , GError *error)
3532 mmf_camcorder_t *hcamcorder = MMF_CAMCORDER(handle);
3533 _MMCamcorderSubContext *sc = NULL;
3534 GstElement *element =NULL;
3535 gchar *msg_src_element;
3537 mmf_return_val_if_fail( hcamcorder, MM_ERROR_CAMCORDER_NOT_INITIALIZED );
3539 sc = MMF_CAMCORDER_SUBCONTEXT(handle);
3540 mmf_return_val_if_fail(sc, MM_ERROR_CAMCORDER_NOT_INITIALIZED);
3544 /* Special message handling */
3546 element = GST_ELEMENT_CAST(sc->element[_MMCAMCORDER_VIDEOSRC_SRC].gst);
3547 if (GST_ELEMENT_CAST(message->src) == element) {
3548 if (error->code == GST_RESOURCE_ERROR_FAILED) {
3549 msg_src_element = GST_ELEMENT_NAME(GST_ELEMENT_CAST(message->src));
3550 _mmcam_dbg_warn("-Msg src:[%s] Domain:[%s] Error:[%s]",
3551 msg_src_element, g_quark_to_string(error->domain), error->message);
3552 return MM_ERROR_NONE;
3556 /* General plugin */
3557 switch (error->code) {
3558 case GST_RESOURCE_ERROR_WRITE:
3559 case GST_RESOURCE_ERROR_NO_SPACE_LEFT:
3560 case GST_RESOURCE_ERROR_SEEK:
3561 case GST_RESOURCE_ERROR_NOT_FOUND:
3562 case GST_RESOURCE_ERROR_FAILED:
3563 case GST_RESOURCE_ERROR_TOO_LAZY:
3564 case GST_RESOURCE_ERROR_BUSY:
3565 case GST_RESOURCE_ERROR_OPEN_READ:
3566 case GST_RESOURCE_ERROR_OPEN_WRITE:
3567 case GST_RESOURCE_ERROR_OPEN_READ_WRITE:
3568 case GST_RESOURCE_ERROR_CLOSE:
3569 case GST_RESOURCE_ERROR_READ:
3570 case GST_RESOURCE_ERROR_SYNC:
3571 case GST_RESOURCE_ERROR_SETTINGS:
3573 _mmcam_dbg_warn("General GST warning(%d)", error->code);
3577 return MM_ERROR_NONE;