ZslProcessor.cpp revision 656e86250cd68f7f362c50a4bc92a865e9deacbe
1da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala/*
2da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * Copyright (C) 2012 The Android Open Source Project
3da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala *
4da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * Licensed under the Apache License, Version 2.0 (the "License");
5da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * you may not use this file except in compliance with the License.
6da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * You may obtain a copy of the License at
7da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala *
8da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala *      http://www.apache.org/licenses/LICENSE-2.0
9da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala *
10da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * Unless required by applicable law or agreed to in writing, software
11da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * distributed under the License is distributed on an "AS IS" BASIS,
12da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * See the License for the specific language governing permissions and
14da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala * limitations under the License.
15da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala */
16da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
174bb8118816874c696d9f1adab48490df1da365f7Eino-Ville Talvala#define LOG_TAG "Camera2-ZslProcessor"
18da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#define ATRACE_TAG ATRACE_TAG_CAMERA
19da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala//#define LOG_NDEBUG 0
20da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala//#define LOG_NNDEBUG 0
21da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
22da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#ifdef LOG_NNDEBUG
23da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#define ALOGVV(...) ALOGV(__VA_ARGS__)
24da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#else
25da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#define ALOGVV(...) ((void)0)
26da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#endif
27da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
28da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#include <utils/Log.h>
29da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#include <utils/Trace.h>
30da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
31da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#include "ZslProcessor.h"
321a2952aee048ca7b1765e2bc09ebe9aeddaeafa3Mathias Agopian#include <gui/Surface.h>
33b99c5b8eebb35133a08c46b015624bd4c4a6c477Eino-Ville Talvala#include "../CameraDeviceBase.h"
34da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala#include "../Camera2Client.h"
35da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
36da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
37da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalanamespace android {
38da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalanamespace camera2 {
39da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
40da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville TalvalaZslProcessor::ZslProcessor(
41d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    sp<Camera2Client> client,
42da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    wp<CaptureSequencer> sequencer):
43da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        Thread(false),
44da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mState(RUNNING),
45da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mClient(client),
46d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        mDevice(client->getCameraDevice()),
47da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mSequencer(sequencer),
48d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        mId(client->getCameraId()),
49da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslBufferAvailable(false),
50da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslStreamId(NO_STREAM),
51da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslReprocessStreamId(NO_STREAM),
52da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mFrameListHead(0),
53da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslQueueHead(0),
54da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslQueueTail(0) {
55da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    mZslQueue.insertAt(0, kZslBufferDepth);
56da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    mFrameList.insertAt(0, kFrameListDepth);
57da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    sp<CaptureSequencer> captureSequencer = mSequencer.promote();
58da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (captureSequencer != 0) captureSequencer->setZslProcessor(this);
59da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
60da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
61da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville TalvalaZslProcessor::~ZslProcessor() {
62da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ALOGV("%s: Exit", __FUNCTION__);
63cf70d3469332445dc3ffd09729da3538612b1bb2Eino-Ville Talvala    deleteStream();
64da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
65da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
66da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalavoid ZslProcessor::onFrameAvailable() {
67da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
68da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (!mZslBufferAvailable) {
69da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslBufferAvailable = true;
70da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslBufferAvailableSignal.signal();
71da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
72da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
73da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
74d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvalavoid ZslProcessor::onFrameAvailable(int32_t /*frameId*/,
75d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        const CameraMetadata &frame) {
76da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
774865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala    camera_metadata_ro_entry_t entry;
78da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    entry = frame.find(ANDROID_SENSOR_TIMESTAMP);
79da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    nsecs_t timestamp = entry.data.i64[0];
80ddf3c5025e2f6f35a4c188c19f30142c64a092c4Igor Murashkin    (void)timestamp;
81da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ALOGVV("Got preview frame for timestamp %lld", timestamp);
82da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
83da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mState != RUNNING) return;
84da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
854865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala    mFrameList.editItemAt(mFrameListHead) = frame;
86da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    mFrameListHead = (mFrameListHead + 1) % kFrameListDepth;
87da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
88da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    findMatchesLocked();
89da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
90da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
91da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalavoid ZslProcessor::onBufferReleased(buffer_handle_t *handle) {
92da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
93da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
9497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    // Verify that the buffer is in our queue
9597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    size_t i = 0;
9697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    for (; i < mZslQueue.size(); i++) {
9797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        if (&(mZslQueue[i].buffer.mGraphicBuffer->handle) == handle) break;
9897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    }
9997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    if (i == mZslQueue.size()) {
10097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        ALOGW("%s: Released buffer %p not found in queue",
10197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                __FUNCTION__, handle);
102da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
103da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
104768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    // Erase entire ZSL queue since we've now completed the capture and preview
105768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    // is stopped.
106768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    clearZslQueueLocked();
107768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala
108da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    mState = RUNNING;
109da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
110da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
111da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalastatus_t ZslProcessor::updateStream(const Parameters &params) {
112da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ATRACE_CALL();
113da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ALOGV("%s: Configuring ZSL streams", __FUNCTION__);
114da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    status_t res;
115da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
116da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
117da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
118da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    sp<Camera2Client> client = mClient.promote();
119d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    if (client == 0) {
120d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        ALOGE("%s: Camera %d: Client does not exist", __FUNCTION__, mId);
121d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        return INVALID_OPERATION;
122d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    }
123d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    sp<CameraDeviceBase> device = mDevice.promote();
124d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    if (device == 0) {
125d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId);
126d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        return INVALID_OPERATION;
127d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    }
128da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
129da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mZslConsumer == 0) {
130da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        // Create CPU buffer queue endpoint
131da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslConsumer = new BufferItemConsumer(
132da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            GRALLOC_USAGE_HW_CAMERA_ZSL,
133da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            kZslBufferDepth,
134da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            true);
135da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslConsumer->setFrameAvailableListener(this);
136da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslConsumer->setName(String8("Camera2Client::ZslConsumer"));
1371a2952aee048ca7b1765e2bc09ebe9aeddaeafa3Mathias Agopian        mZslWindow = new Surface(
138da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            mZslConsumer->getProducerInterface());
139da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
140da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
141da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mZslStreamId != NO_STREAM) {
142da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        // Check if stream parameters have to change
143da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        uint32_t currentWidth, currentHeight;
144da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = device->getStreamInfo(mZslStreamId,
145da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                &currentWidth, &currentHeight, 0);
146da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK) {
147da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Camera %d: Error querying capture output stream info: "
148da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    "%s (%d)", __FUNCTION__,
149d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    mId, strerror(-res), res);
150da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return res;
151da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
1526e4db898bac9499a8abe7e6b6fbf729b78f6bd68Eino-Ville Talvala        if (currentWidth != (uint32_t)params.fastInfo.arrayWidth ||
1536e4db898bac9499a8abe7e6b6fbf729b78f6bd68Eino-Ville Talvala                currentHeight != (uint32_t)params.fastInfo.arrayHeight) {
15447512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala            res = device->deleteReprocessStream(mZslReprocessStreamId);
155da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            if (res != OK) {
156da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                ALOGE("%s: Camera %d: Unable to delete old reprocess stream "
157da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        "for ZSL: %s (%d)", __FUNCTION__,
158d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                        mId, strerror(-res), res);
159da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                return res;
160da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            }
161ecf17e82505fdb60d59e00b6dd59036df93de655Igor Murashkin            ALOGV("%s: Camera %d: Deleting stream %d since the buffer dimensions changed",
162d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                __FUNCTION__, mId, mZslStreamId);
163da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            res = device->deleteStream(mZslStreamId);
164da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            if (res != OK) {
165da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                ALOGE("%s: Camera %d: Unable to delete old output stream "
166da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        "for ZSL: %s (%d)", __FUNCTION__,
167d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                        mId, strerror(-res), res);
168da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                return res;
169da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            }
170da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            mZslStreamId = NO_STREAM;
171da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
172da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
173da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
174da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mZslStreamId == NO_STREAM) {
175da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        // Create stream for HAL production
1766e4db898bac9499a8abe7e6b6fbf729b78f6bd68Eino-Ville Talvala        // TODO: Sort out better way to select resolution for ZSL
177e382ee28709b83264a46b09e8f766c5ef42efa35Eino-Ville Talvala        int streamType = params.quirks.useZslFormat ?
178e382ee28709b83264a46b09e8f766c5ef42efa35Eino-Ville Talvala                (int)CAMERA2_HAL_PIXEL_FORMAT_ZSL :
179e382ee28709b83264a46b09e8f766c5ef42efa35Eino-Ville Talvala                (int)HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED;
180da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = device->createStream(mZslWindow,
1816e4db898bac9499a8abe7e6b6fbf729b78f6bd68Eino-Ville Talvala                params.fastInfo.arrayWidth, params.fastInfo.arrayHeight,
182e382ee28709b83264a46b09e8f766c5ef42efa35Eino-Ville Talvala                streamType, 0,
183da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                &mZslStreamId);
184da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK) {
185da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Camera %d: Can't create output stream for ZSL: "
186d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    "%s (%d)", __FUNCTION__, mId,
187da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    strerror(-res), res);
188da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return res;
189da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
190da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = device->createReprocessStreamFromStream(mZslStreamId,
191da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                &mZslReprocessStreamId);
192da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK) {
193da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Camera %d: Can't create reprocess stream for ZSL: "
194d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    "%s (%d)", __FUNCTION__, mId,
195da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    strerror(-res), res);
196da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return res;
197da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
198da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
1994865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala    client->registerFrameListener(Camera2Client::kPreviewRequestIdStart,
2004865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala            Camera2Client::kPreviewRequestIdEnd,
2014865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala            this);
202da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
203da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return OK;
204da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
205da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
206da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalastatus_t ZslProcessor::deleteStream() {
207da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ATRACE_CALL();
208da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    status_t res;
209da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
210da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
211da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
212da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mZslStreamId != NO_STREAM) {
213d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        sp<CameraDeviceBase> device = mDevice.promote();
214d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        if (device == 0) {
215d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala            ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId);
216d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala            return INVALID_OPERATION;
217d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        }
218d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala
219d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        clearZslQueueLocked();
220da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
22147512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        res = device->deleteReprocessStream(mZslReprocessStreamId);
22247512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        if (res != OK) {
22347512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala            ALOGE("%s: Camera %d: Cannot delete ZSL reprocessing stream %d: "
224d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    "%s (%d)", __FUNCTION__, mId,
22547512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala                    mZslReprocessStreamId, strerror(-res), res);
22647512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala            return res;
22747512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        }
22847512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala
229da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslReprocessStreamId = NO_STREAM;
23047512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        res = device->deleteStream(mZslStreamId);
23147512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        if (res != OK) {
23247512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala            ALOGE("%s: Camera %d: Cannot delete ZSL output stream %d: "
233d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    "%s (%d)", __FUNCTION__, mId,
23447512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala                    mZslStreamId, strerror(-res), res);
23547512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala            return res;
23647512a7da600ababdfd052b574488b9e499c22f6Eino-Ville Talvala        }
237cf70d3469332445dc3ffd09729da3538612b1bb2Eino-Ville Talvala
238cf70d3469332445dc3ffd09729da3538612b1bb2Eino-Ville Talvala        mZslWindow.clear();
239cf70d3469332445dc3ffd09729da3538612b1bb2Eino-Ville Talvala        mZslConsumer.clear();
240cf70d3469332445dc3ffd09729da3538612b1bb2Eino-Ville Talvala
241da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslStreamId = NO_STREAM;
242da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
243da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return OK;
244da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
245da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
246da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalaint ZslProcessor::getStreamId() const {
247da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
248da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return mZslStreamId;
249da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
250da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
251da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalastatus_t ZslProcessor::pushToReprocess(int32_t requestId) {
252da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ALOGV("%s: Send in reprocess request with id %d",
253da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            __FUNCTION__, requestId);
254da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
255da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    status_t res;
256da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    sp<Camera2Client> client = mClient.promote();
257da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
258d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    if (client == 0) {
259d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        ALOGE("%s: Camera %d: Client does not exist", __FUNCTION__, mId);
260d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        return INVALID_OPERATION;
261d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    }
26297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
26397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    IF_ALOGV() {
26497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        dumpZslQueue(-1);
26597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    }
26697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
267da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mZslQueueTail != mZslQueueHead) {
268bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        CameraMetadata request;
269bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        size_t index = mZslQueueTail;
2704d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala        while (index != mZslQueueHead) {
2714d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala            if (!mZslQueue[index].frame.isEmpty()) {
2724d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala                request = mZslQueue[index].frame;
2734d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala                break;
2744d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala            }
275bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            index = (index + 1) % kZslBufferDepth;
276bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        }
2774d410ede659448557398c84552eb0bf50ef09cbcEino-Ville Talvala        if (index == mZslQueueHead) {
27897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            ALOGV("%s: ZSL queue has no valid frames to send yet.",
27997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                  __FUNCTION__);
28097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            return NOT_ENOUGH_DATA;
28197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        }
28297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        // Verify that the frame is reasonable for reprocessing
28397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
28497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        camera_metadata_entry_t entry;
28597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        entry = request.find(ANDROID_CONTROL_AE_STATE);
28697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        if (entry.count == 0) {
28797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            ALOGE("%s: ZSL queue frame has no AE state field!",
28897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                    __FUNCTION__);
289bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            return BAD_VALUE;
290bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        }
29197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        if (entry.data.u8[0] != ANDROID_CONTROL_AE_STATE_CONVERGED &&
29297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                entry.data.u8[0] != ANDROID_CONTROL_AE_STATE_LOCKED) {
29397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            ALOGV("%s: ZSL queue frame AE state is %d, need full capture",
29497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                    __FUNCTION__, entry.data.u8[0]);
29597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            return NOT_ENOUGH_DATA;
29697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        }
29797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
298da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        buffer_handle_t *handle =
299bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            &(mZslQueue[index].buffer.mGraphicBuffer->handle);
300bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala
301da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        uint8_t requestType = ANDROID_REQUEST_TYPE_REPROCESS;
302da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = request.update(ANDROID_REQUEST_TYPE,
303da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                &requestType, 1);
304b99c5b8eebb35133a08c46b015624bd4c4a6c477Eino-Ville Talvala        uint8_t inputStreams[1] =
305b99c5b8eebb35133a08c46b015624bd4c4a6c477Eino-Ville Talvala                { static_cast<uint8_t>(mZslReprocessStreamId) };
306da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res == OK) request.update(ANDROID_REQUEST_INPUT_STREAMS,
307da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                inputStreams, 1);
308b99c5b8eebb35133a08c46b015624bd4c4a6c477Eino-Ville Talvala        uint8_t outputStreams[1] =
309b99c5b8eebb35133a08c46b015624bd4c4a6c477Eino-Ville Talvala                { static_cast<uint8_t>(client->getCaptureStreamId()) };
310da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res == OK) request.update(ANDROID_REQUEST_OUTPUT_STREAMS,
311da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                outputStreams, 1);
312da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = request.update(ANDROID_REQUEST_ID,
313da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                &requestId, 1);
314da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
315da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK ) {
316da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Unable to update frame to a reprocess request", __FUNCTION__);
317da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return INVALID_OPERATION;
318da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
319da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
3204865c526e681366481b0ab242ffa1ead57bb02ccEino-Ville Talvala        res = client->stopStream();
321c20630569431234db23b6182dd17102023dee68eAlex Ray        if (res != OK) {
322c20630569431234db23b6182dd17102023dee68eAlex Ray            ALOGE("%s: Camera %d: Unable to stop preview for ZSL capture: "
323c20630569431234db23b6182dd17102023dee68eAlex Ray                "%s (%d)",
324d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                __FUNCTION__, mId, strerror(-res), res);
325c20630569431234db23b6182dd17102023dee68eAlex Ray            return INVALID_OPERATION;
326c20630569431234db23b6182dd17102023dee68eAlex Ray        }
327c20630569431234db23b6182dd17102023dee68eAlex Ray        // TODO: have push-and-clear be atomic
328da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = client->getCameraDevice()->pushReprocessBuffer(mZslReprocessStreamId,
329da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                handle, this);
330da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK) {
331da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Unable to push buffer for reprocessing: %s (%d)",
332da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    __FUNCTION__, strerror(-res), res);
333da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return res;
334da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
335da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
336ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        // Update JPEG settings
337ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        {
338ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala            SharedParameters::Lock l(client->getParameters());
339ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala            res = l.mParameters.updateRequestJpeg(&request);
340ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala            if (res != OK) {
341ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala                ALOGE("%s: Camera %d: Unable to update JPEG entries of ZSL "
342ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala                        "capture request: %s (%d)", __FUNCTION__,
343d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                        mId,
344ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala                        strerror(-res), res);
345ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala                return res;
346ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala            }
347ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        }
348ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala
349ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        mLatestCapturedRequest = request;
350da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        res = client->getCameraDevice()->capture(request);
351da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (res != OK ) {
352da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            ALOGE("%s: Unable to send ZSL reprocess request to capture: %s (%d)",
353da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    __FUNCTION__, strerror(-res), res);
354da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            return res;
355da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
356da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
357da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mState = LOCKED;
358da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    } else {
35997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        ALOGV("%s: No ZSL buffers yet", __FUNCTION__);
36097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        return NOT_ENOUGH_DATA;
361da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
362da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return OK;
363da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
364da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
365768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvalastatus_t ZslProcessor::clearZslQueue() {
366768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
367768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    // If in middle of capture, can't clear out queue
368768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    if (mState == LOCKED) return OK;
369768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala
370768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    return clearZslQueueLocked();
371768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala}
372768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala
373768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvalastatus_t ZslProcessor::clearZslQueueLocked() {
374768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    for (size_t i = 0; i < mZslQueue.size(); i++) {
375768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala        if (mZslQueue[i].buffer.mTimestamp != 0) {
376768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala            mZslConsumer->releaseBuffer(mZslQueue[i].buffer);
377768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala        }
378768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala        mZslQueue.replaceAt(i);
379768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    }
380768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    mZslQueueHead = 0;
381768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    mZslQueueTail = 0;
382768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala    return OK;
383768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala}
384768cf093dade9085e0ad6305d9f7c16ae9ad9e26Eino-Ville Talvala
385ddf3c5025e2f6f35a4c188c19f30142c64a092c4Igor Murashkinvoid ZslProcessor::dump(int fd, const Vector<String16>& /*args*/) const {
38697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    Mutex::Autolock l(mInputMutex);
387ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala    if (!mLatestCapturedRequest.isEmpty()) {
388ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        String8 result("    Latest ZSL capture request:\n");
389ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        write(fd, result.string(), result.size());
390ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        mLatestCapturedRequest.dump(fd, 2, 6);
391ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala    } else {
392ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        String8 result("    Latest ZSL capture request: none yet\n");
393ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala        write(fd, result.string(), result.size());
394ec7710898208162576c3242f5a590651ab42aa2dEino-Ville Talvala    }
39597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    dumpZslQueue(fd);
396da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
397da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
398da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalabool ZslProcessor::threadLoop() {
399da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    status_t res;
400da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
401da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    {
402da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        Mutex::Autolock l(mInputMutex);
403da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        while (!mZslBufferAvailable) {
404da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            res = mZslBufferAvailableSignal.waitRelative(mInputMutex,
405da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    kWaitDuration);
406da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            if (res == TIMED_OUT) return true;
407da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
408da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslBufferAvailable = false;
409da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
410da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
411da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    do {
412d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        res = processNewZslBuffer();
413da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    } while (res == OK);
414da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
415da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return true;
416da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
417da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
418d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvalastatus_t ZslProcessor::processNewZslBuffer() {
419da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ATRACE_CALL();
420da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    status_t res;
421d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    sp<BufferItemConsumer> zslConsumer;
422d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    {
423d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        Mutex::Autolock l(mInputMutex);
424d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        if (mZslConsumer == 0) return OK;
425d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        zslConsumer = mZslConsumer;
426d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala    }
427bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    ALOGVV("Trying to get next buffer");
428bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    BufferItemConsumer::BufferItem item;
429656e86250cd68f7f362c50a4bc92a865e9deacbeAndy McFadden    res = zslConsumer->acquireBuffer(&item, 0);
430bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    if (res != OK) {
431bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        if (res != BufferItemConsumer::NO_BUFFER_AVAILABLE) {
432bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            ALOGE("%s: Camera %d: Error receiving ZSL image buffer: "
433bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala                    "%s (%d)", __FUNCTION__,
434d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala                    mId, strerror(-res), res);
435bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        } else {
436bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            ALOGVV("  No buffer");
437bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        }
438bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        return res;
439bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    }
440bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala
441da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    Mutex::Autolock l(mInputMutex);
442da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
443da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if (mState == LOCKED) {
444bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        ALOGVV("In capture, discarding new ZSL buffers");
445d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        zslConsumer->releaseBuffer(item);
446da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        return OK;
447da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
448da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
449da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ALOGVV("Got ZSL buffer: head: %d, tail: %d", mZslQueueHead, mZslQueueTail);
450da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
451da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    if ( (mZslQueueHead + 1) % kZslBufferDepth == mZslQueueTail) {
452bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        ALOGVV("Releasing oldest buffer");
453d09801b99503b57c35e321ad9afa7e861e012813Eino-Ville Talvala        zslConsumer->releaseBuffer(mZslQueue[mZslQueueTail].buffer);
454da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslQueue.replaceAt(mZslQueueTail);
455da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        mZslQueueTail = (mZslQueueTail + 1) % kZslBufferDepth;
456da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
457da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
458da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    ZslPair &queueHead = mZslQueue.editItemAt(mZslQueueHead);
459da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
460bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    queueHead.buffer = item;
461da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    queueHead.frame.release();
462da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
463da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    mZslQueueHead = (mZslQueueHead + 1) % kZslBufferDepth;
464da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
465bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    ALOGVV("  Acquired buffer, timestamp %lld", queueHead.buffer.mTimestamp);
466da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
467da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    findMatchesLocked();
468da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
469da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return OK;
470da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
471da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
472da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalavoid ZslProcessor::findMatchesLocked() {
473bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala    ALOGVV("Scanning");
474da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    for (size_t i = 0; i < mZslQueue.size(); i++) {
475da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        ZslPair &queueEntry = mZslQueue.editItemAt(i);
476da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        nsecs_t bufferTimestamp = queueEntry.buffer.mTimestamp;
477bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        IF_ALOGV() {
478bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            camera_metadata_entry_t entry;
479bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            nsecs_t frameTimestamp = 0;
480bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            if (!queueEntry.frame.isEmpty()) {
481bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala                entry = queueEntry.frame.find(ANDROID_SENSOR_TIMESTAMP);
482bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala                frameTimestamp = entry.data.i64[0];
483bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            }
484bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala            ALOGVV("   %d: b: %lld\tf: %lld", i,
485bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala                    bufferTimestamp, frameTimestamp );
486bdde5f884eaf270ab4b806849f3122a46cd872ceEino-Ville Talvala        }
487da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        if (queueEntry.frame.isEmpty() && bufferTimestamp != 0) {
488da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            // Have buffer, no matching frame. Look for one
489da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            for (size_t j = 0; j < mFrameList.size(); j++) {
490da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                bool match = false;
491da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                CameraMetadata &frame = mFrameList.editItemAt(j);
492da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                if (!frame.isEmpty()) {
493da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    camera_metadata_entry_t entry;
494da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    entry = frame.find(ANDROID_SENSOR_TIMESTAMP);
495da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    if (entry.count == 0) {
496da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        ALOGE("%s: Can't find timestamp in frame!",
497da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                                __FUNCTION__);
498da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        continue;
499da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    }
500da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    nsecs_t frameTimestamp = entry.data.i64[0];
501da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    if (bufferTimestamp == frameTimestamp) {
502da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        ALOGVV("%s: Found match %lld", __FUNCTION__,
503da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                                frameTimestamp);
504da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        match = true;
505da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    } else {
506da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        int64_t delta = abs(bufferTimestamp - frameTimestamp);
507da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        if ( delta < 1000000) {
508da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                            ALOGVV("%s: Found close match %lld (delta %lld)",
509da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                                    __FUNCTION__, bufferTimestamp, delta);
510da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                            match = true;
511da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                        }
512da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    }
513da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                }
514da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                if (match) {
515da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    queueEntry.frame.acquire(frame);
516da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                    break;
517da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala                }
518da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala            }
519da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala        }
520da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    }
521da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
522da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
52397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvalavoid ZslProcessor::dumpZslQueue(int fd) const {
52497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    String8 header("ZSL queue contents:");
52597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    String8 indent("    ");
52697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    ALOGV("%s", header.string());
52797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    if (fd != -1) {
52897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        header = indent + header + "\n";
52997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        write(fd, header.string(), header.size());
53097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    }
53197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    for (size_t i = 0; i < mZslQueue.size(); i++) {
53297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        const ZslPair &queueEntry = mZslQueue[i];
53397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        nsecs_t bufferTimestamp = queueEntry.buffer.mTimestamp;
53497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        camera_metadata_ro_entry_t entry;
53597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        nsecs_t frameTimestamp = 0;
53697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        int frameAeState = -1;
53797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        if (!queueEntry.frame.isEmpty()) {
53897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            entry = queueEntry.frame.find(ANDROID_SENSOR_TIMESTAMP);
53997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            if (entry.count > 0) frameTimestamp = entry.data.i64[0];
54097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            entry = queueEntry.frame.find(ANDROID_CONTROL_AE_STATE);
54197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            if (entry.count > 0) frameAeState = entry.data.u8[0];
54297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        }
54397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        String8 result =
54497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                String8::format("   %d: b: %lld\tf: %lld, AE state: %d", i,
54597b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala                        bufferTimestamp, frameTimestamp, frameAeState);
54697b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        ALOGV("%s", result.string());
54797b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        if (fd != -1) {
54897b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            result = indent + result + "\n";
54997b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala            write(fd, result.string(), result.size());
55097b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala        }
55197b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
55297b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala    }
55397b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala}
55497b38a81ac989ccba02d726011a82541f14166dfEino-Ville Talvala
555da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}; // namespace camera2
556da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}; // namespace android
557