一 問題描述
工廠測試camera,會出現兩種現象:
1 camera preview有顯示,但是按鍵無響應,無法拍照測試
2 camera preview黑屏,按鍵無響應
以上情況,系統都沒有死,adb log正常
二 復現路徑確認
按照正常測試手法,進入camera測試,preview取景出來,再按confirm鍵拍照,測試camera都不會出現問題,反覆試驗發現,一進入camera測試,preview取景還沒有出來,就按confirm鍵拍照,則必現按鍵無響應現象。
三 問題分析
代碼流程分析:
int camera_entry(structftm_param *param, void *priv)
{
//Camera item view/textinit
camera_state = CAMERA_STATE_IDLE;
acdkIFInit();//acdkinit camera_update_capture_tv_thread(priv);//previewcapture
camera_preview_stop();
do
{
switch (chosen)
{
caseITEM_CAMERA_TEST://重新測試
break;
case ITEM_PASS: //測試通過
break;
caseITEM_FAIL: //測試失敗
break;
}
While(1);
}
static void*camera_update_capture_tv_thread(void *priv)
{
//register key handle
ui_init_textview(tv,camera_cap_key_handler,(void*)cam);
camera_preview_test();//preview entry
cam->exit_thd = MFALSE;
//waite key event
while (1)
{
key = ui_wait_key();
usleep(200000);
chkcnt--;
tv->m_khandler(key, tv->m_priv);
if (cam ->exit_thd)
break;
if (chkcnt > 0)
continue;
chkcnt = 5;
}
}
static MINT32camera_preview_test()
{
bool bRet =bSendDataToACDK(ACDK_CMD_PREVIEW_START,
(MUINT8*)&rACDKPrvConfig,
sizeof(ACDK_PREVIEW_STRUCT),
NULL,
0,
&u4RetLen);
camera_state = CAMERA_STATE_PREVIEW;
}
static volatile intcapture_done = MFALSE;
static intcamera_cap_key_handler(int key, void *priv)
{
switch (key)
{
case UI_KEY_CONFIRM:
err =camera_capture_test();
if(err == 0)
{
capture_done =MTRUE;
}
else
{
FTM_CAMERA_DBG("Capture Fail\n");
}
exit = 1;
break;
case UI_KEY_BACK:
exit = 1;
break;
if (exit)
{
cam->exit_thd =MTRUE;
tv->exit(tv);
}
}
static intcamera_capture_test()
{
gCapCBDone = MFALSE;
bRet = bSendDataToACDK(ACDK_CMD_CAPTURE,
(unsigned char*)&rACDKCapConfig,
sizeof(ACDK_CAPTURE_STRUCT),
NULL,
0,
&u4RetLen);
//wait capture done
if(bRet == MTRUE)
{
// gCapCBDone在capture success cb置true
while(!gCapCBDone) {
usleep(1000);
}
}
else
{
return 1;
}
}
問題的本質原因是camera ftm thread 調用acdk preview/capture是異步的,通過發消息給acdk module。而進入 camera_update_capture_tv_thread就註冊key handle,這時confirm key就能正常相應,然而camera preview 還要通過發消息ACDK_CMD_PREVIEW_START給acdk,返回後preview還沒有ok,因爲是異步的,但是這時confirm keyevent來,就得跑到handle的capture流程,發送ACDK_CMD_CAPTURE消息給acdk做拍照,一直等待capture成功,但是由於preivew流程都沒有正常執行,這時capture一直不能成功執行,導致thread 死鎖,按鍵無響應。
四 修改方法
將key handle 註冊後移到camera preview ready後,camera ftm發ACDK_CMD_PREVIEW_START消息給acdk啓動preview,返回後等待1.5s 使得camerapreview取景正常。這時confirm key按下就能正常相應了。
+ pthread_mutex_lock(&camera_mutex);
camera_preview_test();
+ usleep(1500000);//2s
+ pthread_mutex_unlock(&camera_mutex);
+ ui_init_textview(tv,camera_cap_key_handler, (void*)cam );
+ tv->set_title(tv, &cam->title);
+ tv->set_text(tv, &cam->text);
+ tv->set_btn(tv,&cam->left_btn, &cam->center_btn, &cam->right_btn);
+ tv->redraw(tv);