bool OTClient:: doOT(ImgBufQueNode const& rQueNode, bool &rIsDetected_OT) { bool ret = true; MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "+"); src_buf = (unsigned char *)rQueNode.getImgBuf()->getVirAddr(); dst_rgb = (unsigned char *)OTWorkingBuffer; int ot_plane = Format::queryPlaneCount(Format::queryImageFormat(rQueNode->getImgFormat().string())); mpOTHalObj->halOTBufferCreate(dst_rgb, src_buf, (MUINT8)ot_plane); if((OT_StartX < -1000) || (OT_StartX > 1000) || (OT_StartY < -1000) || (OT_StartY > 1000)) { MY_LOGD("Error! Incorrect Initial Coordinate\n"); return false; } //®y¼Ð´«ºâ mpOTHalObj->halOTDo(dst_rgb, OT_StartX, OT_StartY); #if (GET_OT_RESULT) if( NULL != mpDetectedObjs ) numFace = mpOTHalObj->halOTGetResult(mpDetectedObjs); MY_LOGD("OT Status: %d\n",numFace ); if(numFace>0) rIsDetected_OT = 1; else rIsDetected_OT = 0; #endif return ret; }
// // Callback of Postview for Display // // Arguments: // i8Timestamp // [I] Postview timestamp // // u4PostviewSize // [I] Postview buffer size in bytes. // // puPostviewBuf // [I] Postview buffer with its size = u4PostviewSize // bool CamAdapter:: onCB_PostviewDisplay( int64_t const i8Timestamp, uint32_t const u4PostviewSize, uint8_t const* puPostviewBuf ) { MY_LOGD("timestamp(%lld), size/buf=%d/%p", i8Timestamp, u4PostviewSize, puPostviewBuf); #if 1 // if ( ! u4PostviewSize || ! puPostviewBuf ) { MY_LOGW("Bad callback: size/buf=%d/%p", i8Timestamp, u4PostviewSize, puPostviewBuf); return false; } // sp<IImgBufProvider> pImgBufPvdr = mpImgBufProvidersMgr->getProvider(IImgBufProvider::eID_DISPLAY); if ( pImgBufPvdr == 0 ) { MY_LOGW("Bad IImgBufProvider"); return false; } // ImgBufQueNode node; if ( ! pImgBufPvdr->dequeProvider(node) ) { MY_LOGW("dequeProvider fail"); return false; } // sp<IImgBuf> pImgBuf = node.getImgBuf(); if ( u4PostviewSize != pImgBuf->getBufSize() ) { MY_LOGW( "callback size(%d) != display:[%d %s %dx%d]", u4PostviewSize, pImgBuf->getBufSize(), pImgBuf->getImgFormat().string(), pImgBuf->getImgWidth(), pImgBuf->getImgHeight() ); node.setStatus(ImgBufQueNode::eSTATUS_CANCEL); } else { ::memcpy(pImgBuf->getVirAddr(), puPostviewBuf, u4PostviewSize); globalcacheFlushAll(); MY_LOGD_IF(1, "- globalcacheFlushAll()"); // pImgBuf->setTimestamp(i8Timestamp); node.setStatus(ImgBufQueNode::eSTATUS_DONE); } // if ( ! pImgBufPvdr->enqueProvider(node) ) { MY_LOGW("enqueProvider fail"); return false; } // #endif return true; }
// Derived class must implement threadLoop(). The thread starts its life // here. There are two ways of using the Thread object: // 1) loop: if threadLoop() returns true, it will be called again if // requestExit() wasn't called. // 2) once: if threadLoop() returns false, the thread will exit upon return. virtual bool threadLoop() { ImgBufQueNode QueNode; // for (int i = 0; i < miLoopCount; i++) { if ( mpImgBufQueue->dequeProvider(QueNode) ) { renderImgBuf(QueNode.getImgBuf()); // mpImgBufQueue->enqueProvider(ImgBufQueNode(QueNode.getImgBuf(), ImgBufQueNode::eSTATUS_DONE)); } // ::usleep(miSleepInUs); } return false; }
bool FDClient:: doFD(ImgBufQueNode const& rQueNode, bool &rIsDetected_FD, bool &rIsDetected_SD, bool rDoSD) { bool ret = true; MINT32 SD_Result; MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "+"); //MY_LOGD("Rotation_Info1:%d", Rotation_Info); //********************************************************************************************// dst_rgb = (unsigned char *)DDPBuffer; src_buf = (unsigned char *)rQueNode.getImgBuf()->getVirAddr(); g_BufferGroup = doBufferAnalysis(rQueNode); //g_BufferGroup = 1; mpFDHalObj->halFDBufferCreate(dst_rgb, src_buf, g_BufferGroup); mpFDHalObj->halFDDo(0, (MINT32)dst_rgb, (MINT32)rQueNode.getImgBuf()->getVirAddr(), rDoSD, Rotation_Info); //********************************************************************************************// #if (GET_FD_RESULT) if( NULL != mpDetectedFaces ) numFace = mpFDHalObj->halFDGetFaceResult(mpDetectedFaces); MY_LOGD("Scenario FD Num: %d\n",numFace ); if(numFace>0) rIsDetected_FD = 1; else rIsDetected_FD = 0; #endif #if (GET_SD_RESULT) SD_Result = mpFDHalObj->halSDGetSmileResult(); MY_LOGD("Scenario SD Result1: %d\n",SD_Result ); if(SD_Result>0) rIsDetected_SD = 1; else rIsDetected_SD = 0; #endif MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "-"); return ret; }
int FDClient:: doBufferAnalysis(ImgBufQueNode const& a_rQueNode) { int plane =0; int BufWidth = a_rQueNode.getImgBuf()->getImgWidth(); int BufHeight = a_rQueNode.getImgBuf()->getImgHeight(); //plane = a_rQueNode.getPlaneCount(); plane = FmtUtils::queryPlaneCount(a_rQueNode.getImgBuf()->getImgFormat().string()); //MY_LOGD("getImgWidth:%d, getImgHeight:%d", a_rQueNode.getImgBuf()->getImgWidth(), a_rQueNode.getImgBuf()->getImgHeight()); //MY_LOGD("plane: %d\n",plane ); //Need PlaneCount Information if( (BufWidth==640) && (BufHeight == 480) && (plane==2)) return 0; else if ( (BufWidth*3 == BufHeight*4) && (plane==2) ) return 1; else if ( (BufWidth*3 == BufHeight*4) && (plane==3) ) return 2; else if ( ( BufWidth*9 == BufHeight*16) && (plane==2) ) return 3; else if ( ( BufWidth*9 == BufHeight*16) && (plane==3) ) return 4; else if ( ( BufWidth*3 == BufHeight*5) && (plane==2) ) return 5; else if ( ( BufWidth*3 == BufHeight*5) && (plane==3) ) return 6; else if ( (plane==2) ) return 3; else if ( (plane==3) ) return 4; else return 9; return plane; }
bool PREFEATUREABSE:: handleReturnBuffers(sp<IImgBufQueue>const& rpBufQueue, ImgBufQueNode const &rQueNode) { bool ret = true; ret = rpBufQueue->enqueProcessor( ImgBufQueNode(rQueNode.getImgBuf(), ImgBufQueNode::eSTATUS_TODO)); if ( ! ret ) { MY_LOGE("enqueProcessor() fails"); ret = false; } return ret; }
/****************************************************************************** * buffer can be reached either by client enque back buffer * or by previewclient. *******************************************************************************/ bool PREFEATUREABSE:: waitAndHandleReturnBuffers(sp<IImgBufQueue>const& rpBufQueue, ImgBufQueNode &rQueNode) { bool ret = false; Vector<ImgBufQueNode> vQueNode; // MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "+"); // // (1) wait and deque from processor rpBufQueue->dequeProcessor(vQueNode); if ( vQueNode.empty() ) { ret = false; MY_LOGD("Deque from processor is empty. Suppose stopProcessor has been called"); goto lbExit; } // (2) check vQueNode: // - TODO or CANCEL // - get and keep the latest one with TODO tag; // - otherwise, return to processors for (size_t i = 0; i < vQueNode.size(); i++) { if (vQueNode[i].isDONE() && vQueNode[i].getImgBuf() != 0) { if (rQueNode.getImgBuf() != 0 ) // already got { handleReturnBuffers(rpBufQueue, rQueNode); } rQueNode = vQueNode[i]; // update a latest one ret = true; } else { handleReturnBuffers(rpBufQueue, vQueNode[i]); } } lbExit: // MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "-"); return ret; }
bool PreviewBufMgr:: enqueBuffer(ImgBufQueNode const& node) { // (1) set DONE tag into package const_cast<ImgBufQueNode*>(&node)->setStatus(ImgBufQueNode::eSTATUS_DONE); // (2) choose the correct "client" switch (node.getCookieDE()) { case eBuf_Pass1: { if (mspHwBufPvdr != 0) { mspHwBufPvdr->enque(node.getImgBuf()); } } break; // case eBuf_Disp: { sp<IImgBufProvider> bufProvider = mspImgBufProvidersMgr->getDisplayPvdr(); if (bufProvider != 0) { bufProvider->enqueProvider(node); } } break; // case eBuf_AP: { sp<IImgBufProvider> bufProvider; { bufProvider = mspImgBufProvidersMgr->getPrvCBPvdr(); if ( bufProvider != 0 ) { const_cast<ImgBufQueNode*>(&node)->setCookieDE(0); // 0 for preview bufProvider->enqueProvider(node); } // If fd exists, copy to it bufProvider = mspImgBufProvidersMgr->getFDBufPvdr(); ImgBufQueNode FDnode; if (bufProvider != 0 && bufProvider->dequeProvider(FDnode)) { if ( FDnode.getImgBuf()->getBufSize() >= node.getImgBuf()->getBufSize()) { memcpy(FDnode.getImgBuf()->getVirAddr(), node.getImgBuf()->getVirAddr(), node.getImgBuf()->getBufSize()); const_cast<ImgBufQueNode*>(&FDnode)->setStatus(ImgBufQueNode::eSTATUS_DONE); } else { MY_LOGE("fd buffer size < ap buffer size"); const_cast<ImgBufQueNode*>(&FDnode)->setStatus(ImgBufQueNode::eSTATUS_CANCEL); } // bufProvider->enqueProvider(FDnode); } } } break; // case eBuf_FD: { sp<IImgBufProvider> bufProvider = mspImgBufProvidersMgr->getFDBufPvdr(); if (bufProvider != 0) { bufProvider->enqueProvider(node); } } break; // case eBuf_Generic: { sp<IImgBufProvider> bufProvider = mspImgBufProvidersMgr->getGenericBufPvdr(); if (bufProvider != 0) { bufProvider->enqueProvider(node); } } break; // default: MY_LOGE("unknown port(%d)!!", node.getCookieDE()); break; } return true; }
void FDClient:: onClientThreadLoop() { MY_LOGD("+"); //(0) pre-check sp<IImgBufQueue> pBufQueue = NULL; { //Mutex::Autolock _l(mModuleMtx); // pBufQueue = mpImgBufQueue; if ( pBufQueue == 0 || ! isEnabledState()) { MY_LOGE("pBufMgr(%p), isEnabledState(%d)", pBufQueue.get(), isEnabledState()); return; } } //(1) prepare all TODO buffers if ( ! initBuffers(pBufQueue) ) { MY_LOGE("initBuffers failed"); return; } //(2) start if ( !pBufQueue->startProcessor() ) { MY_LOGE("startProcessor failed"); return; } //BinChang 2012/11/01 //Initial FD int srcWidth=0, srcHeight=0; mpParamsMgr->getPreviewSize(&srcWidth, &srcHeight); //mpFDHalObj = new halFDBase(); mpFDHalObj = halFDBase::createInstance(HAL_FD_OBJ_FDFT_SW); //mpFDHalObj->halFDInit(srcWidth, srcHeight, (MUINT32) FDWorkingBuffer, FDWorkingBufferSize, 1); //1:Enale SW resizer mpFDHalObj->halFDInit(srcWidth, srcHeight, (MUINT32) FDWorkingBuffer, FDWorkingBufferSize, 1, mIsSDenabled); //1:Enale SW resizer g_last_SDenabled = 0; //************************************************************// //BinChang 2014/01/07 //Initial GD Start mpGDHalObj = halGSBase::createInstance(HAL_GS_OBJ_SW); mpGDHalObj->halGSInit(srcWidth, srcHeight, (MUINT32) FDWorkingBuffer, FDWorkingBufferSize); //************************************************************// //ASD Init mpASDClient = IAsdClient::createInstance(mpParamsMgr); if ( mpASDClient == 0 || ! mpASDClient->init() ) { MY_LOGE("mpASDClient init failed"); } mpASDClient->setCallbacks(mpCamMsgCbInfo); //(3) Do in loop until stopFaceDetection has been called // either by sendCommand() or by stopPreview() while ( isEnabledState() ) { // (3.1) deque from processor ImgBufQueNode rQueNode; if ( ! waitAndHandleReturnBuffers(pBufQueue, rQueNode) ) { MY_LOGD("No available deque-ed buffer; to be leaving"); continue; } if ( rQueNode.getImgBuf() == 0 ) { MY_LOGE("rQueNode.getImgBuf() == 0"); continue; } // (3.2) do FD algorithm bool isDetected_FD = false; bool isDetected_SD = false; bool isDetected_GD = false; int const i4CamMode = mpParamsMgr->getInt(MtkCameraParameters::KEY_CAMERA_MODE); if ( i4CamMode == MtkCameraParameters::CAMERA_MODE_NORMAL ) Rotation_Info = 180; else Rotation_Info = mpParamsMgr->getInt(CameraParameters::KEY_ROTATION); //MY_LOGD("Rotation_Info:%d", Rotation_Info); CPTLog(Event_Hal_Client_CamClient_FD, CPTFlagStart); // Profiling Start. if ( ! isMsgEnabled() ) { MY_LOGD("Don't do FD"); } else { if( g_last_SDenabled != mIsSDenabled) { mpFDHalObj->halFDUninit(); mpFDHalObj->destroyInstance(); mpFDHalObj = NULL; mpFDHalObj = halFDBase::createInstance(HAL_FD_OBJ_FDFT_SW); mpFDHalObj->halFDInit(srcWidth, srcHeight, (MUINT32) FDWorkingBuffer, FDWorkingBufferSize, 1, mIsSDenabled); //1:Enale SW resizer g_last_SDenabled = mIsSDenabled; } //if ( ! doFD(rQueNode, isDetected_FD, isDetected_SD, mIsSDenabled) ) if ( ! doFD(rQueNode, isDetected_FD, isDetected_SD, mIsSDenabled, isDetected_GD, mIsGDenabled) ) { MY_LOGE("doFD failed"); CPTLog(Event_Hal_Client_CamClient_FD, CPTFlagEnd); // Profiling End. continue; } } CPTLog(Event_Hal_Client_CamClient_FD, CPTFlagEnd); // Profiling End. // (3.3) #if '1'==MTKCAM_HAVE_3A_HAL Hal3ABase* p3AHal = Hal3ABase::createInstance(DevMetaInfo::queryHalSensorDev(mpParamsMgr->getOpenId())); if (p3AHal) { if (isEnabledState()) p3AHal->setFDInfo(mpDetectedFaces); p3AHal->destroyInstance(); } #endif // (3.4) //performCallback(isDetected_FD, isDetected_SD); performCallback(isDetected_FD, isDetected_SD, isDetected_GD); //Call ASD if doFD if(isMsgEnabled()) { mpASDClient->update(DDPBuffer, srcWidth, srcHeight); } // (3.5) // enque back to processor handleReturnBuffers(pBufQueue, rQueNode); //enque to "TODO" } if ( mpASDClient != 0 ) { mpASDClient->uninit(); mpASDClient = NULL; } //(4) stop. pBufQueue->pauseProcessor(); pBufQueue->flushProcessor(); // clear "TODO" pBufQueue->stopProcessor(); // clear "DONE" /* #if '1'==MTKCAM_HAVE_3A_HAL Hal3ABase* p3AHal = Hal3ABase::createInstance(DevMetaInfo::queryHalSensorDev(mpParamsMgr->getOpenId())); if (p3AHal) { mpDetectedFaces->number_of_faces = 0; p3AHal->setFDInfo(mpDetectedFaces); p3AHal->destroyInstance(); } #endif */ uninitBuffers(); mpGDHalObj->halGSUninit(); mpGDHalObj->destroyInstance(); mpGDHalObj = NULL; mpFDHalObj->halFDUninit(); mpFDHalObj->destroyInstance(); mpFDHalObj = NULL; MY_LOGD("-"); }
bool FDClient:: doFD(ImgBufQueNode const& rQueNode, bool &rIsDetected_FD, bool &rIsDetected_SD, bool rDoSD, bool &rIsDetected_GD, bool rDoGD) { bool ret = true; MINT32 SD_Result, GD_Result; MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "+"); //MY_LOGD("Rotation_Info1:%d", Rotation_Info); //********************************************************************************************// int srcWidth=0, srcHeight=0; mpParamsMgr->getPreviewSize(&srcWidth, &srcHeight); //********************************************************************************************// dst_rgb = (unsigned char *)DDPBuffer; src_buf = (unsigned char *)rQueNode.getImgBuf()->getVirAddr(); dst_y = (unsigned char *)ExtractYBuffer; g_BufferGroup = doBufferAnalysis(rQueNode); //g_BufferGroup = 1; //mpFDHalObj->halFDBufferCreate(dst_rgb, src_buf, g_BufferGroup); //if(numFace>0) //ASD buffer mpFDHalObj->halFTBufferCreate(dst_rgb, src_buf, plane, srcWidth, srcHeight); if(plane == 1) { mpFDHalObj->halFDYUYV2ExtractY(dst_y, src_buf, srcWidth, srcHeight); mpFDHalObj->halFDDo((unsigned char *)0, dst_rgb, dst_y, rDoSD, Rotation_Info, (unsigned char *)rQueNode.getImgBuf()->getPhyAddr()); } else mpFDHalObj->halFDDo((unsigned char *)0, dst_rgb, (unsigned char *)rQueNode.getImgBuf()->getVirAddr(), rDoSD, Rotation_Info, (unsigned char *)rQueNode.getImgBuf()->getPhyAddr()); if( NULL != mpDetectedFaces ) numFace = mpFDHalObj->halFDGetFaceResult(mpDetectedFaces); else MY_LOGW("Get FD Result Fail!"); if(rDoGD == 1) { if(plane == 1) mpGDHalObj->halGSDo(dst_y, Rotation_Info); else mpGDHalObj->halGSDo((MUINT8*)rQueNode.getImgBuf()->getVirAddr(), Rotation_Info); } //********************************************************************************************// #if (GET_FD_RESULT) MY_LOGD("Scenario FD Num: %d",numFace ); if(numFace>0) rIsDetected_FD = 1; else rIsDetected_FD = 0; #endif #if (GET_SD_RESULT) SD_Result = mpFDHalObj->halSDGetSmileResult(); MY_LOGD("Scenario SD Result1: %d",SD_Result ); if(SD_Result>0) rIsDetected_SD = 1; else rIsDetected_SD = 0; #endif #if (GET_GD_RESULT) if(rDoGD == 1) { if( NULL != mpDetectedGestures ) GD_Result = mpGDHalObj->halGSGetGestureResult(mpDetectedGestures); ///////////////////////////////////////////////////////////////////// // cpchen: filter GS results with FD results: no gesture inside face regions ///////////////////////////////////////////////////////////////////// bool bEnableGSFilterWithFD = true; //bool bEnableGSFilterWithFD = false; float fIntersetAreaRatio = 0.25f; float fMaxRelativeRatio = 3.0f; if( bEnableGSFilterWithFD ) { int newCount = 0; for (int gi = 0; gi < mpDetectedGestures->number_of_faces; ++gi) { // gesture rectangle int gx0 = mpDetectedGestures->faces[gi].rect[0]; int gy0 = mpDetectedGestures->faces[gi].rect[1]; int gx1 = mpDetectedGestures->faces[gi].rect[2]; int gy1 = mpDetectedGestures->faces[gi].rect[3]; int garea = (gx1 - gx0) * (gy1 - gy0); bool bIsOverlap = false; for (int fi = 0; fi < mpDetectedFaces->number_of_faces; ++fi) { // face rectangle int fx0 = mpDetectedFaces->faces[fi].rect[0]; int fy0 = mpDetectedFaces->faces[fi].rect[1]; int fx1 = mpDetectedFaces->faces[fi].rect[2]; int fy1 = mpDetectedFaces->faces[fi].rect[3]; int farea = (fx1 - fx0) * (fy1 - fy0); // interset rectangle int ix0 = max(gx0, fx0); int iy0 = max(gy0, fy0); int ix1 = min(gx1, fx1); int iy1 = min(gy1, fy1); int iarea = 0; if ((ix1 > ix0) && (iy1 > iy0)) iarea = (ix1 - ix0) * (iy1 - iy0); // overlap determination float minArea = min(garea, farea); float overlapRatio = (float)iarea / minArea; float relativeRatio = (float)farea / garea; // if ( overlapRatio >= fIntersetAreaRatio && // relativeRatio <= fMaxRelativeRatio && relativeRatio >= (1.0 / fMaxRelativeRatio) ) if (overlapRatio >= fIntersetAreaRatio) { //MY_LOGD("Gesture overlap with Face: (%d,%d,%d,%d) + (%d,%d,%d,%d) = (%d,%d,%d,%d)\n", gx0, gy0, gx1, gy1, fx0, fy0, fx1, fy1, ix0, iy0, ix1, iy1, iarea); //MY_LOGD("Gesture overlap ratio = %.3f, area = %d, minArea = %.0f\n", overlapRatio, iarea, minArea); bIsOverlap = true; break; } } // end of for each face rectangle // skip overlapped gesture rectangles, move non-overlapped gesture rectangles forward if (!bIsOverlap) { mpDetectedGestures->faces[newCount].rect[0] = mpDetectedGestures->faces[gi].rect[0]; mpDetectedGestures->faces[newCount].rect[1] = mpDetectedGestures->faces[gi].rect[1]; mpDetectedGestures->faces[newCount].rect[2] = mpDetectedGestures->faces[gi].rect[2]; mpDetectedGestures->faces[newCount].rect[3] = mpDetectedGestures->faces[gi].rect[3]; mpDetectedGestures->faces[newCount].score = mpDetectedGestures->faces[gi].score; mpDetectedGestures->faces[newCount].id = mpDetectedGestures->faces[gi].id; mpDetectedGestures->faces[newCount].left_eye[0] = mpDetectedGestures->faces[gi].left_eye[0]; mpDetectedGestures->faces[newCount].left_eye[1] = mpDetectedGestures->faces[gi].left_eye[1]; mpDetectedGestures->faces[newCount].right_eye[0] = mpDetectedGestures->faces[gi].right_eye[0]; mpDetectedGestures->faces[newCount].right_eye[1] = mpDetectedGestures->faces[gi].right_eye[1]; mpDetectedGestures->faces[newCount].mouth[0] = mpDetectedGestures->faces[gi].mouth[0]; mpDetectedGestures->faces[newCount].mouth[1] = mpDetectedGestures->faces[gi].mouth[1]; mpDetectedGestures->posInfo[newCount].rop_dir = mpDetectedGestures->posInfo[gi].rop_dir; mpDetectedGestures->posInfo[newCount].rip_dir = mpDetectedGestures->posInfo[gi].rip_dir; ++newCount; } } // number of gesture rectangles after filtering mpDetectedGestures->number_of_faces = newCount; GD_Result = newCount; // debug message if (GD_Result == 0) MY_LOGD("Scenario GD: Gesture detected but filtered out by face!!!"); } ///////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////// // cpchen: face is a prerequiste of gesture shot, no face no gesture shot ///////////////////////////////////////////////////////////////////// bool bEnableGSPrerequisteWithFD = true; if (bEnableGSPrerequisteWithFD && mpDetectedFaces->number_of_faces == 0) { mpDetectedGestures->number_of_faces = 0; GD_Result = 0; // debug message MY_LOGD("Scenario GD: Gesture detected but no face!"); } ///////////////////////////////////////////////////////////////////// MY_LOGD("Scenario GD Result: %d",GD_Result ); if(GD_Result>0) rIsDetected_GD = 1; else rIsDetected_GD = 0; #endif } //mpFDHalObj->halFDASDBufferCreate(dst_rgb, src_buf, plane); MY_LOGD_IF(ENABLE_LOG_PER_FRAME, "-"); return ret; }
MBOOL EngBufHandlerImpl:: enqueBuffer(MUINT32 const data, IImageBuffer const * pImageBuffer) { Mutex::Autolock _l(mLock); // MINT32 i, bufQueIdx = mapNode2Dst(data); ImgBufQueNode keepImgBufQueNode; // #if 0 MY_LOGD("data(0x%08X)",data); #endif // if(bufQueIdx == -1) { return MFALSE; } // if(bufQueIdx >= 0) { if(mvBufQueNode[bufQueIdx].size() > 0) { keepImgBufQueNode = mvBufQueNode[bufQueIdx][0]; } else { MY_LOGE("mvBufQueNode[%d] size(%d) = 0", bufQueIdx, mvBufQueNode[bufQueIdx].size()); return MFALSE; } } else { MY_LOGE("bufQueIdx(%d) < 0",bufQueIdx); } // MUINTPTR keepAddr = (MUINTPTR)(mvBufQueNode[bufQueIdx][0].getImgBuf()->getVirAddr()); MUINTPTR enqueAddr = (MUINTPTR)(GET_IIMAGEBUFFER_BUF_VA(pImageBuffer, 0)); // #if 0 MY_LOGD("Addr(0x%08X/0x%08X),Port(%d)", keepAddr, enqueAddr, mvBufQueNode[bufQueIdx][0].getCookieDE()); #endif // if(keepAddr == enqueAddr) { MBOOL isAPClientFromFD = MFALSE; sp<IImgBufProvider> bufProvider = NULL; IImageBuffer* tempBuffer = const_cast<IImageBuffer*>(pImageBuffer); // switch(keepImgBufQueNode.getCookieDE()) { case eBuf_Disp: { bufProvider = mspImgBufProvidersMgr->getDisplayPvdr(); break; } case eBuf_Rec: { bufProvider = mspImgBufProvidersMgr->getRecCBPvdr(); break; } case eBuf_AP: { bufProvider = mspImgBufProvidersMgr->getPrvCBPvdr(); const_cast<ImgBufQueNode*>(&keepImgBufQueNode)->setCookieDE(0); // 0 for preview break; } case eBuf_Generic: { bufProvider = mspImgBufProvidersMgr->getGenericBufPvdr(); break; } case eBuf_FD: { bufProvider = mspImgBufProvidersMgr->getFDBufPvdr(); isAPClientFromFD = MTRUE; break; } case eBuf_OT: { bufProvider = mspImgBufProvidersMgr->getOTBufPvdr(); break; } default: { MY_LOGE("unknown port(%d)",keepImgBufQueNode.getCookieDE()); return MFALSE; } } // if (bufProvider == NULL) { MY_LOGW("bufProvider(%d) is not available, drop it!", keepImgBufQueNode.getCookieDE()); tempBuffer->unlockBuf(LOG_TAG); tempBuffer->decStrong(tempBuffer); mvBufQueNode[bufQueIdx].erase(mvBufQueNode[bufQueIdx].begin()); return MTRUE; } else { const_cast<ImgBufQueNode*>(&(keepImgBufQueNode))->setStatus(ImgBufQueNode::eSTATUS_DONE); const_cast<ImgBufQueNode*>(&(keepImgBufQueNode))->getImgBuf()->setTimestamp(pImageBuffer->getTimestamp()); // char debugMsg[150]; sprintf(debugMsg, "buf(%p),heap(%p),VA(0x%08X),BS(%d),Id(%d),TS(%d.%06d),F(0x%08X),S(%dx%d),Str(%d,%d,%d)", pImageBuffer, pImageBuffer->getImageBufferHeap(), GET_IIMAGEBUFFER_BUF_VA(pImageBuffer, 0), ( GET_IIMAGEBUFFER_BUF_SIZE(pImageBuffer, 0)+ GET_IIMAGEBUFFER_BUF_SIZE(pImageBuffer, 1)+ GET_IIMAGEBUFFER_BUF_SIZE(pImageBuffer, 2)), pImageBuffer->getFD(0), (MUINT32)((pImageBuffer->getTimestamp()/1000)/1000000), (MUINT32)((pImageBuffer->getTimestamp()/1000)%1000000), pImageBuffer->getImgFormat(), pImageBuffer->getImgSize().w, pImageBuffer->getImgSize().h, GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImageBuffer, 0), GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImageBuffer, 1), GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImageBuffer, 2)); // tempBuffer->unlockBuf(LOG_TAG); tempBuffer->decStrong(tempBuffer); // bufProvider->enqueProvider(keepImgBufQueNode); // only dequeue is not from APClient if(isAPClientFromFD) { // If APClient exists, copy to it sp<IImgBufProvider> pBufProvider; pBufProvider = mspImgBufProvidersMgr->getAPClientBufPvdr(); ImgBufQueNode APClientnode; if (pBufProvider != 0 && pBufProvider->dequeProvider(APClientnode)) { MY_LOGD("APClient size:%d, fdClient size:%d", APClientnode.getImgBuf()->getBufSize() , keepImgBufQueNode.getImgBuf()->getBufSize()); //if ( APClientnode.getImgBuf()->getBufSize() >= keepImgBufQueNode.getImgBuf()->getBufSize()) if (1) { MY_LOGD("APClient addr:0x%x, FDCLient addr:0x%x", APClientnode.getImgBuf()->getVirAddr(), keepImgBufQueNode.getImgBuf()->getVirAddr()); memcpy(APClientnode.getImgBuf()->getVirAddr(), keepImgBufQueNode.getImgBuf()->getVirAddr(), APClientnode.getImgBuf()->getBufSize()); //keepImgBufQueNode.getImgBuf()->getBufSize()); const_cast<ImgBufQueNode*>(&APClientnode)->setStatus(ImgBufQueNode::eSTATUS_DONE); } else { MY_LOGE("APClient buffer size < FD buffer size"); const_cast<ImgBufQueNode*>(&APClientnode)->setStatus(ImgBufQueNode::eSTATUS_CANCEL); } // pBufProvider->enqueProvider(APClientnode); } } // mvBufQueNode[bufQueIdx].erase(mvBufQueNode[bufQueIdx].begin()); // #if 1 MY_LOGD("%s",debugMsg); #endif // return MTRUE; } } else { MY_LOGE("Addr(0x%X != 0x%X),Port(%d), drop it!", keepAddr, enqueAddr, mvBufQueNode[bufQueIdx][0].getCookieDE()); return MFALSE; } }
MBOOL EngBufHandlerImpl:: dequeBuffer(MUINT32 const data, ImgRequest * pImgReq) { Mutex::Autolock _l(mLock); // MBOOL isDequeProvider = MFALSE; MBOOL doCacheInvalid = MFALSE; MINT32 bufQueIdx = mapNode2Dst(data); ImgBufQueNode node; list<MAP_PORT_INFO>::iterator iterMapPort; // #if 0 MY_LOGD("data(0x%08X)",data); #endif // if(bufQueIdx == -1) { return MFALSE; } // for(iterMapPort = mlMapPort[bufQueIdx].begin(); iterMapPort != mlMapPort[bufQueIdx].end(); iterMapPort++) { #if 0 MY_LOGD("bufQueIdx(%d),data(%d,%d),bufType(%d)", bufQueIdx,data, (*iterMapPort).nodeType, (*iterMapPort).bufType); #endif if(data == (*iterMapPort).nodeType) { sp<IImgBufProvider> bufProvider = NULL; pImgReq->mUsage = NSIoPipe::EPortCapbility_None; switch((*iterMapPort).bufType) { case eBuf_Disp: { bufProvider = mspImgBufProvidersMgr->getDisplayPvdr(); pImgReq->mUsage = NSIoPipe::EPortCapbility_Disp; break; } case eBuf_Rec: { bufProvider = mspImgBufProvidersMgr->getRecCBPvdr(); pImgReq->mUsage = NSIoPipe::EPortCapbility_Rcrd; break; } case eBuf_AP: { bufProvider = mspImgBufProvidersMgr->getPrvCBPvdr(); doCacheInvalid = MTRUE; break; } case eBuf_Generic: { bufProvider = mspImgBufProvidersMgr->getGenericBufPvdr(); break; } case eBuf_FD: { bufProvider = mspImgBufProvidersMgr->getFDBufPvdr(); break; } case eBuf_OT: { bufProvider = mspImgBufProvidersMgr->getOTBufPvdr(); break; } default: { MY_LOGE("un-supported bufType(%d)",(*iterMapPort).bufType); return MFALSE; } } // if(bufProvider != 0 && bufProvider->dequeProvider(node)) { node.setCookieDE((*iterMapPort).bufType); mvBufQueNode[bufQueIdx].push_back(node); isDequeProvider = MTRUE; break; } } } // if(isDequeProvider) { size_t bufStridesInBytes[] = { GET_IIMGBUF_IMG_STRIDE_IN_BYTE(node.getImgBuf(), 0), GET_IIMGBUF_IMG_STRIDE_IN_BYTE(node.getImgBuf(), 1), GET_IIMGBUF_IMG_STRIDE_IN_BYTE(node.getImgBuf(), 2)}; size_t bufBoundaryInBytes[] = {0,0,0}; IImageBufferAllocator::ImgParam imgParam = IImageBufferAllocator::ImgParam( Format::queryImageFormat(node.getImgBuf()->getImgFormat().string()), MSize( node.getImgBuf()->getImgWidth(), node.getImgBuf()->getImgHeight()), bufStridesInBytes, bufBoundaryInBytes, Format::queryPlaneCount(Format::queryImageFormat(node.getImgBuf()->getImgFormat().string()))); PortBufInfo_v1 portBufInfo = PortBufInfo_v1( node.getImgBuf()->getIonFd(), (MUINTPTR)node.getImgBuf()->getVirAddr(), 0, node.getImgBuf()->getBufSecu(), node.getImgBuf()->getBufCohe()); // sp<ImageBufferHeap> pHeap = ImageBufferHeap::create( LOG_TAG, imgParam, portBufInfo, mbEnableIImageBufferLog); if(pHeap == 0) { MY_LOGE("pHeap is NULL"); return MFALSE; } // IImageBuffer* tempBuffer = pHeap->createImageBuffer(); tempBuffer->incStrong(tempBuffer); tempBuffer->lockBuf( LOG_TAG, eBUFFER_USAGE_HW_CAMERA_READWRITE | eBUFFER_USAGE_SW_READ_OFTEN); if( doCacheInvalid ) { if( !tempBuffer->syncCache(eCACHECTRL_INVALID) ) MY_LOGE("invalid cache failed imgbuf 0x%x", tempBuffer); } pImgReq->mBuffer = tempBuffer; if(mbIsForceRotation) { pImgReq->mTransform = mRotationAnagle == 0 ? 0 : mRotationAnagle == 90 ? eTransform_ROT_90 : mRotationAnagle == 180 ? eTransform_ROT_180 : eTransform_ROT_270; } else { pImgReq->mTransform = node.getRotation() == 0 ? 0 : node.getRotation() == 90 ? eTransform_ROT_90 : node.getRotation() == 180 ? eTransform_ROT_180 : eTransform_ROT_270; } // #if 0 MY_LOGD("Node:DE(%d),VA(0x%08X),S(%d),Id(%d)", node.getCookieDE(), (MUINT32)node.getImgBuf()->getVirAddr(), node.getImgBuf()->getBufSize(), node.getImgBuf()->getIonFd()); MY_LOGD("Node:F(%s),W(%d),H(%d),Str(%d,%d,%d),Rot(%d)", node.getImgBuf()->getImgFormat().string(), node.getImgBuf()->getImgWidth(), node.getImgBuf()->getImgHeight(), GET_IIMGBUF_IMG_W_STRIDE(node.getImgBuf(), 0), GET_IIMGBUF_IMG_W_STRIDE(node.getImgBuf(), 1), GET_IIMGBUF_IMG_W_STRIDE(node.getImgBuf(), 2), node.getRotation()); #endif // #if 1 MY_LOGD("buf(%p),heap(%p),VA(0x%08X/0x%08X/0x%08X),PA(0x%08X/0x%08X/0x%08X),BS(%d=%d+%d+%d),Id(%d),F(0x%08X),S(%dx%d),Str(%d,%d,%d),R(%d),U(%d)", pImgReq->mBuffer, pImgReq->mBuffer->getImageBufferHeap(), GET_IIMAGEBUFFER_BUF_VA(pImgReq->mBuffer, 0), GET_IIMAGEBUFFER_BUF_VA(pImgReq->mBuffer, 1), GET_IIMAGEBUFFER_BUF_VA(pImgReq->mBuffer, 2), GET_IIMAGEBUFFER_BUF_PA(pImgReq->mBuffer, 0), GET_IIMAGEBUFFER_BUF_PA(pImgReq->mBuffer, 1), GET_IIMAGEBUFFER_BUF_PA(pImgReq->mBuffer, 2), ( GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 0)+ GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 1)+ GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 2)), GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 0), GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 1), GET_IIMAGEBUFFER_BUF_SIZE(pImgReq->mBuffer, 2), pImgReq->mBuffer->getFD(), pImgReq->mBuffer->getImgFormat(), pImgReq->mBuffer->getImgSize().w, pImgReq->mBuffer->getImgSize().h, GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImgReq->mBuffer, 0), GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImgReq->mBuffer, 1), GET_IIMAGEBUFFER_BUF_STRIDE_IN_BYTE(pImgReq->mBuffer, 2), pImgReq->mTransform, pImgReq->mUsage); #endif // return MTRUE; } // #if 0 MY_LOGD("empty data(0x%08X)",data); #endif return MFALSE; }