Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 1f5a1790 authored by Android Build Coastguard Worker's avatar Android Build Coastguard Worker
Browse files

Snap for 7595830 from 2a7630de to sc-release

Change-Id: I7419070b06f8a457af9ea1531b8444d4209dc405
parents e3e71d93 2a7630de
Loading
Loading
Loading
Loading
+1 −0
Original line number Original line Diff line number Diff line
@@ -83,6 +83,7 @@ cc_library_shared {
        "device3/Camera3OutputStreamInterface.cpp",
        "device3/Camera3OutputStreamInterface.cpp",
        "device3/Camera3OutputUtils.cpp",
        "device3/Camera3OutputUtils.cpp",
        "device3/Camera3DeviceInjectionMethods.cpp",
        "device3/Camera3DeviceInjectionMethods.cpp",
        "device3/UHRCropAndMeteringRegionMapper.cpp",
        "gui/RingBufferConsumer.cpp",
        "gui/RingBufferConsumer.cpp",
        "hidl/AidlCameraDeviceCallbacks.cpp",
        "hidl/AidlCameraDeviceCallbacks.cpp",
        "hidl/AidlCameraServiceListener.cpp",
        "hidl/AidlCameraServiceListener.cpp",
+34 −1
Original line number Original line Diff line number Diff line
@@ -171,6 +171,13 @@ status_t Camera3Device::initialize(sp<CameraProviderManager> manager, const Stri
            mZoomRatioMappers[physicalId] = ZoomRatioMapper(
            mZoomRatioMappers[physicalId] = ZoomRatioMapper(
                    &mPhysicalDeviceInfoMap[physicalId],
                    &mPhysicalDeviceInfoMap[physicalId],
                    mSupportNativeZoomRatio, usePrecorrectArray);
                    mSupportNativeZoomRatio, usePrecorrectArray);

            if (SessionConfigurationUtils::isUltraHighResolutionSensor(
                    mPhysicalDeviceInfoMap[physicalId])) {
                mUHRCropAndMeteringRegionMappers[physicalId] =
                        UHRCropAndMeteringRegionMapper(mPhysicalDeviceInfoMap[physicalId],
                                usePrecorrectArray);
            }
        }
        }
    }
    }


