diff options
author | Jeongmo Yang <jm80.yang@samsung.com> | 2018-10-25 10:52:34 +0900 |
---|---|---|
committer | Jeongmo Yang <jm80.yang@samsung.com> | 2018-10-25 13:49:40 +0900 |
commit | 64c5a0dbf468c0fdf76710c3bce1f0fb14bb3601 (patch) | |
tree | 4107b44758f940fd4e120674eae8eff6ebaba5c4 | |
parent | f9c2ba607eb3b701265f2da198d781d27e1df168 (diff) | |
download | camera-64c5a0dbf468c0fdf76710c3bce1f0fb14bb3601.tar.gz camera-64c5a0dbf468c0fdf76710c3bce1f0fb14bb3601.tar.bz2 camera-64c5a0dbf468c0fdf76710c3bce1f0fb14bb3601.zip |
Update idle event handling to fix crash in idle event callback
- The idle event could be called after handle is destroyed.
- ASan issue : TDAF-748
[Version] 0.3.12
[Profile] Common
[Issue Type] Bug fix
[Dependency module] N/A
Change-Id: I70466177edc1451669ef664f880fbb3f9f786f02
Signed-off-by: Jeongmo Yang <jm80.yang@samsung.com>
-rw-r--r-- | include/camera_private.h | 3 | ||||
-rw-r--r-- | packaging/capi-media-camera.spec | 2 | ||||
-rw-r--r-- | src/camera.c | 56 |
3 files changed, 13 insertions, 48 deletions
diff --git a/include/camera_private.h b/include/camera_private.h index 582d3d3..03aef07 100644 --- a/include/camera_private.h +++ b/include/camera_private.h @@ -131,8 +131,6 @@ typedef struct _camera_cb_info_s { /* idle event */ GList *idle_event_list; - GCond idle_event_cond; - GMutex idle_event_mutex; /* user callback */ gpointer user_cb[MUSE_CAMERA_EVENT_TYPE_NUM]; @@ -175,7 +173,6 @@ typedef struct _camera_idle_event_s { camera_cb_info_s *cb_info; gchar recv_msg[MUSE_CAMERA_MSG_MAX_LENGTH + 1]; muse_camera_event_e event; - GMutex event_mutex; } camera_idle_event_s; typedef struct _camera_wl_info_s { diff --git a/packaging/capi-media-camera.spec b/packaging/capi-media-camera.spec index b7fa839..8980018 100644 --- a/packaging/capi-media-camera.spec +++ b/packaging/capi-media-camera.spec @@ -1,6 +1,6 @@ Name: capi-media-camera Summary: A Camera API -Version: 0.3.11 +Version: 0.3.12 Release: 0 Group: Multimedia/API License: Apache-2.0 diff --git a/src/camera.c b/src/camera.c index 69088f2..ef99d90 100644 --- a/src/camera.c +++ b/src/camera.c @@ -49,6 +49,7 @@ static GList *g_cam_dev_state_changed_cb_list; static int g_cam_dev_state_changed_cb_id; static GDBusConnection *g_cam_dev_state_changed_cb_conn; static guint g_cam_dev_state_changed_cb_subscribe_id; +static GMutex g_cam_idle_event_lock; static void __global(void *data, struct wl_registry *registry, @@ -1589,7 +1590,7 @@ static void _camera_client_user_callback(camera_cb_info_s *cb_info, char *recv_m return; } -static bool _camera_idle_event_callback(void *data) +static gboolean _camera_idle_event_callback(gpointer data) { camera_cb_info_s *cb_info = NULL; camera_idle_event_s *cam_idle_event = (camera_idle_event_s *)data; @@ -1600,34 +1601,26 @@ static bool _camera_idle_event_callback(void *data) } /* lock event */ - g_mutex_lock(&cam_idle_event->event_mutex); + g_mutex_lock(&g_cam_idle_event_lock); cb_info = cam_idle_event->cb_info; if (cb_info == NULL) { LOGW("camera cb_info is NULL. event %p %d", cam_idle_event, cam_idle_event->event); + g_mutex_unlock(&g_cam_idle_event_lock); goto IDLE_EVENT_CALLBACK_DONE; } /* remove event from list */ - g_mutex_lock(&cb_info->idle_event_mutex); - if (cb_info->idle_event_list) cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)cam_idle_event); - /*LOGD("remove camera idle event %p, %p", cam_idle_event, cb_info->idle_event_list);*/ - g_mutex_unlock(&cb_info->idle_event_mutex); + g_mutex_unlock(&g_cam_idle_event_lock); /* user callback */ _camera_client_user_callback(cb_info, cam_idle_event->recv_msg, cam_idle_event->event); - /* send signal for waiting thread */ - g_cond_signal(&cb_info->idle_event_cond); - IDLE_EVENT_CALLBACK_DONE: - /* unlock and release event */ - g_mutex_unlock(&cam_idle_event->event_mutex); - g_mutex_clear(&cam_idle_event->event_mutex); - + /* release event */ g_free(cam_idle_event); cam_idle_event = NULL; @@ -1714,14 +1707,14 @@ static void *_camera_msg_handler_func(gpointer data) cam_idle_event->event = cam_msg->event; cam_idle_event->cb_info = cb_info; - g_mutex_init(&cam_idle_event->event_mutex); + strncpy(cam_idle_event->recv_msg, cam_msg->recv_msg, sizeof(cam_idle_event->recv_msg) - 1); /*LOGD("t:%d add camera event[%d, %p] to IDLE", type, cam_msg->event, cam_idle_event);*/ - g_mutex_lock(&cb_info->idle_event_mutex); + g_mutex_lock(&g_cam_idle_event_lock); cb_info->idle_event_list = g_list_append(cb_info->idle_event_list, (gpointer)cam_idle_event); - g_mutex_unlock(&cb_info->idle_event_mutex); + g_mutex_unlock(&g_cam_idle_event_lock); g_idle_add_full(G_PRIORITY_DEFAULT, (GSourceFunc)_camera_idle_event_callback, @@ -1766,18 +1759,17 @@ static void _camera_deactivate_idle_event_all(camera_cb_info_s *cb_info) { camera_idle_event_s *cam_idle_event = NULL; GList *list = NULL; - gint64 end_time = 0; if (cb_info == NULL) { LOGE("cb_info is NULL"); return; } - g_mutex_lock(&cb_info->idle_event_mutex); + g_mutex_lock(&g_cam_idle_event_lock); if (cb_info->idle_event_list == NULL) { LOGD("No remained idle event"); - g_mutex_unlock(&cb_info->idle_event_mutex); + g_mutex_unlock(&g_cam_idle_event_lock); return; } @@ -1797,42 +1789,24 @@ static void _camera_deactivate_idle_event_all(camera_cb_info_s *cb_info) cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)cam_idle_event); - g_mutex_clear(&cam_idle_event->event_mutex); g_free(cam_idle_event); cam_idle_event = NULL; continue; } - LOGW("remove idle event %p failed", cam_idle_event); - - if (!g_mutex_trylock(&cam_idle_event->event_mutex)) { - LOGW("lock failed, %p event is calling now", cam_idle_event); - - end_time = g_get_monotonic_time() + G_TIME_SPAN_MILLISECOND * 100; - - if (g_cond_wait_until(&cb_info->idle_event_cond, &cb_info->idle_event_mutex, end_time)) - LOGW("signal received"); - else - LOGW("timeout"); - - continue; - } - LOGW("set NULL cb_info for event %p %d, it will be freed on idle callback", cam_idle_event, cam_idle_event->event); cam_idle_event->cb_info = NULL; cb_info->idle_event_list = g_list_remove(cb_info->idle_event_list, (gpointer)cam_idle_event); - - g_mutex_unlock(&cam_idle_event->event_mutex); } g_list_free(cb_info->idle_event_list); cb_info->idle_event_list = NULL; - g_mutex_unlock(&cb_info->idle_event_mutex); + g_mutex_unlock(&g_cam_idle_event_lock); return; } @@ -2258,8 +2232,6 @@ static camera_cb_info_s *_camera_client_callback_new(gint sockfd) } g_mutex_init(&cb_info->fd_lock); - g_mutex_init(&cb_info->idle_event_mutex); - g_cond_init(&cb_info->idle_event_cond); g_mutex_init(&cb_info->mp_data_mutex); g_mutex_init(&cb_info->preview_cb_mutex); #ifdef TIZEN_FEATURE_EVAS_RENDERER @@ -2313,8 +2285,6 @@ ErrorExit: __destroy_msg_handler_thread(&cb_info->capture_cb_info); g_mutex_clear(&cb_info->fd_lock); - g_mutex_clear(&cb_info->idle_event_mutex); - g_cond_clear(&cb_info->idle_event_cond); g_mutex_clear(&cb_info->mp_data_mutex); g_mutex_clear(&cb_info->preview_cb_mutex); #ifdef TIZEN_FEATURE_EVAS_RENDERER @@ -2352,8 +2322,6 @@ static void _camera_client_callback_destroy(camera_cb_info_s *cb_info) __destroy_msg_handler_thread(&cb_info->capture_cb_info); g_mutex_clear(&cb_info->fd_lock); - g_mutex_clear(&cb_info->idle_event_mutex); - g_cond_clear(&cb_info->idle_event_cond); g_mutex_clear(&cb_info->mp_data_mutex); g_mutex_clear(&cb_info->preview_cb_mutex); #ifdef TIZEN_FEATURE_EVAS_RENDERER |