其他分享
首页 > 其他分享> > Camera2 OpenCamera流程

Camera2 OpenCamera流程

作者:互联网

文章目录


转载链接: Android P Camera2相机简单解析

1.CameraManager

文件路径:framework\base\core\java\android\hardware\camera2\CameraManager.java

1.1 openCamera函数

CameraManager中两个openCamera(),一个Handler,一个Executor,Executor用于线程池来执行Camera中的耗时操作。

/*
* cameraId 是一个标识,标识当前要打开的camera;
* callback 是一个状态回调,当前camera被打开的时候,这个状态回调会被触发的;
* handler 是传入的一个执行耗时操作的handler;
*/
@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);
}
// Executor用于线程池来执行Camera中的耗时操作
@RequiresPermission(android.Manifest.permission.CAMERA)
public void openCamera(@NonNull String cameraId,
		@NonNull @CallbackExecutor Executor executor,
		@NonNull final CameraDevice.StateCallback callback)
		throws CameraAccessException {
	if (executor == null) {
		throw new IllegalArgumentException("executor was null");
	}
	openCameraForUid(cameraId, callback, executor, USE_CALLING_UID);
}

1.1.1 实现StateCallback 接口,当相机打开后会回调onOpened方法,在这个方法里面开启预览

private final CameraDevice.StateCallback mStateCallback = new CameraDevice.StateCallback() {
	@Override
	public void onOpened(CameraDevice cameraDevice) {
		int id = Integer.parseInt(cameraDevice.getId());
		Log.d(TAG, "onOpened " + id);
		//+add by renshangyuan.wt for cameraId find index 2019/3/22
		int cameraId = id;
		id = getIndex(id);
		//-add by renshangyuan.wt for cameraId find index 2019/3/22
		Log.d(TAG, "onOpened " + id+" cameraId="+cameraId);
		mCameraOpenCloseLock.release();
		if (mPaused) {
			return;
		}
		mCameraDevice[id] = cameraDevice;
		mCameraOpened[id] = true;
		if (isBackCamera() && getCameraMode() == DUAL_MODE && cameraId == BAYER_ID) {
			Message msg = mCameraHandler.obtainMessage(OPEN_CAMERA, MONO_ID, 0);
			mCameraHandler.sendMessage(msg);
		} else {
			mCamerasOpened = true;
			mActivity.runOnUiThread(new Runnable() {
				@Override
				public void run() {
					mUI.onCameraOpened(mCameraIdList);
				}
			});
			createSessions();
		}
	}

	@Override
	public void onDisconnected(CameraDevice cameraDevice) {
		int id = Integer.parseInt(cameraDevice.getId());
		//+add by renshangyuan.wt for cameraId find index 2019/3/22
		id = getIndex(id);
		//-add by renshangyuan.wt for cameraId find index 2019/3/22
		Log.d(TAG, "onDisconnected " + id);
		cameraDevice.close();
		mCameraDevice[id] = null;
		mCameraOpenCloseLock.release();
		mCamerasOpened = false;
		if (null != mActivity) {
			Toast.makeText(mActivity,"open camera error id =" + id,
					Toast.LENGTH_LONG).show();
			mActivity.finish();
		}
	}

	@Override
	public void one rror(CameraDevice cameraDevice, int error) {
		int id = Integer.parseInt(cameraDevice.getId());
		//+add by renshangyuan.wt for cameraId find index 2019/3/22
		id = getIndex(id);
		//-add by renshangyuan.wt for cameraId find index 2019/3/22
		Log.e(TAG, "onError " + id + " " + error);
		if (mCamerasOpened) {
			mCameraDevice[id].close();
			mCameraDevice[id] = null;
		}
		mCameraOpenCloseLock.release();
		mCamerasOpened = false;
		if (null != mActivity) {
			Toast.makeText(mActivity,"open camera error id =" + id,
					Toast.LENGTH_LONG).show();
			mActivity.finish();
		}
	}

	@Override
	public void onClosed(CameraDevice cameraDevice) {
		int id = Integer.parseInt(cameraDevice.getId());
		//+add by renshangyuan.wt for cameraId find index 2019/3/22
		id = getIndex(id);
		//-add by renshangyuan.wt for cameraId find index 2019/3/22
		Log.d(TAG, "onClosed " + id);
		mCameraDevice[id] = null;
		clearBufferLostFrames();
		mCameraOpenCloseLock.release();
		mCamerasOpened = false;
	}
};

1.2 openCameraForUid()

两种实际都是调用了 openCameraForUid(cameraId, callback, executor, USE_CALLING_UID)这个方法,
具体实现如下:

public void openCameraForUid(@NonNull String cameraId,
            @NonNull final CameraDevice.StateCallback callback, @NonNull Executor executor,
            int clientUid)
            throws CameraAccessException {
        if (cameraId == null) {
            throw new IllegalArgumentException("cameraId was null");
        } else if (callback == null) {
            throw new IllegalArgumentException("callback was null");
        }
        if (CameraManagerGlobal.sCameraServiceDisabled) {
            throw new IllegalArgumentException("No cameras available on device");
        }
        openCameraDeviceUserAsync(cameraId, callback, executor, clientUid);
    }

1.3 openCameraDeviceUserAsync()

这里做了容错性判断,紧接着调用了 openCameraDeviceUserAsync(cameraId, callback, executor, clientUid),
返回值是CameraDevice,CameraDevice是抽象类,CameraDeviceImpl是其实现类,就是要获取CameraDeviceImpl的实例。
这个函数的主要作用就是到底层获取相机设备的信息,并获取当前指定cameraId的设备实例。
本函数的主要工作可以分为下面五点:

private CameraDevice openCameraDeviceUserAsync(String cameraId,
		CameraDevice.StateCallback callback, Executor executor, final int uid)
		throws CameraAccessException {
	CameraCharacteristics characteristics = getCameraCharacteristics(cameraId);
	CameraDevice device = null;

	synchronized (mLock) {

		ICameraDeviceUser cameraUser = null;
// 创建CameraDeviceImpl实例,返回给应用端的相机对象
		android.hardware.camera2.impl.CameraDeviceImpl deviceImpl =
				new android.hardware.camera2.impl.CameraDeviceImpl(
					cameraId,
					callback,
					executor,
					characteristics,
					mContext.getApplicationInfo().targetSdkVersion);
// 将ICameraDeviceCallbacks 设置到cameraservice中
		ICameraDeviceCallbacks callbacks = deviceImpl.getCallbacks();

		try {
			if (supportsCamera2ApiLocked(cameraId)) {
				// 获取Framework层CameraServer的服务代理
				ICameraService cameraService = CameraManagerGlobal.get().getCameraService();
				if (cameraService == null) {
					throw new ServiceSpecificException(
						ICameraService.ERROR_DISCONNECTED,
						"Camera service is currently unavailable");
				}
				// 通过cameraService跨进程获得BpCameraDeviceUser对象,连接到相机设备,返回得到
				// 远端CameraDeviceClient的本地接口
				cameraUser = cameraService.connectDevice(callbacks, cameraId,
						mContext.getOpPackageName(), uid);
			} else {
				// Use legacy camera implementation for HAL1 devices
				int id;
				try {
					id = Integer.parseInt(cameraId);
				} catch (NumberFormatException e) {
					throw new IllegalArgumentException("Expected cameraId to be numeric, but it was: "
							+ cameraId);
				}

				Log.i(TAG, "Using legacy camera HAL.");
				cameraUser = CameraDeviceUserShim.connectBinderShim(callbacks, id,
						getDisplaySize());
			}
		} catch (ServiceSpecificException e) {

		} catch (RemoteException e) {

		}
		
		// 将CameraDeviceClient本地代理cameraUser设置到CameraDeviceImpl中进行管理,
		//CameraDeviceImpl中的mRemoteDevice由该cameraUsr包装而来
		deviceImpl.setRemoteDevice(cameraUser);
		device = deviceImpl;
	}

	return device;
}

