MTK平台闪光灯相关信息

(1)概念

  • MTK打闪一般分为预闪、主闪两个阶段。相应的执行一次拍照会有预闪、主闪两次开灯。预闪可以用来防红眼(red-eye reduction)。闪光时使环境发生变化,会按新的光线条件(有闪光时)重新测光,来实现更精确;
  • 预闪是开灯让AE/AF收敛,其持续的时间取决于AF/AF收敛的速度,Flash本身没有控制预闪时间长短的能力。理论上环境亮度越暗,对应的Sensor Framerate越低,AE/AF收敛的时间就越长(AE收敛完之后,才会做AF收敛)。预闪阶段会提前计算主闪时会使用的参数(AE/AWB/AF/Duty)。
  • 主闪是在Capture阶段去开灯,一般flow至少会亮三张Frame,在第三帧P1 Done关灯。主闪Duty, doCap要使用的AE参数、AWB权重、AF lock focus都是在预闪阶段就决定了。所以主闪的持续时间相对比预闪的会短一些,电流强度也会稍微高一点。

这里我们以普通的mt6761为例,可以查看部分代码的设置。

(2)闪光灯Hal逻辑代码

//vendor/mediatek/proprietary/hardware/mtkcam/aaa/source/common/flash_mgr/flash_hal.cpp

int FlashHal::getTorchStatus()
{
    logI("getTorchStatus(): torch status(%d).", mTorchStatus);
    return mTorchStatus;
}

int FlashHal::setTorchOnOff(MBOOL enable)
{
    logI("[CAT][flash] setTorchOnOff(): type:%d enable:%d", mStrobeTypeId, enable);

    if (mStrobeTypeId == STROBE_TYPE_FRONT && !cust_isSubFlashSupport())
        return 1;

    if (enable == 1) {
        init();
        setInCharge(1);
        setOnOff(enable, FLASH_HAL_SCENARIO_TORCH);
        mTorchStatus = 1;
    } else {
        setOnOff(enable, FLASH_HAL_SCENARIO_TORCH);
        setInCharge(0);
        uninit();
        mTorchStatus = 0;
    }

    return 0;
}

int FlashHal::setVideoTorchOnOff(int enable)
{
    logI("setVideoTorchOnOff(): enable(%d).", enable);
    setOnOff(enable, FLASH_HAL_SCENARIO_VIDEO_TORCH);
    return 0;
}

int FlashHal::setAfLampOnOff(int enable)
{
    logI("setAfLampOnOff(): enable(%d).", enable);
    setOnOff(enable, FLASH_HAL_SCENARIO_AF_LAMP);
    return 0;
}

int FlashHal::setPfOnOff(int enable)
{
    logI("setPfOnOff(): enable(%d).", enable);
    setOnOff(enable, FLASH_HAL_SCENARIO_PRE_FLASH);
    return 0;
}

int FlashHal::setCaptureFlashOnOff(int enable)
{
    logI("setCaptureFlashOnOff(): enable(%d).", enable);
    setOnOff(enable, FLASH_HAL_SCENARIO_MAIN_FLASH);
    return 0;
}

int FlashHal::setTorchDuty(int level)
{
    int duty = 0, dutyLt = 0;

    logI("setTorchLevel(): level(%d).", level);

    mTorchLevel = level;

    FlashCustomAdapter::getInstance(mSensorDev)->getTorchDuty(level, &duty, &dutyLt);
    mpStrobe->setDuty(duty);
    if (mStrobeCtNum > 1) {
        mpStrobe2->setDuty(dutyLt);
    }
    return 0;
}

//setOnOff
int FlashHal::setOnOff(int enable, FLASH_HAL_SCENARIO_ENUM scenario)
{
    logI("[CAT][flash] setOnOff(): type:%d enable:%d scenario:%d", mStrobeTypeId, enable, scenario);

    /* verify arguments */
    if (verifyScenario(scenario)) {
        logE("setOnOff(): invalid arguments.");
        return -1;
    }
    if (!isAvailable()) {
        logI("setOnOff(): sensorDev(%d) not available.", mSensorDev);
        return -1;
    }

    if (scenario == FLASH_HAL_SCENARIO_MAIN_FLASH) {
        //...
    } else if (scenario == FLASH_HAL_SCENARIO_VIDEO_TORCH) {
        //...
    }

    if (enable)
        return setFlashOn(mFlashHalInfo[scenario]);
    else
        return setFlashOff();
}

