1. Camera Open 流程源碼分析

        共 13633字,需瀏覽 28分鐘

         ·

        2020-11-27 14:51

        和你一起終身學(xué)習(xí),這里是程序員Android

        經(jīng)典好文推薦,通過閱讀本文,您將收獲以下知識點(diǎn):

        1.app層 MainActivity.java CameraManager 可以直接調(diào)用 其openCamera 方法

        getCameraIdList 用來存儲可用Camera設(shè)備 list, openCamera 成功后會調(diào)用CameraDevice.StateCallback#onOpened,

        然后會創(chuàng)建Session CameraDevice#createCaptureSession 以及拍照CameraDevice#createCaptureRequest等等。

        public class MainActivity extends AppCompatActivity {

        protected void onCreate(@Nullable Bundle savedInstanceState) {

        ... ...
        //
        CameraManager mCameraManager.openCamera(mCameraId, mStateCallback, mBackgroundHandler);
        ... ...

        }

        2.CameraManager.java
        (frameworks\base\core\java\android\hardware\camera2)

        CameraManager 會根據(jù)傳遞過來的參數(shù)不同,調(diào)用不同的Opencamera 方法。


        @RequiresPermission(android.Manifest.permission.CAMERA)
        public void openCamera(@NonNull String cameraId,
        @NonNull final CameraDevice.StateCallback callback, @Nullable Handler handler)
        throws CameraAccessException {

        openCameraForUid(cameraId, callback, CameraDeviceImpl.checkAndWrapHandler(handler),
        USE_CALLING_UID);
        }
        // CameraDeviceImpl.checkAndWrapHandler 會將 Handler 封裝成Executor 類型
        public static Executor checkAndWrapHandler(Handler handler) {
        return new CameraHandlerExecutor(checkHandler(handler));
        }

        @RequiresPermission(android.Manifest.permission.CAMERA)
        public void openCamera(@NonNull String cameraId,
        @NonNull @CallbackExecutor Executor executor,
        @NonNull final CameraDevice.StateCallback callback)
        throws CameraAccessException {

        openCameraForUid(cameraId, callback, executor, USE_CALLING_UID);
        }


        從代碼中看,openCamera 參數(shù)主要區(qū)別是 CallbackExecutor 、Handler 這兩個,最終都會走到 openCameraForUid 方法。
        openCameraForUid 主要是 根據(jù) Camera id 打開一個Camera 連接。

            public void openCameraForUid(@NonNull String cameraId,
        @NonNull final CameraDevice.StateCallback callback, @NonNull Executor executor,
        int clientUid)
        throws CameraAccessException {
        //
        openCameraDeviceUserAsync(cameraId, callback, executor, clientUid);

        }


        openCameraForUid 會調(diào)用 openCameraDeviceUserAsync 方法去幫助opencamera 連接的創(chuàng)建

            private CameraDevice openCameraDeviceUserAsync(String cameraId,
        CameraDevice.StateCallback callback, Executor executor, final int uid)
        throws CameraAccessException {
        // 獲取 特定camera的特性
        CameraCharacteristics characteristics = getCameraCharacteristics(cameraId);

        android.hardware.camera2.impl.CameraDeviceImpl deviceImpl = new CameraDeviceImpl();
        ICameraDeviceCallbacks callbacks = deviceImpl.getCallbacks()

        if (supportsCamera2ApiLocked(cameraId)) {
        // Use cameraservice's cameradeviceclient implementation for HAL3.2+ devices
        ICameraService cameraService = CameraManagerGlobal.get().getCameraService();

        cameraService.connectDevice(callbacks, cameraId,mContext.getOpPackageName(), uid);

        }else{
        ... ...
        }
        // TODO: factor out callback to be non-nested, then move setter to constructor
        // For now, calling setRemoteDevice will fire initial
        // onOpened/onUnconfigured callbacks.
        // This function call may post onDisconnected and throw CAMERA_DISCONNECTED if
        // cameraUser dies during setup.
        deviceImpl.setRemoteDevice(cameraUser);

        }

        cameraService是通過Binder 繼承 ICameraServiceListener.Stub

            private static final class CameraManagerGlobal extends ICameraServiceListener.Stub
        implements IBinder.DeathRecipient {
        // This must match the ICameraService definition
        private static final String CAMERA_SERVICE_BINDER_NAME = "media.camera";

        public ICameraService getCameraService() {

        synchronized(mLock) {
        //
        connectCameraServiceLocked();
        return mCameraService;
        }
        }

        private void connectCameraServiceLocked() {
        IBinder cameraServiceBinder = ServiceManager.getService(CAMERA_SERVICE_BINDER_NAME);

        ICameraService cameraService = ICameraService.Stub.asInterface(cameraServiceBinder);

        for (CameraStatus c : cameraStatuses) {
        onStatusChangedLocked(c.status, c.cameraId);
        }
        mCameraService = cameraService;
        }
        }

        3.CameraService.cpp
        (frameworks\av\services\camera\libcameraservice)

        cameraService.connectDevice 通過AIDL 到用到 CameraService.cpp 中的connectDevice 方法。

        Status CameraService::connectDevice(
        const sp<hardware::camera2::ICameraDeviceCallbacks>& cameraCb,
        const String16& cameraId,
        const String16& clientPackageName,
        int clientUid,
        /*out*/
        sp<hardware::camera2::ICameraDeviceUser>* device) {
        //調(diào)用connectHelper 方法
        ret = connectHelper<hardware::camera2::ICameraDeviceCallbacks,CameraDeviceClient>(cameraCb, id,
        /*api1CameraId*/-1,
        CAMERA_HAL_API_VERSION_UNSPECIFIED, clientPackageNameAdj,
        clientUid, USE_CALLING_PID, API_2, /*shimUpdateOnly*/ false, /*out*/client);

        }

        connectDevice 會調(diào)用到 connectHelper 方法


        Status CameraService::connectHelper(){

        // 閃光燈進(jìn)入預(yù)準(zhǔn)備階段
        mFlashlight->prepareDeviceOpen(cameraId);

        //獲取當(dāng)前設(shè)備的Version
        int deviceVersion = getDeviceVersion(cameraId, /*out*/&facing);


        // 初始化CameraproviderManager
        err = client->initialize(mCameraProviderManager, mMonitorTags);

        }

        4.CameraProviderManager.cpp
        (frameworks\av\services\camera\libcameraservice\common)


        status_t CameraProviderManager::initialize(wp<CameraProviderManager::StatusListener> listener,
        ServiceInteractionProxy* proxy) {
        // 調(diào)用 addProviderLocked 方法
        for (const auto& instance : mServiceProxy->listServices()) {
        this->addProviderLocked(instance);
        }

        }

        status_t CameraProviderManager::addProviderLocked(const std::string& newProvider) {

        sp<ProviderInfo> providerInfo = new ProviderInfo(newProvider, this);
        status_t res = providerInfo->initialize(interface, mDeviceState);

        }

        //ProviderInfo::initialize 初始化方法
        status_t CameraProviderManager::ProviderInfo::initialize(){


        status_t res = addDevice(device, common::V1_0::CameraDeviceStatus::PRESENT, &id);

        }


        status_t CameraProviderManager::ProviderInfo::addDevice(const std::string& name,
        CameraDeviceStatus initialStatus, /*out*/ std::string* parsedId) {

        //
        deviceInfo = initializeDeviceInfo<DeviceInfo3>(name, mProviderTagid,
        id, minor);

        }


        std::unique_ptr<CameraProviderManager::ProviderInfo::DeviceInfo>
        CameraProviderManager::ProviderInfo::initializeDeviceInfo(){
        // 后續(xù)調(diào)用待完善 如何 跳轉(zhuǎn)到 Camera3device.cpp 的initialize 方法
        return std::unique_ptr<DeviceInfo>(
        new DeviceInfoT(name, tagId, id, minorVersion, resourceCost, this,
        mProviderPublicCameraIds, cameraInterface));
        }


        5.Camera3Device.cpp
        (frameworks\av\services\camera\libcameraservice\device3)

        status_t Camera3Device::initialize(sp<CameraProviderManager> manager, const String8& monitorTags) {

        // 調(diào)用 CameraProviderManager openSession
        ATRACE_BEGIN("CameraHal::openSession");
        status_t res = manager->openSession(mId.string(), this,
        /*out*/ &session);
        ATRACE_END();

        return initializeCommonLocked();
        }

        6.CameraProviderManager.cpp
        (frameworks\av\services\camera\libcameraservice\common)

        status_t CameraProviderManager::openSession(const std::string &id,
        const sp<device::V3_2::ICameraDeviceCallback>& callback,
        /*out*/
        sp<device::V3_2::ICameraDeviceSession> *session) {

        auto interface = deviceInfo3->startDeviceInterface<
        CameraProviderManager::ProviderInfo::DeviceInfo3::InterfaceT>();

        ret = interface->open(callback, [&status, &session]
        (Status s, const sp<device::V3_2::ICameraDeviceSession>& cameraSession) {
        status = s;
        if (status == Status::OK) {
        *session = cameraSession;
        }
        });


        }

        7.ICameraDevice.hal
        (hardware\interfaces\camera\device\3.2)

        //Power on and initialize this camera device for active use, returning a
        //session handle for active operations.
        open(ICameraDeviceCallback callback) generates
        (Status status, ICameraDeviceSession session);

        8.CameraDevice.cpp
        (hardware\interfaces\camera\device\3.2\default)

        Return<void> CameraDevice::open(const sp<ICameraDeviceCallback>& callback,
        ICameraDevice::open_cb _hidl_cb) {


        /** Open HAL device */
        status_t res;
        camera3_device_t *device;
        // 1. 開始 open Hal Device
        ATRACE_BEGIN("camera3->open");
        res = mModule->open(mCameraId.c_str(),
        reinterpret_cast<hw_device_t**>(&device));
        ATRACE_END();

        // 2. 獲取Camera 信息
        res = mModule->getCameraInfo(mCameraIdInt, &info);

        // 3. 創(chuàng)建 CameraDeviceSession
        session = createSession(device, info.static_camera_characteristics, callback);
        }
        1. CameraModule.cpp
          (hardware\interfaces\camera\common\1.0\default)

        int CameraModule::open(const char* id, struct hw_device_t** device) {
        int res;
        ATRACE_BEGIN("camera_module->open");
        res = filterOpenErrorCode(mModule->common.methods->open(&mModule->common, id, device));
        ATRACE_END();
        return res;
        }

        10.Camxhal3entry.cpp
        (vendor\qcom\proprietary\camx\src\core\hal)

        int open(
        const struct hw_module_t* pHwModuleAPI,
        const char* pCameraIdAPI,
        struct hw_device_t** ppHwDeviceAPI)
        {
        /// @todo (CAMX-43) - Reload Jumptable from settings
        JumpTableHAL3* pHAL3 = static_cast<JumpTableHAL3*>(g_dispatchHAL3.GetJumpTable());

        return pHAL3->open(pHwModuleAPI, pCameraIdAPI, ppHwDeviceAPI);
        }

        11.Camxhal3.cpp
        (vendor\qcom\proprietary\camx\src\core\hal)

        static int open(){
        // 檢查CameraId 是否有效
        cameraId = OsUtils::StrToUL(pCameraIdAPI, &pNameEnd, 10);

        // 檢查閃光燈狀態(tài),如果 on 狀態(tài),需要off
        HAL3Module::GetInstance()->ReserveTorchForCamera(
        GetCHIAppCallbacks()->chi_remap_camera_id(cameraId, IdRemapTorch), cameraId);

        // 調(diào)用 Camxhal3module ProcessCameraOpen 方法
        result = HAL3Module::GetInstance()->ProcessCameraOpen(logicalCameraId, &extend);

        // 創(chuàng)建HalDevice 實例并初始化
        pHALDevice = HALDevice::Create(pHwModule, logicalCameraId, cameraId);
        }

        12.Camxhal3module.cpp
        (vendor\qcom\proprietary\camx\src\core\hal)

        CamxResult HAL3Module::ProcessCameraOpen(){

        result = m_ChiAppCallbacks.chi_extend_open(logicalCameraId, pPriv);
        }

        13.Chxextensioninterface.cpp
        (vendor\qcom\proprietary\chi-cdk\core\chiframework)

        static CDKResult chi_extend_open(){

        ExtensionModule* pExtensionModule = ExtensionModule::GetInstance();
        CHX_LOG_DEBUG("[OP_EXT] OPEN_CAMERA E cameraId %d", cameraId);
        CDKResult result = pExtensionModule->ExtendOpen(cameraId, priv);
        CHX_LOG_DEBUG("[OP_EXT] OPEN_CAMERA X");
        }

        14.Chxextensionmodule.cpp
        (vendor\qcom\proprietary\chi-cdk\core\chiframework)

        CDKResult ExtensionModule::ExtendOpen(){

        // 調(diào)用 Perflock 提高 opencamera 性能
        m_pPerfLockManager[logicalCameraId] = PerfLockManager::Create();

        if (PERF_LOCK_OPEN_CAMERA != m_previousPowerHint)
        {

        m_pPerfLockManager[logicalCameraId]->ReleasePerfLock(m_previousPowerHint);
        m_pPerfLockManager[logicalCameraId]->AcquirePerfLock(PERF_LOCK_OPEN_CAMERA, 10000);
        m_previousPowerHint = PERF_LOCK_OPEN_CAMERA;
        }
        // open 結(jié)束返回到 camxhal3.cpp
        }

        15.Camxhal3.cpp
        (vendor\qcom\proprietary\camx\src\core\hal)

        static int open(){
        // 檢查CameraId 是否有效
        cameraId = OsUtils::StrToUL(pCameraIdAPI, &pNameEnd, 10);

        // 檢查閃光燈狀態(tài),如果 on 狀態(tài),需要off
        HAL3Module::GetInstance()->ReserveTorchForCamera(
        GetCHIAppCallbacks()->chi_remap_camera_id(cameraId, IdRemapTorch), cameraId);

        // 調(diào)用 Camxhal3module ProcessCameraOpen 方法
        result = HAL3Module::GetInstance()->ProcessCameraOpen(logicalCameraId, &extend);

        // 創(chuàng)建HalDevice 實例并初始化
        pHALDevice = HALDevice::Create(pHwModule, logicalCameraId, cameraId);
        }

        16.Camxhaldevice.cpp
        (vendor\qcom\proprietary\camx\src\core\hal)


        HALDevice* HALDevice::Create(){

        result = pHALDevice->Initialize(pHwModule, cameraId);

        }

        CamxResult HALDevice::Initialize(){
        ... ...

        // 初始化完成后,需要返回 CameraDevice.cpp 中繼續(xù)執(zhí)行 open 中的方法
        }

        17.CameraDevice.cpp
        (hardware\interfaces\camera\device\3.2\default)

        Return<void> CameraDevice::open(const sp<ICameraDeviceCallback>& callback,
        ICameraDevice::open_cb _hidl_cb) {


        /** Open HAL device */
        status_t res;
        camera3_device_t *device;
        // 1. 開始 open Hal Device
        ATRACE_BEGIN("camera3->open");
        res = mModule->open(mCameraId.c_str(),
        reinterpret_cast<hw_device_t**>(&device));
        ATRACE_END();

        // 2. 獲取Camera 信息
        res = mModule->getCameraInfo(mCameraIdInt, &info);

        // 3. 創(chuàng)建 CameraDeviceSession
        session = createSession(device, info.static_camera_characteristics, callback);
        }

        //3. 創(chuàng)建 CameraDeviceSession 方法實現(xiàn)
        sp<CameraDeviceSession> CameraDevice::createSession(camera3_device_t* device,
        const camera_metadata_t* deviceInfo,
        const sp<ICameraDeviceCallback>& callback) {
        return new CameraDeviceSession(device, deviceInfo, callback);
        }

        18.CameraDeviceSession.cpp
        (hardware\interfaces\camera\device\3.2\default) 62313 2020/8/11

        CameraDeviceSession::CameraDeviceSession(){

        //調(diào)用 initialize 方法
        mInitFail = initialize();

        }

        bool CameraDeviceSession::initialize() {

        // 初始化完成之后返回 CameraProviderManager
        }

        CamxOpen流程(參考網(wǎng)絡(luò))

        至此,本篇已結(jié)束。轉(zhuǎn)載網(wǎng)絡(luò)的文章,小編覺得很優(yōu)秀,歡迎點(diǎn)擊閱讀原文,支持原創(chuàng)作者,如有侵權(quán),懇請聯(lián)系小編刪除。同時感謝您的閱讀,期待您的關(guān)注。

        點(diǎn)個在看,方便您使用時快速查找!

        瀏覽 126
        點(diǎn)贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報
        評論
        圖片
        表情
        推薦
        點(diǎn)贊
        評論
        收藏
        分享

        手機(jī)掃一掃分享

        分享
        舉報
          
          

            1. 性免费网站 | 成人天美麻豆久久久久久 | 久久88| 国产强 暴 疼 哭 处 女 五月天色婷婷亚洲麻豆 | 中文字幕aV一区二区三区 |