这里主要关注上面的代码中的cameraService.connectDevice,这仅仅是Connect到我们的Camera设备,并不能打开我们的Camera,所以ICameraDeviceUser cameraUser = null和deviceImpl.setRemoteDevice(cameraUser)也是非常重要的,这里对应了CameraDeviceImpl .java文件。但是这里我们还是先看cameraService.connectDevice实现,实际上是ICameraService.connectDevice,这里需要注意的是ICameraService实际上是aidl文件,也是就是说CameraManager通过通过 Binder 机制调用了 connectDevice 方法,这个connectDevice方法的实现在CameraService 中。

1.3.1 CameraDeviceImpl继承CameraDevice

public class CameraDeviceImpl extends CameraDevice
    public CameraDeviceImpl(String cameraId, StateCallback callback, Executor executor,
                        CameraCharacteristics characteristics, int appTargetSdkVersion) {
        mCameraId = cameraId;
        mDeviceCallback = callback;
        mDeviceExecutor = executor;
    }
}

1.3.2 setRemoteDevice的实现

frameworks/base/core/java/android/hardware/camera2/impl/CameraDeviceImpl.java

private ICameraDeviceUserWrapper mRemoteDevice;
    public void setRemoteDevice(ICameraDeviceUser remoteDevice) throws CameraAccessException {
        synchronized(mInterfaceLock) {
            mRemoteDevice = new ICameraDeviceUserWrapper(remoteDevice);
            mDeviceExecutor.execute(mCallOnOpened);
            mDeviceExecutor.execute(mCallOnUnconfigured);
        }
    }
    private final Runnable mCallOnOpened = new Runnable() {
        public void run() {
            sessionCallback = mSessionStateCallback;
            sessionCallback.onOpened(CameraDeviceImpl.this);
            //通知相机应用设备已打开,并且返回CameraDeviceImpl对象,相机应用已实现该函数
            mDeviceCallback.onOpened(CameraDeviceImpl.this);
        }
    };

1.3.3 ICameraDeviceUserWrapper

frameworks/base/core/java/android/hardware/camera2/impl/ICameraDeviceUserWrapper.java

public ICameraDeviceUserWrapper(ICameraDeviceUser remoteDevice) {
    mRemoteDevice = remoteDevice;
}

通过以上流程,相机应用获得了CameraDevice对象,而CameraDevice保存ICameraDeviceUserWrapper对象,ICameraDeviceUserWrapper保存BpCameraDeviceUser对象,BpCameraDeviceUser具有跨进程的能力,这样应用就可以和CameraService端的CameraDeviceClient进行通信了。

1.3.4 获取当前cameraId指定相机的设备信息

CameraCharacteristics getCameraCharacteristics(@NonNull String cameraId)
一句简单的调用,返回值是CameraCharacteristics,CameraCharacteristics提供了CameraDevice的各种属性,可以通过getCameraCharacteristics函数来查询。

@NonNull
public CameraCharacteristics getCameraCharacteristics(@NonNull String cameraId)
		throws CameraAccessException {
	CameraCharacteristics characteristics = null;
	if (CameraManagerGlobal.sCameraServiceDisabled) {
		throw new IllegalArgumentException("No cameras available on device");
	}
	synchronized (mLock) {
		/*
		 * Get the camera characteristics from the camera service directly if it supports it,
		 * otherwise get them from the legacy shim instead.
		 */
		ICameraService cameraService = CameraManagerGlobal.get().getCameraService();
		if (cameraService == null) {
			throw new CameraAccessException(CameraAccessException.CAMERA_DISCONNECTED,
					"Camera service is currently unavailable");
		}
		try {
			Size displaySize = getDisplaySize();

			// First check isHiddenPhysicalCamera to avoid supportsCamera2ApiLocked throwing
			// exception in case cameraId is a hidden physical camera.
			if (!isHiddenPhysicalCamera(cameraId) && !supportsCamera2ApiLocked(cameraId)) {
				// Legacy backwards compatibility path; build static info from the camera
				// parameters
				int id = Integer.parseInt(cameraId);

				String parameters = cameraService.getLegacyParameters(id);

				CameraInfo info = cameraService.getCameraInfo(id);

				characteristics = LegacyMetadataMapper.createCharacteristics(parameters, info,
						id, displaySize);
			} else {
				// Normal path: Get the camera characteristics directly from the camera service
				CameraMetadataNative info = cameraService.getCameraCharacteristics(cameraId);
				try {
					info.setCameraId(Integer.parseInt(cameraId));
				} catch (NumberFormatException e) {
					Log.e(TAG, "Failed to parse camera Id " + cameraId + " to integer");
				}
				info.setDisplaySize(displaySize);

				characteristics = new CameraCharacteristics(info);
			}
		} catch (ServiceSpecificException e) {
			throwAsPublicException(e);
		} catch (RemoteException e) {
			// Camera service died - act as if the camera was disconnected
			throw new CameraAccessException(CameraAccessException.CAMERA_DISCONNECTED,
					"Camera service is currently unavailable", e);
		}
	}
	return characteristics;
}

ICameraService cameraService = CameraManagerGlobal.get().getCameraService();
调用的CameraService对应的是ICameraService.aidl,对应的实现类在frameworks/av/services/camera/libcameraservice/CameraService.h
下面是CameraManager与CameraService之间的连接关系图示:

2. CameraService.cpp

文件路径:/frameworks/av/services/camera/libcameraservice/CameraService.cpp

2.1 cameraService.connectDevice的实现

跨进程调用CameraManager->CameraService,返回CameraDeviceClient,将应用端的回调函数设置给cameraService。

Status CameraService::connectDevice(
        const sp<hardware::camera2::ICameraDeviceCallbacks>& cameraCb,
        const String16& cameraId,
        const String16& clientPackageName,
        int clientUid,
        /*out*/
        sp<hardware::camera2::ICameraDeviceUser>* device) {
    sp<CameraDeviceClient> client = nullptr;
    //调用了connectHelper来实现连接相机的逻辑
    ret = connectHelper<hardware::camera2::ICameraDeviceCallbacks,CameraDeviceClient>(cameraCb, id,
            /*api1CameraId*/-1,
            CAMERA_HAL_API_VERSION_UNSPECIFIED, clientPackageName,
            clientUid, USE_CALLING_PID, API_2,
            /*legacyMode*/ false, /*shimUpdateOnly*/ false,
            /*out*/client);
            // device指针会在BnCameraService中将其打包为ICamraDeviceUser对象写到binder reply中返回
    *device = client; // client = CameraDeviceClient
    return ret;
}