(3)关闭真闪配置

//vendor/mediatek/proprietary/custom/mt6761/hal/camera_3a/flashawb_tuning_custom.cpp

MBOOL
isFlashAWBv2Enabled(MINT32 i4SensorDev)
{
    switch (i4SensorDev)
    {
    case NSIspTuning::ESensorDev_Main: //  Main Sensor
        return  MTRUE;//MFALSE
    case NSIspTuning::ESensorDev_MainSecond: //  Main Second Sensor
        return  MTRUE;
    case NSIspTuning::ESensorDev_Sub: //  Sub Sensor
        return  MTRUE;
    case NSIspTuning::ESensorDev_SubSecond: //  Sub Second Sensor
        return  MTRUE;
    default:
        return MTRUE;
    }
}

(4)默认关闭双闪通道,并进行闪光灯校准

//kernel-4.19/arch/arm64/boot/dts/mediatek/mt6761.dts

flashlight_core: flashlight_core {
		compatible = "mediatek,flashlight_core";
	};

	flashlights_mt6370: flashlights_mt6370 {
		compatible = "mediatek,flashlights_mt6370";
		decouple = <1>;//默认为0,需要配置为1
		channel@1 {
			type = <0>;
			ct = <0>;
			part = <0>;
		};
	};

	flashlights_aw3644: flashlights_aw3644 {
		compatible = "mediatek,flashlights_aw3644";
	};
//vendor/mediatek/proprietary/custom/mt6761/hal/flashlight/flash_custom.cpp

int cust_isDualFlashSupport(int sensorDev)
{
    if(sensorDev == DUAL_CAMERA_MAIN_SENSOR || sensorDev == DUAL_CAMERA_MAIN_2_SENSOR)
        return 0;
    else
        return 0;
    return 0;
}

如下修改为闪光灯校准:vendor/mediatek/proprietary/custom/mt6761/hal/flashlight/flash_tuning_custom_cct.cpp

在这里插入图片描述

(5)闪光灯亮度相关参数

//vendor/mediatek/proprietary/custom/mt6761/hal/flashlight

//flash_tuning_custom_cct.cpp
//--------------------
    //eng level
    //index mode
    //torch
    p->engLevel.torchDuty = 6;//手电筒亮度
    //af
    p->engLevel.afDuty = 6;//对焦闪光灯亮度
    //pf, mf, normal
    p->engLevel.pfDuty = 6;//预闪亮度
    p->engLevel.mfDutyMax = 27;//主闪亮度范围值
    p->engLevel.mfDutyMin = 0;
    
    //...

(6)闪光灯打闪Log分析

(A)main Log查看(3次打闪)

打闪几次可通过如下Log判断。

W TaskMgr : [sendEvent] TaskEvent:TouchAEStart, fgLampflashCond(1)/bCustEnableFlash(1)/bStrobeBVTrigger(1)
W TaskMgr : [sendEvent] TaskEvent:TouchAEStart, fgLampflashCond(1)/bCustEnableFlash(1)/bStrobeBVTrigger(1)
W TaskMgr : [sendEvent] TaskEvent:TouchAEStart, fgLampflashCond(1)/bCustEnableFlash(1)/bStrobeBVTrigger(1)

另可通过如下源码查看调用过程。

//vendor/mediatek/proprietary/hardware/mtkcam/aaa/source/isp_30/ae_mgr/ae_mgr.cpp

