summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTyler Luu <tluu@ti.com>2012-03-26 19:09:14 -0500
committerDaniel Levin <dendy@ti.com>2012-07-25 08:55:45 -0500
commitf1582e6e9dc33bf5cd13c24e0e755edbaaec9868 (patch)
treea79a61495588d03156f697b9160c21206ad4d3b8
parent69a4da08343fcf51fb3181422c84f9bb2af8dfe6 (diff)
downloadhardware_ti_omap4-f1582e6e9dc33bf5cd13c24e0e755edbaaec9868.tar.gz
hardware_ti_omap4-f1582e6e9dc33bf5cd13c24e0e755edbaaec9868.tar.bz2
hardware_ti_omap4-f1582e6e9dc33bf5cd13c24e0e755edbaaec9868.zip
camera: add reprocess() functionality
implementation for reprocess state change sequence should look like this: preview->loaded_reprocess->loaded_reprocess_capture-> reprocess Reprocess uses takePicture call to send output buffers to camera adapter and to signal start reprocess. Change-Id: I98a7ccd32778760603e9c367ab3cd4ef30fab8dc Signed-off-by: Tyler Luu <tluu@ti.com>
-rw-r--r--camera/Android.mk1
-rw-r--r--camera/AppCallbackNotifier.cpp2
-rw-r--r--camera/BaseCameraAdapter.cpp149
-rw-r--r--camera/BufferSourceAdapter.cpp4
-rw-r--r--camera/CameraHal.cpp92
-rw-r--r--camera/CameraHal_Module.cpp36
-rw-r--r--camera/OMXCameraAdapter/OMXCameraAdapter.cpp67
-rw-r--r--camera/OMXCameraAdapter/OMXCapture.cpp86
-rw-r--r--camera/OMXCameraAdapter/OMXReprocess.cpp325
-rw-r--r--camera/inc/BaseCameraAdapter.h6
-rw-r--r--camera/inc/CameraHal.h71
-rw-r--r--camera/inc/OMXCameraAdapter/OMXCameraAdapter.h20
12 files changed, 802 insertions, 57 deletions
diff --git a/camera/Android.mk b/camera/Android.mk
index 68e30f0..48bdf48 100644
--- a/camera/Android.mk
+++ b/camera/Android.mk
@@ -59,6 +59,7 @@ OMAP4_CAMERA_OMX_SRC:= \
OMXCameraAdapter/OMXCameraAdapter.cpp \
OMXCameraAdapter/OMXCapabilities.cpp \
OMXCameraAdapter/OMXCapture.cpp \
+ OMXCameraAdapter/OMXReprocess.cpp \
OMXCameraAdapter/OMXDefaults.cpp \
OMXCameraAdapter/OMXExif.cpp \
OMXCameraAdapter/OMXFD.cpp \
diff --git a/camera/AppCallbackNotifier.cpp b/camera/AppCallbackNotifier.cpp
index 3b9c63f..28cac05 100644
--- a/camera/AppCallbackNotifier.cpp
+++ b/camera/AppCallbackNotifier.cpp
@@ -619,7 +619,7 @@ void AppCallbackNotifier::copyAndSendPictureFrame(CameraFrame* frame, int32_t ms
void *dest = NULL, *src = NULL;
// scope for lock
- {
+ if (mCameraHal->msgTypeEnabled(msgType)) {
Mutex::Autolock lock(mLock);
if(mNotifierState != AppCallbackNotifier::NOTIFIER_STARTED) {
diff --git a/camera/BaseCameraAdapter.cpp b/camera/BaseCameraAdapter.cpp
index fe4e9b2..05a32c4 100644
--- a/camera/BaseCameraAdapter.cpp
+++ b/camera/BaseCameraAdapter.cpp
@@ -46,7 +46,9 @@ const LUT cameraCommandsUserToHAL[] = {
{ "CAMERA_START_FD", CameraAdapter::CAMERA_START_FD },
{ "CAMERA_STOP_FD", CameraAdapter::CAMERA_STOP_FD },
{ "CAMERA_SWITCH_TO_EXECUTING", CameraAdapter::CAMERA_SWITCH_TO_EXECUTING },
- { "CAMERA_USE_BUFFERS_VIDEO_CAPTURE", CameraAdapter::CAMERA_USE_BUFFERS_VIDEO_CAPTURE }
+ { "CAMERA_USE_BUFFERS_VIDEO_CAPTURE", CameraAdapter::CAMERA_USE_BUFFERS_VIDEO_CAPTURE },
+ { "CAMERA_USE_BUFFERS_REPROCESS", CameraAdapter::CAMERA_USE_BUFFERS_REPROCESS },
+ { "CAMERA_START_REPROCESS", CameraAdapter::CAMERA_START_REPROCESS }
};
const LUTtypeHAL CamCommandsLUT =
@@ -103,6 +105,7 @@ BaseCameraAdapter::~BaseCameraAdapter()
mImageSubscribers.clear();
mRawSubscribers.clear();
mVideoSubscribers.clear();
+ mVideoInSubscribers.clear();
mFocusSubscribers.clear();
mShutterSubscribers.clear();
mZoomSubscribers.clear();
@@ -190,6 +193,9 @@ void BaseCameraAdapter::enableMsgType(int32_t msgs, frame_callback callback, eve
case CameraFrame::VIDEO_FRAME_SYNC:
mVideoSubscribers.add((int) cookie, callback);
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME:
+ mVideoInSubscribers.add((int) cookie, callback);
+ break;
default:
CAMHAL_LOGEA("Frame message type id=0x%x subscription no supported yet!", frameMsg);
break;
@@ -244,12 +250,16 @@ void BaseCameraAdapter::disableMsgType(int32_t msgs, void* cookie)
case CameraFrame::VIDEO_FRAME_SYNC:
mVideoSubscribers.removeItem((int) cookie);
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME:
+ mVideoInSubscribers.removeItem((int) cookie);
+ break;
case CameraFrame::ALL_FRAMES:
mFrameSubscribers.removeItem((int) cookie);
mFrameDataSubscribers.removeItem((int) cookie);
mImageSubscribers.removeItem((int) cookie);
mRawSubscribers.removeItem((int) cookie);
mVideoSubscribers.removeItem((int) cookie);
+ mVideoInSubscribers.removeItem((int) cookie);
break;
default:
CAMHAL_LOGEA("Frame message type id=0x%x subscription remove not supported yet!", frameMsg);
@@ -551,6 +561,46 @@ status_t BaseCameraAdapter::sendCommand(CameraCommands operation, int value1, in
break;
+ case CameraAdapter::CAMERA_USE_BUFFERS_REPROCESS:
+ CAMHAL_LOGDA("Use buffers for reprocessing");
+ desc = (BuffersDescriptor *) value1;
+
+ if (NULL == desc) {
+ CAMHAL_LOGEA("Invalid capture buffers!");
+ return -EINVAL;
+ }
+
+ if (ret == NO_ERROR) {
+ ret = setState(operation);
+ }
+
+ if (ret == NO_ERROR) {
+ Mutex::Autolock lock(mVideoInBufferLock);
+ mVideoInBuffers = desc->mBuffers;
+ mVideoInBuffersAvailable.clear();
+ for (uint32_t i = 0 ; i < desc->mMaxQueueable ; i++) {
+ mVideoInBuffersAvailable.add(&mVideoInBuffers[i], 0);
+ }
+ // initial ref count for undeqeueued buffers is 1 since buffer provider
+ // is still holding on to it
+ for ( uint32_t i = desc->mMaxQueueable ; i < desc->mCount ; i++ ) {
+ mVideoInBuffersAvailable.add(&mVideoInBuffers[i], 1);
+ }
+ ret = useBuffers(CameraAdapter::CAMERA_REPROCESS,
+ desc->mBuffers,
+ desc->mCount,
+ desc->mLength,
+ desc->mMaxQueueable);
+ }
+
+ if ( ret == NO_ERROR ) {
+ ret = commitState();
+ } else {
+ ret |= rollbackState();
+ }
+
+ break;
+
case CameraAdapter::CAMERA_START_SMOOTH_ZOOM:
{
@@ -1262,6 +1312,11 @@ status_t BaseCameraAdapter::sendFrameToSubscribers(CameraFrame *frame)
ret = __sendFrameToSubscribers(frame, &mFrameDataSubscribers, CameraFrame::FRAME_DATA_SYNC);
}
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME:
+ {
+ ret = __sendFrameToSubscribers(frame, &mVideoInSubscribers, CameraFrame::REPROCESS_INPUT_FRAME);
+ }
+ break;
default:
CAMHAL_LOGEB("FRAMETYPE NOT SUPPORTED 0x%x", mask);
break;
@@ -1385,6 +1440,11 @@ int BaseCameraAdapter::setInitFrameRefCount(CameraBuffer * buf, unsigned int mas
setFrameRefCount(buf, CameraFrame::FRAME_DATA_SYNC, mFrameDataSubscribers.size());
}
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME:
+ {
+ setFrameRefCount(buf,CameraFrame::REPROCESS_INPUT_FRAME, mVideoInSubscribers.size());
+ }
+ break;
default:
CAMHAL_LOGEB("FRAMETYPE NOT SUPPORTED 0x%x", lmask);
break;
@@ -1430,6 +1490,11 @@ int BaseCameraAdapter::getFrameRefCount(CameraBuffer * frameBuf, CameraFrame::Fr
res = mVideoBuffersAvailable.valueFor(frameBuf );
}
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME: {
+ Mutex::Autolock lock(mVideoInBufferLock);
+ res = mVideoInBuffersAvailable.valueFor(frameBuf );
+ }
+ break;
default:
break;
};
@@ -1472,6 +1537,11 @@ void BaseCameraAdapter::setFrameRefCount(CameraBuffer * frameBuf, CameraFrame::F
mVideoBuffersAvailable.replaceValueFor(frameBuf, refCount);
}
break;
+ case CameraFrame::REPROCESS_INPUT_FRAME: {
+ Mutex::Autolock lock(mVideoInBufferLock);
+ mVideoInBuffersAvailable.replaceValueFor(frameBuf, refCount);
+ }
+ break;
default:
break;
};
@@ -1860,6 +1930,12 @@ status_t BaseCameraAdapter::setState(CameraCommands operation)
mNextState = LOADED_CAPTURE_STATE;
break;
+ case CAMERA_USE_BUFFERS_REPROCESS:
+ CAMHAL_LOGDB("Adapter state switch PREVIEW_STATE->LOADED_REPROCESS_STATE event = %s",
+ printState);
+ mNextState = LOADED_REPROCESS_STATE;
+ break;
+
case CAMERA_START_VIDEO:
CAMHAL_LOGDB("Adapter state switch PREVIEW_STATE->VIDEO_STATE event = %s",
printState);
@@ -1884,6 +1960,42 @@ status_t BaseCameraAdapter::setState(CameraCommands operation)
break;
+ case LOADED_REPROCESS_STATE:
+ switch (operation) {
+ case CAMERA_USE_BUFFERS_IMAGE_CAPTURE:
+ CAMHAL_LOGDB("Adapter state switch LOADED_REPROCESS_STATE->LOADED_REPROCESS_CAPTURE_STATE event = %s",
+ printState);
+ mNextState = LOADED_REPROCESS_CAPTURE_STATE;
+ break;
+ case CAMERA_QUERY_BUFFER_SIZE_IMAGE_CAPTURE:
+ CAMHAL_LOGDB("Adapter state switch LOADED_REPROCESS_STATE->LOADED_REPROCESS_STATE event = %s",
+ printState);
+ mNextState = LOADED_REPROCESS_STATE;
+ break;
+ default:
+ CAMHAL_LOGEB("Adapter state switch LOADED_REPROCESS_STATE Invalid Op! event = %s",
+ printState);
+ ret = INVALID_OPERATION;
+ break;
+ }
+
+ break;
+
+ case LOADED_REPROCESS_CAPTURE_STATE:
+ switch (operation) {
+ case CAMERA_START_IMAGE_CAPTURE:
+ CAMHAL_LOGDB("Adapter state switch LOADED_REPROCESS_CAPTURE_STATE->REPROCESS_STATE event = %s",
+ printState);
+ mNextState = REPROCESS_STATE;
+ break;
+ default:
+ CAMHAL_LOGEB("Adapter state switch LOADED_REPROCESS_CAPTURE_STATE Invalid Op! event = %s",
+ printState);
+ ret = INVALID_OPERATION;
+ break;
+ }
+ break;
+
case LOADED_CAPTURE_STATE:
switch ( operation )
@@ -1923,11 +2035,17 @@ status_t BaseCameraAdapter::setState(CameraCommands operation)
break;
case CAMERA_START_IMAGE_CAPTURE:
- CAMHAL_LOGDB("Adapter state switch CAPTURE_STATE->CAPTURE_STATE event = 0x%x",
- operation);
+ CAMHAL_LOGDB("Adapter state switch CAPTURE_STATE->CAPTURE_STATE event = %s",
+ printState);
mNextState = CAPTURE_STATE;
break;
+ case CAMERA_USE_BUFFERS_REPROCESS:
+ CAMHAL_LOGDB("Adapter state switch CAPTURE_STATE->->LOADED_REPROCESS_STATE event = %s",
+ printState);
+ mNextState = LOADED_REPROCESS_STATE;
+ break;
+
default:
CAMHAL_LOGEB("Adapter state switch CAPTURE_STATE Invalid Op! event = %s",
printState);
@@ -2214,6 +2332,31 @@ status_t BaseCameraAdapter::setState(CameraCommands operation)
break;
+ case REPROCESS_STATE:
+ switch (operation) {
+ case CAMERA_STOP_IMAGE_CAPTURE:
+ CAMHAL_LOGDB("Adapter state switch REPROCESS_STATE->PREVIEW_STATE event = %s",
+ printState);
+ mNextState = PREVIEW_STATE;
+ break;
+ case CAMERA_START_IMAGE_CAPTURE:
+ case CAMERA_USE_BUFFERS_REPROCESS:
+ CAMHAL_LOGDB("Adapter state switch REPROCESS_STATE->REPROCESS_STATE event = %s",
+ printState);
+ mNextState = REPROCESS_STATE;
+ break;
+
+ default:
+ CAMHAL_LOGEB("Adapter state switch REPROCESS_STATE Invalid Op! event = %s",
+ printState);
+ ret = INVALID_OPERATION;
+ break;
+
+ }
+
+ break;
+
+
default:
CAMHAL_LOGEA("Invalid Adapter state!");
ret = INVALID_OPERATION;
diff --git a/camera/BufferSourceAdapter.cpp b/camera/BufferSourceAdapter.cpp
index edf78fb..b11304d 100644
--- a/camera/BufferSourceAdapter.cpp
+++ b/camera/BufferSourceAdapter.cpp
@@ -429,7 +429,7 @@ CameraBuffer* BufferSourceAdapter::getBufferList(int *num) {
LOG_FUNCTION_NAME;
status_t err;
const int lnumBufs = 1;
- int format, stride;
+ int format;
GraphicBufferMapper &mapper = GraphicBufferMapper::get();
buffer_handle_t *handle;
@@ -442,7 +442,7 @@ CameraBuffer* BufferSourceAdapter::getBufferList(int *num) {
return NULL;
}
- err = mBufferSource->update_and_get_buffer(mBufferSource, &handle, &stride);
+ err = mBufferSource->update_and_get_buffer(mBufferSource, &handle, &mBuffers[0].stride);
if (err != 0) {
CAMHAL_LOGEB("update and get buffer failed: %s (%d)", strerror(-err), -err);
if ( ENODEV == err ) {
diff --git a/camera/CameraHal.cpp b/camera/CameraHal.cpp
index 840dc04..f3751b8 100644
--- a/camera/CameraHal.cpp
+++ b/camera/CameraHal.cpp
@@ -43,7 +43,7 @@ extern "C" CameraAdapter* V4LCameraAdapter_Factory(size_t);
//// Currently, they are hard-coded
const int CameraHal::NO_BUFFERS_PREVIEW = MAX_CAMERA_BUFFERS;
-const int CameraHal::NO_BUFFERS_IMAGE_CAPTURE = 9;
+const int CameraHal::NO_BUFFERS_IMAGE_CAPTURE = 5;
const int CameraHal::SW_SCALING_FPS_LIMIT = 15;
const uint32_t MessageNotifier::EVENT_BIT_FIELD_POSITION = 16;
@@ -2692,6 +2692,20 @@ status_t CameraHal::stopImageBracketing()
*/
status_t CameraHal::takePicture(const char *params)
{
+ Mutex::Autolock lock(mLock);
+ return __takePicture(params);
+}
+
+/**
+ @brief Internal function for getting a captured image.
+ shared by takePicture and reprocess.
+ @param none
+ @return NO_ERROR If able to switch to image capture
+ @todo Define error codes if unable to switch to image capture
+
+ */
+status_t CameraHal::__takePicture(const char *params)
+{
status_t ret = NO_ERROR;
CameraFrame frame;
CameraAdapter::BuffersDescriptor desc;
@@ -2702,8 +2716,6 @@ status_t CameraHal::takePicture(const char *params)
unsigned int rawBufferCount = 1;
bool isCPCamMode = false;
- Mutex::Autolock lock(mLock);
-
#if PPM_INSTRUMENTATION || PPM_INSTRUMENTATION_ABS
gettimeofday(&mStartCapture, NULL);
@@ -2775,8 +2787,9 @@ status_t CameraHal::takePicture(const char *params)
// if we are already in the middle of a capture...then we just need
// setParameters and start image capture to queue more shots
- if ((mCameraAdapter->getState() == CameraAdapter::CAPTURE_STATE &&
- mCameraAdapter->getNextState() != CameraAdapter::PREVIEW_STATE)) {
+ if (((mCameraAdapter->getState() & CameraAdapter::CAPTURE_STATE) ==
+ CameraAdapter::CAPTURE_STATE) &&
+ (mCameraAdapter->getNextState() != CameraAdapter::PREVIEW_STATE)) {
#if PPM_INSTRUMENTATION || PPM_INSTRUMENTATION_ABS
//pass capture timestamp along with the camera adapter command
ret = mCameraAdapter->sendCommand(CameraAdapter::CAMERA_START_IMAGE_CAPTURE,
@@ -3032,6 +3045,73 @@ char* CameraHal::getParameters()
return params_string;
}
+/**
+ @brief Starts reprocessing operation.
+ */
+status_t CameraHal::reprocess(const char *params)
+{
+ status_t ret = NO_ERROR;
+ int bufferCount = 0;
+ CameraAdapter::BuffersDescriptor desc;
+ CameraBuffer *reprocBuffers = NULL;
+ ShotParameters shotParams;
+
+ Mutex::Autolock lock(mLock);
+
+ LOG_FUNCTION_NAME;
+
+ // 1. Get buffers
+ if (mBufferSourceAdapter_In.get()) reprocBuffers = mBufferSourceAdapter_In->getBufferList(&bufferCount);
+ if (!reprocBuffers) {
+ CAMHAL_LOGE("Error: couldn't get input buffers for reprocess()");
+ goto exit;
+ }
+
+ // 2. Get buffer information and parse parameters
+ {
+ shotParams.setBurst(bufferCount);
+ }
+
+ // 3. Give buffer to camera adapter
+ desc.mBuffers = reprocBuffers;
+ desc.mOffsets = 0;
+ desc.mFd = 0;
+ desc.mLength = 0;
+ desc.mCount = (size_t) bufferCount;
+ desc.mMaxQueueable = (size_t) bufferCount;
+ ret = mCameraAdapter->sendCommand(CameraAdapter::CAMERA_USE_BUFFERS_REPROCESS, (int) &desc);
+ if (ret != NO_ERROR) {
+ CAMHAL_LOGE("Error calling camera use buffers");
+ goto exit;
+ }
+
+ // 4. Start reprocessing
+ ret = mBufferSourceAdapter_In->enableDisplay(0, 0, NULL);
+ if (ret != NO_ERROR) {
+ CAMHAL_LOGE("Error enabling tap in point");
+ goto exit;
+ }
+
+ // 5. Start capturing
+ ret = __takePicture(shotParams.flatten().string());
+
+ exit:
+ return ret;
+}
+
+/**
+ @brief Cancels current reprocessing operation
+
+ */
+status_t CameraHal::cancel_reprocess( )
+{
+ LOG_FUNCTION_NAME;
+ status_t ret = NO_ERROR;
+
+ ret = signalEndImageCapture();
+ return NO_ERROR;
+}
+
void CameraHal::putParameters(char *parms)
{
free(parms);
@@ -3962,7 +4042,7 @@ void CameraHal::resetPreviewRes(CameraParameters *mParams, int width, int height
void *
camera_buffer_get_omx_ptr (CameraBuffer *buffer)
{
- CAMHAL_LOGD("buffer_type %d opaque %p", buffer->type, buffer->opaque);
+ CAMHAL_LOGV("buffer_type %d opaque %p", buffer->type, buffer->opaque);
if (buffer->type == CAMERA_BUFFER_ANW) {
buffer_handle_t *handle = (buffer_handle_t *)buffer->opaque;
diff --git a/camera/CameraHal_Module.cpp b/camera/CameraHal_Module.cpp
index 2181cc2..91baca6 100644
--- a/camera/CameraHal_Module.cpp
+++ b/camera/CameraHal_Module.cpp
@@ -365,6 +365,38 @@ int camera_cancel_picture(struct camera_device * device)
return rv;
}
+int camera_reprocess(struct camera_device * device, const char *params)
+{
+ int rv = -EINVAL;
+ ti_camera_device_t* ti_dev = NULL;
+
+ LOGV("%s", __FUNCTION__);
+
+ if(!device)
+ return rv;
+
+ ti_dev = (ti_camera_device_t*) device;
+
+ rv = gCameraHals[ti_dev->cameraid]->reprocess(params);
+ return rv;
+}
+
+int camera_cancel_reprocess(struct camera_device * device)
+{
+ int rv = -EINVAL;
+ ti_camera_device_t* ti_dev = NULL;
+
+ LOGV("%s", __FUNCTION__);
+
+ if(!device)
+ return rv;
+
+ ti_dev = (ti_camera_device_t*) device;
+
+ rv = gCameraHals[ti_dev->cameraid]->cancel_reprocess();
+ return rv;
+}
+
int camera_set_parameters(struct camera_device * device, const char *params)
{
int rv = -EINVAL;
@@ -588,6 +620,10 @@ int camera_device_open(const hw_module_t* module, const char* name,
camera_ops->send_command = camera_send_command;
camera_ops->release = camera_release;
camera_ops->dump = camera_dump;
+#ifdef OMAP_ENHANCEMENT
+ camera_ops->reprocess = camera_reprocess;
+ camera_ops->cancel_reprocess = camera_cancel_reprocess;
+#endif
*device = &camera_device->base.common;
diff --git a/camera/OMXCameraAdapter/OMXCameraAdapter.cpp b/camera/OMXCameraAdapter/OMXCameraAdapter.cpp
index 09d9b04..5f08a27 100644
--- a/camera/OMXCameraAdapter/OMXCameraAdapter.cpp
+++ b/camera/OMXCameraAdapter/OMXCameraAdapter.cpp
@@ -80,6 +80,7 @@ status_t OMXCameraAdapter::initialize(CameraProperties::Properties* caps)
mCameraAdapterParameters.mMeasurementPortIndex = OMX_CAMERA_PORT_VIDEO_OUT_MEASUREMENT;
//currently not supported use preview port instead
mCameraAdapterParameters.mVideoPortIndex = OMX_CAMERA_PORT_VIDEO_OUT_VIDEO;
+ mCameraAdapterParameters.mVideoInPortIndex = OMX_CAMERA_PORT_VIDEO_IN_VIDEO;
eError = OMX_Init();
if (eError != OMX_ErrorNone) {
@@ -180,6 +181,7 @@ status_t OMXCameraAdapter::initialize(CameraProperties::Properties* caps)
mCaptureSignalled = false;
mCaptureConfigured = false;
+ mReprocConfigured = false;
mRecording = false;
mWaitingForSnapshot = false;
mSnapshotCount = 0;
@@ -294,6 +296,7 @@ status_t OMXCameraAdapter::initialize(CameraProperties::Properties* caps)
memset(&mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mImagePortIndex], 0, sizeof(OMXCameraPortParameters));
memset(&mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mPrevPortIndex], 0, sizeof(OMXCameraPortParameters));
memset(&mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoPortIndex], 0, sizeof(OMXCameraPortParameters));
+ memset(&mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex], 0, sizeof(OMXCameraPortParameters));
// initialize 3A defaults
mParameters3A.Effect = getLUTvalue_HALtoOMX(OMXCameraAdapter::DEFAULT_EFFECT, EffLUT);
@@ -983,6 +986,13 @@ status_t OMXCameraAdapter::setFormat(OMX_U32 port, OMXCameraPortParameters &port
portCheck.format.image.nStride = 0;
portCheck.nBufferSize = portParams.mStride * portParams.mWidth * portParams.mHeight;
portCheck.nBufferCountActual = portParams.mNumBufs;
+ } else if (OMX_CAMERA_PORT_VIDEO_IN_VIDEO == port) {
+ portCheck.format.video.nFrameWidth = portParams.mWidth;
+ portCheck.format.video.nStride = portParams.mStride;
+ portCheck.format.video.nFrameHeight = portParams.mHeight;
+ portCheck.format.video.eColorFormat = portParams.mColorFormat;
+ portCheck.format.video.xFramerate = 30 << 16;
+ portCheck.nBufferCountActual = portParams.mNumBufs;
} else {
CAMHAL_LOGEB("Unsupported port index (%lu)", port);
}
@@ -1182,6 +1192,11 @@ status_t OMXCameraAdapter::useBuffers(CameraMode mode, CameraBuffer * bufArr, in
ret = UseBuffersPreviewData(bufArr, num);
break;
+ case CAMERA_REPROCESS:
+ mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex].mNumBufs = num;
+ mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex].mMaxQueueable = queueable;
+ ret = UseBuffersReprocess(bufArr, num);
+ break;
}
LOG_FUNCTION_NAME_EXIT;
@@ -2464,7 +2479,14 @@ status_t OMXCameraAdapter::takePicture()
}
}
- msg.command = CommandHandler::CAMERA_START_IMAGE_CAPTURE;
+ // TODO(XXX): re-using take picture to kick off reprocessing pipe
+ // Need to rethink this approach during reimplementation
+ if (mNextState == REPROCESS_STATE) {
+ msg.command = CommandHandler::CAMERA_START_REPROCESS;
+ } else {
+ msg.command = CommandHandler::CAMERA_START_IMAGE_CAPTURE;
+ }
+
msg.arg1 = mErrorNotifier;
ret = mCommandHandler->put(&msg);
@@ -2998,11 +3020,36 @@ OMX_ERRORTYPE OMXCameraAdapter::OMXCameraAdapterEmptyBufferDone(OMX_IN OMX_HANDL
OMX_IN OMX_BUFFERHEADERTYPE* pBuffHeader)
{
- LOG_FUNCTION_NAME;
+ LOG_FUNCTION_NAME;
+ status_t stat = NO_ERROR;
+ status_t res1, res2;
+ OMXCameraPortParameters *pPortParam;
+ CameraFrame::FrameType typeOfFrame = CameraFrame::ALL_FRAMES;
+ unsigned int refCount = 0;
+ unsigned int mask = 0xFFFF;
+ CameraFrame cameraFrame;
+ OMX_TI_PLATFORMPRIVATE *platformPrivate;
- LOG_FUNCTION_NAME_EXIT;
+ res1 = res2 = NO_ERROR;
+
+ if (!pBuffHeader || !pBuffHeader->pBuffer) {
+ CAMHAL_LOGE("NULL Buffer from OMX");
+ return OMX_ErrorNone;
+ }
+
+ pPortParam = &(mCameraAdapterParameters.mCameraPortParams[pBuffHeader->nInputPortIndex]);
+ platformPrivate = (OMX_TI_PLATFORMPRIVATE*) pBuffHeader->pPlatformPrivate;
+
+ if (pBuffHeader->nInputPortIndex == OMX_CAMERA_PORT_VIDEO_IN_VIDEO) {
+ typeOfFrame = CameraFrame::REPROCESS_INPUT_FRAME;
+ mask = (unsigned int)CameraFrame::REPROCESS_INPUT_FRAME;
+
+ stat = sendCallBacks(cameraFrame, pBuffHeader, mask, pPortParam);
+ }
+
+ LOG_FUNCTION_NAME_EXIT;
- return OMX_ErrorNone;
+ return OMX_ErrorNone;
}
static void debugShowFPS()
@@ -3518,8 +3565,14 @@ bool OMXCameraAdapter::CommandHandler::Handler()
}
case CommandHandler::CAMERA_SWITCH_TO_EXECUTING:
{
- stat = mCameraAdapter->doSwitchToExecuting();
- break;
+ stat = mCameraAdapter->doSwitchToExecuting();
+ break;
+ }
+ case CommandHandler::CAMERA_START_REPROCESS:
+ {
+ stat = mCameraAdapter->startReprocess();
+ stat = mCameraAdapter->startImageCapture(false);
+ break;
}
}
@@ -3670,10 +3723,12 @@ OMXCameraAdapter::OMXCameraAdapter(size_t sensor_index)
mUsePreviewDataSem.Create(0);
mUsePreviewSem.Create(0);
mUseCaptureSem.Create(0);
+ mUseReprocessSem.Create(0);
mStartPreviewSem.Create(0);
mStopPreviewSem.Create(0);
mStartCaptureSem.Create(0);
mStopCaptureSem.Create(0);
+ mStopReprocSem.Create(0);
mSwitchToLoadedSem.Create(0);
mCaptureSem.Create(0);
diff --git a/camera/OMXCameraAdapter/OMXCapture.cpp b/camera/OMXCameraAdapter/OMXCapture.cpp
index fa8acd5..e5e5bf5 100644
--- a/camera/OMXCameraAdapter/OMXCapture.cpp
+++ b/camera/OMXCameraAdapter/OMXCapture.cpp
@@ -304,6 +304,7 @@ status_t OMXCameraAdapter::setParametersCapture(const CameraParameters &params,
// shots
inCaptureState = (CAPTURE_ACTIVE & mAdapterState) && (CAPTURE_ACTIVE & mNextState);
if ((mPendingCaptureSettings & ~SetExpBracket) && !inCaptureState) {
+ disableReprocess();
disableImagePort();
if ( NULL != mReleaseImageBuffersCallback ) {
mReleaseImageBuffersCallback(mReleaseData);
@@ -480,8 +481,6 @@ status_t OMXCameraAdapter::doExposureBracketing(int *evValues,
}
}
- if (0) initInternalBuffers();
-
LOG_FUNCTION_NAME_EXIT;
return ret;
@@ -1052,6 +1051,29 @@ status_t OMXCameraAdapter::startImageCapture(bool bracketing)
}
}
+ // Choose proper single preview mode for cpcapture capture (reproc or hs)
+ if (( NO_ERROR == ret) && (OMXCameraAdapter::CP_CAM == mCapMode)) {
+ OMX_TI_CONFIG_SINGLEPREVIEWMODETYPE singlePrevMode;
+ OMX_INIT_STRUCT_PTR (&singlePrevMode, OMX_TI_CONFIG_SINGLEPREVIEWMODETYPE);
+ if (mAdapterState == CAPTURE_STATE) {
+ singlePrevMode.eMode = OMX_TI_SinglePreviewMode_ImageCaptureHighSpeed;
+ } else if (mAdapterState == REPROCESS_STATE) {
+ singlePrevMode.eMode = OMX_TI_SinglePreviewMode_Reprocess;
+ } else {
+ CAMHAL_LOGE("Wrong state trying to start a capture in CPCAM mode?");
+ singlePrevMode.eMode = OMX_TI_SinglePreviewMode_ImageCaptureHighSpeed;
+ }
+ eError = OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
+ (OMX_INDEXTYPE) OMX_TI_IndexConfigSinglePreviewMode,
+ &singlePrevMode);
+ if ( OMX_ErrorNone != eError ) {
+ CAMHAL_LOGEB("Error while configuring single preview mode 0x%x", eError);
+ ret = ErrorUtils::omxToAndroidError(eError);
+ } else {
+ CAMHAL_LOGDA("single preview mode configured successfully");
+ }
+ }
+
if ( NO_ERROR == ret ) {
if (mPendingCaptureSettings & SetRotation) {
mPendingCaptureSettings &= ~SetRotation;
@@ -1124,6 +1146,8 @@ status_t OMXCameraAdapter::startImageCapture(bool bracketing)
while ((mBurstFramesQueued < mBurstFramesAccum) && (index < capData->mNumBufs)) {
if (capData->mStatus[index] == OMXCameraPortParameters::IDLE) {
+ CAMHAL_LOGDB("Queuing buffer on Capture port - %p",
+ capData->mBufferHeader[index]->pBuffer);
capData->mStatus[index] = OMXCameraPortParameters::FILL;
eError = OMX_FillThisBuffer(mCameraAdapterParameters.mHandleComp,
(OMX_BUFFERHEADERTYPE*)capData->mBufferHeader[index]);
@@ -1135,9 +1159,9 @@ status_t OMXCameraAdapter::startImageCapture(bool bracketing)
} else if ( NO_ERROR == ret ) {
///Queue all the buffers on capture port
for ( int index = 0 ; index < capData->mMaxQueueable ; index++ ) {
- CAMHAL_LOGDB("Queuing buffer on Capture port - 0x%x",
- ( unsigned int ) capData->mBufferHeader[index]->pBuffer);
if (mBurstFramesQueued < mBurstFramesAccum) {
+ CAMHAL_LOGDB("Queuing buffer on Capture port - %p",
+ capData->mBufferHeader[index]->pBuffer);
capData->mStatus[index] = OMXCameraPortParameters::FILL;
eError = OMX_FillThisBuffer(mCameraAdapterParameters.mHandleComp,
(OMX_BUFFERHEADERTYPE*)capData->mBufferHeader[index]);
@@ -1249,6 +1273,11 @@ status_t OMXCameraAdapter::stopImageCapture()
goto EXIT;
}
+ // TODO(XXX): Reprocessing is currently piggy-backing capture commands
+ if (mAdapterState == REPROCESS_STATE) {
+ ret = stopReprocess();
+ }
+
//Disable the callback first
mWaitingForSnapshot = false;
mSnapshotCount = 0;
@@ -1319,6 +1348,16 @@ status_t OMXCameraAdapter::stopImageCapture()
mFirstFrameCondition.broadcast();
}
+ // Stop is always signalled externally in CPCAM mode
+ // We need to make sure we really stop
+ if ((mCapMode == CP_CAM)) {
+ disableReprocess();
+ disableImagePort();
+ if ( NULL != mReleaseImageBuffersCallback ) {
+ mReleaseImageBuffersCallback(mReleaseData);
+ }
+ }
+
return (ret | ErrorUtils::omxToAndroidError(eError));
EXIT:
@@ -1401,6 +1440,8 @@ status_t OMXCameraAdapter::disableImagePort(){
goto EXIT;
}
+ deinitInternalBuffers(mCameraAdapterParameters.mImagePortIndex);
+
if (mRawCapture) {
///Register for Video port Disable event
@@ -1439,16 +1480,15 @@ EXIT:
return (ret | ErrorUtils::omxToAndroidError(eError));
}
-status_t OMXCameraAdapter::initInternalBuffers(void)
+status_t OMXCameraAdapter::initInternalBuffers(OMX_U32 portIndex)
{
OMX_ERRORTYPE eError = OMX_ErrorNone;
- int ion_fd;
int index = 0;
OMX_TI_PARAM_USEBUFFERDESCRIPTOR bufferdesc;
/* Indicate to Ducati that we're planning to use dynamically-mapped buffers */
OMX_INIT_STRUCT_PTR (&bufferdesc, OMX_TI_PARAM_USEBUFFERDESCRIPTOR);
- bufferdesc.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
+ bufferdesc.nPortIndex = portIndex;
bufferdesc.bEnabled = OMX_FALSE;
bufferdesc.eBufferType = OMX_TI_BufferTypePhysicalPageList;
@@ -1460,14 +1500,12 @@ status_t OMXCameraAdapter::initInternalBuffers(void)
return -EINVAL;
}
- ion_fd = ion_open ();
-
CAMHAL_LOGDA("Initializing internal buffers");
do {
OMX_TI_PARAM_COMPONENTBUFALLOCTYPE bufferalloc;
OMX_TI_PARAM_COMPONENTBUFALLOCTYPE bufferallocset;
OMX_INIT_STRUCT_PTR (&bufferalloc, OMX_TI_PARAM_COMPONENTBUFALLOCTYPE);
- bufferalloc.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
+ bufferalloc.nPortIndex = portIndex;
bufferalloc.nIndex = index;
eError = OMX_GetParameter (mCameraAdapterParameters.mHandleComp,
@@ -1488,7 +1526,7 @@ status_t OMXCameraAdapter::initInternalBuffers(void)
bufferalloc.eBufType = OMX_TI_BufferTypeHardwareReserved1D;
OMX_INIT_STRUCT_PTR (&bufferallocset, OMX_TI_PARAM_COMPONENTBUFALLOCTYPE);
- bufferallocset.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
+ bufferallocset.nPortIndex = portIndex;
bufferallocset.nIndex = index;
bufferallocset.eBufType = OMX_TI_BufferTypeHardwareReserved1D;
bufferallocset.nAllocWidth = bufferalloc.nAllocWidth;
@@ -1499,6 +1537,7 @@ status_t OMXCameraAdapter::initInternalBuffers(void)
&bufferallocset);
if (eError != OMX_ErrorNone) {
CAMHAL_LOGE("SetParameter failed, error=%08x", eError);
+ if (eError == OMX_ErrorNoMore) return NO_ERROR;
break;
}
@@ -1512,6 +1551,27 @@ status_t OMXCameraAdapter::initInternalBuffers(void)
return -EINVAL;
}
+status_t OMXCameraAdapter::deinitInternalBuffers(OMX_U32 portIndex)
+{
+ OMX_ERRORTYPE eError = OMX_ErrorNone;
+ OMX_TI_PARAM_USEBUFFERDESCRIPTOR bufferdesc;
+
+ OMX_INIT_STRUCT_PTR (&bufferdesc, OMX_TI_PARAM_USEBUFFERDESCRIPTOR);
+ bufferdesc.nPortIndex = portIndex;
+ bufferdesc.bEnabled = OMX_FALSE;
+ bufferdesc.eBufferType = OMX_TI_BufferTypeDefault;
+
+ eError = OMX_SetParameter(mCameraAdapterParameters.mHandleComp,
+ (OMX_INDEXTYPE) OMX_TI_IndexUseBufferDescriptor,
+ &bufferdesc);
+ if (eError!=OMX_ErrorNone) {
+ CAMHAL_LOGEB("OMX_SetParameter - %x", eError);
+ return -EINVAL;
+ }
+
+ return ErrorUtils::omxToAndroidError(eError);
+}
+
status_t OMXCameraAdapter::UseBuffersCapture(CameraBuffer * bufArr, int num)
{
LOG_FUNCTION_NAME;
@@ -1581,6 +1641,8 @@ status_t OMXCameraAdapter::UseBuffersCapture(CameraBuffer * bufArr, int num)
}
}
+ initInternalBuffers(mCameraAdapterParameters.mImagePortIndex);
+
///Register for Image port ENABLE event
ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
OMX_EventCmdComplete,
@@ -1604,8 +1666,10 @@ status_t OMXCameraAdapter::UseBuffersCapture(CameraBuffer * bufArr, int num)
domxUseGrallocHandles.nPortIndex = mCameraAdapterParameters.mImagePortIndex;
if (bufArr[0].type == CAMERA_BUFFER_ANW) {
+ CAMHAL_LOGD ("Using ANW Buffers");
domxUseGrallocHandles.bEnable = OMX_TRUE;
} else {
+ CAMHAL_LOGD ("Using ION Buffers");
domxUseGrallocHandles.bEnable = OMX_FALSE;
}
diff --git a/camera/OMXCameraAdapter/OMXReprocess.cpp b/camera/OMXCameraAdapter/OMXReprocess.cpp
new file mode 100644
index 0000000..586b1c7
--- /dev/null
+++ b/camera/OMXCameraAdapter/OMXReprocess.cpp
@@ -0,0 +1,325 @@
+/*
+ * Copyright (C) Texas Instruments - http://www.ti.com/
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+* @file OMXReprocess.cpp
+*
+* This file contains functionality for handling reprocessing operations.
+*
+*/
+
+#include "CameraHal.h"
+#include "OMXCameraAdapter.h"
+#include "ErrorUtils.h"
+
+
+namespace android {
+
+status_t OMXCameraAdapter::setParametersReprocess(const CameraParameters &params,
+ CameraBuffer* buffers,
+ BaseCameraAdapter::AdapterState state)
+{
+ status_t ret = NO_ERROR;
+ int w, h, s;
+ OMX_COLOR_FORMATTYPE pixFormat;
+ OMXCameraPortParameters *portData;
+ const char* valstr;
+
+ LOG_FUNCTION_NAME;
+
+ if (!buffers) {
+ CAMHAL_LOGE("invalid buffer array");
+ return BAD_VALUE;
+ }
+
+ portData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex];
+
+ w = buffers[0].width;
+ h = buffers[0].height;
+ s = buffers[0].stride;
+
+ valstr = buffers[0].format;
+ if (valstr != NULL) {
+ if(strcmp(valstr, (const char *) CameraParameters::PIXEL_FORMAT_YUV420SP) == 0) {
+ CAMHAL_LOGDA("YUV420SP format selected");
+ pixFormat = OMX_COLOR_FormatYUV420SemiPlanar;
+ } else {
+ CAMHAL_LOGDA("Format not supported, selecting YUV420SP by default");
+ pixFormat = OMX_COLOR_FormatYUV420SemiPlanar;
+ }
+ } else {
+ CAMHAL_LOGDA("Format not supported, selecting YUV420SP by default");
+ pixFormat = OMX_COLOR_FormatYUV420SemiPlanar;
+ }
+
+ if ( (w != (int)portData->mWidth) || (h != (int)portData->mHeight) ||
+ (s != (int) portData->mStride) || (pixFormat != portData->mColorFormat)) {
+ portData->mWidth = w;
+ portData->mHeight = h;
+ portData->mStride = s;
+ portData->mColorFormat = pixFormat;
+
+ ret = setFormat(OMX_CAMERA_PORT_VIDEO_IN_VIDEO, *portData);
+ if ( ret != NO_ERROR ) {
+ CAMHAL_LOGEB("setFormat() failed %d", ret);
+ LOG_FUNCTION_NAME_EXIT;
+ return ret;
+ }
+ }
+
+ LOG_FUNCTION_NAME_EXIT;
+
+ return ret;
+}
+
+status_t OMXCameraAdapter::startReprocess()
+{
+ status_t ret = NO_ERROR;
+ OMX_ERRORTYPE eError = OMX_ErrorNone;
+ OMXCameraPortParameters * portData = NULL;
+
+ LOG_FUNCTION_NAME;
+ CAMHAL_LOGD ("mReprocConfigured = %d", mReprocConfigured);
+ if (!mReprocConfigured) {
+ return NO_ERROR;
+ }
+
+ portData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex];
+
+ CAMHAL_LOGD ("mReprocConfigured = %d", mBurstFramesQueued);
+ if (NO_ERROR == ret) {
+ Mutex::Autolock lock(mBurstLock);
+
+ for ( int index = 0 ; index < portData->mMaxQueueable ; index++ ) {
+ CAMHAL_LOGDB("Queuing buffer on video input port - %p",
+ portData->mBufferHeader[index]->pBuffer);
+ portData->mStatus[index] = OMXCameraPortParameters::FILL;
+ eError = OMX_EmptyThisBuffer(mCameraAdapterParameters.mHandleComp,
+ (OMX_BUFFERHEADERTYPE*)portData->mBufferHeader[index]);
+ GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
+ }
+ }
+
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+
+EXIT:
+ CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
+ performCleanupAfterError();
+ LOG_FUNCTION_NAME_EXIT;
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+}
+
+status_t OMXCameraAdapter::stopReprocess()
+{
+ status_t ret = NO_ERROR;
+ OMX_ERRORTYPE eError = OMX_ErrorNone;
+ OMXCameraPortParameters *portData = NULL;
+
+ if (!mReprocConfigured) {
+ return NO_ERROR;
+ }
+
+ portData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex];
+
+ // Disable port - send command and then free all buffers
+ ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
+ OMX_EventCmdComplete,
+ OMX_CommandPortDisable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ mStopReprocSem);
+ eError = OMX_SendCommand(mCameraAdapterParameters.mHandleComp,
+ OMX_CommandPortDisable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ NULL);
+ if (portData) {
+ CAMHAL_LOGDB("Freeing buffers on reproc port - num: %d", portData->mNumBufs);
+ for (int index = 0 ; index < portData->mNumBufs ; index++) {
+ CAMHAL_LOGDB("Freeing buffer on reproc port - 0x%x",
+ ( unsigned int ) portData->mBufferHeader[index]->pBuffer);
+ eError = OMX_FreeBuffer(mCameraAdapterParameters.mHandleComp,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ (OMX_BUFFERHEADERTYPE*)portData->mBufferHeader[index]);
+ GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
+ }
+ }
+ CAMHAL_LOGDA("Waiting for port disable");
+ ret = mStopReprocSem.WaitTimeout(OMX_CMD_TIMEOUT);
+ if (mComponentState == OMX_StateInvalid) {
+ CAMHAL_LOGEA("Invalid State after Disable Image Port Exitting!!!");
+ goto EXIT;
+ }
+ if (NO_ERROR == ret) {
+ CAMHAL_LOGDA("Port disabled");
+ } else {
+ ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
+ OMX_EventCmdComplete,
+ OMX_CommandPortDisable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ NULL);
+ CAMHAL_LOGDA("Timeout expired on port disable");
+ goto EXIT;
+ }
+
+ deinitInternalBuffers(mCameraAdapterParameters.mVideoInPortIndex);
+
+ mReprocConfigured = false;
+
+EXIT:
+ CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
+ LOG_FUNCTION_NAME_EXIT;
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+}
+
+status_t OMXCameraAdapter::disableReprocess(){
+ status_t ret = NO_ERROR;
+ OMX_ERRORTYPE eError = OMX_ErrorNone;
+
+ // no-op..for now
+
+EXIT:
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+}
+
+status_t OMXCameraAdapter::UseBuffersReprocess(CameraBuffer *bufArr, int num)
+{
+ LOG_FUNCTION_NAME;
+
+ status_t ret = NO_ERROR;
+ OMX_ERRORTYPE eError = OMX_ErrorNone;
+ OMXCameraPortParameters *portData = NULL;
+
+ portData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mVideoInPortIndex];
+
+ if ( 0 != mUseReprocessSem.Count() ) {
+ CAMHAL_LOGEB("Error mUseReprocessSem semaphore count %d", mUseReprocessSem.Count());
+ return BAD_VALUE;
+ }
+
+ if (mAdapterState == REPROCESS_STATE) {
+ stopReprocess();
+ } else if (mAdapterState == CAPTURE_STATE) {
+ stopImageCapture();
+ disableImagePort();
+ }
+
+ if (mReprocConfigured) {
+ return NO_ERROR;
+ }
+
+ portData->mNumBufs = num;
+
+ // Configure
+ ret = setParametersReprocess(mParams, bufArr, mAdapterState);
+
+ initInternalBuffers(mCameraAdapterParameters.mVideoInPortIndex);
+
+ // Configure DOMX to use either gralloc handles or vptrs
+ OMX_TI_PARAMUSENATIVEBUFFER domxUseGrallocHandles;
+ OMX_INIT_STRUCT_PTR (&domxUseGrallocHandles, OMX_TI_PARAMUSENATIVEBUFFER);
+
+ domxUseGrallocHandles.nPortIndex = mCameraAdapterParameters.mVideoInPortIndex;
+ if (bufArr[0].type == CAMERA_BUFFER_ANW) {
+ CAMHAL_LOGD("Using ANW");
+ domxUseGrallocHandles.bEnable = OMX_TRUE;
+ } else {
+ CAMHAL_LOGD("Using ION");
+ domxUseGrallocHandles.bEnable = OMX_FALSE;
+ }
+ eError = OMX_SetParameter(mCameraAdapterParameters.mHandleComp,
+ (OMX_INDEXTYPE)OMX_TI_IndexUseNativeBuffers, &domxUseGrallocHandles);
+ if (eError!=OMX_ErrorNone) {
+ CAMHAL_LOGEB("OMX_SetParameter - %x", eError);
+ }
+ GOTO_EXIT_IF((eError!=OMX_ErrorNone), eError);
+
+ // Enable Port
+ ret = RegisterForEvent(mCameraAdapterParameters.mHandleComp,
+ OMX_EventCmdComplete,
+ OMX_CommandPortEnable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ mUseReprocessSem);
+ eError = OMX_SendCommand(mCameraAdapterParameters.mHandleComp,
+ OMX_CommandPortEnable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ NULL);
+ GOTO_EXIT_IF(( eError != OMX_ErrorNone ), eError);
+
+ for (int index = 0 ; index < portData->mNumBufs ; index++)
+ {
+ OMX_BUFFERHEADERTYPE *pBufferHdr;
+ CAMHAL_LOGDB("OMX_UseBuffer Capture address: 0x%x, size = %d",
+ (unsigned int)bufArr[index].opaque,
+ (int)portData->mBufSize);
+
+ eError = OMX_UseBuffer(mCameraAdapterParameters.mHandleComp,
+ &pBufferHdr,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ 0,
+ portData->mBufSize,
+ (OMX_U8*)camera_buffer_get_omx_ptr(&bufArr[index]));
+
+ CAMHAL_LOGDB("OMX_UseBuffer = 0x%x", eError);
+ GOTO_EXIT_IF(( eError != OMX_ErrorNone ), eError);
+
+ pBufferHdr->pAppPrivate = (OMX_PTR) &bufArr[index];
+ bufArr[index].index = index;
+ pBufferHdr->nSize = sizeof(OMX_BUFFERHEADERTYPE);
+ pBufferHdr->nVersion.s.nVersionMajor = 1 ;
+ pBufferHdr->nVersion.s.nVersionMinor = 1 ;
+ pBufferHdr->nVersion.s.nRevision = 0;
+ pBufferHdr->nVersion.s.nStep = 0;
+ portData->mBufferHeader[index] = pBufferHdr;
+ }
+
+ // Wait for port enable event
+ CAMHAL_LOGDA("Waiting for port enable");
+ ret = mUseReprocessSem.WaitTimeout(OMX_CMD_TIMEOUT);
+
+ // Error out if somethiing bad happened while we wait
+ if (mComponentState == OMX_StateInvalid) {
+ CAMHAL_LOGEA("Invalid State while trying to enable port for reprocessing");
+ goto EXIT;
+ }
+
+ if (ret == NO_ERROR) {
+ CAMHAL_LOGDA("Port enabled");
+ } else {
+ ret |= RemoveEvent(mCameraAdapterParameters.mHandleComp,
+ OMX_EventCmdComplete,
+ OMX_CommandPortEnable,
+ mCameraAdapterParameters.mVideoInPortIndex,
+ NULL);
+ CAMHAL_LOGDA("Timeout expired on port enable");
+ goto EXIT;
+ }
+
+ mReprocConfigured = true;
+
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+
+EXIT:
+ CAMHAL_LOGEB("Exiting function %s because of ret %d eError=%x", __FUNCTION__, ret, eError);
+ // Release image buffers
+ if ( NULL != mReleaseImageBuffersCallback ) {
+ mReleaseImageBuffersCallback(mReleaseData);
+ }
+ performCleanupAfterError();
+ LOG_FUNCTION_NAME_EXIT;
+ return (ret | ErrorUtils::omxToAndroidError(eError));
+
+}
+
+};
diff --git a/camera/inc/BaseCameraAdapter.h b/camera/inc/BaseCameraAdapter.h
index 0467b7e..7a084d9 100644
--- a/camera/inc/BaseCameraAdapter.h
+++ b/camera/inc/BaseCameraAdapter.h
@@ -220,6 +220,7 @@ protected:
KeyedVector<int, frame_callback> mFrameSubscribers;
KeyedVector<int, frame_callback> mFrameDataSubscribers;
KeyedVector<int, frame_callback> mVideoSubscribers;
+ KeyedVector<int, frame_callback> mVideoInSubscribers;
KeyedVector<int, frame_callback> mImageSubscribers;
KeyedVector<int, frame_callback> mRawSubscribers;
KeyedVector<int, event_callback> mFocusSubscribers;
@@ -255,6 +256,11 @@ protected:
size_t mPreviewDataBuffersLength;
mutable Mutex mPreviewDataBufferLock;
+ //Video input buffer management data (used for reproc pipe)
+ CameraBuffer *mVideoInBuffers;
+ KeyedVector<CameraBuffer *, int> mVideoInBuffersAvailable;
+ mutable Mutex mVideoInBufferLock;
+
TIUTILS::MessageQueue mFrameQ;
TIUTILS::MessageQueue mAdapterQ;
mutable Mutex mSubscriberLock;
diff --git a/camera/inc/CameraHal.h b/camera/inc/CameraHal.h
index 5d04881..c613749 100644
--- a/camera/inc/CameraHal.h
+++ b/camera/inc/CameraHal.h
@@ -354,6 +354,7 @@ typedef struct _CameraBuffer {
/* These describe the camera buffer */
int width;
+ int stride;
int height;
const char *format;
} CameraBuffer;
@@ -878,15 +879,17 @@ class CameraAdapter: public FrameNotifier, public virtual RefBase
{
protected:
enum AdapterActiveStates {
- INTIALIZED_ACTIVE = 1 << 0,
- LOADED_PREVIEW_ACTIVE = 1 << 1,
- PREVIEW_ACTIVE = 1 << 2,
- LOADED_CAPTURE_ACTIVE = 1 << 3,
- CAPTURE_ACTIVE = 1 << 4,
- BRACKETING_ACTIVE = 1 << 5,
- AF_ACTIVE = 1 << 6,
- ZOOM_ACTIVE = 1 << 7,
- VIDEO_ACTIVE = 1 << 8,
+ INTIALIZED_ACTIVE = 1 << 0,
+ LOADED_PREVIEW_ACTIVE = 1 << 1,
+ PREVIEW_ACTIVE = 1 << 2,
+ LOADED_CAPTURE_ACTIVE = 1 << 3,
+ CAPTURE_ACTIVE = 1 << 4,
+ BRACKETING_ACTIVE = 1 << 5,
+ AF_ACTIVE = 1 << 6,
+ ZOOM_ACTIVE = 1 << 7,
+ VIDEO_ACTIVE = 1 << 8,
+ LOADED_REPROCESS_ACTIVE = 1 << 9,
+ REPROCESS_ACTIVE = 1 << 10,
};
public:
typedef struct
@@ -927,6 +930,8 @@ public:
CAMERA_STOP_FD = 23,
CAMERA_SWITCH_TO_EXECUTING = 24,
CAMERA_USE_BUFFERS_VIDEO_CAPTURE = 25,
+ CAMERA_USE_BUFFERS_REPROCESS = 26,
+ CAMERA_START_REPROCESS = 27,
};
enum CameraMode
@@ -934,25 +939,29 @@ public:
CAMERA_PREVIEW,
CAMERA_IMAGE_CAPTURE,
CAMERA_VIDEO,
- CAMERA_MEASUREMENT
+ CAMERA_MEASUREMENT,
+ CAMERA_REPROCESS,
};
enum AdapterState {
- INTIALIZED_STATE = INTIALIZED_ACTIVE,
- LOADED_PREVIEW_STATE = LOADED_PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- PREVIEW_STATE = PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- LOADED_CAPTURE_STATE = LOADED_CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- CAPTURE_STATE = CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- BRACKETING_STATE = BRACKETING_ACTIVE | CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE ,
- AF_STATE = AF_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- ZOOM_STATE = ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- VIDEO_STATE = VIDEO_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- VIDEO_AF_STATE = VIDEO_ACTIVE | AF_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- VIDEO_ZOOM_STATE = VIDEO_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- VIDEO_LOADED_CAPTURE_STATE = VIDEO_ACTIVE | LOADED_CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- VIDEO_CAPTURE_STATE = VIDEO_ACTIVE | CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- AF_ZOOM_STATE = AF_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
- BRACKETING_ZOOM_STATE = BRACKETING_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ INTIALIZED_STATE = INTIALIZED_ACTIVE,
+ LOADED_PREVIEW_STATE = LOADED_PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ PREVIEW_STATE = PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ LOADED_CAPTURE_STATE = LOADED_CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ CAPTURE_STATE = CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ BRACKETING_STATE = BRACKETING_ACTIVE | CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE ,
+ AF_STATE = AF_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ ZOOM_STATE = ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ VIDEO_STATE = VIDEO_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ VIDEO_AF_STATE = VIDEO_ACTIVE | AF_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ VIDEO_ZOOM_STATE = VIDEO_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ VIDEO_LOADED_CAPTURE_STATE = VIDEO_ACTIVE | LOADED_CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ VIDEO_CAPTURE_STATE = VIDEO_ACTIVE | CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ AF_ZOOM_STATE = AF_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ BRACKETING_ZOOM_STATE = BRACKETING_ACTIVE | ZOOM_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ LOADED_REPROCESS_STATE = LOADED_REPROCESS_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ LOADED_REPROCESS_CAPTURE_STATE = LOADED_REPROCESS_ACTIVE | LOADED_CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
+ REPROCESS_STATE = REPROCESS_ACTIVE | CAPTURE_ACTIVE | PREVIEW_ACTIVE | INTIALIZED_ACTIVE,
};
@@ -1206,6 +1215,16 @@ public:
*/
int dump(int fd) const;
+ /**
+ * start a reprocessing operation.
+ */
+ int reprocess(const char* params);
+
+ /**
+ * cancels current reprocessing operation
+ */
+ int cancel_reprocess();
+
status_t storeMetaDataInBuffers(bool enable);
@@ -1330,6 +1349,8 @@ private:
bool setPreferredPreviewRes(const CameraParameters &params, int width, int height);
void resetPreviewRes(CameraParameters *mParams, int width, int height);
+ // Internal __takePicture function - used in public takePicture() and reprocess()
+ int __takePicture(const char* params);
//@}
diff --git a/camera/inc/OMXCameraAdapter/OMXCameraAdapter.h b/camera/inc/OMXCameraAdapter/OMXCameraAdapter.h
index c820396..c41c652 100644
--- a/camera/inc/OMXCameraAdapter/OMXCameraAdapter.h
+++ b/camera/inc/OMXCameraAdapter/OMXCameraAdapter.h
@@ -366,6 +366,7 @@ public:
OMX_U32 mPrevPortIndex;
OMX_U32 mImagePortIndex;
OMX_U32 mMeasurementPortIndex;
+ OMX_U32 mVideoInPortIndex;
OMXCameraPortParameters mCameraPortParams[MAX_NO_PORTS];
};
@@ -739,7 +740,16 @@ private:
FILE * parseDCCsubDir(DIR *pDir, char *path);
// Internal buffers
- status_t initInternalBuffers (void);
+ status_t initInternalBuffers (OMX_U32);
+ status_t deinitInternalBuffers (OMX_U32);
+
+ // Reprocess Methods -- implementation in OMXReprocess.cpp
+ status_t setParametersReprocess(const CameraParameters &params, CameraBuffer* bufs,
+ BaseCameraAdapter::AdapterState state);
+ status_t startReprocess();
+ status_t disableReprocess();
+ status_t stopReprocess();
+ status_t UseBuffersReprocess(CameraBuffer *bufArr, int num);
class CommandHandler : public Thread {
public:
@@ -766,8 +776,9 @@ private:
enum {
COMMAND_EXIT = -1,
CAMERA_START_IMAGE_CAPTURE = 0,
- CAMERA_PERFORM_AUTOFOCUS = 1,
- CAMERA_SWITCH_TO_EXECUTING
+ CAMERA_PERFORM_AUTOFOCUS,
+ CAMERA_SWITCH_TO_EXECUTING,
+ CAMERA_START_REPROCESS
};
private:
@@ -1027,6 +1038,7 @@ private:
unsigned int mPendingPreviewSettings;
OMX_TI_ANCILLARYDATATYPE* mCaptureAncillaryData;
OMX_TI_WHITEBALANCERESULTTYPE* mWhiteBalanceData;
+ bool mReprocConfigured;
//Temporal bracketing management data
bool mBracketingSet;
@@ -1054,6 +1066,8 @@ private:
Semaphore mStopCaptureSem;
Semaphore mSwitchToLoadedSem;
Semaphore mSwitchToExecSem;
+ Semaphore mStopReprocSem;
+ Semaphore mUseReprocessSem;
mutable Mutex mStateSwitchLock;