2.2 CameraService::connectHelper 实现逻辑

template<class CALLBACK, class CLIENT>
Status CameraService::connectHelper(const sp<CALLBACK>& cameraCb, const String8& cameraId,
        int api1CameraId, int halVersion, const String16& clientPackageName, int clientUid,
        int clientPid, apiLevel effectiveApiLevel, bool legacyMode, bool shimUpdateOnly,
        /*out*/sp<CLIENT>& device) {
        if(!(ret = makeClient(this, cameraCb, clientPackageName,
                cameraId, api1CameraId, facing,
                clientPid, clientUid, getpid(), legacyMode,
                halVersion, deviceVersion, effectiveApiLevel,
                /*out*/&tmp)).isOk()) {
            return ret;
        }
        //转换BasicClient类型为CLIENT=CameraDeviceClient
        client = static_cast<CLIENT*>(tmp.get());
        //初始化CameraDeviceClient对象
        err = client->initialize(mCameraProviderManager, mMonitorTags);
        device = client;
}

2.3 makeClient的实现

在connectHelper中我们通过makeClient方法完成了client的生成并初始化,具体实现如下:

Status CameraService::makeClient(const sp<CameraService>& cameraService,
        const sp<IInterface>& cameraCb, const String16& packageName, const String8& cameraId,
        int api1CameraId, int facing, int clientPid, uid_t clientUid, int servicePid,
        bool legacyMode, int halVersion, int deviceVersion, apiLevel effectiveApiLevel,
        /*out*/sp<BasicClient>* client) {

    if (halVersion < 0 || halVersion == deviceVersion) {
        switch(deviceVersion) {
          case CAMERA_DEVICE_API_VERSION_3_0:
          case CAMERA_DEVICE_API_VERSION_3_1:
          case CAMERA_DEVICE_API_VERSION_3_2:
          case CAMERA_DEVICE_API_VERSION_3_3:
          case CAMERA_DEVICE_API_VERSION_3_4:
            if (effectiveApiLevel == API_1) { // Camera1 API route
                sp<ICameraClient> tmp = static_cast<ICameraClient*>(cameraCb.get());
                *client = new Camera2Client(cameraService, tmp, packageName,
                        cameraId, api1CameraId,
                        facing, clientPid, clientUid,
                        servicePid, legacyMode);
            } else { // Camera2 API route
                sp<hardware::camera2::ICameraDeviceCallbacks> tmp =
                        static_cast<hardware::camera2::ICameraDeviceCallbacks*>(cameraCb.get());
                *client = new CameraDeviceClient(cameraService, tmp, packageName, cameraId,
                        facing, clientPid, clientUid, servicePid);
            }
            break;
        }
    }
}

这一块儿基本就是根据API版本和Device版本来实例化Client的,在Android P 和Camera2的框架上,这里CameraDeviceClient方法是由CameraDeviceClient.cpp实现的。

3. CameraDeviceClient.cpp

文件路径:frameworks/av/services/camera/libcameraservice/api2/CameraDeviceClient.cpp

CameraDeviceClient::CameraDeviceClient(const sp<CameraService>& cameraService,
        const sp<hardware::camera2::ICameraDeviceCallbacks>& remoteCallback,
        const String16& clientPackageName,
        const String8& cameraId,
        int cameraFacing,
        int clientPid,
        uid_t clientUid,
        int servicePid) :
    Camera2ClientBase(cameraService, remoteCallback, clientPackageName,
                cameraId, /*API1 camera ID*/ -1,
                cameraFacing, clientPid, clientUid, servicePid),
    mInputStream(),
    mStreamingRequestId(REQUEST_ID_NONE),
    mRequestIdCounter(0),
    mPrivilegedClient(false) {

    char value[PROPERTY_VALUE_MAX];
    property_get("persist.vendor.camera.privapp.list", value, "");
    String16 packagelist(value);
    if (packagelist.contains(clientPackageName.string())) {
        mPrivilegedClient = true;
    }

    ATRACE_CALL();
    ALOGI("CameraDeviceClient %s: Opened", cameraId.string());
}

3.1 获得CameraDeviceClient之后进行initialize

status_t CameraDeviceClient::initialize(sp<CameraProviderManager> manager,
        const String8& monitorTags) {
    return initializeImpl(manager, monitorTags);
}
//调用父类函数,CameraDeviceClient继承Camera2ClientBase,初始化时会创建Camera3Device对象
Camera2ClientBase<TClientBase>::Camera2ClientBase(){
    mInitialClientPid = clientPid;
    mDevice = new Camera3Device(cameraId);
}
status_t CameraDeviceClient::initializeImpl(TProviderPtr providerPtr, const String8& monitorTags) {
    res = Camera2ClientBase::initialize(providerPtr, monitorTags);
    mFrameProcessor = new FrameProcessorBase(mDevice);
    mFrameProcessor->run(threadName.string());
    mFrameProcessor->registerListener(FRAME_PROCESSOR_LISTENER_MIN_ID,
                                      FRAME_PROCESSOR_LISTENER_MAX_ID,
                                      /*listener*/this,
                                      /*sendPartials*/true);
}

调用了Camera2ClientBase方法,实现代码如下:

frameworks/av/services/camera/libcameraservice/common/Camera2ClientBase.cpp

status_t Camera2ClientBase<TClientBase>::initialize(sp<CameraProviderManager> manager,
        const String8& monitorTags) {
    return initializeImpl(manager, monitorTags);
}
status_t Camera2ClientBase<TClientBase>::initializeImpl(TProviderPtr providerPtr,
        const String8& monitorTags) {
    status_t res;
    res = TClientBase::startCameraOps();
    //初始化Camera3Device
    res = mDevice->initialize(providerPtr, monitorTags);
    wp<CameraDeviceBase::NotificationListener> weakThis(this);
    res = mDevice->setNotifyCallback(weakThis);
    return OK;
}

mDevice = new Camera3Device(cameraId)才是重点,是由Camera3Device.cpp实现的。

4. Camera3Device.cpp

文件路径:/frameworks/av/services/camera/libcameraservice/device3/Camera3Device.cpp

Camera3Device::Camera3Device(const String8 &id):
        mId(id),
        mOperatingMode(NO_MODE),
        mIsConstrainedHighSpeedConfiguration(false),
        mStatus(STATUS_UNINITIALIZED),
        mStatusWaiters(0),
        mUsePartialResult(false),
        mNumPartialResults(1),
        mTimestampOffset(0),
        mNextResultFrameNumber(0),
        mNextReprocessResultFrameNumber(0),
        mNextShutterFrameNumber(0),
        mNextReprocessShutterFrameNumber(0),
        mListener(NULL),
        mVendorTagId(CAMERA_METADATA_INVALID_VENDOR_ID),
        mLastTemplateId(-1)
{
    ATRACE_CALL();
    camera3_callback_ops::notify = &sNotify;
    camera3_callback_ops::process_capture_result = &sProcessCaptureResult;
    ALOGV("%s: Created device for camera %s", __FUNCTION__, mId.string());
}

