当前位置:首页>技术文档>高通CamX初始化流程

高通CamX初始化流程

(1)
|--> CameraProvider::initialize() //#LegacyCameraProviderImpl_2_4.cpp CameraProvider初始化
|--> hw_get_module(CAMERA_HARDWARE_MODULE_ID,(const hw_module_t **)&rawModule); // 获取CAMERA_HARDWARE_MODULE_ID的hw_moduke, 也就是camera.qcom.so
| |--> camxhal3entry.cpp(CAMERA_HARDWARE_MODULE_ID) // camera.qcom.so的入口
|--> mModule = new CameraModule(rawModule);
|--> mModule->init();
| |--> CameraModule::init() //#CameraModule.cpp]
| | |--> mModule->init(); <--> Camx::init //camxhal3entry.cpp CamX初始化
| | |--> getNumberOfCameras() // 获取镜头的数量
| | | |--> numCameras = mModule->get_number_of_cameras(); <--> camxhal3entry.cpp() // 继续通过hardware获取镜头数量
| | | | |--> CamX::get_number_of_cameras --> (2) //camxhal3entry.cpp 比较庞大的函数,请进入(2)继续
|--> VendorTagDescriptor::clearGlobalVendorTagDescriptor();
|--> mModule->setCallbacks(this); <--> CameraModule::setCallbacks
| |--> mModule->set_callbacks(callbacks); <--> camxhal3entry.cpp(CamX::set_callbacks)

