From e10043f41912e35b59520d282b1f8f5ac051eca6 Mon Sep 17 00:00:00 2001 From: RaymondWu Date: Fri, 5 Nov 2010 17:14:34 +0800 Subject: Fix vmeta segmentation fault in unit test. Root causes are : a) In QA's test case, it only calls driver init() and clean(). So some variables have not been initialized yet. b) init() and clean() are not protected by mutexes in multi-threads case. Change-Id: I0b0f36d2d840c23e4848f8b1a89522eb42660be0 Signed-off-by: RaymondWu --- vmeta_lib.c | 27 +++++++++++++++++++++++++-- 1 file changed, 25 insertions(+), 2 deletions(-) diff --git a/vmeta_lib.c b/vmeta_lib.c index 2fa6602..57f3702 100755 --- a/vmeta_lib.c +++ b/vmeta_lib.c @@ -51,6 +51,7 @@ static SIGN32 vdec_os_api_get_ks(kernel_share **pp_ks);//get kernel shared resou vdec_os_driver_cb_t *vdec_iface = NULL; UNSG32 globalDbgLevel = VDEC_DEBUG_NONE; UNSG32 syncTimeout = 500; +pthread_mutex_t pmt = PTHREAD_MUTEX_INITIALIZER; static inline int get_bit(int nr, unsigned int *addr) { @@ -407,8 +408,10 @@ SIGN32 vdec_os_driver_init(void) FILE *fp_log; #endif + pthread_mutex_lock(&pmt); if(vdec_iface != NULL) { // already been initiated in this process vdec_iface->refcount++; + pthread_mutex_unlock(&pmt); return ret; } @@ -416,6 +419,7 @@ SIGN32 vdec_os_driver_init(void) fp_log = fopen(VMETA_LOG_FILE,"w"); if(fp_log == NULL) { + pthread_mutex_unlock(&pmt); return -1; } fclose(fp_log); @@ -426,7 +430,10 @@ SIGN32 vdec_os_driver_init(void) vdec_iface = (vdec_os_driver_cb_t*)malloc(sizeof(vdec_os_driver_cb_t)); memset((void*)vdec_iface, 0, sizeof(vdec_os_driver_cb_t)); if(vdec_iface == NULL) + { + pthread_mutex_unlock(&pmt); return -VDEC_OS_DRIVER_INIT_FAIL; + } // initialize reference count vdec_iface->refcount++; @@ -472,6 +479,7 @@ SIGN32 vdec_os_driver_init(void) } dbg_printf(VDEC_DEBUG_MEM, "vdec os driver io mem map to: 0x%x\n", vdec_iface->io_mem_virt_addr); + pthread_mutex_unlock(&pmt); return ret; err_mmap_fail: @@ -482,20 +490,26 @@ err_open_fail: free((void*)vdec_iface); vdec_iface = NULL; + pthread_mutex_unlock(&pmt); return ret; } // clean vdec os driver SIGN32 vdec_os_driver_clean(void) { - if(vdec_iface == NULL) + pthread_mutex_lock(&pmt); + + if(vdec_iface == NULL){ + pthread_mutex_unlock(&pmt); return -VDEC_OS_DRIVER_CLEAN_FAIL; + } // decrease the refcount vdec_iface->refcount--; if(vdec_iface->refcount != 0) { dbg_printf(VDEC_DEBUG_ALL, "refcount = %d\n", vdec_iface->refcount); + pthread_mutex_unlock(&pmt); return 0; } @@ -527,6 +541,7 @@ SIGN32 vdec_os_driver_clean(void) } dbg_printf(VDEC_DEBUG_ALL, "vmeta clean done\n"); + pthread_mutex_unlock(&pmt); return 0; } @@ -958,7 +973,15 @@ tag_monitor_fail: printf("vdec_os_api_get_user_count error: point is NULL\n"); return -1; } - p_ks = (kernel_share*)p_cb->kernel_share_va; + + if(p_cb->kernel_share_va==0) + { + vdec_os_api_get_ks(&p_ks); + } + else + { + p_ks = (kernel_share *)p_cb->kernel_share_va; + } dbg_printf(VDEC_DEBUG_ALL, "get_user_count=%d \n",p_ks->ref_count); -- cgit