到此CameraService.cpp中的makeClient工作就已经完成了并构造了"CameraDeviceClient"

接下来就是connectHelper中的client->initialize这块儿了,从上面分析我们知道这里的client 指的对象就是Camera3Device了,所以我们继续找到Camera3Device中的initialize方法,代码如下:

status_t Camera3Device::initialize(sp<CameraProviderManager> manager, const String8& monitorTags) {
    ATRACE_CALL();
    Mutex::Autolock il(mInterfaceLock);
    Mutex::Autolock l(mLock);

    ALOGV("%s: Initializing HIDL device for camera %s", __FUNCTION__, mId.string());
    if (mStatus != STATUS_UNINITIALIZED) {
        CLOGE("Already initialized!");
        return INVALID_OPERATION;
    }
    if (manager == nullptr) return INVALID_OPERATION;

    sp<ICameraDeviceSession> session;
    ATRACE_BEGIN("CameraHal::openSession");
    status_t res = manager->openSession(mId.string(), this,
            /*out*/ &session);
    ATRACE_END();
    if (res != OK) {
        SET_ERR_L("Could not open camera session: %s (%d)", strerror(-res), res);
        return res;
    }

    res = manager->getCameraCharacteristics(mId.string(), &mDeviceInfo);
    if (res != OK) {
        SET_ERR_L("Could not retrive camera characteristics: %s (%d)", strerror(-res), res);
        session->close();
        return res;
    }

    std::shared_ptr<RequestMetadataQueue> queue;
    auto requestQueueRet = session->getCaptureRequestMetadataQueue(
        [&queue](const auto& descriptor) {
            queue = std::make_shared<RequestMetadataQueue>(descriptor);
            if (!queue->isValid() || queue->availableToWrite() <= 0) {
                ALOGE("HAL returns empty request metadata fmq, not use it");
                queue = nullptr;
                // don't use the queue onwards.
            }
        });
    if (!requestQueueRet.isOk()) {
        ALOGE("Transaction error when getting request metadata fmq: %s, not use it",
                requestQueueRet.description().c_str());
        return DEAD_OBJECT;
    }

    std::unique_ptr<ResultMetadataQueue>& resQueue = mResultMetadataQueue;
    auto resultQueueRet = session->getCaptureResultMetadataQueue(
        [&resQueue](const auto& descriptor) {
            resQueue = std::make_unique<ResultMetadataQueue>(descriptor);
            if (!resQueue->isValid() || resQueue->availableToWrite() <= 0) {
                ALOGE("HAL returns empty result metadata fmq, not use it");
                resQueue = nullptr;
                // Don't use the resQueue onwards.
            }
        });
    if (!resultQueueRet.isOk()) {
        ALOGE("Transaction error when getting result metadata queue from camera session: %s",
                resultQueueRet.description().c_str());
        return DEAD_OBJECT;
    }
    IF_ALOGV() {
        session->interfaceChain([](
            ::android::hardware::hidl_vec<::android::hardware::hidl_string> interfaceChain) {
                ALOGV("Session interface chain:");
                for (auto iface : interfaceChain) {
                    ALOGV("  %s", iface.c_str());
                }
            });
    }

    mInterface = new HalInterface(session, queue); //新建硬件抽象层接口实例
    std::string providerType;
    mVendorTagId = manager->getProviderTagIdLocked(mId.string());
    mTagMonitor.initialize(mVendorTagId);
    if (!monitorTags.isEmpty()) {
        mTagMonitor.parseTagsToMonitor(String8(monitorTags));
    }

    return initializeCommonLocked();
}

res = manager->openSession 就是走向open的地方了,但是还是需要继续到一个方法,不难发现openSession方法由CameraProviderManager.cpp实现。此外在这里我们还需要注意

  1. auto requestQueueRet = session->getCaptureRequestMetadataQueue(
  2. auto resultQueueRet = session->getCaptureResultMetadataQueue(
    是请求队列,2中的resultQueueRet 是结果队列在下一篇中将使用到。

4. CameraProviderManager.cpp

文件路径:***/frameworks/av/services/camera/libcameraservice/common/CameraProviderManager.cpp***
具体代码如下:

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

    std::lock_guard<std::mutex> lock(mInterfaceMutex);

    auto deviceInfo = findDeviceInfoLocked(id,
            /*minVersion*/ {3,0}, /*maxVersion*/ {4,0});
    if (deviceInfo == nullptr) return NAME_NOT_FOUND;

    auto *deviceInfo3 = static_cast<ProviderInfo::DeviceInfo3*>(deviceInfo);

    Status status;
    hardware::Return<void> ret;
    ret = deviceInfo3->mInterface->open(callback, [&status, &session]
            (Status s, const sp<device::V3_2::ICameraDeviceSession>& cameraSession) {
                status = s;
                if (status == Status::OK) {
                    *session = cameraSession;
                }
            });
    if (!ret.isOk()) {
        ALOGE("%s: Transaction error opening a session for camera device %s: %s",
                __FUNCTION__, id.c_str(), ret.description().c_str());
        return DEAD_OBJECT;
    }
    return mapToStatusT(status);
}

ret = deviceInfo3->mInterface->open 实际上通过Hidl指向了CameraDevice::open(),该方法由CameraDevice.cpp实现。

5. CameraDevice.cpp

文件路径:***/hardware/interfaces/camera/device/3.2/default/CameraDevice.cpp***
代码如下:

Return<void> CameraDevice::open(const sp<ICameraDeviceCallback>& callback, open_cb _hidl_cb)  {
    Status status = initStatus();
    sp<CameraDeviceSession> session = nullptr;

    if (callback == nullptr) {
        ALOGE("%s: cannot open camera %s. callback is null!",
                __FUNCTION__, mCameraId.c_str());
        _hidl_cb(Status::ILLEGAL_ARGUMENT, nullptr);
        return Void();
    }
    
    if (status != Status::OK) {
        // Provider will never pass initFailed device to client, so
        // this must be a disconnected camera
        ALOGE("%s: cannot open camera %s. camera is disconnected!",
                __FUNCTION__, mCameraId.c_str());
        _hidl_cb(Status::CAMERA_DISCONNECTED, nullptr);
        return Void();
    } else {
        mLock.lock();

        ALOGV("%s: Initializing device for camera %d", __FUNCTION__, mCameraIdInt);
        session = mSession.promote();
        if (session != nullptr && !session->isClosed()) {
            ALOGE("%s: cannot open an already opened camera!", __FUNCTION__);
            mLock.unlock();
            _hidl_cb(Status::CAMERA_IN_USE, nullptr);
            return Void();
        }

        /** Open HAL device */
        status_t res;
        camera3_device_t *device;

        ATRACE_BEGIN("camera3->open");
        res = mModule->open(mCameraId.c_str(),
                reinterpret_cast<hw_device_t**>(&device));
        ATRACE_END();

        if (res != OK) {
            ALOGE("%s: cannot open camera %s!", __FUNCTION__, mCameraId.c_str());
            mLock.unlock();
            _hidl_cb(getHidlStatus(res), nullptr);
            return Void();
        }

        /** Cross-check device version */
        if (device->common.version < CAMERA_DEVICE_API_VERSION_3_2) {
            ALOGE("%s: Could not open camera: "
                    "Camera device should be at least %x, reports %x instead",
                    __FUNCTION__,
                    CAMERA_DEVICE_API_VERSION_3_2,
                    device->common.version);
            device->common.close(&device->common);
            mLock.unlock();
            _hidl_cb(Status::ILLEGAL_ARGUMENT, nullptr);
            return Void();
        }

        struct camera_info info;
        res = mModule->getCameraInfo(mCameraIdInt, &info);
        if (res != OK) {
            ALOGE("%s: Could not open camera: getCameraInfo failed", __FUNCTION__);
            device->common.close(&device->common);
            mLock.unlock();
            _hidl_cb(Status::ILLEGAL_ARGUMENT, nullptr);
            return Void();
        }

        session = createSession(
                device, info.static_camera_characteristics, callback);
        if (session == nullptr) {
            ALOGE("%s: camera device session allocation failed", __FUNCTION__);
            mLock.unlock();
            _hidl_cb(Status::INTERNAL_ERROR, nullptr);
            return Void();
        }
        if (session->isInitFailed()) {
            ALOGE("%s: camera device session init failed", __FUNCTION__);
            session = nullptr;
            mLock.unlock();
            _hidl_cb(Status::INTERNAL_ERROR, nullptr);
            return Void();
        }
        mSession = session;

        IF_ALOGV() {
            session->getInterface()->interfaceChain([](
                ::android::hardware::hidl_vec<::android::hardware::hidl_string> interfaceChain) {
                    ALOGV("Session interface chain:");
                    for (auto iface : interfaceChain) {
                        ALOGV("  %s", iface.c_str());
                    }
                });
        }
        mLock.unlock();
    }
    _hidl_cb(status, session->getInterface());
    return Void();
}

res = mModule->open(mCameraId.c_str(), reinterpret_cast<hw_device_t**>(&device))为打开Camera的地方,但是这里还需要继续跟下去,指向了CameraModule.cpp中实现的open方法。

6. CameraModule.cpp

文件路径:***/hardware/interfaces/camera/common/1.0/default/CameraModule.cpp***
代码如下:

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;
}

