本讲是Android Camera Native Framework专题的第9讲,我们介绍cameraserver进程启动之HIDL CameraProvider初始化。
更多资源:
资源 | 描述 |
---|---|
在线课程 | 极客笔记在线课程 |
知识星球 | 星球名称:深入浅出Android Camera 星球ID: 17296815 |
极客笔记圈 |
HIDL Camera Provider初始化
HIDL Camera Provider初始化流程如下:
initializeHidlProvider详解
代码基于Android 13:
status_t HidlProviderInfo::initializeHidlProvider( sp<provider::V2_4::ICameraProvider>& interface, int64_t currentDeviceState) { 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(), interface->isRemote());
// Determine minor version mMinorVersion = 4; auto cast2_6 = provider::V2_6::ICameraProvider::castFrom(interface); sp<provider::V2_6::ICameraProvider> interface2_6 = nullptr; if (cast2_6.isOk()) { interface2_6 = cast2_6; if (interface2_6 != nullptr) { mMinorVersion = 6; } } // We need to check again since cast2_6.isOk() succeeds even if the provider // version isn't actually 2.6. if (interface2_6 == nullptr){ auto cast2_5 = provider::V2_5::ICameraProvider::castFrom(interface); sp<provider::V2_5::ICameraProvider> interface2_5 = nullptr; if (cast2_5.isOk()) { interface2_5 = cast2_5; if (interface != nullptr) { mMinorVersion = 5; } } } else { auto cast2_7 = provider::V2_7::ICameraProvider::castFrom(interface); if (cast2_7.isOk()) { sp<provider::V2_7::ICameraProvider> interface2_7 = cast2_7; if (interface2_7 != nullptr) { mMinorVersion = 7; } } } // cameraDeviceStatusChange callbacks may be called (and causing new devices added) // before setCallback returns hardware::Return<Status> status = interface->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 = interface->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()); } if (!kEnableLazyHal) { // Save HAL reference indefinitely mSavedInterface = interface; } else { mActiveInterface = interface; } ALOGV("%s: Setting device state for %s: 0x%" PRIx64, __FUNCTION__, mProviderName.c_str(), mDeviceState); notifyDeviceStateChange(currentDeviceState); res = setUpVendorTags(); if (res != OK) { ALOGE("%s: Unable to set up vendor tags from provider '%s'", __FUNCTION__, mProviderName.c_str()); return res; } // Get initial list of camera devices, if any std::vector<std::string> devices; hardware::Return<void> ret = interface->getCameraIdList([&status, this, &devices]( Status idStatus, const hardware::hidl_vec<hardware::hidl_string>& cameraDeviceNames) { status = idStatus; if (status == Status::OK) { for (auto& name : cameraDeviceNames) { uint16_t major, minor; std::string type, id; status_t res = parseDeviceName(name, &major, &minor, &type, &id); if (res != OK) { ALOGE("%s: Error parsing deviceName: %s: %d", __FUNCTION__, name.c_str(), res); status = Status::INTERNAL_ERROR; } else { devices.push_back(name); mProviderPublicCameraIds.push_back(id); } } } }); 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); } // Get list of concurrent streaming camera device combinations if (mMinorVersion >= 6) { res = getConcurrentCameraIdsInternalLocked(interface2_6); if (res != OK) { return res; } } ret = interface->isSetTorchModeSupported( [this](auto status, bool supported) { if (status == Status::OK) { mSetTorchModeSupported = supported; } }); if (!ret.isOk()) { ALOGE("%s: Transaction error checking torch mode support '%s': %s", __FUNCTION__, mProviderName.c_str(), ret.description().c_str()); return DEAD_OBJECT; } mIsRemote = interface->isRemote(); initializeProviderInfoCommon(devices); return OK;
}
解释:
-
通过castFrom来判断ICameraProvider的mMinorVersion
-
调用setCallback方法,接收ICameraProviderCallback的回调
-
调用linkToDeath方法,在serviceDied处理HAL进程挂掉后的异常,remove掉Provider
-
调用notifyDeviceStateChange通知Camera HAL进程,当前摄像头的状态(NORMAL/BACK_COVERED/FRONT_COVERED/FOLDED,可以一次性通知多个状态),该功能在Provider 2.5及之后的版本才有
-
setUpVendorTags,调用ICameraProvider的getVendorTags方法拿到VendorTagSection,然后创建VendorTagDescriptor,通过VendorTagDescriptor就能知道有哪些Vendor Tag了
-
调用ICameraProvider的getCameraIdList方法获取到当前Provider支持的Camera Device,解析出Camera ID存放在mProviderPublicCameraIds(解析规则解读)
-
针对Provider >= 2.6
- 调用Provider的getConcurrentStreamingCameraIds获取哪些Camera可以同时做ConfigureStream,存放在mConcurrentCameraIdCombinations
-
调用Provider的isSetTorchModeSupported判断是否支持手电筒,存放在mSetTorchModeSupported
-
调用initializeProviderInfoCommon,完成Device的初始化