1cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala/*
2cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * Copyright (C) 2012 The Android Open Source Project
3cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala *
4cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * Licensed under the Apache License, Version 2.0 (the "License");
5cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * you may not use this file except in compliance with the License.
6cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * You may obtain a copy of the License at
7cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala *
8cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala *      http://www.apache.org/licenses/LICENSE-2.0
9cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala *
10cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * Unless required by applicable law or agreed to in writing, software
11cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * distributed under the License is distributed on an "AS IS" BASIS,
12cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * See the License for the specific language governing permissions and
14cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala * limitations under the License.
15cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala */
16cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
17e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin// #define LOG_NDEBUG 0
18e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin
194bb8118816874c696d9f1adab48490df1da365f7Eino-Ville Talvala#define LOG_TAG "Camera2-Metadata"
20cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala#include <utils/Log.h>
21cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala#include <utils/Errors.h>
22cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
237efa520c76e6a1f6b3146404cc6aca5a8353583aIgor Murashkin#include <camera/CameraMetadata.h>
24e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin#include <binder/Parcel.h>
25cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
26cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalanamespace android {
27cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
28146aed1ec05579b8840a592c3654c641ab36065cZhijun He#define ALIGN_TO(val, alignment) \
29146aed1ec05579b8840a592c3654c641ab36065cZhijun He    (((uintptr_t)(val) + ((alignment) - 1)) & ~((alignment) - 1))
30146aed1ec05579b8840a592c3654c641ab36065cZhijun He
31e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkintypedef Parcel::WritableBlob WritableBlob;
32e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkintypedef Parcel::ReadableBlob ReadableBlob;
33e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
34cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville TalvalaCameraMetadata::CameraMetadata() :
353b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        mBuffer(NULL), mLocked(false) {
36cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
37cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
383b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville TalvalaCameraMetadata::CameraMetadata(size_t entryCapacity, size_t dataCapacity) :
393b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        mLocked(false)
40cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala{
41cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    mBuffer = allocate_camera_metadata(entryCapacity, dataCapacity);
42cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
43cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
443b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville TalvalaCameraMetadata::CameraMetadata(const CameraMetadata &other) :
453b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        mLocked(false) {
46cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    mBuffer = clone_camera_metadata(other.mBuffer);
47cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
48cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
493b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville TalvalaCameraMetadata::CameraMetadata(camera_metadata_t *buffer) :
503b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        mBuffer(NULL), mLocked(false) {
517efa520c76e6a1f6b3146404cc6aca5a8353583aIgor Murashkin    acquire(buffer);
527efa520c76e6a1f6b3146404cc6aca5a8353583aIgor Murashkin}
537efa520c76e6a1f6b3146404cc6aca5a8353583aIgor Murashkin
54cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville TalvalaCameraMetadata &CameraMetadata::operator=(const CameraMetadata &other) {
55cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return operator=(other.mBuffer);
56cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
57cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
58cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville TalvalaCameraMetadata &CameraMetadata::operator=(const camera_metadata_t *buffer) {
593b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
603b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: Assignment to a locked CameraMetadata!", __FUNCTION__);
613b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return *this;
623b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
633b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala
64cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (CC_LIKELY(buffer != mBuffer)) {
65cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        camera_metadata_t *newBuffer = clone_camera_metadata(buffer);
66cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        clear();
67cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        mBuffer = newBuffer;
68cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
69cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return *this;
70cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
71cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
72cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville TalvalaCameraMetadata::~CameraMetadata() {
733b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    mLocked = false;
74cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    clear();
75cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
76cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
773b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvalaconst camera_metadata_t* CameraMetadata::getAndLock() {
783b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    mLocked = true;
793b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return mBuffer;
803b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala}
813b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala
823b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvalastatus_t CameraMetadata::unlock(const camera_metadata_t *buffer) {
833b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (!mLocked) {
843b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: Can't unlock a non-locked CameraMetadata!", __FUNCTION__);
853b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
863b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
873b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (buffer != mBuffer) {
883b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: Can't unlock CameraMetadata with wrong pointer!",
893b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala                __FUNCTION__);
903b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return BAD_VALUE;
913b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
923b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    mLocked = false;
933b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return OK;
943b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala}
953b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala
96cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalacamera_metadata_t* CameraMetadata::release() {
973b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
983b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
993b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return NULL;
1003b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
101cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    camera_metadata_t *released = mBuffer;
102cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    mBuffer = NULL;
103cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return released;
104cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
105cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
106cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalavoid CameraMetadata::clear() {
1073b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1083b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1093b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return;
1103b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
111cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (mBuffer) {
112cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        free_camera_metadata(mBuffer);
113cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        mBuffer = NULL;
114cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
115cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
116cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
117cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalavoid CameraMetadata::acquire(camera_metadata_t *buffer) {
1183b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1193b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1203b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return;
1213b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
122cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    clear();
123cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    mBuffer = buffer;
124e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin
125e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin    ALOGE_IF(validate_camera_metadata_structure(mBuffer, /*size*/NULL) != OK,
126e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin             "%s: Failed to validate metadata structure %p",
127e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin             __FUNCTION__, buffer);
128cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
129cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
130cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalavoid CameraMetadata::acquire(CameraMetadata &other) {
1313b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1323b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1333b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return;
1343b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
135cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    acquire(other.release());
136cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
137cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
138cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::append(const CameraMetadata &other) {
139fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala    return append(other.mBuffer);
140fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala}
141fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala
142fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvalastatus_t CameraMetadata::append(const camera_metadata_t* other) {
1433b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1443b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1453b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
1463b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
147fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala    size_t extraEntries = get_camera_metadata_entry_count(other);
148fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala    size_t extraData = get_camera_metadata_data_count(other);
149fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala    resizeIfNeeded(extraEntries, extraData);
150fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala
151fd6ecdd39bd83ea020f78b425e96310380d66c35Eino-Ville Talvala    return append_camera_metadata(mBuffer, other);
152cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
153cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
154cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalasize_t CameraMetadata::entryCount() const {
155cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return (mBuffer == NULL) ? 0 :
156cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            get_camera_metadata_entry_count(mBuffer);
157cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
158cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
159da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvalabool CameraMetadata::isEmpty() const {
160da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala    return entryCount() == 0;
161da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala}
162da6665cbd06ca58d3357c3002b7366d13e23f152Eino-Ville Talvala
163cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::sort() {
1643b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1653b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1663b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
1673b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
168cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return sort_camera_metadata(mBuffer);
169cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
170cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
171cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::checkType(uint32_t tag, uint8_t expectedType) {
172cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    int tagType = get_camera_metadata_tag_type(tag);
173cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( CC_UNLIKELY(tagType == -1)) {
174cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("Update metadata entry: Unknown tag %d", tag);
175cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return INVALID_OPERATION;
176cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
177cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( CC_UNLIKELY(tagType != expectedType) ) {
178cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("Mismatched tag type when updating entry %s (%d) of type %s; "
179cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                "got type %s data instead ",
180cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_tag_name(tag), tag,
181cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                camera_metadata_type_names[tagType],
182cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                camera_metadata_type_names[expectedType]);
183cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return INVALID_OPERATION;
184cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
185cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return OK;
186cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
187cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
188cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
189cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const int32_t *data, size_t data_count) {
190cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
1913b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
1923b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
1933b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
1943b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
195cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_INT32)) != OK) {
196cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
197cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
1983b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
199cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
200cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
201cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
202cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const uint8_t *data, size_t data_count) {
203cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2043b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2053b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2063b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2073b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
208cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_BYTE)) != OK) {
209cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
210cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2113b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
212cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
213cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
214cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
215cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const float *data, size_t data_count) {
216cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2173b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2183b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2193b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2203b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
221cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_FLOAT)) != OK) {
222cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
223cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2243b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
225cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
226cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
227cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
228cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const int64_t *data, size_t data_count) {
229cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2303b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2313b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2323b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2333b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
234cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_INT64)) != OK) {
235cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
236cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2373b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
238cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
239cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
240cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
241cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const double *data, size_t data_count) {
242cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2433b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2443b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2453b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2463b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
247cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_DOUBLE)) != OK) {
248cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
249cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2503b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
251cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
252cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
253cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
254cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const camera_metadata_rational_t *data, size_t data_count) {
255cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2563b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2573b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2583b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2593b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
260cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_RATIONAL)) != OK) {
261cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
262cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2633b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    return updateImpl(tag, (const void*)data, data_count);
264cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
265cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
266cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::update(uint32_t tag,
267cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        const String8 &string) {
268cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2693b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2703b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2713b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2723b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
273cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if ( (res = checkType(tag, TYPE_BYTE)) != OK) {
274cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
275cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
2767595c47b4842d76dba0fcf26ef3ab98d215efe1eZhijun He    // string.size() doesn't count the null termination character.
2777595c47b4842d76dba0fcf26ef3ab98d215efe1eZhijun He    return updateImpl(tag, (const void*)string.string(), string.size() + 1);
278cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
279cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
2803b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvalastatus_t CameraMetadata::updateImpl(uint32_t tag, const void *data,
281cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t data_count) {
282cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
2833b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
2843b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
2853b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
2863b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
287cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    int type = get_camera_metadata_tag_type(tag);
288cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (type == -1) {
289cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("%s: Tag %d not found", __FUNCTION__, tag);
290cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return BAD_VALUE;
291cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
292cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    size_t data_size = calculate_camera_metadata_entry_data_size(type,
293cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            data_count);
294cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
295cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    res = resizeIfNeeded(1, data_size);
296cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
297cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (res == OK) {
298cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        camera_metadata_entry_t entry;
299cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        res = find_camera_metadata_entry(mBuffer, tag, &entry);
300cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        if (res == NAME_NOT_FOUND) {
301cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            res = add_camera_metadata_entry(mBuffer,
302cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                    tag, data, data_count);
303cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        } else if (res == OK) {
304cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            res = update_camera_metadata_entry(mBuffer,
305cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                    entry.index, data, data_count, NULL);
306cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        }
307cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
308cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
309cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (res != OK) {
310cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("%s: Unable to update metadata entry %s.%s (%x): %s (%d)",
311cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                __FUNCTION__, get_camera_metadata_section_name(tag),
312cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
313cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
314e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin
315e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin    IF_ALOGV() {
316e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin        ALOGE_IF(validate_camera_metadata_structure(mBuffer, /*size*/NULL) !=
317e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin                 OK,
318e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin
319e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin                 "%s: Failed to validate metadata structure after update %p",
320e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin                 __FUNCTION__, mBuffer);
321e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin    }
322e2d1e3d0436aec645739c65e6d3131dd814f40a1Igor Murashkin
323cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return res;
324cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
325cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
326fc42642ab78da5fe25bcbea7a568bf880268a9dcIgor Murashkinbool CameraMetadata::exists(uint32_t tag) const {
327fc42642ab78da5fe25bcbea7a568bf880268a9dcIgor Murashkin    camera_metadata_ro_entry entry;
328fc42642ab78da5fe25bcbea7a568bf880268a9dcIgor Murashkin    return find_camera_metadata_ro_entry(mBuffer, tag, &entry) == 0;
329fc42642ab78da5fe25bcbea7a568bf880268a9dcIgor Murashkin}
330fc42642ab78da5fe25bcbea7a568bf880268a9dcIgor Murashkin
331cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalacamera_metadata_entry_t CameraMetadata::find(uint32_t tag) {
332cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
333cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    camera_metadata_entry entry;
3343b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
3353b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
3363b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        entry.count = 0;
3373b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return entry;
3383b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
339cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    res = find_camera_metadata_entry(mBuffer, tag, &entry);
340cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (CC_UNLIKELY( res != OK )) {
341cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        entry.count = 0;
342cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        entry.data.u8 = NULL;
343cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
344cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return entry;
345cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
346cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
347cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalacamera_metadata_ro_entry_t CameraMetadata::find(uint32_t tag) const {
348cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
349cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    camera_metadata_ro_entry entry;
350cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    res = find_camera_metadata_ro_entry(mBuffer, tag, &entry);
351cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (CC_UNLIKELY( res != OK )) {
352cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        entry.count = 0;
353cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        entry.data.u8 = NULL;
354cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
355cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return entry;
356cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
357cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
358cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::erase(uint32_t tag) {
359cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    camera_metadata_entry_t entry;
360cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    status_t res;
3613b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    if (mLocked) {
3623b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
3633b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala        return INVALID_OPERATION;
3643b53bc9b41c262d22f094406e3751bc5a41ef2efEino-Ville Talvala    }
365cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    res = find_camera_metadata_entry(mBuffer, tag, &entry);
366cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (res == NAME_NOT_FOUND) {
367cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return OK;
368cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    } else if (res != OK) {
369cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("%s: Error looking for entry %s.%s (%x): %s %d",
370cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                __FUNCTION__,
371cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_section_name(tag),
372cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
373cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        return res;
374cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
375cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    res = delete_camera_metadata_entry(mBuffer, entry.index);
376cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (res != OK) {
377cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        ALOGE("%s: Error deleting entry %s.%s (%x): %s %d",
378cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                __FUNCTION__,
379cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_section_name(tag),
380cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                get_camera_metadata_tag_name(tag), tag, strerror(-res), res);
381cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
382cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return res;
383cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
384cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
385cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalavoid CameraMetadata::dump(int fd, int verbosity, int indentation) const {
386cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    dump_indented_camera_metadata(mBuffer, fd, verbosity, indentation);
387cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
388cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
389cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvalastatus_t CameraMetadata::resizeIfNeeded(size_t extraEntries, size_t extraData) {
390cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    if (mBuffer == NULL) {
391cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        mBuffer = allocate_camera_metadata(extraEntries * 2, extraData * 2);
392cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        if (mBuffer == NULL) {
393cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            ALOGE("%s: Can't allocate larger metadata buffer", __FUNCTION__);
394cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            return NO_MEMORY;
395cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        }
396cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    } else {
397cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t currentEntryCount = get_camera_metadata_entry_count(mBuffer);
398cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t currentEntryCap = get_camera_metadata_entry_capacity(mBuffer);
399cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t newEntryCount = currentEntryCount +
400cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                extraEntries;
401cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        newEntryCount = (newEntryCount > currentEntryCap) ?
402cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                newEntryCount * 2 : currentEntryCap;
403cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
404cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t currentDataCount = get_camera_metadata_data_count(mBuffer);
405cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t currentDataCap = get_camera_metadata_data_capacity(mBuffer);
406cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        size_t newDataCount = currentDataCount +
407cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                extraData;
408cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        newDataCount = (newDataCount > currentDataCap) ?
409cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                newDataCount * 2 : currentDataCap;
410cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
411cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        if (newEntryCount > currentEntryCap ||
412cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                newDataCount > currentDataCap) {
413cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            camera_metadata_t *oldBuffer = mBuffer;
414cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            mBuffer = allocate_camera_metadata(newEntryCount,
415cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                    newDataCount);
416cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            if (mBuffer == NULL) {
417cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                ALOGE("%s: Can't allocate larger metadata buffer", __FUNCTION__);
418cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala                return NO_MEMORY;
419cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            }
420cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            append_camera_metadata(mBuffer, oldBuffer);
421cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala            free_camera_metadata(oldBuffer);
422cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala        }
423cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    }
424cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala    return OK;
425cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}
426cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala
427e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkinstatus_t CameraMetadata::readFromParcel(const Parcel& data,
428e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin                                        camera_metadata_t** out) {
429e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
430e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    status_t err = OK;
431e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
432e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    camera_metadata_t* metadata = NULL;
433e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
434e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (out) {
435e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        *out = NULL;
436e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
437e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
438146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // See CameraMetadata::writeToParcel for parcel data layout diagram and explanation.
439146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // arg0 = blobSize (int32)
440146aed1ec05579b8840a592c3654c641ab36065cZhijun He    int32_t blobSizeTmp = -1;
441146aed1ec05579b8840a592c3654c641ab36065cZhijun He    if ((err = data.readInt32(&blobSizeTmp)) != OK) {
442e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: Failed to read metadata size (error %d %s)",
443e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin              __FUNCTION__, err, strerror(-err));
444e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return err;
445e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
446146aed1ec05579b8840a592c3654c641ab36065cZhijun He    const size_t blobSize = static_cast<size_t>(blobSizeTmp);
447146aed1ec05579b8840a592c3654c641ab36065cZhijun He    const size_t alignment = get_camera_metadata_alignment();
448e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
449146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // Special case: zero blob size means zero sized (NULL) metadata.
450146aed1ec05579b8840a592c3654c641ab36065cZhijun He    if (blobSize == 0) {
451e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGV("%s: Read 0-sized metadata", __FUNCTION__);
452e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return OK;
453e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
454e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
455146aed1ec05579b8840a592c3654c641ab36065cZhijun He    if (blobSize <= alignment) {
456146aed1ec05579b8840a592c3654c641ab36065cZhijun He        ALOGE("%s: metadata blob is malformed, blobSize(%zu) should be larger than alignment(%zu)",
457146aed1ec05579b8840a592c3654c641ab36065cZhijun He                __FUNCTION__, blobSize, alignment);
458146aed1ec05579b8840a592c3654c641ab36065cZhijun He        return BAD_VALUE;
459146aed1ec05579b8840a592c3654c641ab36065cZhijun He    }
460146aed1ec05579b8840a592c3654c641ab36065cZhijun He
461146aed1ec05579b8840a592c3654c641ab36065cZhijun He    const size_t metadataSize = blobSize - alignment;
462146aed1ec05579b8840a592c3654c641ab36065cZhijun He
463146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // NOTE: this doesn't make sense to me. shouldn't the blob
464e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    // know how big it is? why do we have to specify the size
465e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    // to Parcel::readBlob ?
466e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    ReadableBlob blob;
467e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    // arg1 = metadata (blob)
468e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    do {
469146aed1ec05579b8840a592c3654c641ab36065cZhijun He        if ((err = data.readBlob(blobSize, &blob)) != OK) {
470146aed1ec05579b8840a592c3654c641ab36065cZhijun He            ALOGE("%s: Failed to read metadata blob (sized %zu). Possible "
471e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin                  " serialization bug. Error %d %s",
472146aed1ec05579b8840a592c3654c641ab36065cZhijun He                  __FUNCTION__, blobSize, err, strerror(-err));
473e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            break;
474e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        }
475e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
476146aed1ec05579b8840a592c3654c641ab36065cZhijun He        // arg2 = offset (blob)
477146aed1ec05579b8840a592c3654c641ab36065cZhijun He        // Must be after blob since we don't know offset until after writeBlob.
478146aed1ec05579b8840a592c3654c641ab36065cZhijun He        int32_t offsetTmp;
479146aed1ec05579b8840a592c3654c641ab36065cZhijun He        if ((err = data.readInt32(&offsetTmp)) != OK) {
480146aed1ec05579b8840a592c3654c641ab36065cZhijun He            ALOGE("%s: Failed to read metadata offsetTmp (error %d %s)",
481146aed1ec05579b8840a592c3654c641ab36065cZhijun He                  __FUNCTION__, err, strerror(-err));
482146aed1ec05579b8840a592c3654c641ab36065cZhijun He            break;
483146aed1ec05579b8840a592c3654c641ab36065cZhijun He        }
484146aed1ec05579b8840a592c3654c641ab36065cZhijun He        const size_t offset = static_cast<size_t>(offsetTmp);
485146aed1ec05579b8840a592c3654c641ab36065cZhijun He        if (offset >= alignment) {
486146aed1ec05579b8840a592c3654c641ab36065cZhijun He            ALOGE("%s: metadata offset(%zu) should be less than alignment(%zu)",
487146aed1ec05579b8840a592c3654c641ab36065cZhijun He                    __FUNCTION__, blobSize, alignment);
488146aed1ec05579b8840a592c3654c641ab36065cZhijun He            err = BAD_VALUE;
489146aed1ec05579b8840a592c3654c641ab36065cZhijun He            break;
490146aed1ec05579b8840a592c3654c641ab36065cZhijun He        }
491146aed1ec05579b8840a592c3654c641ab36065cZhijun He
492146aed1ec05579b8840a592c3654c641ab36065cZhijun He        const uintptr_t metadataStart = reinterpret_cast<uintptr_t>(blob.data()) + offset;
493146aed1ec05579b8840a592c3654c641ab36065cZhijun He        const camera_metadata_t* tmp =
494146aed1ec05579b8840a592c3654c641ab36065cZhijun He                       reinterpret_cast<const camera_metadata_t*>(metadataStart);
495146aed1ec05579b8840a592c3654c641ab36065cZhijun He        ALOGV("%s: alignment is: %zu, metadata start: %p, offset: %zu",
496146aed1ec05579b8840a592c3654c641ab36065cZhijun He                __FUNCTION__, alignment, tmp, offset);
497e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        metadata = allocate_copy_camera_metadata_checked(tmp, metadataSize);
498e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        if (metadata == NULL) {
499e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            // We consider that allocation only fails if the validation
500e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            // also failed, therefore the readFromParcel was a failure.
501146aed1ec05579b8840a592c3654c641ab36065cZhijun He            ALOGE("%s: metadata allocation and copy failed", __FUNCTION__);
502e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            err = BAD_VALUE;
503e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        }
504e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    } while(0);
505e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    blob.release();
506e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
507e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (out) {
508e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGV("%s: Set out metadata to %p", __FUNCTION__, metadata);
509e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        *out = metadata;
510e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    } else if (metadata != NULL) {
511e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGV("%s: Freed camera metadata at %p", __FUNCTION__, metadata);
512e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        free_camera_metadata(metadata);
513e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
514e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
515e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    return err;
516e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin}
517e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
518e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkinstatus_t CameraMetadata::writeToParcel(Parcel& data,
519e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin                                       const camera_metadata_t* metadata) {
520e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    status_t res = OK;
521e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
522146aed1ec05579b8840a592c3654c641ab36065cZhijun He    /**
523146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * Below is the camera metadata parcel layout:
524146aed1ec05579b8840a592c3654c641ab36065cZhijun He     *
525146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |--------------------------------------------|
526146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |             arg0: blobSize                 |
527146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |              (length = 4)                  |
528146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |--------------------------------------------|<--Skip the rest if blobSize == 0.
529146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                            |
530146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                            |
531146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |              arg1: blob                    |
532146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * | (length = variable, see arg1 layout below) |
533146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                            |
534146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                            |
535146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |--------------------------------------------|
536146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |              arg2: offset                  |
537146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |              (length = 4)                  |
538146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |--------------------------------------------|
539146aed1ec05579b8840a592c3654c641ab36065cZhijun He     */
540146aed1ec05579b8840a592c3654c641ab36065cZhijun He
541146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // arg0 = blobSize (int32)
542e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (metadata == NULL) {
543146aed1ec05579b8840a592c3654c641ab36065cZhijun He        // Write zero blobSize for null metadata.
544e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return data.writeInt32(0);
545e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
546e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
547146aed1ec05579b8840a592c3654c641ab36065cZhijun He    /**
548146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * Always make the blob size sufficiently larger, as we need put alignment
549146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * padding and metadata into the blob. Since we don't know the alignment
550146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * offset before writeBlob. Then write the metadata to aligned offset.
551146aed1ec05579b8840a592c3654c641ab36065cZhijun He     */
552e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    const size_t metadataSize = get_camera_metadata_compact_size(metadata);
553146aed1ec05579b8840a592c3654c641ab36065cZhijun He    const size_t alignment = get_camera_metadata_alignment();
554146aed1ec05579b8840a592c3654c641ab36065cZhijun He    const size_t blobSize = metadataSize + alignment;
555146aed1ec05579b8840a592c3654c641ab36065cZhijun He    res = data.writeInt32(static_cast<int32_t>(blobSize));
556e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (res != OK) {
557e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return res;
558e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
559e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
560146aed1ec05579b8840a592c3654c641ab36065cZhijun He    size_t offset = 0;
561146aed1ec05579b8840a592c3654c641ab36065cZhijun He    /**
562146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * arg1 = metadata (blob).
563146aed1ec05579b8840a592c3654c641ab36065cZhijun He     *
564146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * The blob size is the sum of front padding size, metadata size and back padding
565146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * size, which is equal to metadataSize + alignment.
566146aed1ec05579b8840a592c3654c641ab36065cZhijun He     *
567146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * The blob layout is:
568146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |------------------------------------|<----Start address of the blob (unaligned).
569146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |           front padding            |
570146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |          (size = offset)           |
571146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |------------------------------------|<----Aligned start address of metadata.
572146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                    |
573146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                    |
574146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |            metadata                |
575146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |       (size = metadataSize)        |
576146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                    |
577146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |                                    |
578146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |------------------------------------|
579146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |           back padding             |
580146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |     (size = alignment - offset)    |
581146aed1ec05579b8840a592c3654c641ab36065cZhijun He     * |------------------------------------|<----End address of blob.
582146aed1ec05579b8840a592c3654c641ab36065cZhijun He     *                                            (Blob start address + blob size).
583146aed1ec05579b8840a592c3654c641ab36065cZhijun He     */
584e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    WritableBlob blob;
585e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    do {
586146aed1ec05579b8840a592c3654c641ab36065cZhijun He        res = data.writeBlob(blobSize, &blob);
587e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        if (res != OK) {
588e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            break;
589e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        }
590146aed1ec05579b8840a592c3654c641ab36065cZhijun He        const uintptr_t metadataStart = ALIGN_TO(blob.data(), alignment);
591146aed1ec05579b8840a592c3654c641ab36065cZhijun He        offset = metadataStart - reinterpret_cast<uintptr_t>(blob.data());
592146aed1ec05579b8840a592c3654c641ab36065cZhijun He        ALOGV("%s: alignment is: %zu, metadata start: %p, offset: %zu",
5931a93f0cbb99fc5a59c92bd913f29409022ae236dMark Salyzyn                __FUNCTION__, alignment,
5941a93f0cbb99fc5a59c92bd913f29409022ae236dMark Salyzyn                reinterpret_cast<const void *>(metadataStart), offset);
595146aed1ec05579b8840a592c3654c641ab36065cZhijun He        copy_camera_metadata(reinterpret_cast<void*>(metadataStart), metadataSize, metadata);
596e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
597e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        // Not too big of a problem since receiving side does hard validation
598e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        // Don't check the size since the compact size could be larger
599e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        if (validate_camera_metadata_structure(metadata, /*size*/NULL) != OK) {
600e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin            ALOGW("%s: Failed to validate metadata %p before writing blob",
601e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin                   __FUNCTION__, metadata);
602e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        }
603e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
604e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    } while(false);
605e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    blob.release();
606e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
607146aed1ec05579b8840a592c3654c641ab36065cZhijun He    // arg2 = offset (int32)
608146aed1ec05579b8840a592c3654c641ab36065cZhijun He    res = data.writeInt32(static_cast<int32_t>(offset));
609146aed1ec05579b8840a592c3654c641ab36065cZhijun He
610e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    return res;
611e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin}
612e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
613e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkinstatus_t CameraMetadata::readFromParcel(Parcel *parcel) {
614e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
615e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    ALOGV("%s: parcel = %p", __FUNCTION__, parcel);
616e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
617e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    status_t res = OK;
618e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
619e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (parcel == NULL) {
620e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: parcel is null", __FUNCTION__);
621e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return BAD_VALUE;
622e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
623e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
624e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (mLocked) {
625e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
626e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return INVALID_OPERATION;
627e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
628e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
629e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    camera_metadata *buffer = NULL;
630e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    // TODO: reading should return a status code, in case validation fails
631e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    res = CameraMetadata::readFromParcel(*parcel, &buffer);
632e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
633e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (res != NO_ERROR) {
634e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: Failed to read from parcel. Metadata is unchanged.",
635e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin              __FUNCTION__);
636e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return res;
637e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
638e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
639e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    clear();
640e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    mBuffer = buffer;
641e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
642e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    return OK;
643e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin}
644e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
645e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkinstatus_t CameraMetadata::writeToParcel(Parcel *parcel) const {
646e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
647e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    ALOGV("%s: parcel = %p", __FUNCTION__, parcel);
648e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
649e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (parcel == NULL) {
650e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: parcel is null", __FUNCTION__);
651e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return BAD_VALUE;
652e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
653e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
654e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    return CameraMetadata::writeToParcel(*parcel, mBuffer);
655e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin}
656e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
657e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkinvoid CameraMetadata::swap(CameraMetadata& other) {
658e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    if (mLocked) {
659e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: CameraMetadata is locked", __FUNCTION__);
660e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return;
661e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    } else if (other.mLocked) {
662e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        ALOGE("%s: Other CameraMetadata is locked", __FUNCTION__);
663e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin        return;
664e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    }
665e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
666e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    camera_metadata* thisBuf = mBuffer;
667e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    camera_metadata* otherBuf = other.mBuffer;
668e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
669e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    other.mBuffer = thisBuf;
670e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin    mBuffer = otherBuf;
671e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin}
672e7ee7637747371635a85fedd24d2190bb1f38651Igor Murashkin
673cab96a4a7a2900fa991ab77ae45ba8d4be97e054Eino-Ville Talvala}; // namespace android
674