不难发现,mModule->common.methods->open紧接着就是Hal层了,在这里我们需要先把Hal层启动流程弄清楚。在系统启动后,CameraService服务跑起来就是就会启动Hal层。

7. CameraService

文件路径:***/frameworks/av/services/camera/libcameraservice/CameraService.cpp***
代码如下:

void CameraService::onFirstRef()
{
    ALOGI("CameraService process starting");

    BnCameraService::onFirstRef();

    // Update battery life tracking if service is restarting
    BatteryNotifier& notifier(BatteryNotifier::getInstance());
    notifier.noteResetCamera();
    notifier.noteResetFlashlight();

    status_t res = INVALID_OPERATION;

    res = enumerateProviders();
    if (res == OK) {
        mInitialized = true;
    }

    CameraService::pingCameraServiceProxy();

    mUidPolicy = new UidPolicy(this);
    mUidPolicy->registerSelf();
}

res = enumerateProviders()说明CameraService在初始化时,要先枚举Provider,实现代码如下:

status_t CameraService::enumerateProviders() {
    status_t res;

    std::vector<std::string> deviceIds;
    {
        Mutex::Autolock l(mServiceLock);

        if (nullptr == mCameraProviderManager.get()) {
            mCameraProviderManager = new CameraProviderManager();
            res = mCameraProviderManager->initialize(this);
            if (res != OK) {
                ALOGE("%s: Unable to initialize camera provider manager: %s (%d)",
                        __FUNCTION__, strerror(-res), res);
                return res;
            }
        }


        // Setup vendor tags before we call get_camera_info the first time
        // because HAL might need to setup static vendor keys in get_camera_info
        // TODO: maybe put this into CameraProviderManager::initialize()?
        mCameraProviderManager->setUpVendorTags();

        if (nullptr == mFlashlight.get()) {
            mFlashlight = new CameraFlashlight(mCameraProviderManager, this);
        }

        res = mFlashlight->findFlashUnits();
        if (res != OK) {
            ALOGE("Failed to enumerate flash units: %s (%d)", strerror(-res), res);
        }

        deviceIds = mCameraProviderManager->getCameraDeviceIds();
    }


    for (auto& cameraId : deviceIds) {
        String8 id8 = String8(cameraId.c_str());
        onDeviceStatusChanged(id8, CameraDeviceStatus::PRESENT);
    }

    return OK;
}

这里又先初始化CameraProviderManager,并获取第三方厂家TAG,获取闪光灯,获取相机设备数,其中CameraProviderManager的初始化实现如下。

8. CameraProviderManager.cpp

文件路径:***/frameworks/av/services/camera/libcameraservice/common/CameraProviderManager.cpp***
具体代码如下:

status_t CameraProviderManager::initialize(wp<CameraProviderManager::StatusListener> listener,
        ServiceInteractionProxy* proxy) {
    std::lock_guard<std::mutex> lock(mInterfaceMutex);
    if (proxy == nullptr) {
        ALOGE("%s: No valid service interaction proxy provided", __FUNCTION__);
        return BAD_VALUE;
    }
    mListener = listener;
    mServiceProxy = proxy;

    // Registering will trigger notifications for all already-known providers
    bool success = mServiceProxy->registerForNotifications(
        /* instance name, empty means no filter */ "",
        this);
    if (!success) {
        ALOGE("%s: Unable to register with hardware service manager for notifications "
                "about camera providers", __FUNCTION__);
        return INVALID_OPERATION;
    }

    // See if there's a passthrough HAL, but let's not complain if there's not
    addProviderLocked(kLegacyProviderName, /*expected*/ false);
    addProviderLocked(kExternalProviderName, /*expected*/ false);

    return OK;
}

8.1 CameraProviderManager初始化中做的事情很明了,这里我们需要关注的是addProviderLocked这里进行查找并保存Provider,实现如下:

status_t CameraProviderManager::addProviderLocked(const std::string& newProvider, bool expected) {
    for (const auto& providerInfo : mProviders) {
        if (providerInfo->mProviderName == newProvider) {
            ALOGW("%s: Camera provider HAL with name '%s' already registered", __FUNCTION__,
                    newProvider.c_str());
            return ALREADY_EXISTS;
        }
    }

    sp<provider::V2_4::ICameraProvider> interface;
    interface = mServiceProxy->getService(newProvider); //获取服务

    if (interface == nullptr) {
        if (expected) {
            ALOGE("%s: Camera provider HAL '%s' is not actually available", __FUNCTION__,
                    newProvider.c_str());
            return BAD_VALUE;
        } else {
            return OK;
        }
    }

    sp<ProviderInfo> providerInfo =
            new ProviderInfo(newProvider, interface, this); //构建
    status_t res = providerInfo->initialize(); //初始化
    if (res != OK) {
        return res;
    }

    mProviders.push_back(providerInfo); //备份

    return OK;
}

