CaptureSequencer.cpp revision 25a0aef19e170d2695f64b4c48296e7914155a88
1/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#define LOG_TAG "Camera2-CaptureSequencer"
18#define ATRACE_TAG ATRACE_TAG_CAMERA
19//#define LOG_NDEBUG 0
20
21#include <inttypes.h>
22
23#include <utils/Log.h>
24#include <utils/Trace.h>
25#include <utils/Vector.h>
26
27#include "api1/Camera2Client.h"
28#include "api1/client2/CaptureSequencer.h"
29#include "api1/client2/BurstCapture.h"
30#include "api1/client2/Parameters.h"
31#include "api1/client2/ZslProcessorInterface.h"
32
33namespace android {
34namespace camera2 {
35
36/** Public members */
37
38CaptureSequencer::CaptureSequencer(wp<Camera2Client> client):
39        Thread(false),
40        mStartCapture(false),
41        mBusy(false),
42        mNewAEState(false),
43        mNewFrameReceived(false),
44        mNewCaptureReceived(false),
45        mShutterNotified(false),
46        mClient(client),
47        mCaptureState(IDLE),
48        mStateTransitionCount(0),
49        mTriggerId(0),
50        mTimeoutCount(0),
51        mCaptureId(Camera2Client::kCaptureRequestIdStart),
52        mMsgType(0) {
53    ALOGV("%s", __FUNCTION__);
54}
55
56CaptureSequencer::~CaptureSequencer() {
57    ALOGV("%s: Exit", __FUNCTION__);
58}
59
60void CaptureSequencer::setZslProcessor(wp<ZslProcessorInterface> processor) {
61    Mutex::Autolock l(mInputMutex);
62    mZslProcessor = processor;
63}
64
65status_t CaptureSequencer::startCapture(int msgType) {
66    ALOGV("%s", __FUNCTION__);
67    ATRACE_CALL();
68    Mutex::Autolock l(mInputMutex);
69    if (mBusy) {
70        ALOGE("%s: Already busy capturing!", __FUNCTION__);
71        return INVALID_OPERATION;
72    }
73    if (!mStartCapture) {
74        mMsgType = msgType;
75        mStartCapture = true;
76        mStartCaptureSignal.signal();
77    }
78    return OK;
79}
80
81status_t CaptureSequencer::waitUntilIdle(nsecs_t timeout) {
82    ATRACE_CALL();
83    ALOGV("%s: Waiting for idle", __FUNCTION__);
84    Mutex::Autolock l(mStateMutex);
85    status_t res = -1;
86    while (mCaptureState != IDLE) {
87        nsecs_t startTime = systemTime();
88
89        res = mStateChanged.waitRelative(mStateMutex, timeout);
90        if (res != OK) return res;
91
92        timeout -= (systemTime() - startTime);
93    }
94    ALOGV("%s: Now idle", __FUNCTION__);
95    return OK;
96}
97
98void CaptureSequencer::notifyAutoExposure(uint8_t newState, int triggerId) {
99    ATRACE_CALL();
100    Mutex::Autolock l(mInputMutex);
101    mAEState = newState;
102    mAETriggerId = triggerId;
103    if (!mNewAEState) {
104        mNewAEState = true;
105        mNewNotifySignal.signal();
106    }
107}
108
109void CaptureSequencer::onResultAvailable(const CaptureResult &result) {
110    ATRACE_CALL();
111    ALOGV("%s: New result available.", __FUNCTION__);
112    Mutex::Autolock l(mInputMutex);
113    mNewFrameId = result.mResultExtras.requestId;
114    mNewFrame = result.mMetadata;
115    if (!mNewFrameReceived) {
116        mNewFrameReceived = true;
117        mNewFrameSignal.signal();
118    }
119}
120
121void CaptureSequencer::onCaptureAvailable(nsecs_t timestamp,
122        sp<MemoryBase> captureBuffer) {
123    ATRACE_CALL();
124    ALOGV("%s", __FUNCTION__);
125    Mutex::Autolock l(mInputMutex);
126    mCaptureTimestamp = timestamp;
127    mCaptureBuffer = captureBuffer;
128    if (!mNewCaptureReceived) {
129        mNewCaptureReceived = true;
130        mNewCaptureSignal.signal();
131    }
132}
133
134
135void CaptureSequencer::dump(int fd, const Vector<String16>& /*args*/) {
136    String8 result;
137    if (mCaptureRequest.entryCount() != 0) {
138        result = "    Capture request:\n";
139        write(fd, result.string(), result.size());
140        mCaptureRequest.dump(fd, 2, 6);
141    } else {
142        result = "    Capture request: undefined\n";
143        write(fd, result.string(), result.size());
144    }
145    result = String8::format("    Current capture state: %s\n",
146            kStateNames[mCaptureState]);
147    result.append("    Latest captured frame:\n");
148    write(fd, result.string(), result.size());
149    mNewFrame.dump(fd, 2, 6);
150}
151
152/** Private members */
153
154const char* CaptureSequencer::kStateNames[CaptureSequencer::NUM_CAPTURE_STATES+1] =
155{
156    "IDLE",
157    "START",
158    "ZSL_START",
159    "ZSL_WAITING",
160    "ZSL_REPROCESSING",
161    "STANDARD_START",
162    "STANDARD_PRECAPTURE_WAIT",
163    "STANDARD_CAPTURE",
164    "STANDARD_CAPTURE_WAIT",
165    "BURST_CAPTURE_START",
166    "BURST_CAPTURE_WAIT",
167    "DONE",
168    "ERROR",
169    "UNKNOWN"
170};
171
172const CaptureSequencer::StateManager
173        CaptureSequencer::kStateManagers[CaptureSequencer::NUM_CAPTURE_STATES-1] = {
174    &CaptureSequencer::manageIdle,
175    &CaptureSequencer::manageStart,
176    &CaptureSequencer::manageZslStart,
177    &CaptureSequencer::manageZslWaiting,
178    &CaptureSequencer::manageZslReprocessing,
179    &CaptureSequencer::manageStandardStart,
180    &CaptureSequencer::manageStandardPrecaptureWait,
181    &CaptureSequencer::manageStandardCapture,
182    &CaptureSequencer::manageStandardCaptureWait,
183    &CaptureSequencer::manageBurstCaptureStart,
184    &CaptureSequencer::manageBurstCaptureWait,
185    &CaptureSequencer::manageDone,
186};
187
188bool CaptureSequencer::threadLoop() {
189
190    sp<Camera2Client> client = mClient.promote();
191    if (client == 0) return false;
192
193    CaptureState currentState;
194    {
195        Mutex::Autolock l(mStateMutex);
196        currentState = mCaptureState;
197    }
198
199    currentState = (this->*kStateManagers[currentState])(client);
200
201    Mutex::Autolock l(mStateMutex);
202    if (currentState != mCaptureState) {
203        if (mCaptureState != IDLE) {
204            ATRACE_ASYNC_END(kStateNames[mCaptureState], mStateTransitionCount);
205        }
206        mCaptureState = currentState;
207        mStateTransitionCount++;
208        if (mCaptureState != IDLE) {
209            ATRACE_ASYNC_BEGIN(kStateNames[mCaptureState], mStateTransitionCount);
210        }
211        ALOGV("Camera %d: New capture state %s",
212                client->getCameraId(), kStateNames[mCaptureState]);
213        mStateChanged.signal();
214    }
215
216    if (mCaptureState == ERROR) {
217        ALOGE("Camera %d: Stopping capture sequencer due to error",
218                client->getCameraId());
219        return false;
220    }
221
222    return true;
223}
224
225CaptureSequencer::CaptureState CaptureSequencer::manageIdle(
226        sp<Camera2Client> &/*client*/) {
227    status_t res;
228    Mutex::Autolock l(mInputMutex);
229    while (!mStartCapture) {
230        res = mStartCaptureSignal.waitRelative(mInputMutex,
231                kWaitDuration);
232        if (res == TIMED_OUT) break;
233    }
234    if (mStartCapture) {
235        mStartCapture = false;
236        mBusy = true;
237        return START;
238    }
239    return IDLE;
240}
241
242CaptureSequencer::CaptureState CaptureSequencer::manageDone(sp<Camera2Client> &client) {
243    status_t res = OK;
244    ATRACE_CALL();
245    mCaptureId++;
246    if (mCaptureId >= Camera2Client::kCaptureRequestIdEnd) {
247        mCaptureId = Camera2Client::kCaptureRequestIdStart;
248    }
249    {
250        Mutex::Autolock l(mInputMutex);
251        mBusy = false;
252    }
253
254    int takePictureCounter = 0;
255    {
256        SharedParameters::Lock l(client->getParameters());
257        switch (l.mParameters.state) {
258            case Parameters::DISCONNECTED:
259                ALOGW("%s: Camera %d: Discarding image data during shutdown ",
260                        __FUNCTION__, client->getCameraId());
261                res = INVALID_OPERATION;
262                break;
263            case Parameters::STILL_CAPTURE:
264                res = client->getCameraDevice()->waitUntilDrained();
265                if (res != OK) {
266                    ALOGE("%s: Camera %d: Can't idle after still capture: "
267                            "%s (%d)", __FUNCTION__, client->getCameraId(),
268                            strerror(-res), res);
269                }
270                l.mParameters.state = Parameters::STOPPED;
271                break;
272            case Parameters::VIDEO_SNAPSHOT:
273                l.mParameters.state = Parameters::RECORD;
274                break;
275            default:
276                ALOGE("%s: Camera %d: Still image produced unexpectedly "
277                        "in state %s!",
278                        __FUNCTION__, client->getCameraId(),
279                        Parameters::getStateName(l.mParameters.state));
280                res = INVALID_OPERATION;
281        }
282        takePictureCounter = l.mParameters.takePictureCounter;
283    }
284    sp<ZslProcessorInterface> processor = mZslProcessor.promote();
285    if (processor != 0) {
286        ALOGV("%s: Memory optimization, clearing ZSL queue",
287              __FUNCTION__);
288        processor->clearZslQueue();
289    }
290
291    /**
292     * Fire the jpegCallback in Camera#takePicture(..., jpegCallback)
293     */
294    if (mCaptureBuffer != 0 && res == OK) {
295        ATRACE_ASYNC_END(Camera2Client::kTakepictureLabel, takePictureCounter);
296
297        Camera2Client::SharedCameraCallbacks::Lock
298            l(client->mSharedCameraCallbacks);
299        ALOGV("%s: Sending still image to client", __FUNCTION__);
300        if (l.mRemoteCallback != 0) {
301            l.mRemoteCallback->dataCallback(CAMERA_MSG_COMPRESSED_IMAGE,
302                    mCaptureBuffer, NULL);
303        } else {
304            ALOGV("%s: No client!", __FUNCTION__);
305        }
306    }
307    mCaptureBuffer.clear();
308
309    return IDLE;
310}
311
312CaptureSequencer::CaptureState CaptureSequencer::manageStart(
313        sp<Camera2Client> &client) {
314    ALOGV("%s", __FUNCTION__);
315    status_t res;
316    ATRACE_CALL();
317    SharedParameters::Lock l(client->getParameters());
318    CaptureState nextState = DONE;
319
320    res = updateCaptureRequest(l.mParameters, client);
321    if (res != OK ) {
322        ALOGE("%s: Camera %d: Can't update still image capture request: %s (%d)",
323                __FUNCTION__, client->getCameraId(), strerror(-res), res);
324        return DONE;
325    }
326
327    if(l.mParameters.lightFx != Parameters::LIGHTFX_NONE &&
328            l.mParameters.state == Parameters::STILL_CAPTURE) {
329        nextState = BURST_CAPTURE_START;
330    }
331    else if (l.mParameters.zslMode &&
332            l.mParameters.state == Parameters::STILL_CAPTURE &&
333            l.mParameters.flashMode != Parameters::FLASH_MODE_ON) {
334        nextState = ZSL_START;
335    } else {
336        nextState = STANDARD_START;
337    }
338    mShutterNotified = false;
339
340    return nextState;
341}
342
343CaptureSequencer::CaptureState CaptureSequencer::manageZslStart(
344        sp<Camera2Client> &client) {
345    ALOGV("%s", __FUNCTION__);
346    status_t res;
347    sp<ZslProcessorInterface> processor = mZslProcessor.promote();
348    if (processor == 0) {
349        ALOGE("%s: No ZSL queue to use!", __FUNCTION__);
350        return DONE;
351    }
352
353    // We don't want to get partial results for ZSL capture.
354    client->registerFrameListener(mCaptureId, mCaptureId + 1,
355            this,
356            /*sendPartials*/false);
357
358    // TODO: Actually select the right thing here.
359    res = processor->pushToReprocess(mCaptureId);
360    if (res != OK) {
361        if (res == NOT_ENOUGH_DATA) {
362            ALOGV("%s: Camera %d: ZSL queue doesn't have good frame, "
363                    "falling back to normal capture", __FUNCTION__,
364                    client->getCameraId());
365        } else {
366            ALOGE("%s: Camera %d: Error in ZSL queue: %s (%d)",
367                    __FUNCTION__, client->getCameraId(), strerror(-res), res);
368        }
369        return STANDARD_START;
370    }
371
372    SharedParameters::Lock l(client->getParameters());
373    /* warning: this also locks a SharedCameraCallbacks */
374    shutterNotifyLocked(l.mParameters, client, mMsgType);
375    mShutterNotified = true;
376    mTimeoutCount = kMaxTimeoutsForCaptureEnd;
377    return STANDARD_CAPTURE_WAIT;
378}
379
380CaptureSequencer::CaptureState CaptureSequencer::manageZslWaiting(
381        sp<Camera2Client> &/*client*/) {
382    ALOGV("%s", __FUNCTION__);
383    return DONE;
384}
385
386CaptureSequencer::CaptureState CaptureSequencer::manageZslReprocessing(
387        sp<Camera2Client> &/*client*/) {
388    ALOGV("%s", __FUNCTION__);
389    return START;
390}
391
392CaptureSequencer::CaptureState CaptureSequencer::manageStandardStart(
393        sp<Camera2Client> &client) {
394    ATRACE_CALL();
395
396    bool isAeConverged = false;
397    // Get the onFrameAvailable callback when the requestID == mCaptureId
398    // We don't want to get partial results for normal capture, as we need
399    // Get ANDROID_SENSOR_TIMESTAMP from the capture result, but partial
400    // result doesn't have to have this metadata available.
401    // TODO: Update to use the HALv3 shutter notification for remove the
402    // need for this listener and make it faster. see bug 12530628.
403    client->registerFrameListener(mCaptureId, mCaptureId + 1,
404            this,
405            /*sendPartials*/false);
406
407    {
408        Mutex::Autolock l(mInputMutex);
409        isAeConverged = (mAEState == ANDROID_CONTROL_AE_STATE_CONVERGED);
410    }
411
412    {
413        SharedParameters::Lock l(client->getParameters());
414        // Skip AE precapture when it is already converged and not in force flash mode.
415        if (l.mParameters.flashMode != Parameters::FLASH_MODE_ON && isAeConverged) {
416            return STANDARD_CAPTURE;
417        }
418
419        mTriggerId = l.mParameters.precaptureTriggerCounter++;
420    }
421    client->getCameraDevice()->triggerPrecaptureMetering(mTriggerId);
422
423    mAeInPrecapture = false;
424    mTimeoutCount = kMaxTimeoutsForPrecaptureStart;
425    return STANDARD_PRECAPTURE_WAIT;
426}
427
428CaptureSequencer::CaptureState CaptureSequencer::manageStandardPrecaptureWait(
429        sp<Camera2Client> &/*client*/) {
430    status_t res;
431    ATRACE_CALL();
432    Mutex::Autolock l(mInputMutex);
433    while (!mNewAEState) {
434        res = mNewNotifySignal.waitRelative(mInputMutex, kWaitDuration);
435        if (res == TIMED_OUT) {
436            mTimeoutCount--;
437            break;
438        }
439    }
440    if (mTimeoutCount <= 0) {
441        ALOGW("Timed out waiting for precapture %s",
442                mAeInPrecapture ? "end" : "start");
443        return STANDARD_CAPTURE;
444    }
445    if (mNewAEState) {
446        if (!mAeInPrecapture) {
447            // Waiting to see PRECAPTURE state
448            if (mAETriggerId == mTriggerId &&
449                    mAEState == ANDROID_CONTROL_AE_STATE_PRECAPTURE) {
450                ALOGV("%s: Got precapture start", __FUNCTION__);
451                mAeInPrecapture = true;
452                mTimeoutCount = kMaxTimeoutsForPrecaptureEnd;
453            }
454        } else {
455            // Waiting to see PRECAPTURE state end
456            if (mAETriggerId == mTriggerId &&
457                    mAEState != ANDROID_CONTROL_AE_STATE_PRECAPTURE) {
458                ALOGV("%s: Got precapture end", __FUNCTION__);
459                return STANDARD_CAPTURE;
460            }
461        }
462        mNewAEState = false;
463    }
464    return STANDARD_PRECAPTURE_WAIT;
465}
466
467CaptureSequencer::CaptureState CaptureSequencer::manageStandardCapture(
468        sp<Camera2Client> &client) {
469    status_t res;
470    ATRACE_CALL();
471    SharedParameters::Lock l(client->getParameters());
472    Vector<int32_t> outputStreams;
473    uint8_t captureIntent = static_cast<uint8_t>(ANDROID_CONTROL_CAPTURE_INTENT_STILL_CAPTURE);
474
475    /**
476     * Set up output streams in the request
477     *  - preview
478     *  - capture/jpeg
479     *  - callback (if preview callbacks enabled)
480     *  - recording (if recording enabled)
481     */
482    outputStreams.push(client->getPreviewStreamId());
483    outputStreams.push(client->getCaptureStreamId());
484
485    if (l.mParameters.previewCallbackFlags &
486            CAMERA_FRAME_CALLBACK_FLAG_ENABLE_MASK) {
487        outputStreams.push(client->getCallbackStreamId());
488    }
489
490    if (l.mParameters.state == Parameters::VIDEO_SNAPSHOT) {
491        outputStreams.push(client->getRecordingStreamId());
492        captureIntent = static_cast<uint8_t>(ANDROID_CONTROL_CAPTURE_INTENT_VIDEO_SNAPSHOT);
493    }
494
495    res = mCaptureRequest.update(ANDROID_REQUEST_OUTPUT_STREAMS,
496            outputStreams);
497    if (res == OK) {
498        res = mCaptureRequest.update(ANDROID_REQUEST_ID,
499                &mCaptureId, 1);
500    }
501    if (res == OK) {
502        res = mCaptureRequest.update(ANDROID_CONTROL_CAPTURE_INTENT,
503                &captureIntent, 1);
504    }
505    if (res == OK) {
506        res = mCaptureRequest.sort();
507    }
508
509    if (res != OK) {
510        ALOGE("%s: Camera %d: Unable to set up still capture request: %s (%d)",
511                __FUNCTION__, client->getCameraId(), strerror(-res), res);
512        return DONE;
513    }
514
515    // Create a capture copy since CameraDeviceBase#capture takes ownership
516    CameraMetadata captureCopy = mCaptureRequest;
517    if (captureCopy.entryCount() == 0) {
518        ALOGE("%s: Camera %d: Unable to copy capture request for HAL device",
519                __FUNCTION__, client->getCameraId());
520        return DONE;
521    }
522
523    /**
524     * Clear the streaming request for still-capture pictures
525     *   (as opposed to i.e. video snapshots)
526     */
527    if (l.mParameters.state == Parameters::STILL_CAPTURE) {
528        // API definition of takePicture() - stop preview before taking pic
529        res = client->stopStream();
530        if (res != OK) {
531            ALOGE("%s: Camera %d: Unable to stop preview for still capture: "
532                    "%s (%d)",
533                    __FUNCTION__, client->getCameraId(), strerror(-res), res);
534            return DONE;
535        }
536    }
537    // TODO: Capture should be atomic with setStreamingRequest here
538    res = client->getCameraDevice()->capture(captureCopy);
539    if (res != OK) {
540        ALOGE("%s: Camera %d: Unable to submit still image capture request: "
541                "%s (%d)",
542                __FUNCTION__, client->getCameraId(), strerror(-res), res);
543        return DONE;
544    }
545
546    mTimeoutCount = kMaxTimeoutsForCaptureEnd;
547    return STANDARD_CAPTURE_WAIT;
548}
549
550CaptureSequencer::CaptureState CaptureSequencer::manageStandardCaptureWait(
551        sp<Camera2Client> &client) {
552    status_t res;
553    ATRACE_CALL();
554    Mutex::Autolock l(mInputMutex);
555
556    // Wait for new metadata result (mNewFrame)
557    while (!mNewFrameReceived) {
558        res = mNewFrameSignal.waitRelative(mInputMutex, kWaitDuration);
559        if (res == TIMED_OUT) {
560            mTimeoutCount--;
561            break;
562        }
563    }
564
565    // Approximation of the shutter being closed
566    // - TODO: use the hal3 exposure callback in Camera3Device instead
567    if (mNewFrameReceived && !mShutterNotified) {
568        SharedParameters::Lock l(client->getParameters());
569        /* warning: this also locks a SharedCameraCallbacks */
570        shutterNotifyLocked(l.mParameters, client, mMsgType);
571        mShutterNotified = true;
572    }
573
574    // Wait until jpeg was captured by JpegProcessor
575    while (mNewFrameReceived && !mNewCaptureReceived) {
576        res = mNewCaptureSignal.waitRelative(mInputMutex, kWaitDuration);
577        if (res == TIMED_OUT) {
578            mTimeoutCount--;
579            break;
580        }
581    }
582    if (mTimeoutCount <= 0) {
583        ALOGW("Timed out waiting for capture to complete");
584        return DONE;
585    }
586    if (mNewFrameReceived && mNewCaptureReceived) {
587        if (mNewFrameId != mCaptureId) {
588            ALOGW("Mismatched capture frame IDs: Expected %d, got %d",
589                    mCaptureId, mNewFrameId);
590        }
591        camera_metadata_entry_t entry;
592        entry = mNewFrame.find(ANDROID_SENSOR_TIMESTAMP);
593        if (entry.count == 0) {
594            ALOGE("No timestamp field in capture frame!");
595        } else if (entry.count == 1) {
596            if (entry.data.i64[0] != mCaptureTimestamp) {
597                ALOGW("Mismatched capture timestamps: Metadata frame %" PRId64 ","
598                        " captured buffer %" PRId64,
599                        entry.data.i64[0],
600                        mCaptureTimestamp);
601            }
602        } else {
603            ALOGE("Timestamp metadata is malformed!");
604        }
605        client->removeFrameListener(mCaptureId, mCaptureId + 1, this);
606
607        mNewFrameReceived = false;
608        mNewCaptureReceived = false;
609        return DONE;
610    }
611    return STANDARD_CAPTURE_WAIT;
612}
613
614CaptureSequencer::CaptureState CaptureSequencer::manageBurstCaptureStart(
615        sp<Camera2Client> &client) {
616    ALOGV("%s", __FUNCTION__);
617    status_t res;
618    ATRACE_CALL();
619
620    // check which burst mode is set, create respective burst object
621    {
622        SharedParameters::Lock l(client->getParameters());
623
624        res = updateCaptureRequest(l.mParameters, client);
625        if(res != OK) {
626            return DONE;
627        }
628
629        //
630        // check for burst mode type in mParameters here
631        //
632        mBurstCapture = new BurstCapture(client, this);
633    }
634
635    res = mCaptureRequest.update(ANDROID_REQUEST_ID, &mCaptureId, 1);
636    if (res == OK) {
637        res = mCaptureRequest.sort();
638    }
639    if (res != OK) {
640        ALOGE("%s: Camera %d: Unable to set up still capture request: %s (%d)",
641                __FUNCTION__, client->getCameraId(), strerror(-res), res);
642        return DONE;
643    }
644
645    CameraMetadata captureCopy = mCaptureRequest;
646    if (captureCopy.entryCount() == 0) {
647        ALOGE("%s: Camera %d: Unable to copy capture request for HAL device",
648                __FUNCTION__, client->getCameraId());
649        return DONE;
650    }
651
652    Vector<CameraMetadata> requests;
653    requests.push(mCaptureRequest);
654    res = mBurstCapture->start(requests, mCaptureId);
655    mTimeoutCount = kMaxTimeoutsForCaptureEnd * 10;
656    return BURST_CAPTURE_WAIT;
657}
658
659CaptureSequencer::CaptureState CaptureSequencer::manageBurstCaptureWait(
660        sp<Camera2Client> &/*client*/) {
661    status_t res;
662    ATRACE_CALL();
663
664    while (!mNewCaptureReceived) {
665        res = mNewCaptureSignal.waitRelative(mInputMutex, kWaitDuration);
666        if (res == TIMED_OUT) {
667            mTimeoutCount--;
668            break;
669        }
670    }
671
672    if (mTimeoutCount <= 0) {
673        ALOGW("Timed out waiting for burst capture to complete");
674        return DONE;
675    }
676    if (mNewCaptureReceived) {
677        mNewCaptureReceived = false;
678        // TODO: update mCaptureId to last burst's capture ID + 1?
679        return DONE;
680    }
681
682    return BURST_CAPTURE_WAIT;
683}
684
685status_t CaptureSequencer::updateCaptureRequest(const Parameters &params,
686        sp<Camera2Client> &client) {
687    ATRACE_CALL();
688    status_t res;
689    if (mCaptureRequest.entryCount() == 0) {
690        res = client->getCameraDevice()->createDefaultRequest(
691                CAMERA2_TEMPLATE_STILL_CAPTURE,
692                &mCaptureRequest);
693        if (res != OK) {
694            ALOGE("%s: Camera %d: Unable to create default still image request:"
695                    " %s (%d)", __FUNCTION__, client->getCameraId(),
696                    strerror(-res), res);
697            return res;
698        }
699    }
700
701    res = params.updateRequest(&mCaptureRequest);
702    if (res != OK) {
703        ALOGE("%s: Camera %d: Unable to update common entries of capture "
704                "request: %s (%d)", __FUNCTION__, client->getCameraId(),
705                strerror(-res), res);
706        return res;
707    }
708
709    res = params.updateRequestJpeg(&mCaptureRequest);
710    if (res != OK) {
711        ALOGE("%s: Camera %d: Unable to update JPEG entries of capture "
712                "request: %s (%d)", __FUNCTION__, client->getCameraId(),
713                strerror(-res), res);
714        return res;
715    }
716
717    return OK;
718}
719
720/*static*/ void CaptureSequencer::shutterNotifyLocked(const Parameters &params,
721            sp<Camera2Client> client, int msgType) {
722    ATRACE_CALL();
723
724    if (params.state == Parameters::STILL_CAPTURE
725        && params.playShutterSound
726        && (msgType & CAMERA_MSG_SHUTTER)) {
727        client->getCameraService()->playSound(CameraService::SOUND_SHUTTER);
728    }
729
730    {
731        Camera2Client::SharedCameraCallbacks::Lock
732            l(client->mSharedCameraCallbacks);
733
734        ALOGV("%s: Notifying of shutter close to client", __FUNCTION__);
735        if (l.mRemoteCallback != 0) {
736            // ShutterCallback
737            l.mRemoteCallback->notifyCallback(CAMERA_MSG_SHUTTER,
738                                            /*ext1*/0, /*ext2*/0);
739
740            // RawCallback with null buffer
741            l.mRemoteCallback->notifyCallback(CAMERA_MSG_RAW_IMAGE_NOTIFY,
742                                            /*ext1*/0, /*ext2*/0);
743        } else {
744            ALOGV("%s: No client!", __FUNCTION__);
745        }
746    }
747}
748
749
750}; // namespace camera2
751}; // namespace android
752