(2)
CamX::get_number_of_cameras()
|--> get_number_of_cameras() //#camxhal3.cpp
| |--> HAL3Module::GetInstance() //#camxhal3module.cpp 创建单实例的HAL3Module, HAL3Module将成为CamX与HwEnvironment的接口封装
| | |--> HAL3Module::HAL3Module // HAL3Module构造,并进行初始化
| | | |--> HwEnvironment::GetInstance()->GetSettingsManager()->GetStaticSettings() //#camxhwenvironment.cpp
| | | |--> HwEnvironment::GetInstance() // 开始涉及到HwEnvironment, 对底层硬件环境的进一步封装
| | | | |--> HwEnvironment::HwEnvironment()
| | | | | |--> HwEnvironment::Initialize() // 初始化,功能较多,函数较长,跟踪(3)继续
| | | | | | |--> ... (3)
| | | | | |--> HwEnvironment::InitCaps // 继续初始化
| | | | | | |--> EnumerateDevices(); // 获取HwEnvironment.Initialize过程中通过entity获取的所有设备,填充到m_cslDeviceTable表中
| | | | | | | |--> CSLEnumerateDevices(&device); //#camxcsl.cpp 通过CSL层进行调用封装
| | | | | | | | |--> pJumpTable->CSLEnumerateDevices(pDeviceDescriptor) (CSLEnumerateDevicesHW) // 进一步封装,从HAL3Module->HwEnvironment->pJumpTable(pJumpTableHW, CSLEnumerateDevicesHW), 封装到CSLEnumerateDevicesHW
| | | | | | | |--> GetEEbinDeviceIndex() // 同上
| | | | | | | | |--> CSLQueryDeviceCapabilities();
| | | | | | | | | |--> pJumpTable->CSLQueryDeviceCapabilities(deviceIndex, pDeviceData, deviceDataSize);
| | | | | | |--> ProbeImageSensorModules(); // Sensor的管理模块, 包含sensorModule,包含Tunning等各种管理初始化, 主要是Sensor的各种Tuning数据都在Bin文件中
| | | | | | | | | |--> ImageSensorModuleDataManager::Create(&pSensorManager, this); //#camximagesensormoduledatamanager.cpp 创建ImageSensorModuleDataManager
| | | | | | | | | | |--> pManager = CAMX_NEW ImageSensorModuleDataManager()
| | | | | | | | | | |--> pManager->Initialize(); <-->(ImageSensorModuleDataManager::Initialize)
| | | | | | | | | | | |-->CreateAllSensorModuleSetManagers(); // sensor参数管理接口,包括imx333 sensor, liteon sensor, ov7251, s5k3m3sn03
| | | | | | | | | | | | |--> pEEBinDataObj = CAMX_NEW EEbinData(m_pEnv->m_eebinDeviceIndex, 0);
| | | | | | | | | | | | |--> pEEBinDataObj->ReadEEBin() <--> EEbinData::ReadEEBin() //#camxeebindata.cpp
| | | | | | | | | | | | |--> fileCountMM = pEEBinDataObj->GetEEBinModules(&binaryFiles[0][0], FILENAME_MAX); <--> EEbinData::GetEEBinModules
| | | | | | | | | | | | |--> fileCount = OsUtils::GetFilesFromPath(SensorModulesPath, FILENAME_MAX, &binaryFiles[0][0], "*", "sensormodule", "*", "bin");
| | | | | | | | | | | | |--> GetSensorModuleManagerObj(&binaryFiles[i][0], &pSensorModuleSetManager);
| | | | | | | | | | | | | |--> pFile = OsUtils::FOpen(pBinName, "rb");
| | | | | | | | | | | | | |--> OsUtils::GetFileSize(pBinName);
| | | | | | | | | | | | | |--> pSensorModuleSetManager = CAMX_NEW ImageSensorModuleSetManager();
| | | | | | | | | | | | | |--> loadResult = pSensorModuleSetManager->LoadBinaryParameters(pBuffer, fileSizeBytes); // 解析sensormodule.***.bin文件, 读取sensor配置参数
| | | | | | | | | | | | | | |--> ReadHeader(buffer, length, &pos, &offset, &count) // 解析Bin文件头信息,从TAG"QTI Chromatix Header"开始
| | | | | | | | | | | | | | |--> ReadSections(buffer, length, &pos, count); // 解析Bin文件具体的每个Section
| | | | | | | | | | | | | | |--> AddModule(CreateModule(symbolTable.GetModule(i))) // 根据解析到的Symtable的名字和类型等信息,查找具体的sensor ParameterModule, 也就是SensorDriverDataClass/CameraModuleDataClass..., 将其通过链表链接起来
| | | | | | | | | | | | | | |--> CreateModule --> const ParameterModule* module = GetDefaultModule(entry->Type);
| | | | | | | | | | | | | | | |--> return CameraModuleDataClass("cameraModuleData")/EEPROMDriverDataClass("EEPROMDriverData"); // 返回实际的moduleDataClass, 对bin文件中的数据进行解析
| | | | | | | | | | | | |--> m_pSensorModuleManagers[m_numSensorModuleManagers++] = pSensorModuleSetManager; // 对其进行全局保存
| | | | | | | | | | | |--> createData.pSensorModuleManagerObj = m_pSensorModuleManagers[index];
| | | | | | | | | | | |--> result = ImageSensorModuleData::Create(&createData); //#camximagesensormoduledata.cpp 创建ImageSensorModuleData, 每个sensor module对应一个ImageSensorModuleData, 保存在ImageSensorModuleDataManager的m_ppDataObjs中
| | | | | | | | | | | | |-->pInstance = CAMX_NEW ImageSensorModuleData(pCreateData->pSensorModuleManagerObj);
| | | | | | | | | | | | |--> result = ImageSensorModuleData::initalize()
| | | | | | | | | | | | | |--> pSensorDriverData = GetSensorDriverDataObj(); // 上面已经根据sensor module文件解析并填充每个ModuleDataClass("cameraModuleData")/..., 从这里读取并存到成员变量中
| | | | | | | | | | | | | |--> m_pSensorData = CAMX_NEW ImageSensorData(pSensorDriverData, this);
| | | | | | | | | | | | | |--> m_pCameraModuleData = GetCameraModuleDataObj(); // 同上
| | | | | | | | | | | | | |--> pSensorName = m_pSensorData->GetSensorName();
| | | | | | | | | | | | | |--> pName = GetCameraModuleDataObj()->moduleGroup.moduleConfiguration[m_usedModuleId].sensorName;
| | | | | | | | | | | | | |--> OsUtils::StrCmp(pSensorName, pName)
| | | | | | | | | | | | | |--> GetOverrideI2CFrequencyMode()
| | | | | | | | | | | | | |--> m_pPDAFData = CAMX_NEW PDAFData(GetPDAFConfigDataObj()); // 同上
| | | | | | | | | | | |--> m_ppDataObjs[index] = createData.pImageSensorModuleData;m_numberOfDataObjs++;
| | | | | | | | | | | |--> SortSensorDataObjects(); // sensor排序
| | | | | | | | | |--> moduleCount = m_pImageSensorModuleDataManager->GetNumberOfImageSensorModuleData();
| | | | | | | | | |--> pData = m_pImageSensorModuleDataManager->GetImageSensorModuleData(i);
| | | | | | | | | |--> pData->GetCameraPosition(&cameraPosition);
| | | | | | | | | |--> //pData->ProbeEEPROM(&m_sensorInfoTable[m_numberSensors],m_cslDeviceTable); // 探测Sensor是否存在
| | | | | | | | | |--> result = pData->Probe(&detected, &deviceIndex); // 探测Sensor是否在, 基本都是I2C设备,因此,实际执行I2C的初始化和通信流程
| | | | | | | | | |--> result = CSLQueryDeviceCapabilities(...)
| | | | | | | | | |--> CreateTuningDataManager(pData, m_numberSensors); //#camxhwenvironment.cpp
| | | | | | | | | | |--> m_pTuningManager[sensorIndex] = TuningDataManager::Create(); //#camxtuningdatamanager.cpp
| | | | | | | | | | | |--> pLocalInstance = CAMX_NEW TuningDataManager(); //创建TuningDataManager并初始化
| | | | | | | | | | | |--> Initialize();
| | | | | | | | | | |--> result = CSLQueryCameraPlatform(&CSLPlatform);
| | | | | | | | | | |--> fileCount = OsUtils::GetFilesFromPath(SensorModulesPath,FILENAME_MAX, &binFiles[0][0],"*", "tuned", pChromatixName, "bin"); // tuning参数解析
| | | | | | | | | | |--> result = m_pTuningManager[sensorIndex]->LoadTunedDataFile(binFiles[0]);
| | | | | | | | | | |--> result = m_pTuningManager[sensorIndex]->CreateTunedModeTree();
| | | | | | | | | |--> m_numberSensors++; // 初始化成功Sensor
| | | | | | | | | |--> result = m_pImageSensorModuleDataManager->DeleteEEBinFiles();
| | | | | | |--> EnumerateSensorDevices(); //#camxhwenvironment.cpp
| | | | | | | |--> result = CSLEnumerateDevices(&device);
| | | | | | |--> InitializeSensorSubModules(); // 在初始化过程中已经获取到三种类型的driver Data, 现在继续剩下的三种driver data过程
| | | | | | | |--> m_sensorInfoTable[index].pData->CreateSensorSubModules(&m_sensorInfoTable[index], &m_cslDeviceTable[0]); //#camximagesensormoduledata.cpp
| | | | | | | | |--> GetCameraId(&cameraId)
| | | | | | | | |--> result = CreateAndReadEEPROMData(pSensorInfoTable, &pCSLDeviceTable[CSLDeviceTypeEEPROM], 0);
| | | | | | | | | |--> pEEPROMDriverData = ImageSensorModuleData::GetEEPROMDriverDataObj();
| | | | | | | | | |--> pEepromSlaveAddressPtr = GetOverrideEepromSlaveAddress();
| | | | | | | | | |--> pEEPROMData = CAMX_NEW EEPROMData (...)
| | | | | | | | |--> pActuatorDriverData = ImageSensorModuleData::GetActuatorDriverDataObj();
| | | | | | | | |--> pActuatorDriverData1 = ImageSensorModuleData::GetActuatorDriverDataObj1();
| | | | | | | | |--> m_pActuatorData = CAMX_NEW ActuatorData(pActuatorDriverData);
| | | | | | | | |--> result = m_pActuatorData->InitializeStepTable (...)
| | | | | | | | |--> pOISDriverData = ImageSensorModuleData::GetOisDriverDataObj();
| | | | | | | | |--> m_pOISData = CAMX_NEW OISData(pOISDriverData);
| | | | | | | | |--> pFlashDriverData = ImageSensorModuleData::GetFlashDriverDataObj();
| | | | | | | | |--> m_pFlashData = CAMX_NEW FlashData (...)
| | | | | | |--> InitializeSensorStaticCaps();
| | | | | | |--> //OverriderDualCamCalData();
| | | | | | |--> m_staticEntryMethods.GetStaticCaps(&m_platformCaps);
| | | | | | |--> InitializeHwEnvironmentStaticCaps(); // 初始化m_caps[MaxNumImageSensors]参数,里面记录了相机硬件环境static能力, 具体信息可以看HwEnvironmentStaticCaps, 后期在ISP中或者算法后处理中会用到这些参数
| | | | | | | |--> InitializeAETargetFPSRangesStaticCaps();
| | | | | | | |--> InitializeScalerStaticCaps();
| | | | | | | |--> InitializeJPEGMaxSizeStaticCaps();
| | | | | | | |--> InitializeXiaomiScalerStaticCaps();
| | | | | | | |--> InitializeXiaomiLimitScalerStaticCaps();
| | | |--> GetSettingsManager()->GetStaticSettings()
| | | | |--> pSettingsManager = CAMX_NEW SettingsManager(); //#camxsettingsmanager.cpp
| | | | |--> SettingsManager::Initialize() // 初始化参数配置模块,参数相关配置在/vendor/etc/camera/camxoverridesettings.txt中
| | | | | |--> OverrideSettingsFile::Create() --> /vendor/etc/camera/camxoverridesettings.txt
| | | | | |--> InitializeDefaultSettings();
| | | | | |--> InitializeDefaultDebugSettings();
| | | | | |--> result = LoadOverrideSettings(m_pOverrideSettingsStore);
| | | | | |--> result = LoadOverrideProperties(m_pOverrideSettingsStore, TRUE);
| | | | | |--> UpdateLogSettings();
| | | |--> result = CSLQueryCameraPlatform(&CSLPlatform); //#camxhwenvironment.cpp
| | | |--> DisplayConfigInterface::SetCameraStatus(FALSE); // 设置camera的状态
| | | |--> OsUtils::GetFilesFromPath(CHIOverrideModulePath, FILENAME_MAX, &moduleFileName[0], "*", "chi", "*", &SharedLibraryExtension[0]); // 找到com.qti.chi.so这个库文件
| | | |--> m_hChiOverrideModuleHandle = OsUtils::LibMap(&moduleFileName[0]); // 通过dlopen打开
| | | |--> funcCHIHALOverrideEntry = CamX::OsUtils::LibGetAddr(m_hChiOverrideModuleHandle, "chi_hal_override_entry")); // 通过dlsym获取chi_hal_override_entry API地址
| | | |--> funcCHIHALOverrideEntry(&m_ChiAppCallbacks); // 调用chi_hal_override_entry API
| | | | |--> ExtensionModule::GetInstance() --> ExtensionModule::ExtensionModule() //#chxextensionmodule.cpp调用ExtensionModule构造函数
| | | | | |--> m_pUsecaseSelector = UsecaseSelector::Create(this);
| | | | | |--> m_pUsecaseFactory = UsecaseFactory::Create(this);
| | | | | |--> MultiCamControllerManager::GetInstance(); --> MultiCamControllerManager //#chxmulticamcontroller.cpp
| | | | | |--> m_perfLibHandle = ChxUtils::LibMap(pPerfModule); // 加载perf lock 模块
| | | | | |--> ChxUtils::ThreadCreate(ExtensionModule::RecoveryThread,); // RecoveryThread启动
| | | | | |--> ChxUtils::Memcpy(m_pLogicalCameraConfigurationInfo, logicalCameraConfiguration,); // LogicalCameraConfiguration logicalCameraConfiguration[] = {0, LogicalCameraType_Default, TRUE, 1,
| | | | | |--> OSLIBRARYHANDLE handle = ChxUtils::LibMap(pChiDriver); // dlopen camera.qcom.so, 也就是自己, 获取自己的dlopen句柄
| | | | | |--> ChxUtils::LibGetAddr(handle, "ChiEntry")); // 找到ChiEntry函数, dlsym
| | | | | | |--> funcPChiEntry(&g_chiContextOps); // 通过ChiEntry对g_chiContextOps进行初始化赋值
| | | | | | | |--> m_hCHIContext = g_chiContextOps.pOpenContext(); --> CamX::ChiOpenContext; //#camxchi.cpp pChiContextOps->pOpenContext = CamX::ChiOpenContext;
| | | | | | | | |--> m_hCHIContext = ChiContext::Create() (...)
| | | | | |--> //LoadSlModule();
| | | |--> m_ChiAppCallbacks.CHIGetNumCameras(&m_numFwCameras, &m_numLogicalCameras) <--> chi_get_num_cameras() // 通过chi获取具体的logic和framework id
| | | | |--> ExtensionModule::GetNumCameras(numFwCameras, numLogicalCameras) //#chxextensionmodule.cpp
| | | | | |--> SortCameras();
| | | | | |--> EnumerateCameras();
| | | | | | |--> g_chiContextOps.pGetNumCameras(m_hCHIContext); <--> CamX::ChiGetNumCameras // 获取物理camera的数量
| | | | | | | |--> pChiContext->GetNumCameras(); <--> ChiContext::GetNumCameras
| | | | | | | | |--> HwEnvironment::GetNumCameras() <--> return m_numberSensors
| | | | | | |--> g_chiContextOps..pGetCameraInfo(m_hCHIContext); <--> CamX::ChiGetCameraInfo;
| | | | | | |--> ...
| | | | | |--> FillLogicalCameraCaps()
| | | | | |--> //SortCameras();
| | | | | |--> //GetHwInfo(*pNumFwCameras);
| | | |--> m_pThermalManager = CAMX_NEW ThermalManager(); //#camxthermalmanager.cpp
| | | | |--> ThermalManager
| | | | |--> Initialize();
| | | | |--> RegisterHALDevice()
| |--> HAL3Module::GetNumCameras() //#camxhal3module.cpp
| | |--> return m_numFwCameras