8.2这里需要关注 spprovider::V2_4::ICameraProvider interface这里的interface,最终指向了CameraProvider.cpp,不过我们需要先关注上面的构建和初始化providerInfo->initialize(),代码如下:


status_t CameraProviderManager::ProviderInfo::initialize() {
    status_t res = parseProviderName(mProviderName, &mType, &mId);
    if (res != OK) {
        ALOGE("%s: Invalid provider name, ignoring", __FUNCTION__);
        return BAD_VALUE;
    }
    ALOGI("Connecting to new camera provider: %s, isRemote? %d",
            mProviderName.c_str(), mInterface->isRemote());
    // cameraDeviceStatusChange callbacks may be called (and causing new devices added)
    // before setCallback returns
    hardware::Return<Status> status = mInterface->setCallback(this);
    if (!status.isOk()) {
        ALOGE("%s: Transaction error setting up callbacks with camera provider '%s': %s",
                __FUNCTION__, mProviderName.c_str(), status.description().c_str());
        return DEAD_OBJECT;
    }
    if (status != Status::OK) {
        ALOGE("%s: Unable to register callbacks with camera provider '%s'",
                __FUNCTION__, mProviderName.c_str());
        return mapToStatusT(status);
    }

    hardware::Return<bool> linked = mInterface->linkToDeath(this, /*cookie*/ mId);
    if (!linked.isOk()) {
        ALOGE("%s: Transaction error in linking to camera provider '%s' death: %s",
                __FUNCTION__, mProviderName.c_str(), linked.description().c_str());
        return DEAD_OBJECT;
    } else if (!linked) {
        ALOGW("%s: Unable to link to provider '%s' death notifications",
                __FUNCTION__, mProviderName.c_str());
    }

    // Get initial list of camera devices, if any
    std::vector<std::string> devices;
    hardware::Return<void> ret = mInterface->getCameraIdList([&status, &devices](
            Status idStatus,
            const hardware::hidl_vec<hardware::hidl_string>& cameraDeviceNames) {
        status = idStatus;
        if (status == Status::OK) {
            for (size_t i = 0; i < cameraDeviceNames.size(); i++) {
                devices.push_back(cameraDeviceNames[i]);
            }
        } });
    if (!ret.isOk()) {
        ALOGE("%s: Transaction error in getting camera ID list from provider '%s': %s",
                __FUNCTION__, mProviderName.c_str(), linked.description().c_str());
        return DEAD_OBJECT;
    }
    if (status != Status::OK) {
        ALOGE("%s: Unable to query for camera devices from provider '%s'",
                __FUNCTION__, mProviderName.c_str());
        return mapToStatusT(status);
    }

    sp<StatusListener> listener = mManager->getStatusListener();
    for (auto& device : devices) {
        std::string id;
        status_t res = addDevice(device,
                hardware::camera::common::V1_0::CameraDeviceStatus::PRESENT, &id);//添加device
        if (res != OK) {
            ALOGE("%s: Unable to enumerate camera device '%s': %s (%d)",
                    __FUNCTION__, device.c_str(), strerror(-res), res);
            continue;
        }
    }

    ALOGI("Camera provider %s ready with %zu camera devices",
            mProviderName.c_str(), mDevices.size());

    mInitialized = true;
    return OK;
}

8.3这里主要关注上面的添加设备这块儿

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

    ALOGI("Enumerating new camera device: %s", name.c_str());

    uint16_t major, minor;
    std::string type, id;

    status_t res = parseDeviceName(name, &major, &minor, &type, &id);
    if (res != OK) {
        return res;
    }
    if (type != mType) {
        ALOGE("%s: Device type %s does not match provider type %s", __FUNCTION__,
                type.c_str(), mType.c_str());
        return BAD_VALUE;
    }
    if (mManager->isValidDeviceLocked(id, major)) {
        ALOGE("%s: Device %s: ID %s is already in use for device major version %d", __FUNCTION__,
                name.c_str(), id.c_str(), major);
        return BAD_VALUE;
    }

    std::unique_ptr<DeviceInfo> deviceInfo;
    switch (major) {
    	//实例化
        case 1:
            deviceInfo = initializeDeviceInfo<DeviceInfo1>(name, mProviderTagid,
                    id, minor);
            break;
        case 3:
            deviceInfo = initializeDeviceInfo<DeviceInfo3>(name, mProviderTagid,
                    id, minor);
            break;
        default:
            ALOGE("%s: Device %s: Unknown HIDL device HAL major version %d:", __FUNCTION__,
                    name.c_str(), major);
            return BAD_VALUE;
    }
    if (deviceInfo == nullptr) return BAD_VALUE;
    deviceInfo->mStatus = initialStatus;
    bool isAPI1Compatible = deviceInfo->isAPI1Compatible();

    mDevices.push_back(std::move(deviceInfo));

    mUniqueCameraIds.insert(id);
    if (isAPI1Compatible) {
        mUniqueAPI1CompatibleCameraIds.push_back(id);
    }

    if (parsedId != nullptr) {
        *parsedId = id;
    }
    return OK;
}

8.5 实例化device代码如下:

template<class DeviceInfoT>
std::unique_ptr<CameraProviderManager::ProviderInfo::DeviceInfo>
    CameraProviderManager::ProviderInfo::initializeDeviceInfo(
        const std::string &name, const metadata_vendor_id_t tagId,
        const std::string &id, uint16_t minorVersion) const {
    Status status;

    auto cameraInterface =
            getDeviceInterface<typename DeviceInfoT::InterfaceT>(name); //获取HAL层远程接口
    if (cameraInterface == nullptr) return nullptr;

    CameraResourceCost resourceCost;
    cameraInterface->getResourceCost([&status, &resourceCost](
        Status s, CameraResourceCost cost) {
                status = s;
                resourceCost = cost;
            });
    if (status != Status::OK) {
        ALOGE("%s: Unable to obtain resource costs for camera device %s: %s", __FUNCTION__,
                name.c_str(), statusToString(status));
        return nullptr;
    }

    for (auto& conflictName : resourceCost.conflictingDevices) {
        uint16_t major, minor;
        std::string type, id;
        status_t res = parseDeviceName(conflictName, &major, &minor, &type, &id);
        if (res != OK) {
            ALOGE("%s: Failed to parse conflicting device %s", __FUNCTION__, conflictName.c_str());
            return nullptr;
        }
        conflictName = id;
    }

    return std::unique_ptr<DeviceInfo>(
        new DeviceInfoT(name, tagId, id, minorVersion, resourceCost,
                cameraInterface));
}

8.6 其中获取HAL远程接口代码如下:

