展锐S 上微距模式不识别问题跟进 --- sensor_config的解析

问题:在md.mk中配置了打开macro的属性 persist.vendor.cam.macrophoto.enable,但是CameraApp中仍然不显示微距模式。

按照之前的经验,mk中打开微距的配置,上层就能自动显示微距模式。但是S上这个项目log显示微距的feature是false。

来到SprdCamera3Setting中,看到关于微距feature的控制

 property_get("persist.vendor.cam.macrophoto.enable", prop, "0");//1
 if (SENSOR_ID_INVALID != sensorGetPhyId4Role(SENSOR_ROLE_SINGLE_MACRO, SNS_FACE_BACK)) {
     HAL_LOGD("addMacro photo %d", atoi(prop));
     available_cam_features.add(atoi(prop));
 } else {
     HAL_LOGD("addMacro photo 0");
     available_cam_features.add(0);
 }

看来这个 sensorGetPhyId4Role 函数 是关键。
在 vendor\sprd\modules\libcamera\sensor\sensor_drv_u.c中看到该函数的实现
省略不相关的 case role条目,看到主要是从 phyPtr = sensorGetPhysicalSnsInfo(phyId); 这个phyPtr对象中拿 code 和 face 值做判断,是否符合 SENSOR_ROLE_SINGLE_MACRO 的条件。

int sensorGetPhyId4Role(enum sensor_role role, enum face_type facing) {
    int phyId = SENSOR_ID_INVALID;
    cmr_u32 code = 0;
    cmr_u32 face = 0;
    struct phySensorInfo *phyPtr = NULL;
    /* only return the first sensor that meets role,
     * and surely this sensor has been identified successfully */
    for (phyId = 0; phyId < SENSOR_ID_MAX; phyId++) {
        phyPtr = sensorGetPhysicalSnsInfo(phyId);
        code = phyPtr->sensor_role_code;
        face = phyPtr->face_type;
        SENSOR_LOGI("cyy_phyId=%d code=%d face=%d facing=%d role=%d SENSOR_ROLE_SINGLE_MACRO=%d", phyId, code, face, facing, role, SENSOR_ROLE_SINGLE_MACRO);

        switch (role) {
        case SENSOR_ROLE_DUALCAM_MASTER:
            break;
        case SENSOR_ROLE_DUALCAM_SLAVE:
            break;
        case SENSOR_ROLE_MULTICAM_SUPERWIDE:
            break;
        case SENSOR_ROLE_MULTICAM_WIDE:
            break;
        case SENSOR_ROLE_MULTICAM_TELE:
            break;
        case SENSOR_ROLE_SINGLE_MACRO:
            if ((code & 0xf) == 0x2 && face == facing) {
                goto exit;
            }
            break;
        default:
            SENSOR_LOGD("not support sensor_role %d", role);
            return SENSOR_ID_INVALID;
        }
    }
    SENSOR_LOGD("can't find sensor_role %d at facing %d", role, facing);
    return SENSOR_ID_INVALID;

exit:
    SENSOR_LOGD("find sensor_role %d at facing %d, phyId %d", role, facing,
                phyId);
    return phyId;
}

log看到:

	Line 16357: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=0 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16359: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=1 code=0 face=1 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16360: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=2 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16361: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=3 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16363: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=4 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16364: 07-05 15:17:20.694   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=5 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16386: 07-05 15:17:20.700   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=0 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16387: 07-05 15:17:20.701   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=1 code=0 face=1 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16388: 07-05 15:17:20.701   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=2 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16389: 07-05 15:17:20.701   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=3 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16390: 07-05 15:17:20.701   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=4 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16391: 07-05 15:17:20.701   523   523 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=5 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2

log中所有cameraId的 code 为 0(我们已知macro的camera id为2),导致 case SENSOR_ROLE_SINGLE_MACRO 的 if 条件进去不去。

那就在追,为什么 从 sensorGetPhysicalSnsInfo 里面拿的 phyPtr->sensor_role_code 为 0。

PHYSICAL_SENSOR_INFO_T *sensorGetPhysicalSnsInfo(int phy_id) {

    if (phy_id >= SENSOR_ID_MAX)
        return NULL;

    return &phy_sensor_info_list[phy_id];
}

追 phy_sensor_info_list 的数据来源。