(3)
|--> CSLInitialize()
| |-->CSLModeManager() --> GetCSLJumpTableHw()
| |-->pJumpTable->CSLInitialize()(CSLInitializeHW()) // 通过/dev/media%d设备获取硬件相关信息
| | |-->CSLHwEnumerateAndAddCSLHwDevice() // 这个方法的主要作用是通过ioctl /dev/media%d设备,对mediaDevice上的硬件设备进行整理,填充并实例化到g_CSLHwInstance对象中,保存整个底层硬件结构信息,之后每个设备都可以通过/dev/v4l-subdev%d或者/dev/video%d对设备进行ioctl的操作
| | | |--> result = CSLHwInternalFDIoctl(mediaFd, MEDIA_IOC_DEVICE_INFO, &mediadevInfo); // ioctl /dev/mediaX,获取每个设备的信息,主要是dev->model, dev->serial, dev->bus_info, 其中一个model是cam-req-mgr-devnode
| | | |--> result = CSLHwInternalFDIoctl(mediaFd, MEDIA_IOC_ENUM_ENTITIES, &entity); // 获取所有注册到这个Media_device的相关entity, 可以看驱动的相关介绍,每一个video_device和v4l2_subdevice都会以entity的形式注册到media_device中,通过video_register_media_controller进行注册,有isp, jpeg, csiphy ...
| | | |--> CSLHwAddKMDPrivateDeviceToInstance() ...
| | | |--> CSLHwAddKMDPrivateDeviceToInstance // 循环遍历每个entity,代表硬件设备,硬件设备的操作通过/dev/entity.name进行, 将entity获取到的相关信息加入到g_CSLHwInstance, g_CSLHwInstance也就是代表了硬件设备的整个上下文
| | | |--> CAM_VNODE_DEVICE_TYPE: g_CSLHwInstance.requestManager.kmdGroupId = groupId; // 对request manager设备进行初始化
| | | |--> CAM_VNODE_DEVICE_TYPE: g_CSLHwInstance.numSessions=0 ... for g_CSLHwInstance init
| | |--> CSLHwEnumerateAndAddCSLHwDevice(CSLInternalHwVideoSubdevice, CAM_CPAS_DEVICE_TYPE)) // 对g_CSLHwInstance中的CPAS设备初始化
| | |--> CSLHwEnumerateAndAddCSLHwDevice(CSLInternalHwVideoSubdeviceAll, 0))
| | | | |--> CAM_SENSOR_DEVICE_TYPE: CSLHwAddSensorSlotDeviceToInstance // 对g_CSLHwInstance中的镜头设备进行初始化
| | | | |--> CSLHwAddKMDDeviceToInstance(subdeviceName, entity.type, &deviceIndex); // 对剩下的非request_manager和CPAS和Sensor设备进行初始化和赋值,都是通过/dev/media%d获取到的entity信息进行的初始化
| | | | | |--> pLoophw = &g_CSLHwInstance.CSLInternalKMDDevices
| | | | | |--> CSLHwInternalGetKMDDeviceQueryCap()
| | | | | | |--> pKMDhw->deviceOp.KMDQueryCap() (g_CSLHwDeviceFDOps/g_CSLHwDeviceVFEOps/g_CSLHwDeviceIFEOps...) // 每个设备都有自己的ops,调用对用的ops进行操作
| | | | | | | |--> (...) // 每个设备进行不同的操作,比如jpeg,pDevice->deviceOp.Ioctl(pDevice, VIDIOC_CAM_CONTROL, &ioctlCmd);最终都是通过ioctl来实现的查询
| | |--> CSLHwGetSyncHwDevice(syncDeviceName, CSLHwMaxDevName); // 在驱动层还有一个"cam_sync_device"的设备,注册出来的节点是/dev/media1,这个是个sync设备
| | | |--> result = CSLHwInternalFDIoctl(mediaFd, MEDIA_IOC_DEVICE_INFO, &mediaDeviceInfo);
| | | |--> strncmp(mediaDeviceInfo.model, CAM_SYNC_DEVICE_NAME, sizeof(mediaDeviceInfo.model)) // 对比到这个设备
| | | |--> result = CSLHwInternalFDIoctl(mediaFd, MEDIA_IOC_ENUM_ENTITIES, &entity); // 这个media_device上只有一个entity,找到这个entity所对应的video_device
| | | |--> CamX::OsUtils::SNPrintF(pSyncDeviceName, deviceNameLen, "/dev/%s", entity.name); // pSyncDeviceName进行保存
| | |--> g_CSLHwInstance.pSyncFW->Initialize()
|--> QueryHwContextStaticEntryMethods()
| |--> CSLQueryCameraPlatform(&CSLPlatform)
| | |--> pJumpTable->CSLQueryCameraPlatform(pCameraPlatform)(CSLQueryCameraPlatformHW)
| | | |--> CamX::Utils::Memcpy(pCameraPlatform, &g_CSLHwInstance.pCameraPlatform,...); // 将g_CSLHwInstance中的pCameraPlatform参数copy to pCameraPlatform, platform参数是在CPAS设备中读取出来的
|--> Titan17xGetStaticEntryMethods // Titan Camera SOC 相关操作
| |--> m_staticEntryMethods.create=.Titan17xContext::Create; pStaticEntry->GetStaticMetadataKeysInfo = &Titan17xContext::GetStaticMetadataKeysInfo... // 对m_staticEntryMethods进行成员赋值
|--> m_pHwFactory = m_staticEntryMethods.CreateHwFactory() (Titan17xFactory::Create())
|--> m_pSettingsManager = m_pHwFactory->CreateSettingsManager()
| |-> Titan17xSettingsManager
|--> m_staticEntryMethods.GetHWBugWorkarounds(&m_workarounds);
| |--> bug workaround .... superb
|--> ProbeChiComponents(pExternalComponent, &m_numExternalComponent); // 挂载相关算法,以备调用, 包括node, statitics, hvx等相关算法,算法统一以ChiNodeEntry为入口
| |--> OsUtils::GetFilesFromPath(CHIOverrideModulePath, FILENAME_MAX, &chiOverrideSoFileName[0], "*", "chi", "*", &SharedLibraryExtension[0]);
| | |--> /vendor/lib/hw/com.*.chi.*.so
| |--> OsUtils::GetFilesFromPath(ExtCompPath, FILENAME_MAX, &soFilesName[0][0], "*", "node", "*", &SharedLibraryExtension[0]);
| | |--> /vendor/lib/camera/com.*.node.*.so
| |--> OsUtils::GetFilesFromPath(ExtCompPath, FILENAME_MAX, &soFilesName[fileCountTypeNode][0], "*", "stats", "*", &SharedLibraryExtension[0]);
| | |--> /vendor/lib/camera/com.*.stats.*.so
| |--> OsUtils::GetFilesFromPath(ExtCompPath, FILENAME_MAX, &soFilesName[fileCountTypeNode+fileCountTypeStats][0], "*", "hvx", "*", &SharedLibraryExtension[0]);
| | |--> /vendor/lib/camera/com.*.hvx.*.so
| |--> pNodeEntry = reinterpret_cast<PFCHINODEENTRY>(CamX::OsUtils::LibGetAddr(handle, "ChiNodeEntry"))
| |--> pNodeEntry(&pExternalComponentInfo[index].nodeCallbacks);
| |--> GetComponentTag(pQueryVendorTag);

给TA鼓励
共{{data.count}}人
人已鼓励
技术文档

高通平台node bypass功能介绍

2022-5-7 0:08:18

技术文档

Linux终端复用工具Tmux使用教程

2022-5-7 0:08:47

0 条回复 A文章作者 M管理员
    暂无讨论,说说你的看法吧
个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索