template<>
sp<device::V3_2::ICameraDevice>
CameraProviderManager::ProviderInfo::getDeviceInterface
        <device::V3_2::ICameraDevice>(const std::string &name) const {
    Status status;
    sp<device::V3_2::ICameraDevice> cameraInterface;
    hardware::Return<void> ret;
    ret = mInterface->getCameraDeviceInterface_V3_x(name, [&status, &cameraInterface](
        Status s, sp<device::V3_2::ICameraDevice> interface) {
                status = s;
                cameraInterface = interface;
            });
    if (!ret.isOk()) {
        ALOGE("%s: Transaction error trying to obtain interface for camera device %s: %s",
                __FUNCTION__, name.c_str(), ret.description().c_str());
        return nullptr;
    }
    if (status != Status::OK) {
        ALOGE("%s: Unable to obtain interface for camera device %s: %s", __FUNCTION__,
                name.c_str(), statusToString(status));
        return nullptr;
    }
    return cameraInterface;
}

到了这里,可以看出ICameraDevice关联到了CameraDevice.cpp,那么providerInfo->initialize()就分析得差不多了,下面的就到了硬件层,回头来我们需要继续分析CameraProvider.cpp这里了,在这里就关注其初始化就可以了。

9. CameraProvider.cpp

文件路径:***/hardware/interfaces/camera/provider/2.4/default/CameraProvider.cpp***
代码如下:

bool CameraProvider::initialize() {
    camera_module_t *rawModule;
    int err = hw_get_module(CAMERA_HARDWARE_MODULE_ID,
            (const hw_module_t **)&rawModule);
    if (err < 0) {
        ALOGE("Could not load camera HAL module: %d (%s)", err, strerror(-err));
        return true;
    }

    mModule = new CameraModule(rawModule);
    err = mModule->init();
    if (err != OK) {
        ALOGE("Could not initialize camera HAL module: %d (%s)", err, strerror(-err));
        mModule.clear();
        return true;
    }
    ALOGI("Loaded \"%s\" camera module", mModule->getModuleName());

    // Setup vendor tags here so HAL can setup vendor keys in camera characteristics
    VendorTagDescriptor::clearGlobalVendorTagDescriptor();
    if (!setUpVendorTags()) {
        ALOGE("%s: Vendor tag setup failed, will not be available.", __FUNCTION__);
    }

    // Setup callback now because we are going to try openLegacy next
    err = mModule->setCallbacks(this);
    if (err != OK) {
        ALOGE("Could not set camera module callback: %d (%s)", err, strerror(-err));
        mModule.clear();
        return true;
    }

    mPreferredHal3MinorVersion =
        property_get_int32("ro.vendor.camera.wrapper.hal3TrebleMinorVersion", 3);
    ALOGV("Preferred HAL 3 minor version is %d", mPreferredHal3MinorVersion);
    switch(mPreferredHal3MinorVersion) {
        case 2:
        case 3:
            // OK
            break;
        default:
            ALOGW("Unknown minor camera device HAL version %d in property "
                    "'camera.wrapper.hal3TrebleMinorVersion', defaulting to 3",
                    mPreferredHal3MinorVersion);
            mPreferredHal3MinorVersion = 3;
    }

    mNumberOfLegacyCameras = mModule->getNumberOfCameras();
    for (int i = 0; i < mNumberOfLegacyCameras; i++) {
        struct camera_info info;
        auto rc = mModule->getCameraInfo(i, &info);
        if (rc != NO_ERROR) {
            ALOGE("%s: Camera info query failed!", __func__);
            mModule.clear();
            return true;
        }

        if (checkCameraVersion(i, info) != OK) {
            ALOGE("%s: Camera version check failed!", __func__);
            mModule.clear();
            return true;
        }

        char cameraId[kMaxCameraIdLen];
        snprintf(cameraId, sizeof(cameraId), "%d", i);
        std::string cameraIdStr(cameraId);
        mCameraStatusMap[cameraIdStr] = CAMERA_DEVICE_STATUS_PRESENT;

        addDeviceNames(i);
    }

    return false; // mInitFailed
}

这里就初始化了CameraMoudle。

CameraManagerGlobal.get().getCameraService()的实现

通过ServiceManager获的cameraService,CameraManager通过CameraManagerGlobal访问CameraService服务,并注册监听,CamreaService持有CameraServiceListener列表,并回调结果给CameraManager。

frameworks/base/core/java/android/hardware/camera2/CameraManager.java
private static final class CameraManagerGlobal extends ICameraServiceListener.Stub {
         public ICameraService getCameraService() {
           //连接服务
            connectCameraServiceLocked();
            return mCameraService;
        }
}
private void connectCameraServiceLocked() {
        //查询服务引用,CAMERA_SERVICE_BINDER_NAME="media.camera"
        IBinder cameraServiceBinder = ServiceManager.getService(CAMERA_SERVICE_BINDER_NAME);
        //转换服务接口
        ICameraService cameraService = ICameraService.Stub.asInterface(cameraServiceBinder);
        //注册回调监听,camerService可以通知CameraManagerGlobal状态变化
        CameraStatus[] cameraStatuses = cameraService.addListener(this);
        //存副本
        mCameraService = cameraService;
}
frameworks/av/services/camera/libcameraservice/CameraService.h
static char const* getServiceName() { return "media.camera"; }

采用camera2 api来获取相机设备的信息。

// Normal path: Get the camera characteristics directly from the camera service
CameraMetadataNative info = cameraService.getCameraCharacteristics(cameraId);
try {
	info.setCameraId(Integer.parseInt(cameraId));
} catch (NumberFormatException e) {
	Log.e(TAG, "Failed to parse camera Id " + cameraId + " to integer");
}
info.setDisplaySize(displaySize);

characteristics = new CameraCharacteristics(info);

DeviceInfo3

framework\av\services\camera\libcameraservice\common\CameraProviderManager.h

接下来分析Camera3Device的初始化,Camera3Device通过CameraService保存的CameraProviderManager对象获得mProviders,调用流程mProviders->DeviceInfo->CameraDevice3Impl->CameraDevice3SessionImpl,最终获得CameraDevice3SessionImpl对象,其中CameraDevice3Impl和CameraDevice3SessionImpl由厂商来实现。

DeviceInfo3是CameraProviderManager::ProviderInfo::DeviceInfo3,CameraProviderManager中的结构体,最终返回的是CameraMetadata类型,它是一个Parcelable类型,native中对应的代码是frameworks/av/camera/include/camera/CameraMetadata.h,java中对应的是frameworks/base/core/java/android/hardware/camera2/impl/CameraMetadataNative.java,Parcelable类型是可以跨进程传输的。下面是在native中定义CameraMetadata为CameraMetadataNative
framework\av\camera\include\camera\CameraMetadata.h

namespace hardware {
namespace camera2 {
namespace impl {
using ::android::CameraMetadata;
typedef CameraMetadata CameraMetadataNative;
}
}
}

framework\av\services\camera\libcameraservice\device3\Camera3Device.cpp
1.获取ICameraDeviceSession实例
sp session;
status_t res = manager->openSession(mld.string,this,&session);

2.获取RequestMetadataQueue>类型的queuemession->getCaptureRequestMetdataQueue([&queue])