sensor_drv_create_phy_sensor_info(struct sensor_drv_context *sensor_cxt,
                                  cmr_u32 slot_id, cmr_u32 phy_id) {
	phyPtr->sensor_role_code = sensor_cxt->xml_info->cfgPtr->sensor_role_code;
    phyPtr->face_type = sensor_cxt->xml_info->cfgPtr->facing;
    phyPtr->angle = sensor_cxt->xml_info->cfgPtr->orientation;

信息来自 sensor_cxt->xml_info,在sensor目录下搜一下,找到了 sensor_drv_xml_parse.c中有为该对象赋值,从文件名字也容易看出,是做解析xml文件的。

sensor_drv_xml_str_to_integer(sensor_role[i],&cfgPtr->sensor_role_code);

static int sensor_drv_xml_str_to_integer(char *str, cmr_u32 *digit) {
    if (!strcmp(str, "BACK")) {
        *digit = SNS_FACE_BACK;
    } else if (!strcmp(str, "FRONT")) {
        *digit = SNS_FACE_FRONT;
    } else if (!strcmp(str, "dualcam_master")) {
        *digit = (*digit & ~(0xf << 4)) | (0x1 << 4);
    } else if (!strcmp(str, "dualcam_slave")) {
        *digit = (*digit & ~(0xf << 4)) | (0x2 << 4);
    } else if (!strcmp(str, "multicam_superwide")) {
        *digit = (*digit & ~(0xf << 8)) | (0x1 << 8);
    } else if (!strcmp(str, "multicam_wide")) {
        *digit = (*digit & ~(0xf << 8)) | (0x2 << 8);
    } else if (!strcmp(str, "multicam_tele")) {
        *digit = (*digit & ~(0xf << 8)) | (0x3 << 8);
    } else if (!strcmp(str, "stl3d_rgb")) {
        *digit = (*digit & ~(0xf << 12)) | (0x1 << 12);
    } else if (!strcmp(str, "stl3d_ir_left")) {
        *digit = (*digit & ~(0xf << 12)) | (0x2 << 12);
    } else if (!strcmp(str, "stl3d_ir_right")) {
        *digit = (*digit & ~(0xf << 12)) | (0x3 << 12);
    } else if (!strcmp(str, "single_ir")) {
        *digit = (*digit & ~0xf) | 0x1;
    } else if (!strcmp(str, "macro")) {
        *digit = (*digit & ~0xf) | 0x2;
    } else if (!strcmp(str, "single")) {
        *digit = (*digit & ~0xf) | 0x0;
    } else {
        return -1;
    }
    return 0;
}

这里case了xml的各个标签,其中 else if (!strcmp(str, “macro”)) 是我们要关注的 marco 相关的,这里看到确实读了macro的信息了,在去sensor_config.xml中确认下配置:

<CameraModuleCfg>
 <SlotId>2</SlotId>
 <SensorName>bf2253L_macro</SensorName>
 <Facing>BACK</Facing>
 <Orientation>90</Orientation>
 <Resource_cost>0</Resource_cost>
 <SensorRole>single_macro</SensorRole>
 <TuningParameter>
     <TuningName>bf2253L_macro</TuningName>
 </TuningParameter>
</CameraModuleCfg>

额额额,看到 SensorRole 的这项配置为 single_macro,而 sensor_drv_xml_parse.c 是else if匹配的 macro。

找到坑了,改下sensor_config.xml的 SensorRole 配置 为 macro , push 该文件到 vendor/ect下面,在重启下手机就行了。
改过之后的log

	Line 16373: 07-05 15:39:10.750   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=0 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16374: 07-05 15:39:10.750   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=1 code=0 face=1 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16375: 07-05 15:39:10.750   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=2 code=2 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16376: 07-05 15:39:10.750   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=3 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16377: 07-05 15:39:10.750   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=4 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2
	Line 16378: 07-05 15:39:10.751   525   525 I sns_drv_u: 5282, sensorGetPhyId4Role: cyy_phyId=5 code=0 face=0 facing=0 role=7 SENSOR_ROLE_SINGLE_MACRO=2

cyy_phyId=2 code=2 ,这样在sensor_drv_u.c中 case SENSOR_ROLE_SINGLE_MACRO: 的 if 就能走进去了。SprdCamera3Setting中 sensorGetPhyId4Role(SENSOR_ROLE_SINGLE_MACRO, SNS_FACE_BACK),就能获取到正常的cameraId,从而将 macro的feature值add为1

总结:平台的代码流程理论上是不会出大的问题的,要跟着平台的设计思路去排查,多半是一些细节地方没有注意。

你可能感兴趣的:(Camera,HAL,camera,hal,Camera)