MBOOL AeMgr::IsStrobeBVTrigger()
{
    MBOOL bStrobeBVTrigger;
    MINT32 i4Bv = 0;

    if (m_rAEInitInput.rAEPARAM.strAEParasetting.bEV0TriggerStrobe == MTRUE)
    {
        // The strobe trigger by the EV 0 index
        i4Bv = m_BVvalueWOStrobe;
    }
    else
    {
        if (m_rAEInitInput.rAEPARAM.pEVValueArray[m_eAEEVcomp])
        {
            if (m_pIAeAlgo != NULL)
            {
                i4Bv = m_BVvalueWOStrobe + m_pIAeAlgo->getSenstivityDeltaIndex(1024 * 1024 / m_rAEInitInput.rAEPARAM.pEVValueArray[m_eAEEVcomp]);
            }
            else
            {
                i4Bv = m_BVvalueWOStrobe;
                AE_LOG("[%s()] The AE algo class is NULL, i4SensorDev:%d line:%d\n", __FUNCTION__, m_eSensorDev, __LINE__);
            }
        }
    }

    bStrobeBVTrigger = (i4Bv < m_CurrentCaptureTable.i4StrobeTrigerBV)?MTRUE:MFALSE;

    AE_LOG_IF(m_3ALogEnable, "[%s()] i4SensorDev:%d bStrobeBVTrigger:%d BV:%d %d\n", __FUNCTION__, m_eSensorDev, bStrobeBVTrigger, i4Bv, m_CurrentCaptureTable.i4StrobeTrigerBV);

    return bStrobeBVTrigger;
}

可通过如上Code中的bStrobeBVTrigger字段来查看当前环境值和打闪阈值。

D ae_mgr  : [IsStrobeBVTrigger()] i4SensorDev:1 bStrobeBVTrigger:0 BV:11 -28
D ae_mgr  : [IsStrobeBVTrigger()] i4SensorDev:1 bStrobeBVTrigger:0 BV:10 -28
D ae_mgr  : [IsStrobeBVTrigger()] i4SensorDev:1 bStrobeBVTrigger:1 BV:-36 -28
D ae_mgr  : [IsStrobeBVTrigger()] i4SensorDev:1 bStrobeBVTrigger:0 BV:-2 -28

备注:具体打闪阈值通过效果文件来控制。

//camera_AE_PLineTable_xxxxraw.h

static constexpr strAETable g_AE_PreviewAutoTable =
{
    AETABLE_RPEVIEW_AUTO, //eAETableID
    147, //u4TotalIndex
    -28, //i4StrobeTrigerBV    //为当前配置的打闪阈值
    102, //i4MaxBV
    -44, //i4MinBV, Original:-45
    90, //i4EffectiveMaxBV
    -30, //i4EffectiveMinBV
    LIB3A_AE_ISO_SPEED_AUTO, //ISO
    sPreviewPLineTable_60Hz,
    sPreviewPLineTable_50Hz,
    NULL,
};

(B)kernel Log查看(3次打闪)

//预闪
kernel_log_6__2023_0613_212218:10220: <7>[ 2188.129555]  (0)[7550:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:11035: <7>[ 2189.912077]  (2)[7550:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
//主闪
kernel_log_6__2023_0613_212218:11260: <7>[ 2190.348990]  (0)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:11305: <7>[ 2190.453573]  (3)[7512:CAM_P1]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
kernel_log_6__2023_0613_212218:11463: <7>[ 2190.665271]  (1)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0


kernel_log_6__2023_0613_212218:12779: <7>[ 2193.272978]  (1)[7639:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:13307: <7>[ 2194.481592]  (3)[7639:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
kernel_log_6__2023_0613_212218:13497: <7>[ 2194.918873]  (0)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:13542: <7>[ 2195.016548]  (1)[7512:CAM_P1]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
kernel_log_6__2023_0613_212218:13705: <7>[ 2195.222145]  (2)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0


kernel_log_6__2023_0613_212218:15349: <7>[ 2198.889098]  (2)[7653:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:15942: <7>[ 2200.201315]  (3)[7653:3AEventThd]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
kernel_log_6__2023_0613_212218:16129: <7>[ 2200.869104]  (3)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 1
kernel_log_6__2023_0613_212218:16174: <7>[ 2200.967390]  (0)[7512:CAM_P1]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
kernel_log_6__2023_0613_212218:16347: <7>[ 2201.322911]  (1)[7467:3ATHREAD]flashlight: _flashlight_ioctl: FLASH_IOC_SET_ONOFF(0,0,0): 0
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

雪舞飞影

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值