3.创建HalInterface实例mInterface = new HalInterface(session,queue);

4.Common初始化initializeCommonLocked();

status_t Camera3Device::initialize(sp<CameraProviderManager> manager, const String8& monitorTags) {
    sp<ICameraDeviceSession> session;
    //通过CameraProviderManager打开对应的会话,this为ICameraDeviceCallback类型
    status_t res = manager->openSession(mId.string(), this,
            /*out*/ &session);
    //获得请求队列
    std::shared_ptr<RequestMetadataQueue> queue;
    auto requestQueueRet = session->getCaptureRequestMetadataQueue(
        [&queue](const auto& descriptor) {
            queue = std::make_shared<RequestMetadataQueue>(descriptor);
            if (!queue->isValid() || queue->availableToWrite() <= 0) {
                queue = nullptr;
            }
        });
   //获得结果队列,最终保存在mResultMetadataQueue对象中。
    std::unique_ptr<ResultMetadataQueue>& resQueue = mResultMetadataQueue;
    auto resultQueueRet = session->getCaptureResultMetadataQueue(
        [&resQueue](const auto& descriptor) {
            resQueue = std::make_unique<ResultMetadataQueue>(descriptor);
        });
    //封装CameraDevice3SessionImpl对象,包括请求队列
    mInterface = new HalInterface(session, queue);
}

我们关注其中的一个调用函数:
framework\av\services\camera\libcameraservice\common\CameraProviderManager.cpp

status_t CameraProviderManager::getCameraCharacteristicsLocked(const std::string &id,
        CameraMetadata* characteristics) const {
    auto deviceInfo = findDeviceInfoLocked(id, /*minVersion*/ {3,0}, /*maxVersion*/ {5,0});
    if (deviceInfo != nullptr) {
        return deviceInfo->getCameraCharacteristics(characteristics);
    }

    // Find hidden physical camera characteristics
    for (auto& provider : mProviders) {
        for (auto& deviceInfo : provider->mDevices) {
            status_t res = deviceInfo->getPhysicalCameraCharacteristics(id, characteristics);
            if (res != NAME_NOT_FOUND) return res;
        }
    }

    return NAME_NOT_FOUND;
}

发现了调用了一个findDeviceInfoLocked(…)函数,返回类型是一个DeviceInfo结构体,CameraProviderManager.h中定义了三个DeviceInfo结构体,除了DeviceInfo之外,还有DeviceInfo1与DeviceInfo3,他们都继承DeviceInfo,其中DeviceInfo1为HALv1服务,DeviceInfo3为HALv3-specific服务,都是提供camera device一些基本信息。这里主要看下findDeviceInfoLocked(…)函数:

CameraProviderManager::ProviderInfo::DeviceInfo* CameraProviderManager::findDeviceInfoLocked(
        const std::string& id,
        hardware::hidl_version minVersion, hardware::hidl_version maxVersion) const {
    for (auto& provider : mProviders) {
        for (auto& deviceInfo : provider->mDevices) {
            if (deviceInfo->mId == id &&
                    minVersion <= deviceInfo->mVersion && maxVersion >= deviceInfo->mVersion) {
                return deviceInfo.get();
            }
        }
    }
    return nullptr;
}

mProviders是ProviderInfo类型的列表,这个ProviderInfo也是CameraProviderManager.h中定义的结构体,并且上面3种DeviceInfo都是定义在ProviderInfo里面的。下面给出了ProviderInfo的代码大纲,裁剪了很多代码,但是我们还是能看到核心的代码:ProviderInfo是管理当前手机的camera device设备的,通过addDevice保存在mDevices中,接下来我们看下这个addDevice是如何工作的。

struct ProviderInfo :
		virtual public hardware::camera::provider::V2_4::ICameraProviderCallback,
		virtual public hardware::hidl_death_recipient
{
//......
	ProviderInfo(const std::string &providerName,
			sp<hardware::camera::provider::V2_4::ICameraProvider>& interface,
			CameraProviderManager *manager);
	~ProviderInfo();

	status_t initialize();

	const std::string& getType() const;

	status_t addDevice(const std::string& name,
			hardware::camera::common::V1_0::CameraDeviceStatus initialStatus =
			hardware::camera::common::V1_0::CameraDeviceStatus::PRESENT,
			/*out*/ std::string *parsedId = nullptr);

	// ICameraProviderCallbacks interface - these lock the parent mInterfaceMutex
	virtual hardware::Return<void> cameraDeviceStatusChange(
			const hardware::hidl_string& cameraDeviceName,
			hardware::camera::common::V1_0::CameraDeviceStatus newStatus) override;
	virtual hardware::Return<void> torchModeStatusChange(
			const hardware::hidl_string& cameraDeviceName,
			hardware::camera::common::V1_0::TorchModeStatus newStatus) override;

	// hidl_death_recipient interface - this locks the parent mInterfaceMutex
	virtual void serviceDied(uint64_t cookie, const wp<hidl::base::V1_0::IBase>& who) override;

	// Basic device information, common to all camera devices
	struct DeviceInfo {
		//......
	};
	std::vector<std::unique_ptr<DeviceInfo>> mDevices;
	std::unordered_set<std::string> mUniqueCameraIds;
	int mUniqueDeviceCount;

	// HALv1-specific camera fields, including the actual device interface
	struct DeviceInfo1 : public DeviceInfo {
		//......
	};

	// HALv3-specific camera fields, including the actual device interface
	struct DeviceInfo3 : public DeviceInfo {
		//......
	};

private:
	void removeDevice(std::string id);
};


mProviders添加的流程:

1.CameraService --> onFirstRef()
2.CameraService --> enumerateProviders()
3.CameraProviderManager --> initialize(this)
initialize(…)函数原型是:

status_t initialize(wp<StatusListener> listener,
            ServiceInteractionProxy *proxy = &sHardwareServiceInteractionProxy);

第2个参数默认是sHardwareServiceInteractionProxy类型,

    struct ServiceInteractionProxy {
        virtual bool registerForNotifications(
                const std::string &serviceName,
                const sp<hidl::manager::V1_0::IServiceNotification>
                &notification) = 0;
        virtual sp<hardware::camera::provider::V2_4::ICameraProvider> getService(
                const std::string &serviceName) = 0;
        virtual ~ServiceInteractionProxy() {}
    };

    // Standard use case - call into the normal generated static methods which invoke
    // the real hardware service manager
    struct HardwareServiceInteractionProxy : public ServiceInteractionProxy {
        virtual bool registerForNotifications(
                const std::string &serviceName,
                const sp<hidl::manager::V1_0::IServiceNotification>
                &notification) override {
            return hardware::camera::provider::V2_4::ICameraProvider::registerForNotifications(
                    serviceName, notification);
        }
        virtual sp<hardware::camera::provider::V2_4::ICameraProvider> getService(
                const std::string &serviceName) override {
            return hardware::camera::provider::V2_4::ICameraProvider::getService(serviceName);
        }
    };


hardware:

标签:__,return,Camera2,cameraId,id,camera,OpenCamera,const,流程
来源: https://blog.csdn.net/yaoming168/article/details/111398013