Camera2Client.cpp revision 9cca4c6d976d2d4127286e9eaa54d1b99880c25c
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 "Camera2Client"
18#define ATRACE_TAG ATRACE_TAG_CAMERA
19//#define LOG_NDEBUG 0
20
21#include <utils/Log.h>
22#include <utils/Trace.h>
23
24#include <cutils/properties.h>
25#include <gui/SurfaceTextureClient.h>
26#include <gui/Surface.h>
27
28#include <math.h>
29
30#include "Camera2Client.h"
31
32namespace android {
33
34#define ALOG1(...) ALOGD_IF(gLogLevel >= 1, __VA_ARGS__);
35#define ALOG2(...) ALOGD_IF(gLogLevel >= 2, __VA_ARGS__);
36
37static int getCallingPid() {
38    return IPCThreadState::self()->getCallingPid();
39}
40
41static int getCallingUid() {
42    return IPCThreadState::self()->getCallingUid();
43}
44
45// Interface used by CameraService
46
47Camera2Client::Camera2Client(const sp<CameraService>& cameraService,
48        const sp<ICameraClient>& cameraClient,
49        int cameraId,
50        int cameraFacing,
51        int clientPid):
52        Client(cameraService, cameraClient,
53                cameraId, cameraFacing, clientPid),
54        mState(NOT_INITIALIZED),
55        mPreviewStreamId(NO_STREAM),
56        mPreviewRequest(NULL),
57        mCaptureStreamId(NO_STREAM),
58        mCaptureRequest(NULL),
59        mRecordingStreamId(NO_STREAM),
60        mRecordingRequest(NULL)
61{
62    ATRACE_CALL();
63
64    mDevice = new Camera2Device(cameraId);
65}
66
67status_t Camera2Client::initialize(camera_module_t *module)
68{
69    ATRACE_CALL();
70    status_t res;
71
72    res = mDevice->initialize(module);
73    if (res != OK) {
74        ALOGE("%s: Camera %d: unable to initialize device: %s (%d)",
75                __FUNCTION__, mCameraId, strerror(-res), res);
76        return NO_INIT;
77    }
78
79    res = buildDefaultParameters();
80    if (res != OK) {
81        ALOGE("%s: Camera %d: unable to build defaults: %s (%d)",
82                __FUNCTION__, mCameraId, strerror(-res), res);
83        return NO_INIT;
84    }
85
86    if (gLogLevel >= 1) {
87        ALOGD("%s: Default parameters converted from camera %d:", __FUNCTION__,
88              mCameraId);
89        ALOGD("%s", mParamsFlattened.string());
90    }
91
92    mState = STOPPED;
93
94    return OK;
95}
96
97Camera2Client::~Camera2Client() {
98    ATRACE_CALL();
99    ALOGV("%s: Camera %d: Shutting down", __FUNCTION__, mCameraId);
100
101    mDestructionStarted = true;
102
103    disconnect();
104
105}
106
107status_t Camera2Client::dump(int fd, const Vector<String16>& args) {
108    String8 result;
109    result.appendFormat("Client2[%d] (%p) PID: %d, dump:\n",
110            mCameraId,
111            getCameraClient()->asBinder().get(),
112            mClientPid);
113    result.append("  State: ");
114#define CASE_APPEND_ENUM(x) case x: result.append(#x "\n"); break;
115
116    result.append(getStateName(mState));
117
118    result.append("\n  Current parameters:\n");
119    result.appendFormat("    Preview size: %d x %d\n",
120            mParameters.previewWidth, mParameters.previewHeight);
121    result.appendFormat("    Preview FPS range: %d - %d\n",
122            mParameters.previewFpsRange[0], mParameters.previewFpsRange[1]);
123    result.appendFormat("    Preview HAL pixel format: 0x%x\n",
124            mParameters.previewFormat);
125    result.appendFormat("    Preview transform: %x\n",
126            mParameters.previewTransform);
127    result.appendFormat("    Picture size: %d x %d\n",
128            mParameters.pictureWidth, mParameters.pictureHeight);
129    result.appendFormat("    Jpeg thumbnail size: %d x %d\n",
130            mParameters.jpegThumbSize[0], mParameters.jpegThumbSize[1]);
131    result.appendFormat("    Jpeg quality: %d, thumbnail quality: %d\n",
132            mParameters.jpegQuality, mParameters.jpegThumbQuality);
133    result.appendFormat("    Jpeg rotation: %d\n", mParameters.jpegRotation);
134    result.appendFormat("    GPS tags %s\n",
135            mParameters.gpsEnabled ? "enabled" : "disabled");
136    if (mParameters.gpsEnabled) {
137        result.appendFormat("    GPS lat x long x alt: %f x %f x %f\n",
138                mParameters.gpsCoordinates[0], mParameters.gpsCoordinates[1],
139                mParameters.gpsCoordinates[2]);
140        result.appendFormat("    GPS timestamp: %lld\n",
141                mParameters.gpsTimestamp);
142        result.appendFormat("    GPS processing method: %s\n",
143                mParameters.gpsProcessingMethod.string());
144    }
145
146    result.append("    White balance mode: ");
147    switch (mParameters.wbMode) {
148        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_AUTO)
149        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_INCANDESCENT)
150        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_FLUORESCENT)
151        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_WARM_FLUORESCENT)
152        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_DAYLIGHT)
153        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT)
154        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_TWILIGHT)
155        CASE_APPEND_ENUM(ANDROID_CONTROL_AWB_SHADE)
156        default: result.append("UNKNOWN\n");
157    }
158
159    result.append("    Effect mode: ");
160    switch (mParameters.effectMode) {
161        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_OFF)
162        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_MONO)
163        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_NEGATIVE)
164        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_SOLARIZE)
165        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_SEPIA)
166        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_POSTERIZE)
167        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_WHITEBOARD)
168        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_BLACKBOARD)
169        CASE_APPEND_ENUM(ANDROID_CONTROL_EFFECT_AQUA)
170        default: result.append("UNKNOWN\n");
171    }
172
173    result.append("    Antibanding mode: ");
174    switch (mParameters.antibandingMode) {
175        CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_AUTO)
176        CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_OFF)
177        CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_50HZ)
178        CASE_APPEND_ENUM(ANDROID_CONTROL_AE_ANTIBANDING_60HZ)
179        default: result.append("UNKNOWN\n");
180    }
181
182    result.append("    Scene mode: ");
183    switch (mParameters.sceneMode) {
184        case ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED:
185            result.append("AUTO\n"); break;
186        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_ACTION)
187        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_PORTRAIT)
188        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_LANDSCAPE)
189        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_NIGHT)
190        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT)
191        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_THEATRE)
192        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_BEACH)
193        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SNOW)
194        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SUNSET)
195        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO)
196        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_FIREWORKS)
197        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_SPORTS)
198        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_PARTY)
199        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT)
200        CASE_APPEND_ENUM(ANDROID_CONTROL_SCENE_MODE_BARCODE)
201        default: result.append("UNKNOWN\n");
202    }
203
204    result.append("    Flash mode: ");
205    switch (mParameters.flashMode) {
206        CASE_APPEND_ENUM(Parameters::FLASH_MODE_OFF)
207        CASE_APPEND_ENUM(Parameters::FLASH_MODE_AUTO)
208        CASE_APPEND_ENUM(Parameters::FLASH_MODE_ON)
209        CASE_APPEND_ENUM(Parameters::FLASH_MODE_TORCH)
210        CASE_APPEND_ENUM(Parameters::FLASH_MODE_RED_EYE)
211        CASE_APPEND_ENUM(Parameters::FLASH_MODE_INVALID)
212        default: result.append("UNKNOWN\n");
213    }
214
215    result.append("    Focus mode: ");
216    switch (mParameters.focusMode) {
217        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_AUTO)
218        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_MACRO)
219        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_CONTINUOUS_VIDEO)
220        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_CONTINUOUS_PICTURE)
221        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_EDOF)
222        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_INFINITY)
223        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_FIXED)
224        CASE_APPEND_ENUM(Parameters::FOCUS_MODE_INVALID)
225        default: result.append("UNKNOWN\n");
226    }
227
228    result.append("    Focusing areas:\n");
229    for (size_t i = 0; i < mParameters.focusingAreas.size(); i++) {
230        result.appendFormat("      [ (%d, %d, %d, %d), weight %d ]\n",
231                mParameters.focusingAreas[i].left,
232                mParameters.focusingAreas[i].top,
233                mParameters.focusingAreas[i].right,
234                mParameters.focusingAreas[i].bottom,
235                mParameters.focusingAreas[i].weight);
236    }
237
238    result.appendFormat("    Exposure compensation index: %d\n",
239            mParameters.exposureCompensation);
240
241    result.appendFormat("    AE lock %s, AWB lock %s\n",
242            mParameters.autoExposureLock ? "enabled" : "disabled",
243            mParameters.autoWhiteBalanceLock ? "enabled" : "disabled" );
244
245    result.appendFormat("    Metering areas:\n");
246    for (size_t i = 0; i < mParameters.meteringAreas.size(); i++) {
247        result.appendFormat("      [ (%d, %d, %d, %d), weight %d ]\n",
248                mParameters.meteringAreas[i].left,
249                mParameters.meteringAreas[i].top,
250                mParameters.meteringAreas[i].right,
251                mParameters.meteringAreas[i].bottom,
252                mParameters.meteringAreas[i].weight);
253    }
254
255    result.appendFormat("    Zoom index: %d\n", mParameters.zoom);
256    result.appendFormat("    Video size: %d x %d\n", mParameters.videoWidth,
257            mParameters.videoHeight);
258
259    result.appendFormat("    Recording hint is %s\n",
260            mParameters.recordingHint ? "set" : "not set");
261
262    result.appendFormat("    Video stabilization is %s\n",
263            mParameters.videoStabilization ? "enabled" : "disabled");
264
265    result.append("  Current streams:\n");
266    result.appendFormat("    Preview stream ID: %d\n", mPreviewStreamId);
267    result.appendFormat("    Capture stream ID: %d\n", mCaptureStreamId);
268
269    result.append("  Current requests:\n");
270    if (mPreviewRequest != NULL) {
271        result.append("    Preview request:\n");
272        write(fd, result.string(), result.size());
273        dump_camera_metadata(mPreviewRequest, fd, 2);
274    } else {
275        result.append("    Preview request: undefined\n");
276        write(fd, result.string(), result.size());
277    }
278
279    if (mCaptureRequest != NULL) {
280        result = "    Capture request:\n";
281        write(fd, result.string(), result.size());
282        dump_camera_metadata(mCaptureRequest, fd, 2);
283    } else {
284        result = "    Capture request: undefined\n";
285        write(fd, result.string(), result.size());
286    }
287
288    result = "  Device dump:\n";
289    write(fd, result.string(), result.size());
290
291    status_t res = mDevice->dump(fd, args);
292    if (res != OK) {
293        result = String8::format("   Error dumping device: %s (%d)",
294                strerror(-res), res);
295        write(fd, result.string(), result.size());
296    }
297
298#undef CASE_APPEND_ENUM
299    return NO_ERROR;
300}
301
302const char* Camera2Client::getStateName(State state) {
303#define CASE_ENUM_TO_CHAR(x) case x: return(#x); break;
304    switch(state) {
305        CASE_ENUM_TO_CHAR(NOT_INITIALIZED)
306        CASE_ENUM_TO_CHAR(STOPPED)
307        CASE_ENUM_TO_CHAR(WAITING_FOR_PREVIEW_WINDOW)
308        CASE_ENUM_TO_CHAR(PREVIEW)
309        CASE_ENUM_TO_CHAR(RECORD)
310        CASE_ENUM_TO_CHAR(STILL_CAPTURE)
311        CASE_ENUM_TO_CHAR(VIDEO_SNAPSHOT)
312        default:
313            return "Unknown state!";
314            break;
315    }
316#undef CASE_ENUM_TO_CHAR
317}
318
319// ICamera interface
320
321void Camera2Client::disconnect() {
322    ATRACE_CALL();
323    Mutex::Autolock icl(mICameraLock);
324
325    if (mDevice == 0) return;
326
327    stopPreviewLocked();
328
329    mDevice->waitUntilDrained();
330
331    if (mPreviewStreamId != NO_STREAM) {
332        mDevice->deleteStream(mPreviewStreamId);
333        mPreviewStreamId = NO_STREAM;
334    }
335
336    if (mCaptureStreamId != NO_STREAM) {
337        mDevice->deleteStream(mCaptureStreamId);
338        mCaptureStreamId = NO_STREAM;
339    }
340
341    CameraService::Client::disconnect();
342}
343
344status_t Camera2Client::connect(const sp<ICameraClient>& client) {
345    ATRACE_CALL();
346
347    Mutex::Autolock icl(mICameraLock);
348
349    if (mClientPid != 0 && getCallingPid() != mClientPid) {
350        ALOGE("%s: Camera %d: Connection attempt from pid %d; "
351                "current locked to pid %d", __FUNCTION__,
352                mCameraId, getCallingPid(), mClientPid);
353        return BAD_VALUE;
354    }
355
356    mClientPid = getCallingPid();
357    mCameraClient = client;
358
359    return OK;
360}
361
362status_t Camera2Client::lock() {
363    ATRACE_CALL();
364    Mutex::Autolock icl(mICameraLock);
365    ALOGV("%s: Camera %d: Lock call from pid %d; current client pid %d",
366            __FUNCTION__, mCameraId, getCallingPid(), mClientPid);
367
368    if (mClientPid == 0) {
369        mClientPid = getCallingPid();
370        return OK;
371    }
372
373    if (mClientPid != getCallingPid()) {
374        ALOGE("%s: Camera %d: Lock call from pid %d; currently locked to pid %d",
375                __FUNCTION__, mCameraId, getCallingPid(), mClientPid);
376        return EBUSY;
377    }
378
379    return OK;
380}
381
382status_t Camera2Client::unlock() {
383    ATRACE_CALL();
384    Mutex::Autolock icl(mICameraLock);
385    ALOGV("%s: Camera %d: Unlock call from pid %d; current client pid %d",
386            __FUNCTION__, mCameraId, getCallingPid(), mClientPid);
387
388    // TODO: Check for uninterruptable conditions
389
390    if (mClientPid == getCallingPid()) {
391        mClientPid = 0;
392        mCameraClient.clear();
393        return OK;
394    }
395
396    ALOGE("%s: Camera %d: Unlock call from pid %d; currently locked to pid %d",
397            __FUNCTION__, mCameraId, getCallingPid(), mClientPid);
398    return EBUSY;
399}
400
401status_t Camera2Client::setPreviewDisplay(
402        const sp<Surface>& surface) {
403    ATRACE_CALL();
404    Mutex::Autolock icl(mICameraLock);
405
406    sp<IBinder> binder;
407    sp<ANativeWindow> window;
408    if (surface != 0) {
409        binder = surface->asBinder();
410        window = surface;
411    }
412
413    return setPreviewWindowLocked(binder,window);
414}
415
416status_t Camera2Client::setPreviewTexture(
417        const sp<ISurfaceTexture>& surfaceTexture) {
418    ATRACE_CALL();
419    Mutex::Autolock icl(mICameraLock);
420
421    sp<IBinder> binder;
422    sp<ANativeWindow> window;
423    if (surfaceTexture != 0) {
424        binder = surfaceTexture->asBinder();
425        window = new SurfaceTextureClient(surfaceTexture);
426    }
427    return setPreviewWindowLocked(binder, window);
428}
429
430status_t Camera2Client::setPreviewWindowLocked(const sp<IBinder>& binder,
431        sp<ANativeWindow> window) {
432    ATRACE_CALL();
433    status_t res;
434
435    if (binder == mPreviewSurface) {
436        return NO_ERROR;
437    }
438
439    switch (mState) {
440        case NOT_INITIALIZED:
441        case RECORD:
442        case STILL_CAPTURE:
443        case VIDEO_SNAPSHOT:
444            ALOGE("%s: Camera %d: Cannot set preview display while in state %s",
445                    __FUNCTION__, mCameraId, getStateName(mState));
446            return INVALID_OPERATION;
447        case STOPPED:
448        case WAITING_FOR_PREVIEW_WINDOW:
449            // OK
450            break;
451        case PREVIEW:
452            // Already running preview - need to stop and create a new stream
453            // TODO: Optimize this so that we don't wait for old stream to drain
454            // before spinning up new stream
455            mDevice->setStreamingRequest(NULL);
456            mState = WAITING_FOR_PREVIEW_WINDOW;
457            break;
458    }
459
460    if (mPreviewStreamId != NO_STREAM) {
461        res = mDevice->waitUntilDrained();
462        if (res != OK) {
463            ALOGE("%s: Error waiting for preview to drain: %s (%d)",
464                    __FUNCTION__, strerror(-res), res);
465            return res;
466        }
467        res = mDevice->deleteStream(mPreviewStreamId);
468        if (res != OK) {
469            ALOGE("%s: Unable to delete old preview stream: %s (%d)",
470                    __FUNCTION__, strerror(-res), res);
471            return res;
472        }
473        mPreviewStreamId = NO_STREAM;
474    }
475
476    mPreviewSurface = binder;
477    mPreviewWindow = window;
478
479    if (mState == WAITING_FOR_PREVIEW_WINDOW) {
480        return startPreviewLocked();
481    }
482
483    return OK;
484}
485
486void Camera2Client::setPreviewCallbackFlag(int flag) {
487    ATRACE_CALL();
488    Mutex::Autolock icl(mICameraLock);
489}
490
491status_t Camera2Client::startPreview() {
492    ATRACE_CALL();
493    Mutex::Autolock icl(mICameraLock);
494    return startPreviewLocked();
495}
496
497status_t Camera2Client::startPreviewLocked() {
498    ATRACE_CALL();
499    status_t res;
500    if (mState >= PREVIEW) {
501        ALOGE("%s: Can't start preview in state %s",
502                __FUNCTION__, getStateName(mState));
503        return INVALID_OPERATION;
504    }
505
506    if (mPreviewWindow == 0) {
507        mState = WAITING_FOR_PREVIEW_WINDOW;
508        return OK;
509    }
510    mState = STOPPED;
511
512    Mutex::Autolock pl(mParamsLock);
513
514    res = updatePreviewStream();
515    if (res != OK) {
516        ALOGE("%s: Camera %d: Unable to update preview stream: %s (%d)",
517                __FUNCTION__, mCameraId, strerror(-res), res);
518        return res;
519    }
520
521    if (mPreviewRequest == NULL) {
522        res = updatePreviewRequest();
523        if (res != OK) {
524            ALOGE("%s: Camera %d: Unable to create preview request: %s (%d)",
525                    __FUNCTION__, mCameraId, strerror(-res), res);
526            return res;
527        }
528    }
529
530    res = updateEntry(mPreviewRequest,
531            ANDROID_REQUEST_OUTPUT_STREAMS,
532            &mPreviewStreamId, 1);
533    if (res != OK) {
534        ALOGE("%s: Camera %d: Unable to set up preview request: %s (%d)",
535                __FUNCTION__, mCameraId, strerror(-res), res);
536        return res;
537    }
538    res = sort_camera_metadata(mPreviewRequest);
539    if (res != OK) {
540        ALOGE("%s: Camera %d: Error sorting preview request: %s (%d)",
541                __FUNCTION__, mCameraId, strerror(-res), res);
542        return res;
543    }
544
545    res = mDevice->setStreamingRequest(mPreviewRequest);
546    if (res != OK) {
547        ALOGE("%s: Camera %d: Unable to set preview request to start preview: "
548                "%s (%d)",
549                __FUNCTION__, mCameraId, strerror(-res), res);
550        return res;
551    }
552    mState = PREVIEW;
553
554    return OK;
555}
556
557void Camera2Client::stopPreview() {
558    ATRACE_CALL();
559    Mutex::Autolock icl(mICameraLock);
560    stopPreviewLocked();
561}
562
563void Camera2Client::stopPreviewLocked() {
564    ATRACE_CALL();
565    switch (mState) {
566        case NOT_INITIALIZED:
567            ALOGE("%s: Camera %d: Call before initialized",
568                    __FUNCTION__, mCameraId);
569            break;
570        case STOPPED:
571            break;
572        case STILL_CAPTURE:
573            ALOGE("%s: Camera %d: Cannot stop preview during still capture.",
574                    __FUNCTION__, mCameraId);
575            break;
576        case RECORD:
577            // TODO: Handle record stop here
578        case PREVIEW:
579            mDevice->setStreamingRequest(NULL);
580        case WAITING_FOR_PREVIEW_WINDOW:
581            mState = STOPPED;
582            break;
583        default:
584            ALOGE("%s: Camera %d: Unknown state %d", __FUNCTION__, mCameraId,
585                    mState);
586    }
587}
588
589bool Camera2Client::previewEnabled() {
590    ATRACE_CALL();
591    Mutex::Autolock icl(mICameraLock);
592    return mState == PREVIEW;
593}
594
595status_t Camera2Client::storeMetaDataInBuffers(bool enabled) {
596    ATRACE_CALL();
597    Mutex::Autolock icl(mICameraLock);
598    return BAD_VALUE;
599}
600
601status_t Camera2Client::startRecording() {
602    ATRACE_CALL();
603    Mutex::Autolock icl(mICameraLock);
604    status_t res;
605    switch (mState) {
606        case STOPPED:
607            res = startPreviewLocked();
608            if (res != OK) return res;
609            break;
610        case PREVIEW:
611            // Ready to go
612            break;
613        case RECORD:
614        case VIDEO_SNAPSHOT:
615            // OK to call this when recording is already on
616            return OK;
617            break;
618        default:
619            ALOGE("%s: Camera %d: Can't start recording in state %s",
620                    __FUNCTION__, mCameraId, getStateName(mState));
621            return INVALID_OPERATION;
622    };
623
624    Mutex::Autolock pl(mParamsLock);
625
626    res = updateRecordingStream();
627    if (res != OK) {
628        ALOGE("%s: Camera %d: Unable to update recording stream: %s (%d)",
629                __FUNCTION__, mCameraId, strerror(-res), res);
630        return res;
631    }
632
633    if (mRecordingRequest == NULL) {
634        res = updateRecordingRequest();
635        if (res != OK) {
636            ALOGE("%s: Camera %d: Unable to create recording request: %s (%d)",
637                    __FUNCTION__, mCameraId, strerror(-res), res);
638            return res;
639        }
640    }
641
642    uint8_t outputStreams[2] = { mPreviewStreamId, mRecordingStreamId };
643    res = updateEntry(mRecordingRequest,
644            ANDROID_REQUEST_OUTPUT_STREAMS,
645            outputStreams, 2);
646    if (res != OK) {
647        ALOGE("%s: Camera %d: Unable to set up recording request: %s (%d)",
648                __FUNCTION__, mCameraId, strerror(-res), res);
649        return res;
650    }
651    res = sort_camera_metadata(mRecordingRequest);
652    if (res != OK) {
653        ALOGE("%s: Camera %d: Error sorting recording request: %s (%d)",
654                __FUNCTION__, mCameraId, strerror(-res), res);
655        return res;
656    }
657
658    res = mDevice->setStreamingRequest(mRecordingRequest);
659    if (res != OK) {
660        ALOGE("%s: Camera %d: Unable to set recording request to start "
661                "recording: %s (%d)", __FUNCTION__, mCameraId,
662                strerror(-res), res);
663        return res;
664    }
665    mState = RECORD;
666
667    return OK;
668}
669
670void Camera2Client::stopRecording() {
671    ATRACE_CALL();
672    Mutex::Autolock icl(mICameraLock);
673    status_t res;
674    switch (mState) {
675        case RECORD:
676            // OK to stop
677            break;
678        case STOPPED:
679        case PREVIEW:
680        case STILL_CAPTURE:
681        case VIDEO_SNAPSHOT:
682        default:
683            ALOGE("%s: Camera %d: Can't stop recording in state %s",
684                    __FUNCTION__, mCameraId, getStateName(mState));
685            return;
686    };
687
688    // Back to preview. Since record can only be reached through preview,
689    // all preview stream setup should be up to date.
690    res = mDevice->setStreamingRequest(mPreviewRequest);
691    if (res != OK) {
692        ALOGE("%s: Camera %d: Unable to switch back to preview request: "
693                "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
694        return;
695    }
696
697    // TODO: Should recording heap be freed? Can't do it yet since requests
698    // could still be in flight.
699
700    mState = PREVIEW;
701}
702
703bool Camera2Client::recordingEnabled() {
704    ATRACE_CALL();
705    Mutex::Autolock icl(mICameraLock);
706    return (mState == RECORD || mState == VIDEO_SNAPSHOT);
707}
708
709void Camera2Client::releaseRecordingFrame(const sp<IMemory>& mem) {
710    ATRACE_CALL();
711    Mutex::Autolock icl(mICameraLock);
712    // Make sure this is for the current heap
713    ssize_t offset;
714    size_t size;
715    sp<IMemoryHeap> heap = mem->getMemory(&offset, &size);
716    if (heap->getHeapID() != mRecordingHeap->mHeap->getHeapID()) {
717        ALOGW("%s: Camera %d: Mismatched heap ID, ignoring release "
718                "(got %x, expected %x)", __FUNCTION__, mCameraId,
719                heap->getHeapID(), mRecordingHeap->mHeap->getHeapID());
720        return;
721    }
722    mRecordingHeapFree++;
723}
724
725status_t Camera2Client::autoFocus() {
726    ATRACE_CALL();
727    Mutex::Autolock icl(mICameraLock);
728    return OK;
729}
730
731status_t Camera2Client::cancelAutoFocus() {
732    ATRACE_CALL();
733    Mutex::Autolock icl(mICameraLock);
734    return OK;
735}
736
737status_t Camera2Client::takePicture(int msgType) {
738    ATRACE_CALL();
739    Mutex::Autolock icl(mICameraLock);
740    status_t res;
741
742    switch (mState) {
743        case NOT_INITIALIZED:
744        case STOPPED:
745        case WAITING_FOR_PREVIEW_WINDOW:
746            ALOGE("%s: Camera %d: Cannot take picture without preview enabled",
747                    __FUNCTION__, mCameraId);
748            return INVALID_OPERATION;
749        case PREVIEW:
750        case RECORD:
751            // Good to go for takePicture
752            break;
753        case STILL_CAPTURE:
754        case VIDEO_SNAPSHOT:
755            ALOGE("%s: Camera %d: Already taking a picture",
756                    __FUNCTION__, mCameraId);
757            return INVALID_OPERATION;
758    }
759
760    Mutex::Autolock pl(mParamsLock);
761
762    res = updateCaptureStream();
763    if (res != OK) {
764        ALOGE("%s: Camera %d: Can't set up still image stream: %s (%d)",
765                __FUNCTION__, mCameraId, strerror(-res), res);
766        return res;
767    }
768
769    if (mCaptureRequest == NULL) {
770        res = updateCaptureRequest();
771        if (res != OK) {
772            ALOGE("%s: Camera %d: Can't create still image capture request: "
773                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
774            return res;
775        }
776    }
777
778    camera_metadata_entry_t outputStreams;
779    if (mState == PREVIEW) {
780        uint8_t streamIds[2] = { mPreviewStreamId, mCaptureStreamId };
781        res = updateEntry(mCaptureRequest, ANDROID_REQUEST_OUTPUT_STREAMS,
782                &streamIds, 2);
783    } else if (mState == RECORD) {
784        uint8_t streamIds[3] = { mPreviewStreamId, mRecordingStreamId,
785                                 mCaptureStreamId };
786        res = updateEntry(mCaptureRequest, ANDROID_REQUEST_OUTPUT_STREAMS,
787                &streamIds, 3);
788    }
789
790    if (res != OK) {
791        ALOGE("%s: Camera %d: Unable to set up still image capture request: "
792                "%s (%d)",
793                __FUNCTION__, mCameraId, strerror(-res), res);
794        return res;
795    }
796    res = sort_camera_metadata(mCaptureRequest);
797    if (res != OK) {
798        ALOGE("%s: Camera %d: Unable to sort capture request: %s (%d)",
799                __FUNCTION__, mCameraId, strerror(-res), res);
800        return res;
801    }
802
803    camera_metadata_t *captureCopy = clone_camera_metadata(mCaptureRequest);
804    if (captureCopy == NULL) {
805        ALOGE("%s: Camera %d: Unable to copy capture request for HAL device",
806                __FUNCTION__, mCameraId);
807        return NO_MEMORY;
808    }
809
810    if (mState == PREVIEW) {
811        res = mDevice->setStreamingRequest(NULL);
812        if (res != OK) {
813            ALOGE("%s: Camera %d: Unable to stop preview for still capture: "
814                    "%s (%d)",
815                    __FUNCTION__, mCameraId, strerror(-res), res);
816            return res;
817        }
818    }
819    // TODO: Capture should be atomic with setStreamingRequest here
820    res = mDevice->capture(captureCopy);
821    if (res != OK) {
822        ALOGE("%s: Camera %d: Unable to submit still image capture request: "
823                "%s (%d)",
824                __FUNCTION__, mCameraId, strerror(-res), res);
825        return res;
826    }
827
828    switch (mState) {
829        case PREVIEW:
830            mState = STILL_CAPTURE;
831            break;
832        case RECORD:
833            mState = VIDEO_SNAPSHOT;
834            break;
835        default:
836            ALOGE("%s: Camera %d: Unknown state for still capture!",
837                    __FUNCTION__, mCameraId);
838            return INVALID_OPERATION;
839    }
840
841    return OK;
842}
843
844status_t Camera2Client::setParameters(const String8& params) {
845    ATRACE_CALL();
846    Mutex::Autolock icl(mICameraLock);
847    Mutex::Autolock pl(mParamsLock);
848    status_t res;
849
850    CameraParameters newParams(params);
851
852    // TODO: Currently ignoring any changes to supposedly read-only
853    // parameters such as supported preview sizes, etc. Should probably
854    // produce an error if they're changed.
855
856    /** Extract and verify new parameters */
857
858    size_t i;
859
860    // PREVIEW_SIZE
861    int previewWidth, previewHeight;
862    newParams.getPreviewSize(&previewWidth, &previewHeight);
863
864    if (previewWidth != mParameters.previewWidth ||
865            previewHeight != mParameters.previewHeight) {
866        if (mState >= PREVIEW) {
867            ALOGE("%s: Preview size cannot be updated when preview "
868                    "is active! (Currently %d x %d, requested %d x %d",
869                    __FUNCTION__,
870                    mParameters.previewWidth, mParameters.previewHeight,
871                    previewWidth, previewHeight);
872            return BAD_VALUE;
873        }
874        camera_metadata_entry_t availablePreviewSizes =
875            staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
876        for (i = 0; i < availablePreviewSizes.count; i += 2 ) {
877            if (availablePreviewSizes.data.i32[i] == previewWidth &&
878                    availablePreviewSizes.data.i32[i+1] == previewHeight) break;
879        }
880        if (i == availablePreviewSizes.count) {
881            ALOGE("%s: Requested preview size %d x %d is not supported",
882                    __FUNCTION__, previewWidth, previewHeight);
883            return BAD_VALUE;
884        }
885    }
886
887    // PREVIEW_FPS_RANGE
888    int previewFpsRange[2];
889    int previewFps = 0;
890    bool fpsRangeChanged = false;
891    newParams.getPreviewFpsRange(&previewFpsRange[0], &previewFpsRange[1]);
892    if (previewFpsRange[0] != mParameters.previewFpsRange[0] ||
893            previewFpsRange[1] != mParameters.previewFpsRange[1]) {
894        fpsRangeChanged = true;
895        camera_metadata_entry_t availablePreviewFpsRanges =
896            staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
897        for (i = 0; i < availablePreviewFpsRanges.count; i += 2) {
898            if ((availablePreviewFpsRanges.data.i32[i] ==
899                    previewFpsRange[0]) &&
900                (availablePreviewFpsRanges.data.i32[i+1] ==
901                    previewFpsRange[1]) ) {
902                break;
903            }
904        }
905        if (i == availablePreviewFpsRanges.count) {
906            ALOGE("%s: Requested preview FPS range %d - %d is not supported",
907                __FUNCTION__, previewFpsRange[0], previewFpsRange[1]);
908            return BAD_VALUE;
909        }
910        previewFps = previewFpsRange[0];
911    }
912
913    // PREVIEW_FORMAT
914    int previewFormat = formatStringToEnum(newParams.getPreviewFormat());
915    if (previewFormat != mParameters.previewFormat) {
916        if (mState >= PREVIEW) {
917            ALOGE("%s: Preview format cannot be updated when preview "
918                    "is active!", __FUNCTION__);
919            return BAD_VALUE;
920        }
921        camera_metadata_entry_t availableFormats =
922            staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
923        for (i = 0; i < availableFormats.count; i++) {
924            if (availableFormats.data.i32[i] == previewFormat) break;
925        }
926        if (i == availableFormats.count) {
927            ALOGE("%s: Requested preview format %s (0x%x) is not supported",
928                    __FUNCTION__, newParams.getPreviewFormat(), previewFormat);
929            return BAD_VALUE;
930        }
931    }
932
933    // PREVIEW_FRAME_RATE
934    // Deprecated, only use if the preview fps range is unchanged this time.
935    // The single-value FPS is the same as the minimum of the range.
936    if (!fpsRangeChanged) {
937        previewFps = newParams.getPreviewFrameRate();
938        if (previewFps != mParameters.previewFps) {
939            camera_metadata_entry_t availableFrameRates =
940                staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES);
941            for (i = 0; i < availableFrameRates.count; i+=2) {
942                if (availableFrameRates.data.i32[i] == previewFps) break;
943            }
944            if (i == availableFrameRates.count) {
945                ALOGE("%s: Requested preview frame rate %d is not supported",
946                        __FUNCTION__, previewFps);
947                return BAD_VALUE;
948            }
949            previewFpsRange[0] = availableFrameRates.data.i32[i];
950            previewFpsRange[1] = availableFrameRates.data.i32[i+1];
951        }
952    }
953
954    // PICTURE_SIZE
955    int pictureWidth, pictureHeight;
956    newParams.getPictureSize(&pictureWidth, &pictureHeight);
957    if (pictureWidth == mParameters.pictureWidth ||
958            pictureHeight == mParameters.pictureHeight) {
959        camera_metadata_entry_t availablePictureSizes =
960            staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES);
961        for (i = 0; i < availablePictureSizes.count; i+=2) {
962            if (availablePictureSizes.data.i32[i] == pictureWidth &&
963                    availablePictureSizes.data.i32[i+1] == pictureHeight) break;
964        }
965        if (i == availablePictureSizes.count) {
966            ALOGE("%s: Requested picture size %d x %d is not supported",
967                    __FUNCTION__, pictureWidth, pictureHeight);
968            return BAD_VALUE;
969        }
970    }
971
972    // JPEG_THUMBNAIL_WIDTH/HEIGHT
973    int jpegThumbSize[2];
974    jpegThumbSize[0] =
975            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH);
976    jpegThumbSize[1] =
977            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT);
978    if (jpegThumbSize[0] != mParameters.jpegThumbSize[0] ||
979            jpegThumbSize[1] != mParameters.jpegThumbSize[1]) {
980        camera_metadata_entry_t availableJpegThumbSizes =
981            staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES);
982        for (i = 0; i < availableJpegThumbSizes.count; i+=2) {
983            if (availableJpegThumbSizes.data.i32[i] == jpegThumbSize[0] &&
984                    availableJpegThumbSizes.data.i32[i+1] == jpegThumbSize[1]) {
985                break;
986            }
987        }
988        if (i == availableJpegThumbSizes.count) {
989            ALOGE("%s: Requested JPEG thumbnail size %d x %d is not supported",
990                    __FUNCTION__, jpegThumbSize[0], jpegThumbSize[1]);
991            return BAD_VALUE;
992        }
993    }
994
995    // JPEG_THUMBNAIL_QUALITY
996    int jpegThumbQuality =
997            newParams.getInt(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY);
998    if (jpegThumbQuality < 0 || jpegThumbQuality > 100) {
999        ALOGE("%s: Requested JPEG thumbnail quality %d is not supported",
1000                __FUNCTION__, jpegThumbQuality);
1001        return BAD_VALUE;
1002    }
1003
1004    // JPEG_QUALITY
1005    int jpegQuality =
1006            newParams.getInt(CameraParameters::KEY_JPEG_QUALITY);
1007    if (jpegQuality < 0 || jpegQuality > 100) {
1008        ALOGE("%s: Requested JPEG quality %d is not supported",
1009                __FUNCTION__, jpegQuality);
1010        return BAD_VALUE;
1011    }
1012
1013    // ROTATION
1014    int jpegRotation =
1015            newParams.getInt(CameraParameters::KEY_ROTATION);
1016    if (jpegRotation != 0 &&
1017            jpegRotation != 90 &&
1018            jpegRotation != 180 &&
1019            jpegRotation != 270) {
1020        ALOGE("%s: Requested picture rotation angle %d is not supported",
1021                __FUNCTION__, jpegRotation);
1022        return BAD_VALUE;
1023    }
1024
1025    // GPS
1026    bool gpsEnabled = false;
1027    double gpsCoordinates[3] = {0,0,0};
1028    int64_t gpsTimestamp = 0;
1029    String8 gpsProcessingMethod;
1030    const char *gpsLatStr =
1031            newParams.get(CameraParameters::KEY_GPS_LATITUDE);
1032    if (gpsLatStr != NULL) {
1033        const char *gpsLongStr =
1034                newParams.get(CameraParameters::KEY_GPS_LONGITUDE);
1035        const char *gpsAltitudeStr =
1036                newParams.get(CameraParameters::KEY_GPS_ALTITUDE);
1037        const char *gpsTimeStr =
1038                newParams.get(CameraParameters::KEY_GPS_TIMESTAMP);
1039        const char *gpsProcMethodStr =
1040                newParams.get(CameraParameters::KEY_GPS_PROCESSING_METHOD);
1041        if (gpsLongStr == NULL ||
1042                gpsAltitudeStr == NULL ||
1043                gpsTimeStr == NULL ||
1044                gpsProcMethodStr == NULL) {
1045            ALOGE("%s: Incomplete set of GPS parameters provided",
1046                    __FUNCTION__);
1047            return BAD_VALUE;
1048        }
1049        char *endPtr;
1050        errno = 0;
1051        gpsCoordinates[0] = strtod(gpsLatStr, &endPtr);
1052        if (errno || endPtr == gpsLatStr) {
1053            ALOGE("%s: Malformed GPS latitude: %s", __FUNCTION__, gpsLatStr);
1054            return BAD_VALUE;
1055        }
1056        errno = 0;
1057        gpsCoordinates[1] = strtod(gpsLongStr, &endPtr);
1058        if (errno || endPtr == gpsLongStr) {
1059            ALOGE("%s: Malformed GPS longitude: %s", __FUNCTION__, gpsLongStr);
1060            return BAD_VALUE;
1061        }
1062        errno = 0;
1063        gpsCoordinates[2] = strtod(gpsAltitudeStr, &endPtr);
1064        if (errno || endPtr == gpsAltitudeStr) {
1065            ALOGE("%s: Malformed GPS altitude: %s", __FUNCTION__,
1066                    gpsAltitudeStr);
1067            return BAD_VALUE;
1068        }
1069        errno = 0;
1070        gpsTimestamp = strtoll(gpsTimeStr, &endPtr, 10);
1071        if (errno || endPtr == gpsTimeStr) {
1072            ALOGE("%s: Malformed GPS timestamp: %s", __FUNCTION__, gpsTimeStr);
1073            return BAD_VALUE;
1074        }
1075        gpsProcessingMethod = gpsProcMethodStr;
1076
1077        gpsEnabled = true;
1078    }
1079
1080    // WHITE_BALANCE
1081    int wbMode = wbModeStringToEnum(
1082        newParams.get(CameraParameters::KEY_WHITE_BALANCE) );
1083    if (wbMode != mParameters.wbMode) {
1084        camera_metadata_entry_t availableWbModes =
1085            staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
1086        for (i = 0; i < availableWbModes.count; i++) {
1087            if (wbMode == availableWbModes.data.u8[i]) break;
1088        }
1089        if (i == availableWbModes.count) {
1090            ALOGE("%s: Requested white balance mode %s is not supported",
1091                    __FUNCTION__,
1092                    newParams.get(CameraParameters::KEY_WHITE_BALANCE));
1093            return BAD_VALUE;
1094        }
1095    }
1096
1097    // EFFECT
1098    int effectMode = effectModeStringToEnum(
1099        newParams.get(CameraParameters::KEY_EFFECT) );
1100    if (effectMode != mParameters.effectMode) {
1101        camera_metadata_entry_t availableEffectModes =
1102            staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
1103        for (i = 0; i < availableEffectModes.count; i++) {
1104            if (effectMode == availableEffectModes.data.u8[i]) break;
1105        }
1106        if (i == availableEffectModes.count) {
1107            ALOGE("%s: Requested effect mode \"%s\" is not supported",
1108                    __FUNCTION__,
1109                    newParams.get(CameraParameters::KEY_EFFECT) );
1110            return BAD_VALUE;
1111        }
1112    }
1113
1114    // ANTIBANDING
1115    int antibandingMode = abModeStringToEnum(
1116        newParams.get(CameraParameters::KEY_ANTIBANDING) );
1117    if (antibandingMode != mParameters.antibandingMode) {
1118        camera_metadata_entry_t availableAbModes =
1119            staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
1120        for (i = 0; i < availableAbModes.count; i++) {
1121            if (antibandingMode == availableAbModes.data.u8[i]) break;
1122        }
1123        if (i == availableAbModes.count) {
1124            ALOGE("%s: Requested antibanding mode \"%s\" is not supported",
1125                    __FUNCTION__,
1126                    newParams.get(CameraParameters::KEY_ANTIBANDING));
1127            return BAD_VALUE;
1128        }
1129    }
1130
1131    // SCENE_MODE
1132    int sceneMode = sceneModeStringToEnum(
1133        newParams.get(CameraParameters::KEY_SCENE_MODE) );
1134    if (sceneMode != mParameters.sceneMode) {
1135        camera_metadata_entry_t availableSceneModes =
1136            staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
1137        for (i = 0; i < availableSceneModes.count; i++) {
1138            if (sceneMode == availableSceneModes.data.u8[i]) break;
1139        }
1140        if (i == availableSceneModes.count) {
1141            ALOGE("%s: Requested scene mode \"%s\" is not supported",
1142                    __FUNCTION__,
1143                    newParams.get(CameraParameters::KEY_SCENE_MODE));
1144            return BAD_VALUE;
1145        }
1146    }
1147
1148    // FLASH_MODE
1149    Parameters::flashMode_t flashMode = flashModeStringToEnum(
1150        newParams.get(CameraParameters::KEY_FLASH_MODE) );
1151    if (flashMode != mParameters.flashMode) {
1152        camera_metadata_entry_t flashAvailable =
1153            staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
1154        if (!flashAvailable.data.u8[0] &&
1155                flashMode != Parameters::FLASH_MODE_OFF) {
1156            ALOGE("%s: Requested flash mode \"%s\" is not supported: "
1157                    "No flash on device", __FUNCTION__,
1158                    newParams.get(CameraParameters::KEY_FLASH_MODE));
1159            return BAD_VALUE;
1160        } else if (flashMode == Parameters::FLASH_MODE_RED_EYE) {
1161            camera_metadata_entry_t availableAeModes =
1162                staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
1163            for (i = 0; i < availableAeModes.count; i++) {
1164                if (flashMode == availableAeModes.data.u8[i]) break;
1165            }
1166            if (i == availableAeModes.count) {
1167                ALOGE("%s: Requested flash mode \"%s\" is not supported",
1168                        __FUNCTION__,
1169                        newParams.get(CameraParameters::KEY_FLASH_MODE));
1170                return BAD_VALUE;
1171            }
1172        } else if (flashMode == -1) {
1173            ALOGE("%s: Requested flash mode \"%s\" is unknown",
1174                    __FUNCTION__,
1175                    newParams.get(CameraParameters::KEY_FLASH_MODE));
1176            return BAD_VALUE;
1177        }
1178    }
1179
1180    // FOCUS_MODE
1181    Parameters::focusMode_t focusMode = focusModeStringToEnum(
1182        newParams.get(CameraParameters::KEY_FOCUS_MODE));
1183    if (focusMode != mParameters.focusMode) {
1184        if (focusMode != Parameters::FOCUS_MODE_FIXED) {
1185            camera_metadata_entry_t minFocusDistance =
1186                staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE);
1187            if (minFocusDistance.data.f[0] == 0) {
1188                ALOGE("%s: Requested focus mode \"%s\" is not available: "
1189                        "fixed focus lens",
1190                        __FUNCTION__,
1191                        newParams.get(CameraParameters::KEY_FOCUS_MODE));
1192                return BAD_VALUE;
1193            } else if (focusMode != Parameters::FOCUS_MODE_INFINITY) {
1194                camera_metadata_entry_t availableFocusModes =
1195                    staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
1196                for (i = 0; i < availableFocusModes.count; i++) {
1197                    if (focusMode == availableFocusModes.data.u8[i]) break;
1198                }
1199                if (i == availableFocusModes.count) {
1200                    ALOGE("%s: Requested focus mode \"%s\" is not supported",
1201                            __FUNCTION__,
1202                            newParams.get(CameraParameters::KEY_FOCUS_MODE));
1203                    return BAD_VALUE;
1204                }
1205            }
1206        }
1207    }
1208
1209    // FOCUS_AREAS
1210    Vector<Parameters::Area> focusingAreas;
1211    res = parseAreas(newParams.get(CameraParameters::KEY_FOCUS_AREAS),
1212            &focusingAreas);
1213    size_t max3aRegions =
1214        (size_t)staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1).data.i32[0];
1215    if (res == OK) res = validateAreas(focusingAreas, max3aRegions);
1216    if (res != OK) {
1217        ALOGE("%s: Requested focus areas are malformed: %s",
1218                __FUNCTION__, newParams.get(CameraParameters::KEY_FOCUS_AREAS));
1219        return BAD_VALUE;
1220    }
1221
1222    // EXPOSURE_COMPENSATION
1223    int exposureCompensation =
1224        newParams.getInt(CameraParameters::KEY_EXPOSURE_COMPENSATION);
1225    camera_metadata_entry_t exposureCompensationRange =
1226        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE);
1227    if (exposureCompensation < exposureCompensationRange.data.i32[0] ||
1228            exposureCompensation > exposureCompensationRange.data.i32[1]) {
1229        ALOGE("%s: Requested exposure compensation index is out of bounds: %d",
1230                __FUNCTION__, exposureCompensation);
1231        return BAD_VALUE;
1232    }
1233
1234    // AUTO_EXPOSURE_LOCK (always supported)
1235    bool autoExposureLock = boolFromString(
1236        newParams.get(CameraParameters::KEY_AUTO_EXPOSURE_LOCK));
1237
1238    // AUTO_WHITEBALANCE_LOCK (always supported)
1239    bool autoWhiteBalanceLock = boolFromString(
1240        newParams.get(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK));
1241
1242    // METERING_AREAS
1243    Vector<Parameters::Area> meteringAreas;
1244    res = parseAreas(newParams.get(CameraParameters::KEY_METERING_AREAS),
1245            &meteringAreas);
1246    if (res == OK) res = validateAreas(focusingAreas, max3aRegions);
1247    if (res != OK) {
1248        ALOGE("%s: Requested metering areas are malformed: %s",
1249                __FUNCTION__,
1250                newParams.get(CameraParameters::KEY_METERING_AREAS));
1251        return BAD_VALUE;
1252    }
1253
1254    // ZOOM
1255    int zoom = newParams.getInt(CameraParameters::KEY_ZOOM);
1256    if (zoom < 0 || zoom > (int)NUM_ZOOM_STEPS) {
1257        ALOGE("%s: Requested zoom level %d is not supported",
1258                __FUNCTION__, zoom);
1259        return BAD_VALUE;
1260    }
1261
1262    // VIDEO_SIZE
1263    int videoWidth, videoHeight;
1264    newParams.getVideoSize(&videoWidth, &videoHeight);
1265    if (videoWidth != mParameters.videoWidth ||
1266            videoHeight != mParameters.videoHeight) {
1267        if (mState == RECORD) {
1268            ALOGE("%s: Video size cannot be updated when recording is active!",
1269                    __FUNCTION__);
1270            return BAD_VALUE;
1271        }
1272        camera_metadata_entry_t availableVideoSizes =
1273            staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES);
1274        for (i = 0; i < availableVideoSizes.count; i += 2 ) {
1275            if (availableVideoSizes.data.i32[i] == videoWidth &&
1276                    availableVideoSizes.data.i32[i+1] == videoHeight)  break;
1277        }
1278        if (i == availableVideoSizes.count) {
1279            ALOGE("%s: Requested video size %d x %d is not supported",
1280                    __FUNCTION__, videoWidth, videoHeight);
1281            return BAD_VALUE;
1282        }
1283    }
1284
1285    // RECORDING_HINT (always supported)
1286    bool recordingHint = boolFromString(
1287        newParams.get(CameraParameters::KEY_RECORDING_HINT) );
1288
1289    // VIDEO_STABILIZATION
1290    bool videoStabilization = boolFromString(
1291        newParams.get(CameraParameters::KEY_VIDEO_STABILIZATION) );
1292    camera_metadata_entry_t availableVideoStabilizationModes =
1293        staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
1294    if (videoStabilization && availableVideoStabilizationModes.count == 1) {
1295        ALOGE("%s: Video stabilization not supported", __FUNCTION__);
1296    }
1297
1298    /** Update internal parameters */
1299
1300    mParameters.previewWidth = previewWidth;
1301    mParameters.previewHeight = previewHeight;
1302    mParameters.previewFpsRange[0] = previewFpsRange[0];
1303    mParameters.previewFpsRange[1] = previewFpsRange[1];
1304    mParameters.previewFps = previewFps;
1305    mParameters.previewFormat = previewFormat;
1306
1307    mParameters.pictureWidth = pictureWidth;
1308    mParameters.pictureHeight = pictureHeight;
1309
1310    mParameters.jpegThumbSize[0] = jpegThumbSize[0];
1311    mParameters.jpegThumbSize[1] = jpegThumbSize[1];
1312    mParameters.jpegQuality = jpegQuality;
1313    mParameters.jpegThumbQuality = jpegThumbQuality;
1314
1315    mParameters.gpsEnabled = gpsEnabled;
1316    mParameters.gpsCoordinates[0] = gpsCoordinates[0];
1317    mParameters.gpsCoordinates[1] = gpsCoordinates[1];
1318    mParameters.gpsCoordinates[2] = gpsCoordinates[2];
1319    mParameters.gpsTimestamp = gpsTimestamp;
1320    mParameters.gpsProcessingMethod = gpsProcessingMethod;
1321
1322    mParameters.wbMode = wbMode;
1323    mParameters.effectMode = effectMode;
1324    mParameters.antibandingMode = antibandingMode;
1325    mParameters.sceneMode = sceneMode;
1326
1327    mParameters.flashMode = flashMode;
1328    mParameters.focusMode = focusMode;
1329
1330    mParameters.focusingAreas = focusingAreas;
1331    mParameters.exposureCompensation = exposureCompensation;
1332    mParameters.autoExposureLock = autoExposureLock;
1333    mParameters.autoWhiteBalanceLock = autoWhiteBalanceLock;
1334    mParameters.meteringAreas = meteringAreas;
1335    mParameters.zoom = zoom;
1336
1337    mParameters.videoWidth = videoWidth;
1338    mParameters.videoHeight = videoHeight;
1339
1340    mParameters.recordingHint = recordingHint;
1341    mParameters.videoStabilization = videoStabilization;
1342
1343    res = updatePreviewRequest();
1344    if (res != OK) {
1345        ALOGE("%s: Camera %d: Unable to update preview request: %s (%d)",
1346                __FUNCTION__, mCameraId, strerror(-res), res);
1347        return res;
1348    }
1349    res = updateCaptureRequest();
1350    if (res != OK) {
1351        ALOGE("%s: Camera %d: Unable to update capture request: %s (%d)",
1352                __FUNCTION__, mCameraId, strerror(-res), res);
1353        return res;
1354    }
1355
1356    res = updateRecordingRequest();
1357    if (res != OK) {
1358        ALOGE("%s: Camera %d: Unable to update recording request: %s (%d)",
1359                __FUNCTION__, mCameraId, strerror(-res), res);
1360        return res;
1361    }
1362
1363    if (mState == PREVIEW) {
1364        res = mDevice->setStreamingRequest(mPreviewRequest);
1365        if (res != OK) {
1366            ALOGE("%s: Camera %d: Error streaming new preview request: %s (%d)",
1367                    __FUNCTION__, mCameraId, strerror(-res), res);
1368            return res;
1369        }
1370    } else if (mState == RECORD || mState == VIDEO_SNAPSHOT) {
1371        res = mDevice->setStreamingRequest(mRecordingRequest);
1372        if (res != OK) {
1373            ALOGE("%s: Camera %d: Error streaming new record request: %s (%d)",
1374                    __FUNCTION__, mCameraId, strerror(-res), res);
1375            return res;
1376        }
1377    }
1378
1379    mParamsFlattened = params;
1380
1381    return OK;
1382}
1383
1384String8 Camera2Client::getParameters() const {
1385    ATRACE_CALL();
1386    Mutex::Autolock icl(mICameraLock);
1387
1388    Mutex::Autolock pl(mParamsLock);
1389
1390    // TODO: Deal with focus distances
1391    return mParamsFlattened;
1392}
1393
1394status_t Camera2Client::sendCommand(int32_t cmd, int32_t arg1, int32_t arg2) {
1395    ATRACE_CALL();
1396    Mutex::Autolock icl(mICameraLock);
1397
1398    ALOGV("%s: Camera %d: Command %d (%d, %d)", __FUNCTION__, mCameraId,
1399            cmd, arg1, arg2);
1400
1401    if (cmd == CAMERA_CMD_SET_DISPLAY_ORIENTATION) {
1402        int transform = degToTransform(arg1,
1403                mCameraFacing == CAMERA_FACING_FRONT);
1404        if (transform == -1) {
1405            ALOGE("%s: Camera %d: Error setting %d as display orientation value",
1406                    __FUNCTION__, mCameraId, arg1);
1407            return BAD_VALUE;
1408        }
1409        if (transform != mParameters.previewTransform &&
1410                mPreviewStreamId != NO_STREAM) {
1411            mDevice->setStreamTransform(mPreviewStreamId, transform);
1412        }
1413        mParameters.previewTransform = transform;
1414        return OK;
1415    }
1416
1417    ALOGE("%s: Camera %d: Unimplemented command %d (%d, %d)", __FUNCTION__,
1418            mCameraId, cmd, arg1, arg2);
1419
1420    return OK;
1421}
1422
1423/** Device-related methods */
1424
1425void Camera2Client::onCaptureAvailable() {
1426    ATRACE_CALL();
1427    status_t res;
1428    sp<ICameraClient> currentClient;
1429    ALOGV("%s: Camera %d: Still capture available", __FUNCTION__, mCameraId);
1430
1431    CpuConsumer::LockedBuffer imgBuffer;
1432    {
1433        Mutex::Autolock icl(mICameraLock);
1434
1435        // TODO: Signal errors here upstream
1436        if (mState != STILL_CAPTURE && mState != VIDEO_SNAPSHOT) {
1437            ALOGE("%s: Camera %d: Still image produced unexpectedly!",
1438                    __FUNCTION__, mCameraId);
1439            return;
1440        }
1441
1442        res = mCaptureConsumer->lockNextBuffer(&imgBuffer);
1443        if (res != OK) {
1444            ALOGE("%s: Camera %d: Error receiving still image buffer: %s (%d)",
1445                    __FUNCTION__, mCameraId, strerror(-res), res);
1446            return;
1447        }
1448
1449        if (imgBuffer.format != HAL_PIXEL_FORMAT_BLOB) {
1450            ALOGE("%s: Camera %d: Unexpected format for still image: "
1451                    "%x, expected %x", __FUNCTION__, mCameraId,
1452                    imgBuffer.format,
1453                    HAL_PIXEL_FORMAT_BLOB);
1454            mCaptureConsumer->unlockBuffer(imgBuffer);
1455            return;
1456        }
1457
1458        // TODO: Optimize this to avoid memcopy
1459        void* captureMemory = mCaptureHeap->mHeap->getBase();
1460        size_t size = mCaptureHeap->mHeap->getSize();
1461        memcpy(captureMemory, imgBuffer.data, size);
1462
1463        mCaptureConsumer->unlockBuffer(imgBuffer);
1464
1465        currentClient = mCameraClient;
1466        switch (mState) {
1467            case STILL_CAPTURE:
1468                mState = STOPPED;
1469                break;
1470            case VIDEO_SNAPSHOT:
1471                mState = RECORD;
1472                break;
1473            default:
1474                ALOGE("%s: Camera %d: Unexpected state %d", __FUNCTION__,
1475                        mCameraId, mState);
1476                break;
1477        }
1478    }
1479    // Call outside mICameraLock to allow re-entrancy from notification
1480    if (currentClient != 0) {
1481        currentClient->dataCallback(CAMERA_MSG_COMPRESSED_IMAGE,
1482                mCaptureHeap->mBuffers[0], NULL);
1483    }
1484}
1485
1486void Camera2Client::onRecordingFrameAvailable() {
1487    ATRACE_CALL();
1488    status_t res;
1489    sp<ICameraClient> currentClient;
1490    size_t heapIdx = 0;
1491    nsecs_t timestamp;
1492    {
1493        Mutex::Autolock icl(mICameraLock);
1494        // TODO: Signal errors here upstream
1495        if (mState != RECORD && mState != VIDEO_SNAPSHOT) {
1496            ALOGE("%s: Camera %d: Recording image buffer produced unexpectedly!",
1497                    __FUNCTION__, mCameraId);
1498            return;
1499        }
1500
1501        CpuConsumer::LockedBuffer imgBuffer;
1502        res = mRecordingConsumer->lockNextBuffer(&imgBuffer);
1503        if (res != OK) {
1504            ALOGE("%s: Camera %d: Error receiving recording buffer: %s (%d)",
1505                    __FUNCTION__, mCameraId, strerror(-res), res);
1506            return;
1507        }
1508
1509        if (imgBuffer.format != (int)kRecordingFormat) {
1510            ALOGE("%s: Camera %d: Unexpected recording format: %x",
1511                    __FUNCTION__, mCameraId, imgBuffer.format);
1512            mRecordingConsumer->unlockBuffer(imgBuffer);
1513            return;
1514        }
1515        size_t bufferSize = imgBuffer.width * imgBuffer.height * 3 / 2;
1516
1517        if (mRecordingHeap == 0 ||
1518                bufferSize >
1519                mRecordingHeap->mHeap->getSize() / kRecordingHeapCount) {
1520            ALOGV("%s: Camera %d: Creating recording heap with %d buffers of "
1521                    "size %d bytes", __FUNCTION__, mCameraId,
1522                    kRecordingHeapCount, bufferSize);
1523            if (mRecordingHeap != 0) {
1524                ALOGV("%s: Camera %d: Previous heap has size %d "
1525                        "(new will be %d) bytes", __FUNCTION__, mCameraId,
1526                        mRecordingHeap->mHeap->getSize(),
1527                        bufferSize * kRecordingHeapCount);
1528            }
1529            // Need to allocate memory for heap
1530            mRecordingHeap.clear();
1531
1532            mRecordingHeap = new Camera2Heap(bufferSize, kRecordingHeapCount,
1533                    "Camera2Client::RecordingHeap");
1534            if (mRecordingHeap->mHeap->getSize() == 0) {
1535                ALOGE("%s: Camera %d: Unable to allocate memory for recording",
1536                        __FUNCTION__, mCameraId);
1537                mRecordingConsumer->unlockBuffer(imgBuffer);
1538                return;
1539            }
1540            mRecordingHeapHead = 0;
1541            mRecordingHeapFree = kRecordingHeapCount;
1542        }
1543
1544        // TODO: Optimize this to avoid memcopy
1545        if ( mRecordingHeapFree == 0) {
1546            ALOGE("%s: Camera %d: No free recording buffers, dropping frame",
1547                    __FUNCTION__, mCameraId);
1548            mRecordingConsumer->unlockBuffer(imgBuffer);
1549            return;
1550        }
1551        heapIdx = mRecordingHeapHead;
1552        timestamp = imgBuffer.timestamp;
1553        mRecordingHeapHead = (mRecordingHeapHead + 1) % kRecordingHeapCount;
1554        mRecordingHeapFree--;
1555
1556        ALOGV("%s: Camera %d: Timestamp %lld",
1557                __FUNCTION__, mCameraId, timestamp);
1558
1559        ssize_t offset;
1560        size_t size;
1561        sp<IMemoryHeap> heap =
1562                mRecordingHeap->mBuffers[heapIdx]->getMemory(&offset,
1563                        &size);
1564
1565        memcpy((uint8_t*)heap->getBase() + offset, imgBuffer.data, size);
1566
1567        mRecordingConsumer->unlockBuffer(imgBuffer);
1568
1569        currentClient = mCameraClient;
1570    }
1571    // Call outside mICameraLock to allow re-entrancy from notification
1572    if (currentClient != 0) {
1573        currentClient->dataCallbackTimestamp(timestamp,
1574                CAMERA_MSG_VIDEO_FRAME,
1575                mRecordingHeap->mBuffers[heapIdx]);
1576    }
1577}
1578
1579camera_metadata_entry_t Camera2Client::staticInfo(uint32_t tag,
1580        size_t minCount, size_t maxCount) {
1581    status_t res;
1582    camera_metadata_entry_t entry;
1583    res = find_camera_metadata_entry(mDevice->info(),
1584            tag,
1585            &entry);
1586    if (CC_UNLIKELY( res != OK )) {
1587        const char* tagSection = get_camera_metadata_section_name(tag);
1588        if (tagSection == NULL) tagSection = "<unknown>";
1589        const char* tagName = get_camera_metadata_tag_name(tag);
1590        if (tagName == NULL) tagName = "<unknown>";
1591
1592        ALOGE("Error finding static metadata entry '%s.%s' (%x): %s (%d)",
1593                tagSection, tagName, tag, strerror(-res), res);
1594        entry.count = 0;
1595        entry.data.u8 = NULL;
1596    } else if (CC_UNLIKELY(
1597            (minCount != 0 && entry.count < minCount) ||
1598            (maxCount != 0 && entry.count > maxCount) ) ) {
1599        const char* tagSection = get_camera_metadata_section_name(tag);
1600        if (tagSection == NULL) tagSection = "<unknown>";
1601        const char* tagName = get_camera_metadata_tag_name(tag);
1602        if (tagName == NULL) tagName = "<unknown>";
1603        ALOGE("Malformed static metadata entry '%s.%s' (%x):"
1604                "Expected between %d and %d values, but got %d values",
1605                tagSection, tagName, tag, minCount, maxCount, entry.count);
1606        entry.count = 0;
1607        entry.data.u8 = NULL;
1608    }
1609
1610    return entry;
1611}
1612
1613/** Utility methods */
1614
1615
1616status_t Camera2Client::buildDefaultParameters() {
1617    ATRACE_CALL();
1618    Mutex::Autolock pl(mParamsLock);
1619
1620    status_t res;
1621    CameraParameters params;
1622
1623    camera_metadata_entry_t availableProcessedSizes =
1624        staticInfo(ANDROID_SCALER_AVAILABLE_PROCESSED_SIZES, 2);
1625    if (!availableProcessedSizes.count) return NO_INIT;
1626
1627    // TODO: Pick more intelligently
1628    mParameters.previewWidth = availableProcessedSizes.data.i32[0];
1629    mParameters.previewHeight = availableProcessedSizes.data.i32[1];
1630    mParameters.videoWidth = mParameters.previewWidth;
1631    mParameters.videoHeight = mParameters.previewHeight;
1632
1633    params.setPreviewSize(mParameters.previewWidth, mParameters.previewHeight);
1634    params.setVideoSize(mParameters.videoWidth, mParameters.videoHeight);
1635    params.set(CameraParameters::KEY_PREFERRED_PREVIEW_SIZE_FOR_VIDEO,
1636            String8::format("%dx%d",
1637                    mParameters.previewWidth, mParameters.previewHeight));
1638    {
1639        String8 supportedPreviewSizes;
1640        for (size_t i=0; i < availableProcessedSizes.count; i += 2) {
1641            if (i != 0) supportedPreviewSizes += ",";
1642            supportedPreviewSizes += String8::format("%dx%d",
1643                    availableProcessedSizes.data.i32[i],
1644                    availableProcessedSizes.data.i32[i+1]);
1645        }
1646        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_SIZES,
1647                supportedPreviewSizes);
1648        params.set(CameraParameters::KEY_SUPPORTED_VIDEO_SIZES,
1649                supportedPreviewSizes);
1650    }
1651
1652    camera_metadata_entry_t availableFpsRanges =
1653        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_TARGET_FPS_RANGES, 2);
1654    if (!availableFpsRanges.count) return NO_INIT;
1655
1656    mParameters.previewFpsRange[0] = availableFpsRanges.data.i32[0];
1657    mParameters.previewFpsRange[1] = availableFpsRanges.data.i32[1];
1658
1659    params.set(CameraParameters::KEY_PREVIEW_FPS_RANGE,
1660            String8::format("%d,%d",
1661                    mParameters.previewFpsRange[0],
1662                    mParameters.previewFpsRange[1]));
1663
1664    {
1665        String8 supportedPreviewFpsRange;
1666        for (size_t i=0; i < availableFpsRanges.count; i += 2) {
1667            if (i != 0) supportedPreviewFpsRange += ",";
1668            supportedPreviewFpsRange += String8::format("(%d,%d)",
1669                    availableFpsRanges.data.i32[i],
1670                    availableFpsRanges.data.i32[i+1]);
1671        }
1672        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FPS_RANGE,
1673                supportedPreviewFpsRange);
1674    }
1675
1676    mParameters.previewFormat = HAL_PIXEL_FORMAT_YCrCb_420_SP;
1677    params.set(CameraParameters::KEY_PREVIEW_FORMAT,
1678            formatEnumToString(mParameters.previewFormat)); // NV21
1679
1680    mParameters.previewTransform = degToTransform(0,
1681            mCameraFacing == CAMERA_FACING_FRONT);
1682
1683    camera_metadata_entry_t availableFormats =
1684        staticInfo(ANDROID_SCALER_AVAILABLE_FORMATS);
1685
1686    {
1687        String8 supportedPreviewFormats;
1688        bool addComma = false;
1689        for (size_t i=0; i < availableFormats.count; i++) {
1690            if (addComma) supportedPreviewFormats += ",";
1691            addComma = true;
1692            switch (availableFormats.data.i32[i]) {
1693            case HAL_PIXEL_FORMAT_YCbCr_422_SP:
1694                supportedPreviewFormats +=
1695                    CameraParameters::PIXEL_FORMAT_YUV422SP;
1696                break;
1697            case HAL_PIXEL_FORMAT_YCrCb_420_SP:
1698                supportedPreviewFormats +=
1699                    CameraParameters::PIXEL_FORMAT_YUV420SP;
1700                break;
1701            case HAL_PIXEL_FORMAT_YCbCr_422_I:
1702                supportedPreviewFormats +=
1703                    CameraParameters::PIXEL_FORMAT_YUV422I;
1704                break;
1705            case HAL_PIXEL_FORMAT_YV12:
1706                supportedPreviewFormats +=
1707                    CameraParameters::PIXEL_FORMAT_YUV420P;
1708                break;
1709            case HAL_PIXEL_FORMAT_RGB_565:
1710                supportedPreviewFormats +=
1711                    CameraParameters::PIXEL_FORMAT_RGB565;
1712                break;
1713            case HAL_PIXEL_FORMAT_RGBA_8888:
1714                supportedPreviewFormats +=
1715                    CameraParameters::PIXEL_FORMAT_RGBA8888;
1716                break;
1717            // Not advertizing JPEG, RAW_SENSOR, etc, for preview formats
1718            case HAL_PIXEL_FORMAT_RAW_SENSOR:
1719            case HAL_PIXEL_FORMAT_BLOB:
1720                addComma = false;
1721                break;
1722
1723            default:
1724                ALOGW("%s: Camera %d: Unknown preview format: %x",
1725                        __FUNCTION__, mCameraId, availableFormats.data.i32[i]);
1726                addComma = false;
1727                break;
1728            }
1729        }
1730        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FORMATS,
1731                supportedPreviewFormats);
1732    }
1733
1734    // PREVIEW_FRAME_RATE / SUPPORTED_PREVIEW_FRAME_RATES are deprecated, but
1735    // still have to do something sane for them
1736
1737    params.set(CameraParameters::KEY_PREVIEW_FRAME_RATE,
1738            mParameters.previewFpsRange[0]);
1739
1740    {
1741        String8 supportedPreviewFrameRates;
1742        for (size_t i=0; i < availableFpsRanges.count; i += 2) {
1743            if (i != 0) supportedPreviewFrameRates += ",";
1744            supportedPreviewFrameRates += String8::format("%d",
1745                    availableFpsRanges.data.i32[i]);
1746        }
1747        params.set(CameraParameters::KEY_SUPPORTED_PREVIEW_FRAME_RATES,
1748                supportedPreviewFrameRates);
1749    }
1750
1751    camera_metadata_entry_t availableJpegSizes =
1752        staticInfo(ANDROID_SCALER_AVAILABLE_JPEG_SIZES, 2);
1753    if (!availableJpegSizes.count) return NO_INIT;
1754
1755    // TODO: Pick maximum
1756    mParameters.pictureWidth = availableJpegSizes.data.i32[0];
1757    mParameters.pictureHeight = availableJpegSizes.data.i32[1];
1758
1759    params.setPictureSize(mParameters.pictureWidth,
1760            mParameters.pictureHeight);
1761
1762    {
1763        String8 supportedPictureSizes;
1764        for (size_t i=0; i < availableJpegSizes.count; i += 2) {
1765            if (i != 0) supportedPictureSizes += ",";
1766            supportedPictureSizes += String8::format("%dx%d",
1767                    availableJpegSizes.data.i32[i],
1768                    availableJpegSizes.data.i32[i+1]);
1769        }
1770        params.set(CameraParameters::KEY_SUPPORTED_PICTURE_SIZES,
1771                supportedPictureSizes);
1772    }
1773
1774    params.setPictureFormat(CameraParameters::PIXEL_FORMAT_JPEG);
1775    params.set(CameraParameters::KEY_SUPPORTED_PICTURE_FORMATS,
1776            CameraParameters::PIXEL_FORMAT_JPEG);
1777
1778    camera_metadata_entry_t availableJpegThumbnailSizes =
1779        staticInfo(ANDROID_JPEG_AVAILABLE_THUMBNAIL_SIZES, 2);
1780    if (!availableJpegThumbnailSizes.count) return NO_INIT;
1781
1782    // TODO: Pick default thumbnail size sensibly
1783    mParameters.jpegThumbSize[0] = availableJpegThumbnailSizes.data.i32[0];
1784    mParameters.jpegThumbSize[1] = availableJpegThumbnailSizes.data.i32[1];
1785
1786    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_WIDTH,
1787            mParameters.jpegThumbSize[0]);
1788    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_HEIGHT,
1789            mParameters.jpegThumbSize[1]);
1790
1791    {
1792        String8 supportedJpegThumbSizes;
1793        for (size_t i=0; i < availableJpegThumbnailSizes.count; i += 2) {
1794            if (i != 0) supportedJpegThumbSizes += ",";
1795            supportedJpegThumbSizes += String8::format("%dx%d",
1796                    availableJpegThumbnailSizes.data.i32[i],
1797                    availableJpegThumbnailSizes.data.i32[i+1]);
1798        }
1799        params.set(CameraParameters::KEY_SUPPORTED_JPEG_THUMBNAIL_SIZES,
1800                supportedJpegThumbSizes);
1801    }
1802
1803    mParameters.jpegThumbQuality = 90;
1804    params.set(CameraParameters::KEY_JPEG_THUMBNAIL_QUALITY,
1805            mParameters.jpegThumbQuality);
1806    mParameters.jpegQuality = 90;
1807    params.set(CameraParameters::KEY_JPEG_QUALITY,
1808            mParameters.jpegQuality);
1809    mParameters.jpegRotation = 0;
1810    params.set(CameraParameters::KEY_ROTATION,
1811            mParameters.jpegRotation);
1812
1813    mParameters.gpsEnabled = false;
1814    mParameters.gpsProcessingMethod = "unknown";
1815    // GPS fields in CameraParameters are not set by implementation
1816
1817    mParameters.wbMode = ANDROID_CONTROL_AWB_AUTO;
1818    params.set(CameraParameters::KEY_WHITE_BALANCE,
1819            CameraParameters::WHITE_BALANCE_AUTO);
1820
1821    camera_metadata_entry_t availableWhiteBalanceModes =
1822        staticInfo(ANDROID_CONTROL_AWB_AVAILABLE_MODES);
1823    {
1824        String8 supportedWhiteBalance;
1825        bool addComma = false;
1826        for (size_t i=0; i < availableWhiteBalanceModes.count; i++) {
1827            if (addComma) supportedWhiteBalance += ",";
1828            addComma = true;
1829            switch (availableWhiteBalanceModes.data.u8[i]) {
1830            case ANDROID_CONTROL_AWB_AUTO:
1831                supportedWhiteBalance +=
1832                    CameraParameters::WHITE_BALANCE_AUTO;
1833                break;
1834            case ANDROID_CONTROL_AWB_INCANDESCENT:
1835                supportedWhiteBalance +=
1836                    CameraParameters::WHITE_BALANCE_INCANDESCENT;
1837                break;
1838            case ANDROID_CONTROL_AWB_FLUORESCENT:
1839                supportedWhiteBalance +=
1840                    CameraParameters::WHITE_BALANCE_FLUORESCENT;
1841                break;
1842            case ANDROID_CONTROL_AWB_WARM_FLUORESCENT:
1843                supportedWhiteBalance +=
1844                    CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT;
1845                break;
1846            case ANDROID_CONTROL_AWB_DAYLIGHT:
1847                supportedWhiteBalance +=
1848                    CameraParameters::WHITE_BALANCE_DAYLIGHT;
1849                break;
1850            case ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT:
1851                supportedWhiteBalance +=
1852                    CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT;
1853                break;
1854            case ANDROID_CONTROL_AWB_TWILIGHT:
1855                supportedWhiteBalance +=
1856                    CameraParameters::WHITE_BALANCE_TWILIGHT;
1857                break;
1858            case ANDROID_CONTROL_AWB_SHADE:
1859                supportedWhiteBalance +=
1860                    CameraParameters::WHITE_BALANCE_SHADE;
1861                break;
1862            // Skipping values not mappable to v1 API
1863            case ANDROID_CONTROL_AWB_OFF:
1864                addComma = false;
1865                break;
1866            default:
1867                ALOGW("%s: Camera %d: Unknown white balance value: %d",
1868                        __FUNCTION__, mCameraId,
1869                        availableWhiteBalanceModes.data.u8[i]);
1870                addComma = false;
1871                break;
1872            }
1873        }
1874        params.set(CameraParameters::KEY_SUPPORTED_WHITE_BALANCE,
1875                supportedWhiteBalance);
1876    }
1877
1878    mParameters.effectMode = ANDROID_CONTROL_EFFECT_OFF;
1879    params.set(CameraParameters::KEY_EFFECT,
1880            CameraParameters::EFFECT_NONE);
1881
1882    camera_metadata_entry_t availableEffects =
1883        staticInfo(ANDROID_CONTROL_AVAILABLE_EFFECTS);
1884    if (!availableEffects.count) return NO_INIT;
1885    {
1886        String8 supportedEffects;
1887        bool addComma = false;
1888        for (size_t i=0; i < availableEffects.count; i++) {
1889            if (addComma) supportedEffects += ",";
1890            addComma = true;
1891            switch (availableEffects.data.u8[i]) {
1892                case ANDROID_CONTROL_EFFECT_OFF:
1893                    supportedEffects +=
1894                        CameraParameters::EFFECT_NONE;
1895                    break;
1896                case ANDROID_CONTROL_EFFECT_MONO:
1897                    supportedEffects +=
1898                        CameraParameters::EFFECT_MONO;
1899                    break;
1900                case ANDROID_CONTROL_EFFECT_NEGATIVE:
1901                    supportedEffects +=
1902                        CameraParameters::EFFECT_NEGATIVE;
1903                    break;
1904                case ANDROID_CONTROL_EFFECT_SOLARIZE:
1905                    supportedEffects +=
1906                        CameraParameters::EFFECT_SOLARIZE;
1907                    break;
1908                case ANDROID_CONTROL_EFFECT_SEPIA:
1909                    supportedEffects +=
1910                        CameraParameters::EFFECT_SEPIA;
1911                    break;
1912                case ANDROID_CONTROL_EFFECT_POSTERIZE:
1913                    supportedEffects +=
1914                        CameraParameters::EFFECT_POSTERIZE;
1915                    break;
1916                case ANDROID_CONTROL_EFFECT_WHITEBOARD:
1917                    supportedEffects +=
1918                        CameraParameters::EFFECT_WHITEBOARD;
1919                    break;
1920                case ANDROID_CONTROL_EFFECT_BLACKBOARD:
1921                    supportedEffects +=
1922                        CameraParameters::EFFECT_BLACKBOARD;
1923                    break;
1924                case ANDROID_CONTROL_EFFECT_AQUA:
1925                    supportedEffects +=
1926                        CameraParameters::EFFECT_AQUA;
1927                    break;
1928                default:
1929                    ALOGW("%s: Camera %d: Unknown effect value: %d",
1930                        __FUNCTION__, mCameraId, availableEffects.data.u8[i]);
1931                    addComma = false;
1932                    break;
1933            }
1934        }
1935        params.set(CameraParameters::KEY_SUPPORTED_EFFECTS, supportedEffects);
1936    }
1937
1938    mParameters.antibandingMode = ANDROID_CONTROL_AE_ANTIBANDING_AUTO;
1939    params.set(CameraParameters::KEY_ANTIBANDING,
1940            CameraParameters::ANTIBANDING_AUTO);
1941
1942    camera_metadata_entry_t availableAntibandingModes =
1943        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_ANTIBANDING_MODES);
1944    if (!availableAntibandingModes.count) return NO_INIT;
1945    {
1946        String8 supportedAntibanding;
1947        bool addComma = false;
1948        for (size_t i=0; i < availableAntibandingModes.count; i++) {
1949            if (addComma) supportedAntibanding += ",";
1950            addComma = true;
1951            switch (availableAntibandingModes.data.u8[i]) {
1952                case ANDROID_CONTROL_AE_ANTIBANDING_OFF:
1953                    supportedAntibanding +=
1954                        CameraParameters::ANTIBANDING_OFF;
1955                    break;
1956                case ANDROID_CONTROL_AE_ANTIBANDING_50HZ:
1957                    supportedAntibanding +=
1958                        CameraParameters::ANTIBANDING_50HZ;
1959                    break;
1960                case ANDROID_CONTROL_AE_ANTIBANDING_60HZ:
1961                    supportedAntibanding +=
1962                        CameraParameters::ANTIBANDING_60HZ;
1963                    break;
1964                case ANDROID_CONTROL_AE_ANTIBANDING_AUTO:
1965                    supportedAntibanding +=
1966                        CameraParameters::ANTIBANDING_AUTO;
1967                    break;
1968                default:
1969                    ALOGW("%s: Camera %d: Unknown antibanding value: %d",
1970                        __FUNCTION__, mCameraId,
1971                            availableAntibandingModes.data.u8[i]);
1972                    addComma = false;
1973                    break;
1974            }
1975        }
1976        params.set(CameraParameters::KEY_SUPPORTED_ANTIBANDING,
1977                supportedAntibanding);
1978    }
1979
1980    mParameters.sceneMode = ANDROID_CONTROL_OFF;
1981    params.set(CameraParameters::KEY_SCENE_MODE,
1982            CameraParameters::SCENE_MODE_AUTO);
1983
1984    camera_metadata_entry_t availableSceneModes =
1985        staticInfo(ANDROID_CONTROL_AVAILABLE_SCENE_MODES);
1986    if (!availableSceneModes.count) return NO_INIT;
1987    {
1988        String8 supportedSceneModes(CameraParameters::SCENE_MODE_AUTO);
1989        bool addComma = true;
1990        bool noSceneModes = false;
1991        for (size_t i=0; i < availableSceneModes.count; i++) {
1992            if (addComma) supportedSceneModes += ",";
1993            addComma = true;
1994            switch (availableSceneModes.data.u8[i]) {
1995                case ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED:
1996                    noSceneModes = true;
1997                    break;
1998                case ANDROID_CONTROL_SCENE_MODE_FACE_PRIORITY:
1999                    // Not in old API
2000                    addComma = false;
2001                    break;
2002                case ANDROID_CONTROL_SCENE_MODE_ACTION:
2003                    supportedSceneModes +=
2004                        CameraParameters::SCENE_MODE_ACTION;
2005                    break;
2006                case ANDROID_CONTROL_SCENE_MODE_PORTRAIT:
2007                    supportedSceneModes +=
2008                        CameraParameters::SCENE_MODE_PORTRAIT;
2009                    break;
2010                case ANDROID_CONTROL_SCENE_MODE_LANDSCAPE:
2011                    supportedSceneModes +=
2012                        CameraParameters::SCENE_MODE_LANDSCAPE;
2013                    break;
2014                case ANDROID_CONTROL_SCENE_MODE_NIGHT:
2015                    supportedSceneModes +=
2016                        CameraParameters::SCENE_MODE_NIGHT;
2017                    break;
2018                case ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT:
2019                    supportedSceneModes +=
2020                        CameraParameters::SCENE_MODE_NIGHT_PORTRAIT;
2021                    break;
2022                case ANDROID_CONTROL_SCENE_MODE_THEATRE:
2023                    supportedSceneModes +=
2024                        CameraParameters::SCENE_MODE_THEATRE;
2025                    break;
2026                case ANDROID_CONTROL_SCENE_MODE_BEACH:
2027                    supportedSceneModes +=
2028                        CameraParameters::SCENE_MODE_BEACH;
2029                    break;
2030                case ANDROID_CONTROL_SCENE_MODE_SNOW:
2031                    supportedSceneModes +=
2032                        CameraParameters::SCENE_MODE_SNOW;
2033                    break;
2034                case ANDROID_CONTROL_SCENE_MODE_SUNSET:
2035                    supportedSceneModes +=
2036                        CameraParameters::SCENE_MODE_SUNSET;
2037                    break;
2038                case ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO:
2039                    supportedSceneModes +=
2040                        CameraParameters::SCENE_MODE_STEADYPHOTO;
2041                    break;
2042                case ANDROID_CONTROL_SCENE_MODE_FIREWORKS:
2043                    supportedSceneModes +=
2044                        CameraParameters::SCENE_MODE_FIREWORKS;
2045                    break;
2046                case ANDROID_CONTROL_SCENE_MODE_SPORTS:
2047                    supportedSceneModes +=
2048                        CameraParameters::SCENE_MODE_SPORTS;
2049                    break;
2050                case ANDROID_CONTROL_SCENE_MODE_PARTY:
2051                    supportedSceneModes +=
2052                        CameraParameters::SCENE_MODE_PARTY;
2053                    break;
2054                case ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT:
2055                    supportedSceneModes +=
2056                        CameraParameters::SCENE_MODE_CANDLELIGHT;
2057                    break;
2058                case ANDROID_CONTROL_SCENE_MODE_BARCODE:
2059                    supportedSceneModes +=
2060                        CameraParameters::SCENE_MODE_BARCODE;
2061                    break;
2062                default:
2063                    ALOGW("%s: Camera %d: Unknown scene mode value: %d",
2064                        __FUNCTION__, mCameraId,
2065                            availableSceneModes.data.u8[i]);
2066                    addComma = false;
2067                    break;
2068            }
2069        }
2070        if (!noSceneModes) {
2071            params.set(CameraParameters::KEY_SUPPORTED_SCENE_MODES,
2072                    supportedSceneModes);
2073        }
2074    }
2075
2076    camera_metadata_entry_t flashAvailable =
2077        staticInfo(ANDROID_FLASH_AVAILABLE, 1, 1);
2078    if (!flashAvailable.count) return NO_INIT;
2079
2080    camera_metadata_entry_t availableAeModes =
2081        staticInfo(ANDROID_CONTROL_AE_AVAILABLE_MODES);
2082    if (!availableAeModes.count) return NO_INIT;
2083
2084    if (flashAvailable.data.u8[0]) {
2085        mParameters.flashMode = Parameters::FLASH_MODE_AUTO;
2086        params.set(CameraParameters::KEY_FLASH_MODE,
2087                CameraParameters::FLASH_MODE_AUTO);
2088
2089        String8 supportedFlashModes(CameraParameters::FLASH_MODE_OFF);
2090        supportedFlashModes = supportedFlashModes +
2091            "," + CameraParameters::FLASH_MODE_AUTO +
2092            "," + CameraParameters::FLASH_MODE_ON +
2093            "," + CameraParameters::FLASH_MODE_TORCH;
2094        for (size_t i=0; i < availableAeModes.count; i++) {
2095            if (availableAeModes.data.u8[i] ==
2096                    ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE) {
2097                supportedFlashModes = supportedFlashModes + "," +
2098                    CameraParameters::FLASH_MODE_RED_EYE;
2099                break;
2100            }
2101        }
2102        params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
2103                supportedFlashModes);
2104    } else {
2105        mParameters.flashMode = Parameters::FLASH_MODE_OFF;
2106        params.set(CameraParameters::KEY_FLASH_MODE,
2107                CameraParameters::FLASH_MODE_OFF);
2108        params.set(CameraParameters::KEY_SUPPORTED_FLASH_MODES,
2109                CameraParameters::FLASH_MODE_OFF);
2110    }
2111
2112    camera_metadata_entry_t minFocusDistance =
2113        staticInfo(ANDROID_LENS_MINIMUM_FOCUS_DISTANCE, 1, 1);
2114    if (!minFocusDistance.count) return NO_INIT;
2115
2116    camera_metadata_entry_t availableAfModes =
2117        staticInfo(ANDROID_CONTROL_AF_AVAILABLE_MODES);
2118    if (!availableAfModes.count) return NO_INIT;
2119
2120    if (minFocusDistance.data.f[0] == 0) {
2121        // Fixed-focus lens
2122        mParameters.focusMode = Parameters::FOCUS_MODE_FIXED;
2123        params.set(CameraParameters::KEY_FOCUS_MODE,
2124                CameraParameters::FOCUS_MODE_FIXED);
2125        params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
2126                CameraParameters::FOCUS_MODE_FIXED);
2127    } else {
2128        mParameters.focusMode = Parameters::FOCUS_MODE_AUTO;
2129        params.set(CameraParameters::KEY_FOCUS_MODE,
2130                CameraParameters::FOCUS_MODE_AUTO);
2131        String8 supportedFocusModes(CameraParameters::FOCUS_MODE_FIXED);
2132        supportedFocusModes = supportedFocusModes + "," +
2133            CameraParameters::FOCUS_MODE_INFINITY;
2134        bool addComma = true;
2135
2136        for (size_t i=0; i < availableAfModes.count; i++) {
2137            if (addComma) supportedFocusModes += ",";
2138            addComma = true;
2139            switch (availableAfModes.data.u8[i]) {
2140                case ANDROID_CONTROL_AF_AUTO:
2141                    supportedFocusModes +=
2142                        CameraParameters::FOCUS_MODE_AUTO;
2143                    break;
2144                case ANDROID_CONTROL_AF_MACRO:
2145                    supportedFocusModes +=
2146                        CameraParameters::FOCUS_MODE_MACRO;
2147                    break;
2148                case ANDROID_CONTROL_AF_CONTINUOUS_VIDEO:
2149                    supportedFocusModes +=
2150                        CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO;
2151                    break;
2152                case ANDROID_CONTROL_AF_CONTINUOUS_PICTURE:
2153                    supportedFocusModes +=
2154                        CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE;
2155                    break;
2156                case ANDROID_CONTROL_AF_EDOF:
2157                    supportedFocusModes +=
2158                        CameraParameters::FOCUS_MODE_EDOF;
2159                    break;
2160                // Not supported in old API
2161                case ANDROID_CONTROL_AF_OFF:
2162                    addComma = false;
2163                    break;
2164                default:
2165                    ALOGW("%s: Camera %d: Unknown AF mode value: %d",
2166                        __FUNCTION__, mCameraId, availableAfModes.data.u8[i]);
2167                    addComma = false;
2168                    break;
2169            }
2170        }
2171        params.set(CameraParameters::KEY_SUPPORTED_FOCUS_MODES,
2172                supportedFocusModes);
2173    }
2174
2175    camera_metadata_entry_t max3aRegions =
2176        staticInfo(ANDROID_CONTROL_MAX_REGIONS, 1, 1);
2177    if (!max3aRegions.count) return NO_INIT;
2178
2179    params.set(CameraParameters::KEY_MAX_NUM_FOCUS_AREAS,
2180            max3aRegions.data.i32[0]);
2181    params.set(CameraParameters::KEY_FOCUS_AREAS,
2182            "(0,0,0,0,0)");
2183    mParameters.focusingAreas.clear();
2184    mParameters.focusingAreas.add(Parameters::Area(0,0,0,0,0));
2185
2186    camera_metadata_entry_t availableFocalLengths =
2187        staticInfo(ANDROID_LENS_AVAILABLE_FOCAL_LENGTHS);
2188    if (!availableFocalLengths.count) return NO_INIT;
2189
2190    float minFocalLength = availableFocalLengths.data.f[0];
2191    params.setFloat(CameraParameters::KEY_FOCAL_LENGTH, minFocalLength);
2192
2193    camera_metadata_entry_t sensorSize =
2194        staticInfo(ANDROID_SENSOR_PHYSICAL_SIZE, 2, 2);
2195    if (!sensorSize.count) return NO_INIT;
2196
2197    // The fields of view here assume infinity focus, maximum wide angle
2198    float horizFov = 180 / M_PI *
2199            2 * atanf(sensorSize.data.f[0] / (2 * minFocalLength));
2200    float vertFov  = 180 / M_PI *
2201            2 * atanf(sensorSize.data.f[1] / (2 * minFocalLength));
2202    params.setFloat(CameraParameters::KEY_HORIZONTAL_VIEW_ANGLE, horizFov);
2203    params.setFloat(CameraParameters::KEY_VERTICAL_VIEW_ANGLE, vertFov);
2204
2205    mParameters.exposureCompensation = 0;
2206    params.set(CameraParameters::KEY_EXPOSURE_COMPENSATION,
2207                mParameters.exposureCompensation);
2208
2209    camera_metadata_entry_t exposureCompensationRange =
2210        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_RANGE, 2, 2);
2211    if (!exposureCompensationRange.count) return NO_INIT;
2212
2213    params.set(CameraParameters::KEY_MAX_EXPOSURE_COMPENSATION,
2214            exposureCompensationRange.data.i32[1]);
2215    params.set(CameraParameters::KEY_MIN_EXPOSURE_COMPENSATION,
2216            exposureCompensationRange.data.i32[0]);
2217
2218    camera_metadata_entry_t exposureCompensationStep =
2219        staticInfo(ANDROID_CONTROL_AE_EXP_COMPENSATION_STEP, 1, 1);
2220    if (!exposureCompensationStep.count) return NO_INIT;
2221
2222    params.setFloat(CameraParameters::KEY_EXPOSURE_COMPENSATION_STEP,
2223            exposureCompensationStep.data.r[0].numerator /
2224            exposureCompensationStep.data.r[0].denominator);
2225
2226    mParameters.autoExposureLock = false;
2227    params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK,
2228            CameraParameters::FALSE);
2229    params.set(CameraParameters::KEY_AUTO_EXPOSURE_LOCK_SUPPORTED,
2230            CameraParameters::TRUE);
2231
2232    mParameters.autoWhiteBalanceLock = false;
2233    params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK,
2234            CameraParameters::FALSE);
2235    params.set(CameraParameters::KEY_AUTO_WHITEBALANCE_LOCK_SUPPORTED,
2236            CameraParameters::TRUE);
2237
2238    mParameters.meteringAreas.add(Parameters::Area(0, 0, 0, 0, 0));
2239    params.set(CameraParameters::KEY_MAX_NUM_METERING_AREAS,
2240            max3aRegions.data.i32[0]);
2241    params.set(CameraParameters::KEY_METERING_AREAS,
2242            "(0,0,0,0,0)");
2243
2244    mParameters.zoom = 0;
2245    params.set(CameraParameters::KEY_ZOOM, mParameters.zoom);
2246    params.set(CameraParameters::KEY_MAX_ZOOM, NUM_ZOOM_STEPS - 1);
2247
2248    camera_metadata_entry_t maxDigitalZoom =
2249        staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM, 1, 1);
2250    if (!maxDigitalZoom.count) return NO_INIT;
2251
2252    {
2253        String8 zoomRatios;
2254        float zoom = 1.f;
2255        float zoomIncrement = (maxDigitalZoom.data.f[0] - zoom) /
2256                (NUM_ZOOM_STEPS-1);
2257        bool addComma = false;
2258        for (size_t i=0; i < NUM_ZOOM_STEPS; i++) {
2259            if (addComma) zoomRatios += ",";
2260            addComma = true;
2261            zoomRatios += String8::format("%d", static_cast<int>(zoom * 100));
2262            zoom += zoomIncrement;
2263        }
2264        params.set(CameraParameters::KEY_ZOOM_RATIOS, zoomRatios);
2265    }
2266
2267    params.set(CameraParameters::KEY_ZOOM_SUPPORTED,
2268            CameraParameters::TRUE);
2269    params.set(CameraParameters::KEY_SMOOTH_ZOOM_SUPPORTED,
2270            CameraParameters::TRUE);
2271
2272    params.set(CameraParameters::KEY_FOCUS_DISTANCES,
2273            "Infinity,Infinity,Infinity");
2274
2275    camera_metadata_entry_t maxFacesDetected =
2276        staticInfo(ANDROID_STATS_MAX_FACE_COUNT, 1, 1);
2277    params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_HW,
2278            maxFacesDetected.data.i32[0]);
2279    params.set(CameraParameters::KEY_MAX_NUM_DETECTED_FACES_SW,
2280            0);
2281
2282    params.set(CameraParameters::KEY_VIDEO_FRAME_FORMAT,
2283            formatEnumToString(kRecordingFormat));
2284
2285    params.set(CameraParameters::KEY_RECORDING_HINT,
2286            CameraParameters::FALSE);
2287
2288    params.set(CameraParameters::KEY_VIDEO_SNAPSHOT_SUPPORTED,
2289            CameraParameters::TRUE);
2290
2291    params.set(CameraParameters::KEY_VIDEO_STABILIZATION,
2292            CameraParameters::FALSE);
2293
2294    camera_metadata_entry_t availableVideoStabilizationModes =
2295        staticInfo(ANDROID_CONTROL_AVAILABLE_VIDEO_STABILIZATION_MODES);
2296    if (!availableVideoStabilizationModes.count) return NO_INIT;
2297
2298    if (availableVideoStabilizationModes.count > 1) {
2299        params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
2300                CameraParameters::TRUE);
2301    } else {
2302        params.set(CameraParameters::KEY_VIDEO_STABILIZATION_SUPPORTED,
2303                CameraParameters::FALSE);
2304    }
2305
2306    mParamsFlattened = params.flatten();
2307
2308    return OK;
2309}
2310
2311status_t Camera2Client::updatePreviewStream() {
2312    ATRACE_CALL();
2313    status_t res;
2314    if (mPreviewStreamId != NO_STREAM) {
2315        // Check if stream parameters have to change
2316        uint32_t currentWidth, currentHeight;
2317        res = mDevice->getStreamInfo(mPreviewStreamId,
2318                &currentWidth, &currentHeight, 0);
2319        if (res != OK) {
2320            ALOGE("%s: Camera %d: Error querying preview stream info: "
2321                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2322            return res;
2323        }
2324        if (currentWidth != (uint32_t)mParameters.previewWidth ||
2325                currentHeight != (uint32_t)mParameters.previewHeight) {
2326            res = mDevice->waitUntilDrained();
2327            if (res != OK) {
2328                ALOGE("%s: Camera %d: Error waiting for preview to drain: "
2329                        "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2330                return res;
2331            }
2332            res = mDevice->deleteStream(mPreviewStreamId);
2333            if (res != OK) {
2334                ALOGE("%s: Camera %d: Unable to delete old output stream "
2335                        "for preview: %s (%d)", __FUNCTION__, mCameraId,
2336                        strerror(-res), res);
2337                return res;
2338            }
2339            mPreviewStreamId = NO_STREAM;
2340        }
2341    }
2342
2343    if (mPreviewStreamId == NO_STREAM) {
2344        res = mDevice->createStream(mPreviewWindow,
2345                mParameters.previewWidth, mParameters.previewHeight,
2346                CAMERA2_HAL_PIXEL_FORMAT_OPAQUE, 0,
2347                &mPreviewStreamId);
2348        if (res != OK) {
2349            ALOGE("%s: Camera %d: Unable to create preview stream: %s (%d)",
2350                    __FUNCTION__, mCameraId, strerror(-res), res);
2351            return res;
2352        }
2353    }
2354
2355    res = mDevice->setStreamTransform(mPreviewStreamId,
2356            mParameters.previewTransform);
2357    if (res != OK) {
2358        ALOGE("%s: Camera %d: Unable to set preview stream transform: "
2359                "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2360        return res;
2361    }
2362
2363    return OK;
2364}
2365
2366status_t Camera2Client::updatePreviewRequest() {
2367    ATRACE_CALL();
2368    status_t res;
2369    if (mPreviewRequest == NULL) {
2370        res = mDevice->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW,
2371                &mPreviewRequest);
2372        if (res != OK) {
2373            ALOGE("%s: Camera %d: Unable to create default preview request: "
2374                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2375            return res;
2376        }
2377    }
2378
2379    res = updateRequestCommon(mPreviewRequest);
2380    if (res != OK) {
2381        ALOGE("%s: Camera %d: Unable to update common entries of preview "
2382                "request: %s (%d)", __FUNCTION__, mCameraId,
2383                strerror(-res), res);
2384        return res;
2385    }
2386
2387    return OK;
2388}
2389
2390status_t Camera2Client::updateCaptureStream() {
2391    ATRACE_CALL();
2392    status_t res;
2393    // Find out buffer size for JPEG
2394    camera_metadata_entry_t maxJpegSize =
2395            staticInfo(ANDROID_JPEG_MAX_SIZE);
2396    if (maxJpegSize.count == 0) {
2397        ALOGE("%s: Camera %d: Can't find ANDROID_JPEG_MAX_SIZE!",
2398                __FUNCTION__, mCameraId);
2399        return INVALID_OPERATION;
2400    }
2401
2402    if (mCaptureConsumer == 0) {
2403        // Create CPU buffer queue endpoint
2404        mCaptureConsumer = new CpuConsumer(1);
2405        mCaptureConsumer->setFrameAvailableListener(new CaptureWaiter(this));
2406        mCaptureConsumer->setName(String8("Camera2Client::CaptureConsumer"));
2407        mCaptureWindow = new SurfaceTextureClient(
2408            mCaptureConsumer->getProducerInterface());
2409        // Create memory for API consumption
2410        mCaptureHeap = new Camera2Heap(maxJpegSize.data.i32[0], 1,
2411                                       "Camera2Client::CaptureHeap");
2412        if (mCaptureHeap->mHeap->getSize() == 0) {
2413            ALOGE("%s: Camera %d: Unable to allocate memory for capture",
2414                    __FUNCTION__, mCameraId);
2415            return NO_MEMORY;
2416        }
2417    }
2418
2419    if (mCaptureStreamId != NO_STREAM) {
2420        // Check if stream parameters have to change
2421        uint32_t currentWidth, currentHeight;
2422        res = mDevice->getStreamInfo(mCaptureStreamId,
2423                &currentWidth, &currentHeight, 0);
2424        if (res != OK) {
2425            ALOGE("%s: Camera %d: Error querying capture output stream info: "
2426                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2427            return res;
2428        }
2429        if (currentWidth != (uint32_t)mParameters.pictureWidth ||
2430                currentHeight != (uint32_t)mParameters.pictureHeight) {
2431            res = mDevice->deleteStream(mCaptureStreamId);
2432            if (res != OK) {
2433                ALOGE("%s: Camera %d: Unable to delete old output stream "
2434                        "for capture: %s (%d)", __FUNCTION__, mCameraId,
2435                        strerror(-res), res);
2436                return res;
2437            }
2438            mCaptureStreamId = NO_STREAM;
2439        }
2440    }
2441
2442    if (mCaptureStreamId == NO_STREAM) {
2443        // Create stream for HAL production
2444        res = mDevice->createStream(mCaptureWindow,
2445                mParameters.pictureWidth, mParameters.pictureHeight,
2446                HAL_PIXEL_FORMAT_BLOB, maxJpegSize.data.i32[0],
2447                &mCaptureStreamId);
2448        if (res != OK) {
2449            ALOGE("%s: Camera %d: Can't create output stream for capture: "
2450                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2451            return res;
2452        }
2453
2454    }
2455    return OK;
2456}
2457
2458status_t Camera2Client::updateCaptureRequest() {
2459    ATRACE_CALL();
2460    status_t res;
2461    if (mCaptureRequest == NULL) {
2462        res = mDevice->createDefaultRequest(CAMERA2_TEMPLATE_STILL_CAPTURE,
2463                &mCaptureRequest);
2464        if (res != OK) {
2465            ALOGE("%s: Camera %d: Unable to create default still image request:"
2466                    " %s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2467            return res;
2468        }
2469    }
2470
2471    res = updateRequestCommon(mCaptureRequest);
2472    if (res != OK) {
2473        ALOGE("%s: Camera %d: Unable to update common entries of capture "
2474                "request: %s (%d)", __FUNCTION__, mCameraId,
2475                strerror(-res), res);
2476        return res;
2477    }
2478
2479    res = updateEntry(mCaptureRequest,
2480            ANDROID_JPEG_THUMBNAIL_SIZE,
2481            mParameters.jpegThumbSize, 2);
2482    if (res != OK) return res;
2483    res = updateEntry(mCaptureRequest,
2484            ANDROID_JPEG_THUMBNAIL_QUALITY,
2485            &mParameters.jpegThumbQuality, 1);
2486    if (res != OK) return res;
2487    res = updateEntry(mCaptureRequest,
2488            ANDROID_JPEG_QUALITY,
2489            &mParameters.jpegQuality, 1);
2490    if (res != OK) return res;
2491    res = updateEntry(mCaptureRequest,
2492            ANDROID_JPEG_ORIENTATION,
2493            &mParameters.jpegRotation, 1);
2494    if (res != OK) return res;
2495
2496    if (mParameters.gpsEnabled) {
2497        res = updateEntry(mCaptureRequest,
2498                ANDROID_JPEG_GPS_COORDINATES,
2499                mParameters.gpsCoordinates, 3);
2500        if (res != OK) return res;
2501        res = updateEntry(mCaptureRequest,
2502                ANDROID_JPEG_GPS_TIMESTAMP,
2503                &mParameters.gpsTimestamp, 1);
2504        if (res != OK) return res;
2505        res = updateEntry(mCaptureRequest,
2506                ANDROID_JPEG_GPS_PROCESSING_METHOD,
2507                mParameters.gpsProcessingMethod.string(),
2508                mParameters.gpsProcessingMethod.size());
2509        if (res != OK) return res;
2510    } else {
2511        res = deleteEntry(mCaptureRequest,
2512                ANDROID_JPEG_GPS_COORDINATES);
2513        if (res != OK) return res;
2514        res = deleteEntry(mCaptureRequest,
2515                ANDROID_JPEG_GPS_TIMESTAMP);
2516        if (res != OK) return res;
2517        res = deleteEntry(mCaptureRequest,
2518                ANDROID_JPEG_GPS_PROCESSING_METHOD);
2519        if (res != OK) return res;
2520    }
2521
2522    return OK;
2523}
2524
2525status_t Camera2Client::updateRecordingRequest() {
2526    ATRACE_CALL();
2527    status_t res;
2528    if (mRecordingRequest == NULL) {
2529        res = mDevice->createDefaultRequest(CAMERA2_TEMPLATE_VIDEO_RECORD,
2530                &mRecordingRequest);
2531        if (res != OK) {
2532            ALOGE("%s: Camera %d: Unable to create default recording request:"
2533                    " %s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2534            return res;
2535        }
2536    }
2537
2538    res = updateRequestCommon(mRecordingRequest);
2539    if (res != OK) {
2540        ALOGE("%s: Camera %d: Unable to update common entries of recording "
2541                "request: %s (%d)", __FUNCTION__, mCameraId,
2542                strerror(-res), res);
2543        return res;
2544    }
2545
2546    return OK;
2547}
2548
2549status_t Camera2Client::updateRecordingStream() {
2550    status_t res;
2551
2552    if (mRecordingConsumer == 0) {
2553        // Create CPU buffer queue endpoint
2554        mRecordingConsumer = new CpuConsumer(1);
2555        mRecordingConsumer->setFrameAvailableListener(new RecordingWaiter(this));
2556        mRecordingConsumer->setName(String8("Camera2Client::RecordingConsumer"));
2557        mRecordingWindow = new SurfaceTextureClient(
2558            mRecordingConsumer->getProducerInterface());
2559        // Allocate memory later, since we don't know buffer size until receipt
2560    }
2561
2562    if (mRecordingStreamId != NO_STREAM) {
2563        // Check if stream parameters have to change
2564        uint32_t currentWidth, currentHeight;
2565        res = mDevice->getStreamInfo(mRecordingStreamId,
2566                &currentWidth, &currentHeight, 0);
2567        if (res != OK) {
2568            ALOGE("%s: Camera %d: Error querying recording output stream info: "
2569                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2570            return res;
2571        }
2572        if (currentWidth != (uint32_t)mParameters.videoWidth ||
2573                currentHeight != (uint32_t)mParameters.videoHeight) {
2574            // TODO: Should wait to be sure previous recording has finished
2575            res = mDevice->deleteStream(mRecordingStreamId);
2576            if (res != OK) {
2577                ALOGE("%s: Camera %d: Unable to delete old output stream "
2578                        "for recording: %s (%d)", __FUNCTION__, mCameraId,
2579                        strerror(-res), res);
2580                return res;
2581            }
2582            mRecordingStreamId = NO_STREAM;
2583        }
2584    }
2585
2586    if (mRecordingStreamId == NO_STREAM) {
2587        res = mDevice->createStream(mRecordingWindow,
2588                mParameters.videoWidth, mParameters.videoHeight,
2589                kRecordingFormat, 0, &mRecordingStreamId);
2590        if (res != OK) {
2591            ALOGE("%s: Camera %d: Can't create output stream for recording: "
2592                    "%s (%d)", __FUNCTION__, mCameraId, strerror(-res), res);
2593            return res;
2594        }
2595    }
2596
2597    return OK;
2598}
2599
2600status_t Camera2Client::updateRequestCommon(camera_metadata_t *request) {
2601    ATRACE_CALL();
2602    status_t res;
2603    res = updateEntry(request,
2604            ANDROID_CONTROL_AE_TARGET_FPS_RANGE, mParameters.previewFpsRange, 2);
2605    if (res != OK) return res;
2606
2607    uint8_t wbMode = mParameters.autoWhiteBalanceLock ?
2608            ANDROID_CONTROL_AWB_LOCKED : mParameters.wbMode;
2609    res = updateEntry(request,
2610            ANDROID_CONTROL_AWB_MODE, &wbMode, 1);
2611    if (res != OK) return res;
2612    res = updateEntry(request,
2613            ANDROID_CONTROL_EFFECT_MODE, &mParameters.effectMode, 1);
2614    if (res != OK) return res;
2615    res = updateEntry(request,
2616            ANDROID_CONTROL_AE_ANTIBANDING_MODE,
2617            &mParameters.antibandingMode, 1);
2618    if (res != OK) return res;
2619
2620    uint8_t controlMode =
2621            (mParameters.sceneMode == ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED) ?
2622            ANDROID_CONTROL_AUTO : ANDROID_CONTROL_USE_SCENE_MODE;
2623    res = updateEntry(request,
2624            ANDROID_CONTROL_MODE, &controlMode, 1);
2625    if (res != OK) return res;
2626    if (controlMode == ANDROID_CONTROL_USE_SCENE_MODE) {
2627        res = updateEntry(request,
2628                ANDROID_CONTROL_SCENE_MODE,
2629                &mParameters.sceneMode, 1);
2630        if (res != OK) return res;
2631    }
2632
2633    uint8_t flashMode = ANDROID_FLASH_OFF;
2634    uint8_t aeMode;
2635    switch (mParameters.flashMode) {
2636        case Parameters::FLASH_MODE_OFF:
2637            aeMode = ANDROID_CONTROL_AE_ON; break;
2638        case Parameters::FLASH_MODE_AUTO:
2639            aeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH; break;
2640        case Parameters::FLASH_MODE_ON:
2641            aeMode = ANDROID_CONTROL_AE_ON_ALWAYS_FLASH; break;
2642        case Parameters::FLASH_MODE_TORCH:
2643            aeMode = ANDROID_CONTROL_AE_ON;
2644            flashMode = ANDROID_FLASH_TORCH;
2645            break;
2646        case Parameters::FLASH_MODE_RED_EYE:
2647            aeMode = ANDROID_CONTROL_AE_ON_AUTO_FLASH_REDEYE; break;
2648        default:
2649            ALOGE("%s: Camera %d: Unknown flash mode %d", __FUNCTION__,
2650                    mCameraId, mParameters.flashMode);
2651            return BAD_VALUE;
2652    }
2653    if (mParameters.autoExposureLock) aeMode = ANDROID_CONTROL_AE_LOCKED;
2654
2655    res = updateEntry(request,
2656            ANDROID_FLASH_MODE, &flashMode, 1);
2657    if (res != OK) return res;
2658    res = updateEntry(request,
2659            ANDROID_CONTROL_AE_MODE, &aeMode, 1);
2660    if (res != OK) return res;
2661
2662    float focusDistance = 0; // infinity focus in diopters
2663    uint8_t focusMode;
2664    switch (mParameters.focusMode) {
2665        case Parameters::FOCUS_MODE_AUTO:
2666        case Parameters::FOCUS_MODE_MACRO:
2667        case Parameters::FOCUS_MODE_CONTINUOUS_VIDEO:
2668        case Parameters::FOCUS_MODE_CONTINUOUS_PICTURE:
2669        case Parameters::FOCUS_MODE_EDOF:
2670            focusMode = mParameters.focusMode;
2671            break;
2672        case Parameters::FOCUS_MODE_INFINITY:
2673        case Parameters::FOCUS_MODE_FIXED:
2674            focusMode = ANDROID_CONTROL_AF_OFF;
2675            break;
2676        default:
2677            ALOGE("%s: Camera %d: Unknown focus mode %d", __FUNCTION__,
2678                    mCameraId, mParameters.focusMode);
2679            return BAD_VALUE;
2680    }
2681    res = updateEntry(request,
2682            ANDROID_LENS_FOCUS_DISTANCE, &focusDistance, 1);
2683    if (res != OK) return res;
2684    res = updateEntry(request,
2685            ANDROID_CONTROL_AF_MODE, &focusMode, 1);
2686    if (res != OK) return res;
2687
2688    size_t focusingAreasSize = mParameters.focusingAreas.size() * 5;
2689    int32_t *focusingAreas = new int32_t[focusingAreasSize];
2690    for (size_t i = 0; i < focusingAreasSize; i += 5) {
2691        focusingAreas[i + 0] = mParameters.focusingAreas[i].left;
2692        focusingAreas[i + 1] = mParameters.focusingAreas[i].top;
2693        focusingAreas[i + 2] = mParameters.focusingAreas[i].right;
2694        focusingAreas[i + 3] = mParameters.focusingAreas[i].bottom;
2695        focusingAreas[i + 4] = mParameters.focusingAreas[i].weight;
2696    }
2697    res = updateEntry(request,
2698            ANDROID_CONTROL_AF_REGIONS, focusingAreas,focusingAreasSize);
2699    if (res != OK) return res;
2700    delete[] focusingAreas;
2701
2702    res = updateEntry(request,
2703            ANDROID_CONTROL_AE_EXP_COMPENSATION,
2704            &mParameters.exposureCompensation, 1);
2705    if (res != OK) return res;
2706
2707    size_t meteringAreasSize = mParameters.meteringAreas.size() * 5;
2708    int32_t *meteringAreas = new int32_t[meteringAreasSize];
2709    for (size_t i = 0; i < meteringAreasSize; i += 5) {
2710        meteringAreas[i + 0] = mParameters.meteringAreas[i].left;
2711        meteringAreas[i + 1] = mParameters.meteringAreas[i].top;
2712        meteringAreas[i + 2] = mParameters.meteringAreas[i].right;
2713        meteringAreas[i + 3] = mParameters.meteringAreas[i].bottom;
2714        meteringAreas[i + 4] = mParameters.meteringAreas[i].weight;
2715    }
2716    res = updateEntry(request,
2717            ANDROID_CONTROL_AE_REGIONS, meteringAreas, meteringAreasSize);
2718    if (res != OK) return res;
2719
2720    res = updateEntry(request,
2721            ANDROID_CONTROL_AWB_REGIONS, meteringAreas, meteringAreasSize);
2722    if (res != OK) return res;
2723    delete[] meteringAreas;
2724
2725    // Need to convert zoom index into a crop rectangle. The rectangle is
2726    // chosen to maximize its area on the sensor
2727
2728    camera_metadata_entry_t maxDigitalZoom =
2729            staticInfo(ANDROID_SCALER_AVAILABLE_MAX_ZOOM);
2730    float zoomIncrement = (maxDigitalZoom.data.f[0] - 1) /
2731            (NUM_ZOOM_STEPS-1);
2732    float zoomRatio = 1 + zoomIncrement * mParameters.zoom;
2733
2734    camera_metadata_entry_t activePixelArraySize =
2735            staticInfo(ANDROID_SENSOR_ACTIVE_ARRAY_SIZE, 2, 2);
2736    int32_t arrayWidth = activePixelArraySize.data.i32[0];
2737    int32_t arrayHeight = activePixelArraySize.data.i32[1];
2738    float zoomLeft, zoomTop, zoomWidth, zoomHeight;
2739    if (mParameters.previewWidth >= mParameters.previewHeight) {
2740        zoomWidth =  arrayWidth / zoomRatio;
2741        zoomHeight = zoomWidth *
2742                mParameters.previewHeight / mParameters.previewWidth;
2743    } else {
2744        zoomHeight = arrayHeight / zoomRatio;
2745        zoomWidth = zoomHeight *
2746                mParameters.previewWidth / mParameters.previewHeight;
2747    }
2748    zoomLeft = (arrayWidth - zoomWidth) / 2;
2749    zoomTop = (arrayHeight - zoomHeight) / 2;
2750
2751    int32_t cropRegion[3] = { zoomLeft, zoomTop, zoomWidth };
2752    res = updateEntry(request,
2753            ANDROID_SCALER_CROP_REGION, cropRegion, 3);
2754    if (res != OK) return res;
2755
2756    // TODO: Decide how to map recordingHint, or whether just to ignore it
2757
2758    uint8_t vstabMode = mParameters.videoStabilization ?
2759            ANDROID_CONTROL_VIDEO_STABILIZATION_ON :
2760            ANDROID_CONTROL_VIDEO_STABILIZATION_OFF;
2761    res = updateEntry(request,
2762            ANDROID_CONTROL_VIDEO_STABILIZATION_MODE,
2763            &vstabMode, 1);
2764    if (res != OK) return res;
2765
2766    return OK;
2767}
2768
2769status_t Camera2Client::updateEntry(camera_metadata_t *buffer,
2770        uint32_t tag, const void *data, size_t data_count) {
2771    camera_metadata_entry_t entry;
2772    status_t res;
2773    res = find_camera_metadata_entry(buffer, tag, &entry);
2774    if (res == NAME_NOT_FOUND) {
2775        res = add_camera_metadata_entry(buffer,
2776                tag, data, data_count);
2777    } else if (res == OK) {
2778        res = update_camera_metadata_entry(buffer,
2779                entry.index, data, data_count, NULL);
2780    }
2781
2782    if (res != OK) {
2783        ALOGE("%s: Unable to update metadata entry %s.%s (%x): %s (%d)",
2784                __FUNCTION__, get_camera_metadata_section_name(tag),
2785                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2786    }
2787    return res;
2788}
2789
2790status_t Camera2Client::deleteEntry(camera_metadata_t *buffer, uint32_t tag) {
2791    camera_metadata_entry_t entry;
2792    status_t res;
2793    res = find_camera_metadata_entry(buffer, tag, &entry);
2794    if (res == NAME_NOT_FOUND) {
2795        return OK;
2796    } else if (res != OK) {
2797        ALOGE("%s: Error looking for entry %s.%s (%x): %s %d",
2798                __FUNCTION__,
2799                get_camera_metadata_section_name(tag),
2800                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2801        return res;
2802    }
2803    res = delete_camera_metadata_entry(buffer, entry.index);
2804    if (res != OK) {
2805        ALOGE("%s: Error deleting entry %s.%s (%x): %s %d",
2806                __FUNCTION__,
2807                get_camera_metadata_section_name(tag),
2808                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
2809    }
2810    return res;
2811}
2812int Camera2Client::formatStringToEnum(const char *format) {
2813    return
2814        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422SP) ?
2815            HAL_PIXEL_FORMAT_YCbCr_422_SP : // NV16
2816        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420SP) ?
2817            HAL_PIXEL_FORMAT_YCrCb_420_SP : // NV21
2818        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV422I) ?
2819            HAL_PIXEL_FORMAT_YCbCr_422_I :  // YUY2
2820        !strcmp(format, CameraParameters::PIXEL_FORMAT_YUV420P) ?
2821            HAL_PIXEL_FORMAT_YV12 :         // YV12
2822        !strcmp(format, CameraParameters::PIXEL_FORMAT_RGB565) ?
2823            HAL_PIXEL_FORMAT_RGB_565 :      // RGB565
2824        !strcmp(format, CameraParameters::PIXEL_FORMAT_RGBA8888) ?
2825            HAL_PIXEL_FORMAT_RGBA_8888 :    // RGB8888
2826        !strcmp(format, CameraParameters::PIXEL_FORMAT_BAYER_RGGB) ?
2827            HAL_PIXEL_FORMAT_RAW_SENSOR :   // Raw sensor data
2828        -1;
2829}
2830
2831const char* Camera2Client::formatEnumToString(int format) {
2832    const char *fmt;
2833    switch(format) {
2834        case HAL_PIXEL_FORMAT_YCbCr_422_SP: // NV16
2835            fmt = CameraParameters::PIXEL_FORMAT_YUV422SP;
2836            break;
2837        case HAL_PIXEL_FORMAT_YCrCb_420_SP: // NV21
2838            fmt = CameraParameters::PIXEL_FORMAT_YUV420SP;
2839            break;
2840        case HAL_PIXEL_FORMAT_YCbCr_422_I: // YUY2
2841            fmt = CameraParameters::PIXEL_FORMAT_YUV422I;
2842            break;
2843        case HAL_PIXEL_FORMAT_YV12:        // YV12
2844            fmt = CameraParameters::PIXEL_FORMAT_YUV420P;
2845            break;
2846        case HAL_PIXEL_FORMAT_RGB_565:     // RGB565
2847            fmt = CameraParameters::PIXEL_FORMAT_RGB565;
2848            break;
2849        case HAL_PIXEL_FORMAT_RGBA_8888:   // RGBA8888
2850            fmt = CameraParameters::PIXEL_FORMAT_RGBA8888;
2851            break;
2852        case HAL_PIXEL_FORMAT_RAW_SENSOR:
2853            ALOGW("Raw sensor preview format requested.");
2854            fmt = CameraParameters::PIXEL_FORMAT_BAYER_RGGB;
2855            break;
2856        default:
2857            ALOGE("%s: Unknown preview format: %x",
2858                    __FUNCTION__,  format);
2859            fmt = NULL;
2860            break;
2861    }
2862    return fmt;
2863}
2864
2865int Camera2Client::wbModeStringToEnum(const char *wbMode) {
2866    return
2867        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_AUTO) ?
2868            ANDROID_CONTROL_AWB_AUTO :
2869        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_INCANDESCENT) ?
2870            ANDROID_CONTROL_AWB_INCANDESCENT :
2871        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_FLUORESCENT) ?
2872            ANDROID_CONTROL_AWB_FLUORESCENT :
2873        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_WARM_FLUORESCENT) ?
2874            ANDROID_CONTROL_AWB_WARM_FLUORESCENT :
2875        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_DAYLIGHT) ?
2876            ANDROID_CONTROL_AWB_DAYLIGHT :
2877        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_CLOUDY_DAYLIGHT) ?
2878            ANDROID_CONTROL_AWB_CLOUDY_DAYLIGHT :
2879        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_TWILIGHT) ?
2880            ANDROID_CONTROL_AWB_TWILIGHT :
2881        !strcmp(wbMode, CameraParameters::WHITE_BALANCE_SHADE) ?
2882            ANDROID_CONTROL_AWB_SHADE :
2883        -1;
2884}
2885
2886int Camera2Client::effectModeStringToEnum(const char *effectMode) {
2887    return
2888        !strcmp(effectMode, CameraParameters::EFFECT_NONE) ?
2889            ANDROID_CONTROL_EFFECT_OFF :
2890        !strcmp(effectMode, CameraParameters::EFFECT_MONO) ?
2891            ANDROID_CONTROL_EFFECT_MONO :
2892        !strcmp(effectMode, CameraParameters::EFFECT_NEGATIVE) ?
2893            ANDROID_CONTROL_EFFECT_NEGATIVE :
2894        !strcmp(effectMode, CameraParameters::EFFECT_SOLARIZE) ?
2895            ANDROID_CONTROL_EFFECT_SOLARIZE :
2896        !strcmp(effectMode, CameraParameters::EFFECT_SEPIA) ?
2897            ANDROID_CONTROL_EFFECT_SEPIA :
2898        !strcmp(effectMode, CameraParameters::EFFECT_POSTERIZE) ?
2899            ANDROID_CONTROL_EFFECT_POSTERIZE :
2900        !strcmp(effectMode, CameraParameters::EFFECT_WHITEBOARD) ?
2901            ANDROID_CONTROL_EFFECT_WHITEBOARD :
2902        !strcmp(effectMode, CameraParameters::EFFECT_BLACKBOARD) ?
2903            ANDROID_CONTROL_EFFECT_BLACKBOARD :
2904        !strcmp(effectMode, CameraParameters::EFFECT_AQUA) ?
2905            ANDROID_CONTROL_EFFECT_AQUA :
2906        -1;
2907}
2908
2909int Camera2Client::abModeStringToEnum(const char *abMode) {
2910    return
2911        !strcmp(abMode, CameraParameters::ANTIBANDING_AUTO) ?
2912            ANDROID_CONTROL_AE_ANTIBANDING_AUTO :
2913        !strcmp(abMode, CameraParameters::ANTIBANDING_OFF) ?
2914            ANDROID_CONTROL_AE_ANTIBANDING_OFF :
2915        !strcmp(abMode, CameraParameters::ANTIBANDING_50HZ) ?
2916            ANDROID_CONTROL_AE_ANTIBANDING_50HZ :
2917        !strcmp(abMode, CameraParameters::ANTIBANDING_60HZ) ?
2918            ANDROID_CONTROL_AE_ANTIBANDING_60HZ :
2919        -1;
2920}
2921
2922int Camera2Client::sceneModeStringToEnum(const char *sceneMode) {
2923    return
2924        !strcmp(sceneMode, CameraParameters::SCENE_MODE_AUTO) ?
2925            ANDROID_CONTROL_SCENE_MODE_UNSUPPORTED :
2926        !strcmp(sceneMode, CameraParameters::SCENE_MODE_ACTION) ?
2927            ANDROID_CONTROL_SCENE_MODE_ACTION :
2928        !strcmp(sceneMode, CameraParameters::SCENE_MODE_PORTRAIT) ?
2929            ANDROID_CONTROL_SCENE_MODE_PORTRAIT :
2930        !strcmp(sceneMode, CameraParameters::SCENE_MODE_LANDSCAPE) ?
2931            ANDROID_CONTROL_SCENE_MODE_LANDSCAPE :
2932        !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT) ?
2933            ANDROID_CONTROL_SCENE_MODE_NIGHT :
2934        !strcmp(sceneMode, CameraParameters::SCENE_MODE_NIGHT_PORTRAIT) ?
2935            ANDROID_CONTROL_SCENE_MODE_NIGHT_PORTRAIT :
2936        !strcmp(sceneMode, CameraParameters::SCENE_MODE_THEATRE) ?
2937            ANDROID_CONTROL_SCENE_MODE_THEATRE :
2938        !strcmp(sceneMode, CameraParameters::SCENE_MODE_BEACH) ?
2939            ANDROID_CONTROL_SCENE_MODE_BEACH :
2940        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SNOW) ?
2941            ANDROID_CONTROL_SCENE_MODE_SNOW :
2942        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SUNSET) ?
2943            ANDROID_CONTROL_SCENE_MODE_SUNSET :
2944        !strcmp(sceneMode, CameraParameters::SCENE_MODE_STEADYPHOTO) ?
2945            ANDROID_CONTROL_SCENE_MODE_STEADYPHOTO :
2946        !strcmp(sceneMode, CameraParameters::SCENE_MODE_FIREWORKS) ?
2947            ANDROID_CONTROL_SCENE_MODE_FIREWORKS :
2948        !strcmp(sceneMode, CameraParameters::SCENE_MODE_SPORTS) ?
2949            ANDROID_CONTROL_SCENE_MODE_SPORTS :
2950        !strcmp(sceneMode, CameraParameters::SCENE_MODE_PARTY) ?
2951            ANDROID_CONTROL_SCENE_MODE_PARTY :
2952        !strcmp(sceneMode, CameraParameters::SCENE_MODE_CANDLELIGHT) ?
2953            ANDROID_CONTROL_SCENE_MODE_CANDLELIGHT :
2954        !strcmp(sceneMode, CameraParameters::SCENE_MODE_BARCODE) ?
2955            ANDROID_CONTROL_SCENE_MODE_BARCODE:
2956        -1;
2957}
2958
2959Camera2Client::Parameters::flashMode_t Camera2Client::flashModeStringToEnum(
2960        const char *flashMode) {
2961    return
2962        !strcmp(flashMode, CameraParameters::FLASH_MODE_OFF) ?
2963            Parameters::FLASH_MODE_OFF :
2964        !strcmp(flashMode, CameraParameters::FLASH_MODE_AUTO) ?
2965            Parameters::FLASH_MODE_AUTO :
2966        !strcmp(flashMode, CameraParameters::FLASH_MODE_ON) ?
2967            Parameters::FLASH_MODE_ON :
2968        !strcmp(flashMode, CameraParameters::FLASH_MODE_RED_EYE) ?
2969            Parameters::FLASH_MODE_RED_EYE :
2970        !strcmp(flashMode, CameraParameters::FLASH_MODE_TORCH) ?
2971            Parameters::FLASH_MODE_TORCH :
2972        Parameters::FLASH_MODE_INVALID;
2973}
2974
2975Camera2Client::Parameters::focusMode_t Camera2Client::focusModeStringToEnum(
2976        const char *focusMode) {
2977    return
2978        !strcmp(focusMode, CameraParameters::FOCUS_MODE_AUTO) ?
2979            Parameters::FOCUS_MODE_AUTO :
2980        !strcmp(focusMode, CameraParameters::FOCUS_MODE_INFINITY) ?
2981            Parameters::FOCUS_MODE_INFINITY :
2982        !strcmp(focusMode, CameraParameters::FOCUS_MODE_MACRO) ?
2983            Parameters::FOCUS_MODE_MACRO :
2984        !strcmp(focusMode, CameraParameters::FOCUS_MODE_FIXED) ?
2985            Parameters::FOCUS_MODE_FIXED :
2986        !strcmp(focusMode, CameraParameters::FOCUS_MODE_EDOF) ?
2987            Parameters::FOCUS_MODE_EDOF :
2988        !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO) ?
2989            Parameters::FOCUS_MODE_CONTINUOUS_VIDEO :
2990        !strcmp(focusMode, CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE) ?
2991            Parameters::FOCUS_MODE_CONTINUOUS_PICTURE :
2992        Parameters::FOCUS_MODE_INVALID;
2993}
2994
2995status_t Camera2Client::parseAreas(const char *areasCStr,
2996        Vector<Parameters::Area> *areas) {
2997    static const size_t NUM_FIELDS = 5;
2998    areas->clear();
2999    if (areasCStr == NULL) {
3000        // If no key exists, use default (0,0,0,0,0)
3001        areas->push();
3002        return OK;
3003    }
3004    String8 areasStr(areasCStr);
3005    ssize_t areaStart = areasStr.find("(", 0) + 1;
3006    while (areaStart != 0) {
3007        const char* area = areasStr.string() + areaStart;
3008        char *numEnd;
3009        int vals[NUM_FIELDS];
3010        for (size_t i = 0; i < NUM_FIELDS; i++) {
3011            errno = 0;
3012            vals[i] = strtol(area, &numEnd, 10);
3013            if (errno || numEnd == area) return BAD_VALUE;
3014            area = numEnd + 1;
3015        }
3016        areas->push(Parameters::Area(
3017            vals[0], vals[1], vals[2], vals[3], vals[4]) );
3018        areaStart = areasStr.find("(", areaStart) + 1;
3019    }
3020    return OK;
3021}
3022
3023status_t Camera2Client::validateAreas(const Vector<Parameters::Area> &areas,
3024                                      size_t maxRegions) {
3025    // Definition of valid area can be found in
3026    // include/camera/CameraParameters.h
3027    if (areas.size() == 0) return BAD_VALUE;
3028    if (areas.size() == 1) {
3029        if (areas[0].left == 0 &&
3030                areas[0].top == 0 &&
3031                areas[0].right == 0 &&
3032                areas[0].bottom == 0 &&
3033                areas[0].weight == 0) {
3034            // Single (0,0,0,0,0) entry is always valid (== driver decides)
3035            return OK;
3036        }
3037    }
3038    if (areas.size() > maxRegions) {
3039        ALOGE("%s: Too many areas requested: %d",
3040                __FUNCTION__, areas.size());
3041        return BAD_VALUE;
3042    }
3043
3044    for (Vector<Parameters::Area>::const_iterator a = areas.begin();
3045         a != areas.end(); a++) {
3046        if (a->weight < 1 || a->weight > 1000) return BAD_VALUE;
3047        if (a->left < -1000 || a->left > 1000) return BAD_VALUE;
3048        if (a->top < -1000 || a->top > 1000) return BAD_VALUE;
3049        if (a->right < -1000 || a->right > 1000) return BAD_VALUE;
3050        if (a->bottom < -1000 || a->bottom > 1000) return BAD_VALUE;
3051        if (a->left >= a->right) return BAD_VALUE;
3052        if (a->top >= a->bottom) return BAD_VALUE;
3053    }
3054    return OK;
3055}
3056
3057bool Camera2Client::boolFromString(const char *boolStr) {
3058    return !boolStr ? false :
3059        !strcmp(boolStr, CameraParameters::TRUE) ? true :
3060        false;
3061}
3062
3063int Camera2Client::degToTransform(int degrees, bool mirror) {
3064    if (!mirror) {
3065        if (degrees == 0) return 0;
3066        else if (degrees == 90) return HAL_TRANSFORM_ROT_90;
3067        else if (degrees == 180) return HAL_TRANSFORM_ROT_180;
3068        else if (degrees == 270) return HAL_TRANSFORM_ROT_270;
3069    } else {  // Do mirror (horizontal flip)
3070        if (degrees == 0) {           // FLIP_H and ROT_0
3071            return HAL_TRANSFORM_FLIP_H;
3072        } else if (degrees == 90) {   // FLIP_H and ROT_90
3073            return HAL_TRANSFORM_FLIP_H | HAL_TRANSFORM_ROT_90;
3074        } else if (degrees == 180) {  // FLIP_H and ROT_180
3075            return HAL_TRANSFORM_FLIP_V;
3076        } else if (degrees == 270) {  // FLIP_H and ROT_270
3077            return HAL_TRANSFORM_FLIP_V | HAL_TRANSFORM_ROT_90;
3078        }
3079    }
3080    ALOGE("%s: Bad input: %d", __FUNCTION__, degrees);
3081    return -1;
3082}
3083
3084} // namespace android
3085