openCamera

CameraManager
文件路径:/frameworks/base/core/java/android/hardware/camera2/CameraManager.java
上层调用的API有两个,分别如下:

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

但是两种实际都是调用了 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);    }

这里做了容错性判断,紧接着调用了 openCameraDeviceUserAsync(cameraId, callback, executor, clientUid),此方法也是在当前文件中,实现如下:

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;            android.hardware.camera2.impl.CameraDeviceImpl deviceImpl =                    new android.hardware.camera2.impl.CameraDeviceImpl(                        cameraId,                        callback,                        executor,                        characteristics,                        mContext.getApplicationInfo().targetSdkVersion);            ICameraDeviceCallbacks callbacks = deviceImpl.getCallbacks();            try {                if (supportsCamera2ApiLocked(cameraId)) {                    // Use cameraservice's cameradeviceclient implementation for HAL3.2+ devices                    ICameraService cameraService = CameraManagerGlobal.get().getCameraService();                    if (cameraService == null) {                        throw new ServiceSpecificException(                            ICameraService.ERROR_DISCONNECTED,                            "Camera service is currently unavailable");                    }                    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);                }            } catch (ServiceSpecificException e) {                if (e.errorCode == ICameraService.ERROR_DEPRECATED_HAL) {                    throw new AssertionError("Should've gone down the shim path");                } else if (e.errorCode == ICameraService.ERROR_CAMERA_IN_USE ||                        e.errorCode == ICameraService.ERROR_MAX_CAMERAS_IN_USE ||                        e.errorCode == ICameraService.ERROR_DISABLED ||                        e.errorCode == ICameraService.ERROR_DISCONNECTED ||                        e.errorCode == ICameraService.ERROR_INVALID_OPERATION) {                    // Received one of the known connection errors                    // The remote camera device cannot be connected to, so                    // set the local camera to the startup error state                    deviceImpl.setRemoteFailure(e);                    if (e.errorCode == ICameraService.ERROR_DISABLED ||                            e.errorCode == ICameraService.ERROR_DISCONNECTED ||                            e.errorCode == ICameraService.ERROR_CAMERA_IN_USE) {                        // Per API docs, these failures call onError and throw                        throwAsPublicException(e);                    }                } else {                    // Unexpected failure - rethrow                    throwAsPublicException(e);                }            } catch (RemoteException e) {                // Camera service died - act as if it's a CAMERA_DISCONNECTED case                ServiceSpecificException sse = new ServiceSpecificException(                    ICameraService.ERROR_DISCONNECTED,                    "Camera service is currently unavailable");                deviceImpl.setRemoteFailure(sse);                throwAsPublicException(sse);            }            // 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);            device = deviceImpl;        }        return device;    }

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

Status CameraService::connectDevice(        const sp& cameraCb,        const String16& cameraId,        const String16& clientPackageName,        int clientUid,        /*out*/        sp* device) {    ATRACE_CALL();    Status ret = Status::ok();    String8 id = String8(cameraId);    sp client = nullptr;    ret = connectHelper(cameraCb, id,            /*api1CameraId*/-1,            CAMERA_HAL_API_VERSION_UNSPECIFIED, clientPackageName,            clientUid, USE_CALLING_PID, API_2,            /*legacyMode*/ false, /*shimUpdateOnly*/ false,            /*out*/client);    if(!ret.isOk()) {        logRejected(id, getCallingPid(), String8(clientPackageName),                ret.toString8());        return ret;    }    *device = client;    return ret;}

不难发现这里第13行调用了connectHelper来实现连接相机的逻辑,具体代码如下:

Status CameraService::connectHelper(const sp& cameraCb, const String8& cameraId,        int api1CameraId, int halVersion, const String16& clientPackageName, int clientUid,        int clientPid, apiLevel effectiveApiLevel, bool legacyMode, bool shimUpdateOnly,        /*out*/sp& device) {    binder::Status ret = binder::Status::ok();    String8 clientName8(clientPackageName);    int originalClientPid = 0;    ALOGI("CameraService::connect call (PID %d \"%s\", camera ID %s) for HAL version %s and "            "Camera API version %d", clientPid, clientName8.string(), cameraId.string(),            (halVersion == -1) ? "default" : std::to_string(halVersion).c_str(),            static_cast(effectiveApiLevel));    sp client = nullptr;    {        // Acquire mServiceLock and prevent other clients from connecting        std::unique_ptr lock =                AutoConditionLock::waitAndAcquire(mServiceLockWrapper, DEFAULT_CONNECT_TIMEOUT_NS);        if (lock == nullptr) {            ALOGE("CameraService::connect (PID %d) rejected (too many other clients connecting)."                    , clientPid);            return STATUS_ERROR_FMT(ERROR_MAX_CAMERAS_IN_USE,                    "Cannot open camera %s for \"%s\" (PID %d): Too many other clients connecting",                    cameraId.string(), clientName8.string(), clientPid);        }        // Enforce client permissions and do basic sanity checks        if(!(ret = validateConnectLocked(cameraId, clientName8,                /*inout*/clientUid, /*inout*/clientPid, /*out*/originalClientPid)).isOk()) {            return ret;        }        // Check the shim parameters after acquiring lock, if they have already been updated and        // we were doing a shim update, return immediately        if (shimUpdateOnly) {            auto cameraState = getCameraState(cameraId);            if (cameraState != nullptr) {                if (!cameraState->getShimParams().isEmpty()) return ret;            }        }        status_t err;        sp clientTmp = nullptr;        std::shared_ptr>> partial;        if ((err = handleEvictionsLocked(cameraId, originalClientPid, effectiveApiLevel,                IInterface::asBinder(cameraCb), clientName8, /*out*/&clientTmp,                /*out*/&partial)) != NO_ERROR) {            switch (err) {                case -ENODEV:                    return STATUS_ERROR_FMT(ERROR_DISCONNECTED,                            "No camera device with ID \"%s\" currently available",                            cameraId.string());                case -EBUSY:                    return STATUS_ERROR_FMT(ERROR_CAMERA_IN_USE,                            "Higher-priority client using camera, ID \"%s\" currently unavailable",                            cameraId.string());                default:                    return STATUS_ERROR_FMT(ERROR_INVALID_OPERATION,                            "Unexpected error %s (%d) opening camera \"%s\"",                            strerror(-err), err, cameraId.string());            }        }        if (clientTmp.get() != nullptr) {            // Handle special case for API1 MediaRecorder where the existing client is returned            device = static_cast(clientTmp.get());            return ret;        }        // give flashlight a chance to close devices if necessary.        mFlashlight->prepareDeviceOpen(cameraId);        int facing = -1;        int deviceVersion = getDeviceVersion(cameraId, /*out*/&facing);        if (facing == -1) {            ALOGE("%s: Unable to get camera device \"%s\"  facing", __FUNCTION__, cameraId.string());            return STATUS_ERROR_FMT(ERROR_INVALID_OPERATION,                    "Unable to get camera device \"%s\" facing", cameraId.string());        }        sp tmp = nullptr;        if(!(ret = makeClient(this, cameraCb, clientPackageName,                cameraId, api1CameraId, facing,                clientPid, clientUid, getpid(), legacyMode,                halVersion, deviceVersion, effectiveApiLevel,                /*out*/&tmp)).isOk()) {            return ret;        }        client = static_cast(tmp.get());        LOG_ALWAYS_FATAL_IF(client.get() == nullptr, "%s: CameraService in invalid state",                __FUNCTION__);        err = client->initialize(mCameraProviderManager, mMonitorTags);        if (err != OK) {            ALOGE("%s: Could not initialize client from HAL.", __FUNCTION__);            // Errors could be from the HAL module open call or from AppOpsManager            switch(err) {                case BAD_VALUE:                    return STATUS_ERROR_FMT(ERROR_ILLEGAL_ARGUMENT,                            "Illegal argument to HAL module for camera \"%s\"", cameraId.string());                case -EBUSY:                    return STATUS_ERROR_FMT(ERROR_CAMERA_IN_USE,                            "Camera \"%s\" is already open", cameraId.string());                case -EUSERS:                    return STATUS_ERROR_FMT(ERROR_MAX_CAMERAS_IN_USE,                            "Too many cameras already open, cannot open camera \"%s\"",                            cameraId.string());                case PERMISSION_DENIED:                    return STATUS_ERROR_FMT(ERROR_PERMISSION_DENIED,                            "No permission to open camera \"%s\"", cameraId.string());                case -EACCES:                    return STATUS_ERROR_FMT(ERROR_DISABLED,                            "Camera \"%s\" disabled by policy", cameraId.string());                case -ENODEV:                default:                    return STATUS_ERROR_FMT(ERROR_INVALID_OPERATION,                            "Failed to initialize camera \"%s\": %s (%d)", cameraId.string(),                            strerror(-err), err);            }        }        // Update shim paremeters for legacy clients        if (effectiveApiLevel == API_1) {            // Assume we have always received a Client subclass for API1            sp shimClient = reinterpret_cast(client.get());            String8 rawParams = shimClient->getParameters();            CameraParameters params(rawParams);            auto cameraState = getCameraState(cameraId);            if (cameraState != nullptr) {                cameraState->setShimParams(params);            } else {                ALOGE("%s: Cannot update shim parameters for camera %s, no such device exists.",                        __FUNCTION__, cameraId.string());            }        }        if (shimUpdateOnly) {            // If only updating legacy shim parameters, immediately disconnect client            mServiceLock.unlock();            client->disconnect();            mServiceLock.lock();        } else {            // Otherwise, add client to active clients list            finishConnectLocked(client, partial);        }    } // lock is destroyed, allow further connect calls    // Important: release the mutex here so the client can call back into the service from its    // destructor (can be at the end of the call)    device = client;    return ret;}

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

Status CameraService::makeClient(const sp& cameraService,        const sp& 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* client) {    if (halVersion < 0 || halVersion == deviceVersion) {        // Default path: HAL version is unspecified by caller, create CameraClient        // based on device version reported by the HAL.        switch(deviceVersion) {          case CAMERA_DEVICE_API_VERSION_1_0:            if (effectiveApiLevel == API_1) {  // Camera1 API route                sp tmp = static_cast(cameraCb.get());                *client = new CameraClient(cameraService, tmp, packageName,                        api1CameraId, facing, clientPid, clientUid,                        getpid(), legacyMode);            } else { // Camera2 API route                ALOGW("Camera using old HAL version: %d", deviceVersion);                return STATUS_ERROR_FMT(ERROR_DEPRECATED_HAL,                        "Camera device \"%s\" HAL version %d does not support camera2 API",                        cameraId.string(), deviceVersion);            }            break;          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 tmp = static_cast(cameraCb.get());                *client = new Camera2Client(cameraService, tmp, packageName,                        cameraId, api1CameraId,                        facing, clientPid, clientUid,                        servicePid, legacyMode);            } else { // Camera2 API route                sp tmp =                        static_cast(cameraCb.get());                *client = new CameraDeviceClient(cameraService, tmp, packageName, cameraId,                        facing, clientPid, clientUid, servicePid);            }            break;          default:            // Should not be reachable            ALOGE("Unknown camera device HAL version: %d", deviceVersion);            return STATUS_ERROR_FMT(ERROR_INVALID_OPERATION,                    "Camera device \"%s\" has unknown HAL version %d",                    cameraId.string(), deviceVersion);        }    } else {        // A particular HAL version is requested by caller. Create CameraClient        // based on the requested HAL version.        if (deviceVersion > CAMERA_DEVICE_API_VERSION_1_0 &&            halVersion == CAMERA_DEVICE_API_VERSION_1_0) {            // Only support higher HAL version device opened as HAL1.0 device.            sp tmp = static_cast(cameraCb.get());            *client = new CameraClient(cameraService, tmp, packageName,                    api1CameraId, facing, clientPid, clientUid,                    servicePid, legacyMode);        } else {            // Other combinations (e.g. HAL3.x open as HAL2.x) are not supported yet.            ALOGE("Invalid camera HAL version %x: HAL %x device can only be"                    " opened as HAL %x device", halVersion, deviceVersion,                    CAMERA_DEVICE_API_VERSION_1_0);            return STATUS_ERROR_FMT(ERROR_ILLEGAL_ARGUMENT,                    "Camera device \"%s\" (HAL version %d) cannot be opened as HAL version %d",                    cameraId.string(), deviceVersion, halVersion);        }    }    return Status::ok();}

这一块儿基本就是根据API版本和Device版本来实例化Client的,在Android P 和Camera2的框架上,这里需要跟进的是38-39行,这里CameraDeviceClient方法是由CameraDeviceClient.cpp实现的。
CameraDeviceClient.cpp
文件路径:/frameworks/av/services/camera/libcameraservice/api2/CameraDeviceClient.cpp

CameraDeviceClient::CameraDeviceClient(const sp& cameraService,        const sp& 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) {    ATRACE_CALL();    ALOGI("CameraDeviceClient %s: Opened", cameraId.string());}

这里关注第9行,发现又调用了Camera2ClientBase方法,实现代码如下:

Camera2ClientBase::Camera2ClientBase(        const sp& cameraService,        const sp& remoteCallback,        const String16& clientPackageName,        const String8& cameraId,        int api1CameraId,        int cameraFacing,        int clientPid,        uid_t clientUid,        int servicePid):        TClientBase(cameraService, remoteCallback, clientPackageName,                cameraId, api1CameraId, cameraFacing, clientPid, clientUid, servicePid),        mSharedCameraCallbacks(remoteCallback),        mDeviceVersion(cameraService->getDeviceVersion(TClientBase::mCameraIdStr)),        mDeviceActive(false), mApi1CameraId(api1CameraId){    ALOGI("Camera %s: Opened. Client: %s (PID %d, UID %d)", cameraId.string(),            String8(clientPackageName).string(), clientPid, clientUid);    mInitialClientPid = clientPid;    mDevice = new Camera3Device(cameraId);    LOG_ALWAYS_FATAL_IF(mDevice == 0, "Device should never be NULL here.");}

好吧,第21行mDevice = new Camera3Device(cameraId)才是重点,是由Camera3Device.cpp实现的。
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 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 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 queue;    auto requestQueueRet = session->getCaptureRequestMetadataQueue(        [&queue](const auto& descriptor) {            queue = std::make_shared(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& resQueue = mResultMetadataQueue;    auto resultQueueRet = session->getCaptureResultMetadataQueue(        [&resQueue](const auto& descriptor) {            resQueue = std::make_unique(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();}

代码中第15行 res = manager->openSession 就是走向open的地方了,但是还是需要继续到一个方法,不难发现openSession方法由CameraProviderManager.cpp实现。此外在这里我们还需要注意第31和47行,第31行是请求队列,47行是结果队列在下一篇中将使用到。

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

status_t CameraProviderManager::openSession(const std::string &id,        const sp& callback,        /*out*/        sp *session) {    std::lock_guard lock(mInterfaceMutex);    auto deviceInfo = findDeviceInfoLocked(id,            /*minVersion*/ {3,0}, /*maxVersion*/ {4,0});    if (deviceInfo == nullptr) return NAME_NOT_FOUND;    auto *deviceInfo3 = static_cast(deviceInfo);    Status status;    hardware::Return ret;    ret = deviceInfo3->mInterface->open(callback, [&status, &session]            (Status s, const sp& 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);}

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

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

Return CameraDevice::open(const sp& callback, open_cb _hidl_cb)  {    Status status = initStatus();    sp 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(&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();}

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

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层。
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();}

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

status_t CameraService::enumerateProviders() {    status_t res;    std::vector 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的初始化实现如下。
CameraProviderManager.cpp
文件路径:***/frameworks/av/services/camera/libcameraservice/common/CameraProviderManager.cpp***
具体代码如下:

status_t CameraProviderManager::initialize(wp listener,        ServiceInteractionProxy* proxy) {    std::lock_guard 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;}

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 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 =            new ProviderInfo(newProvider, interface, this); //构建    status_t res = providerInfo->initialize(); //初始化    if (res != OK) {        return res;    }    mProviders.push_back(providerInfo); //备份    return OK;}

这里需要关注 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 = 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 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 devices;    hardware::Return ret = mInterface->getCameraIdList([&status, &devices](            Status idStatus,            const hardware::hidl_vec& 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 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;}

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

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;    switch (major) {    //实例化        case 1:            deviceInfo = initializeDeviceInfo(name, mProviderTagid,                    id, minor);            break;        case 3:            deviceInfo = initializeDeviceInfo(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;}

其中实例化device代码如下:

templatestd::unique_ptr    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(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(        new DeviceInfoT(name, tagId, id, minorVersion, resourceCost,                cameraInterface));}

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

template<>spCameraProviderManager::ProviderInfo::getDeviceInterface        (const std::string &name) const {    Status status;    sp cameraInterface;    hardware::Return ret;    ret = mInterface->getCameraDeviceInterface_V3_x(name, [&status, &cameraInterface](        Status s, sp 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这里了,在这里就关注其初始化就可以了。
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。

更多相关文章

  1. android sql 批量处理插入/修改/删除 操作通用代码
  2. Android之文件搜索工具类
  3. Android写sys文件节点
  4. Android 7.0以上和7.0以下获取USB,sdcard路径的方法
  5. android 图片处理方法(整理)
  6. android XML文件常用字符转义
  7. Android 方法调用堆栈信息显示
  8. Android查看电池电量的方法(基于BroadcastReceiver)
  9. Android功能代码

随机推荐

  1. 【Linux学习】OpenCV+ROS 实现人脸识别(Ub
  2. 常用的两种伪类选择器
  3. 伪类和伪元素和盒模型
  4. Ubuntu软件更新更换源
  5. CSS常用伪类选择器的总结与盒子模型的简
  6. 0707伪类选择器/盒模型
  7. html基础:css伪类选择器的使用和盒模型的
  8. 选择器和盒模型
  9. 伪类选择器的使用与盒模型属性使用方式
  10. 伪类选择器以及盒模型常用属性