@@ -348,6 +355,11 @@ status_t Camera3Device::initializeCommonLocked() {
    mZoomRatioMappers[mId.c_str()] = ZoomRatioMapper(&mDeviceInfo,
    mZoomRatioMappers[mId.c_str()] = ZoomRatioMapper(&mDeviceInfo,
            mSupportNativeZoomRatio, usePrecorrectArray);
            mSupportNativeZoomRatio, usePrecorrectArray);


    if (SessionConfigurationUtils::isUltraHighResolutionSensor(mDeviceInfo)) {
        mUHRCropAndMeteringRegionMappers[mId.c_str()] =
                UHRCropAndMeteringRegionMapper(mDeviceInfo, usePrecorrectArray);
    }

    if (RotateAndCropMapper::isNeeded(&mDeviceInfo)) {
    if (RotateAndCropMapper::isNeeded(&mDeviceInfo)) {
        mRotateAndCropMappers.emplace(mId.c_str(), &mDeviceInfo);
        mRotateAndCropMappers.emplace(mId.c_str(), &mDeviceInfo);
    }
    }
@@ -4815,10 +4827,31 @@ status_t Camera3Device::RequestThread::prepareHalRequests() {
            }
            }


            {
            {
                // Correct metadata regions for distortion correction if enabled
                sp<Camera3Device> parent = mParent.promote();
                sp<Camera3Device> parent = mParent.promote();
                if (parent != nullptr) {
                if (parent != nullptr) {
                    List<PhysicalCameraSettings>::iterator it;
                    List<PhysicalCameraSettings>::iterator it;
                    for (it = captureRequest->mSettingsList.begin();
                            it != captureRequest->mSettingsList.end(); it++) {
                        if (parent->mUHRCropAndMeteringRegionMappers.find(it->cameraId) ==
                                parent->mUHRCropAndMeteringRegionMappers.end()) {
                            continue;
                        }

                        if (!captureRequest->mUHRCropAndMeteringRegionsUpdated) {
                            res = parent->mUHRCropAndMeteringRegionMappers[it->cameraId].
                                    updateCaptureRequest(&(it->metadata));
                            if (res != OK) {
                                SET_ERR("RequestThread: Unable to correct capture requests "
                                        "for scaler crop region and metering regions for request "
                                        "%d: %s (%d)", halRequest->frame_number, strerror(-res),
                                        res);
                                return INVALID_OPERATION;
                            }
                            captureRequest->mUHRCropAndMeteringRegionsUpdated = true;
                        }
                    }

                    // Correct metadata regions for distortion correction if enabled
                    for (it = captureRequest->mSettingsList.begin();
                    for (it = captureRequest->mSettingsList.begin();
                            it != captureRequest->mSettingsList.end(); it++) {
                            it != captureRequest->mSettingsList.end(); it++) {
                        if (parent->mDistortionMappers.find(it->cameraId) ==
                        if (parent->mDistortionMappers.find(it->cameraId) ==
+10 −0
Original line number Original line Diff line number Diff line
@@ -50,6 +50,7 @@
#include "device3/DistortionMapper.h"
#include "device3/DistortionMapper.h"
#include "device3/ZoomRatioMapper.h"
#include "device3/ZoomRatioMapper.h"
#include "device3/RotateAndCropMapper.h"
#include "device3/RotateAndCropMapper.h"
#include "device3/UHRCropAndMeteringRegionMapper.h"
#include "device3/InFlightRequest.h"
#include "device3/InFlightRequest.h"
#include "device3/Camera3OutputInterface.h"
#include "device3/Camera3OutputInterface.h"
#include "device3/Camera3OfflineSession.h"
#include "device3/Camera3OfflineSession.h"
@@ -589,6 +590,9 @@ class Camera3Device :
        bool                                mRotationAndCropUpdated = false;
        bool                                mRotationAndCropUpdated = false;
        // Whether this capture request's zoom ratio update has been done.
        // Whether this capture request's zoom ratio update has been done.
        bool                                mZoomRatioUpdated = false;
        bool                                mZoomRatioUpdated = false;
        // Whether this max resolution capture request's  crop / metering region update has been
        // done.
        bool                                mUHRCropAndMeteringRegionsUpdated = false;
    };
    };
    typedef List<sp<CaptureRequest> > RequestList;
    typedef List<sp<CaptureRequest> > RequestList;


@@ -1223,6 +1227,12 @@ class Camera3Device :
     */
     */
    std::unordered_map<std::string, camera3::ZoomRatioMapper> mZoomRatioMappers;
    std::unordered_map<std::string, camera3::ZoomRatioMapper> mZoomRatioMappers;


    /**
     * UHR request crop / metering region mapper support
     */
    std::unordered_map<std::string, camera3::UHRCropAndMeteringRegionMapper>
            mUHRCropAndMeteringRegionMappers;

    /**
    /**
     * RotateAndCrop mapper support
     * RotateAndCrop mapper support
     */
     */
+168 −0
Original line number Original line Diff line number Diff line
/*
 * Copyright (C) 2021 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#define LOG_TAG "Camera3-UHRCropAndMeteringRegionMapper"
#define ATRACE_TAG ATRACE_TAG_CAMERA
//#define LOG_NDEBUG 0

#include <algorithm>
#include <cmath>

#include "device3/UHRCropAndMeteringRegionMapper.h"
#include "utils/SessionConfigurationUtils.h"

namespace android {

namespace camera3 {
// For Capture request
// metering region -> {fwk private key for metering region set, true}
static std::unordered_map<uint32_t, std::pair<uint32_t, uint32_t>> kMeteringRegionsToCorrect = {
    {ANDROID_CONTROL_AF_REGIONS,
        {ANDROID_CONTROL_AF_REGIONS_SET, ANDROID_CONTROL_AF_REGIONS_SET_TRUE}},
    {ANDROID_CONTROL_AE_REGIONS,
        {ANDROID_CONTROL_AE_REGIONS_SET, ANDROID_CONTROL_AE_REGIONS_SET_TRUE}},
    {ANDROID_CONTROL_AWB_REGIONS,
        {ANDROID_CONTROL_AWB_REGIONS_SET,  ANDROID_CONTROL_AWB_REGIONS_SET_TRUE}}
};

UHRCropAndMeteringRegionMapper::UHRCropAndMeteringRegionMapper(const CameraMetadata &deviceInfo,
        bool usePreCorrectedArray) {

    if (usePreCorrectedArray) {
        if (!SessionConfigurationUtils::getArrayWidthAndHeight(&deviceInfo,
                ANDROID_SENSOR_INFO_PRE_CORRECTION_ACTIVE_ARRAY_SIZE, &mArrayWidth,
                &mArrayHeight)) {
            ALOGE("%s: Couldn't get pre correction active array size", __FUNCTION__);
            return;
        }
        if (!SessionConfigurationUtils::getArrayWidthAndHeight(&deviceInfo,
                ANDROID_SENSOR_INFO_PRE_CORRECTION_ACTIVE_ARRAY_SIZE_MAXIMUM_RESOLUTION,
                &mArrayWidthMaximumResolution, &mArrayHeightMaximumResolution)) {
            ALOGE("%s: Couldn't get maximum resolution pre correction active array size",
                    __FUNCTION__);
            return;
        }
    } else {
        if (!SessionConfigurationUtils::getArrayWidthAndHeight(&deviceInfo,
                ANDROID_SENSOR_INFO_ACTIVE_ARRAY_SIZE, &mArrayWidth,
                &mArrayHeight)) {
            ALOGE("%s: Couldn't get active array size", __FUNCTION__);
            return;
        }
        if (!SessionConfigurationUtils::getArrayWidthAndHeight(&deviceInfo,
                ANDROID_SENSOR_INFO_ACTIVE_ARRAY_SIZE_MAXIMUM_RESOLUTION,
                &mArrayWidthMaximumResolution, &mArrayHeightMaximumResolution)) {
            ALOGE("%s: Couldn't get maximum resolution active array size", __FUNCTION__);
            return;
        }

    }

    mIsValid = true;

    ALOGV("%s: array size: %d x %d, full res array size: %d x %d,",
            __FUNCTION__, mArrayWidth, mArrayHeight, mArrayWidthMaximumResolution,
            mArrayHeightMaximumResolution);
}

void UHRCropAndMeteringRegionMapper::fixMeteringRegionsIfNeeded(CameraMetadata *request) {
    if (request == nullptr) {
      ALOGE("%s request is nullptr, can't fix crop region", __FUNCTION__);
      return;
    }
    for (const auto &entry : kMeteringRegionsToCorrect) {
        // Check if the metering region Set key is set to TRUE, we don't
        // need to correct the metering regions.
        camera_metadata_entry meteringRegionsSetEntry =
                request->find(entry.second.first);
        if (meteringRegionsSetEntry.count == 1 &&
                meteringRegionsSetEntry.data.u8[0] == entry.second.second) {
            // metering region set by client, doesn't need to be fixed.
            continue;
        }
        camera_metadata_entry meteringRegionEntry = request->find(entry.first);
        if (meteringRegionEntry.count % 5 != 0) {
            ALOGE("%s: Metering region entry for tag %d does not have a valid number of entries, "
                    "skipping", __FUNCTION__, (int)entry.first);
            continue;
        }
        for (size_t j = 0; j < meteringRegionEntry.count; j += 5) {
            int32_t *meteringRegionStart = meteringRegionEntry.data.i32 + j;
            meteringRegionStart[0] = 0;
            meteringRegionStart[1] = 0;
            meteringRegionStart[2] = mArrayWidthMaximumResolution;
            meteringRegionStart[3] = mArrayHeightMaximumResolution;
        }
    }
}

void UHRCropAndMeteringRegionMapper::fixCropRegionsIfNeeded(CameraMetadata *request) {
    if (request == nullptr) {
      ALOGE("%s request is nullptr, can't fix crop region", __FUNCTION__);
      return;
    }
    // Check if the scalerCropRegionSet key is set to TRUE, we don't
    // need to correct the crop region.
    camera_metadata_entry cropRegionSetEntry =
            request->find(ANDROID_SCALER_CROP_REGION_SET);
    if (cropRegionSetEntry.count == 1 &&
        cropRegionSetEntry.data.u8[0] == ANDROID_SCALER_CROP_REGION_SET_TRUE) {
        // crop regions set by client, doesn't need to be fixed.
        return;
    }
    camera_metadata_entry_t cropRegionEntry = request->find(ANDROID_SCALER_CROP_REGION);
    if (cropRegionEntry.count == 4) {
        cropRegionEntry.data.i32[0] = 0;
        cropRegionEntry.data.i32[1] = 0;
        cropRegionEntry.data.i32[2] = mArrayWidthMaximumResolution;
        cropRegionEntry.data.i32[3] = mArrayHeightMaximumResolution;
    }
}

status_t UHRCropAndMeteringRegionMapper::updateCaptureRequest(CameraMetadata* request) {
    if (request == nullptr) {
        ALOGE("%s Invalid request, request is nullptr", __FUNCTION__);
        return BAD_VALUE;
    }
    if (!mIsValid) {
        ALOGE("%s UHRCropAndMeteringRegionMapper didn't initialize correctly", __FUNCTION__);
        return INVALID_OPERATION;
    }

    camera_metadata_entry sensorPixelModeEntry = request->find(ANDROID_SENSOR_PIXEL_MODE);

    // Check if this is max resolution capture, if not, we don't need to do
    // anything.
    if (sensorPixelModeEntry.count != 0) {
        int32_t sensorPixelMode = sensorPixelModeEntry.data.u8[0];
        if (sensorPixelMode != ANDROID_SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION) {
            // Correction not needed for default mode requests.
           return OK;
        }
    } else {
        // sensor pixel mode not set -> default sensor pixel mode request, which
        // doesn't need correction.
        return OK;
    }

    fixCropRegionsIfNeeded(request);
    fixMeteringRegionsIfNeeded(request);
    return OK;
}

} // namespace camera3

} // namespace android
+59 −0
Original line number Original line Diff line number Diff line
/*
 * Copyright (C) 2021 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef ANDROID_SERVERS_UHRCROP_REGIONS_MAPPER_H
#define ANDROID_SERVERS_UHRCROP_REGIONS_MAPPER_H

#include <utils/Errors.h>
#include <array>

#include "camera/CameraMetadata.h"

namespace android {

namespace camera3 {

/**
 * Utilities to transform SCALER_CROP_REGION and metering regions for ultra high
 * resolution sensors.
 */
class UHRCropAndMeteringRegionMapper {
 public:
    UHRCropAndMeteringRegionMapper() = default;
    UHRCropAndMeteringRegionMapper(const CameraMetadata &deviceInfo, bool usePreCorrectionArray);

    /**
     * Adjust capture request assuming rotate and crop AUTO is enabled
     */
    status_t updateCaptureRequest(CameraMetadata *request);

 private:

    void fixCropRegionsIfNeeded(CameraMetadata *request);
    void fixMeteringRegionsIfNeeded(CameraMetadata *request);

    int32_t mArrayWidth = 0;
    int32_t mArrayHeight = 0;
    int32_t mArrayWidthMaximumResolution = 0;
    int32_t mArrayHeightMaximumResolution = 0;
    bool mIsValid = false;
}; // class UHRCropAndMeteringRegionMapper

} // namespace camera3

} // namespace android

#endif
Loading