⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 image_sensor.c

📁 mtk siv100A for MT6226
💻 C
📖 第 1 页 / 共 4 页
字号:
//        write_cmos_sensor(0x25, iVal2Write & 0x00FF);
    }
}   /* ConfigVBlank */

/*************************************************************************
* FUNCTION
*   ConfigHBlank
*
* DESCRIPTION
*   This function is to set HBlank size.
*
* PARAMETERS
*   iBlank: target HBlank size
*      iHz: banding frequency
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void ConfigHBlank(const kal_uint16 iBlank, const kal_uint8 iHz)
{
    /********************************************
    *   50Hz-relative registers can not be used *
    ********************************************/
    const kal_uint16 iVal2Write = iBlank - 1;

    ASSERT(iBlank < (1 << 10));

    switch (iHz) {
    case CAM_BANDING_50HZ:
    case CAM_BANDING_60HZ:
        write_cmos_sensor(0x20, (read_cmos_sensor(0x20) & 0xCF) | ((iVal2Write & 0x0300) >> 4));
        write_cmos_sensor(0x21, iVal2Write & 0x00FF);
        break;

//    case CAM_BANDING_50HZ:
        // SIV100A cannot use all blank size registers of 50Hz
//        write_cmos_sensor(0x23, (read_cmos_sensor(0x23) & 0xCF) | ((iVal2Write & 0x0300) >> 4));
//        write_cmos_sensor(0x24, iVal2Write & 0x00FF);
    }
}   /* ConfigHBlank */

/*************************************************************************
* FUNCTION
*   SIV100A_PowerOff
*
* DESCRIPTION
*   This function is to turn off sensor module power.
*
* PARAMETERS
*   None
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_PowerOff(void)
{
    cis_module_power_on(KAL_FALSE); // power off sensor

    SET_SCCB_CLK_LOW;
    SET_SCCB_DATA_LOW;

    UPLL_Disable(UPLL_OWNER_ISP);
}   /* SIV100A_PowerOff */

/*************************************************************************
* FUNCTION
*   SIV100A_Get_I2C_ID
*
* DESCRIPTION
*   This function return the sensor read/write IDs of I2C I/F.
*
* PARAMETERS
*   *pI2C_WriteID : address pointer of sensor's I2C write id
*   *pI2C_ReadID  : address pointer of sensor's I2C read id
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_Get_I2C_ID(kal_uint8 *pI2C_WriteID, kal_uint8 *pI2C_ReadID)
{
    *pI2C_WriteID = SIV100A_I2C_WRITE_ID;
    *pI2C_ReadID = SIV100A_I2C_READ_ID;
}   /* SIV100A_Get_I2C_ID */

/*************************************************************************
* FUNCTION
*   SIV100A_GetSize
*
* DESCRIPTION
*   This function return the image width and height of image sensor.
*
* PARAMETERS
*   *pWidth : address pointer of horizontal effective pixels of image sensor
*  *pHeight : address pointer of vertical effective lines of image sensor
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_GetSize(kal_uint16 *pWidth, kal_uint16 *pHeight)
{
    *pWidth = IMAGE_SENSOR_VGA_WIDTH;   // valid pixel # in one frame
    *pHeight = IMAGE_SENSOR_VGA_HEIGHT; // valid line # in one frame
}   /* SIV100A_GetSize */

/*************************************************************************
* FUNCTION
*   SIV100A_GetPeriod
*
* DESCRIPTION
*   This function return the image width and height of image sensor.
*
* PARAMETERS
*   *pPixelNumber : address pointer of pixel numbers in one period of HSYNC
*   *pLineNumber : address pointer of line numbers in one period of VSYNC
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_GetPeriod(kal_uint16 *pPixelNumber, kal_uint16 *pLineNumber)
{
    /************************************
    *   No need for YUV sensor driver   *
    ************************************/
//    *pPixelNumber = VGA_PERIOD_PIXEL_NUMS;  // pixel numbers in one period of HSYNC
//    *pLineNumber = VGA_PERIOD_LINE_NUMS;    // line numbers in one period of VSYNC
}   /* SIV100A_GetPeriod */

/*************************************************************************
* FUNCTION
*	SIV100A_Preview
*
* DESCRIPTION
*	This function configure the sensor to preview mode.
*
* PARAMETERS
*
* RETURNS
*	None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_Preview(image_sensor_exposure_window_struct *pImage_Window, image_sensor_config_struct *pSensor_Config_Data)
{
    kal_uint8 iHV_Mirror = 0;
    kal_uint8 iStartX = 0, iStartY = 1;
    kal_uint8 iTemp = 0;
    volatile kal_uint16 iRetry;
    static kal_uint16 iBound = 0x00FF;

    write_cmos_sensor(0x40, 0x80);  // enable *NORMAL* AE
    write_cmos_sensor(0x60, 0x90);  // enable AWB
    write_cmos_sensor(0x4E, 0x00);
    if (pSensor_Config_Data->frame_rate == 0x0F) {  // MPEG4 Encode Mode
        g_bVideoMode = KAL_TRUE;

        // config TG for video recorder mode
        SET_TG_OUTPUT_CLK_DIVIDER(3);   // MCLK = 12MHz
        SET_CMOS_RISING_EDGE(0);
        SET_CMOS_FALLING_EDGE(2);
        SET_TG_PIXEL_CLK_DIVIDER(3);
        SET_CMOS_DATA_LATCH(2);
    }else {
        g_bVideoMode = KAL_FALSE;
        g_bCaptureMode = KAL_FALSE;

        iTemp = read_cmos_sensor(0x04) & 0xF3;
        write_cmos_sensor(0x04, iTemp | 0x00);  // set CLK divider to 1/2
        // config TG for camera preview mode
        SET_TG_OUTPUT_CLK_DIVIDER(1);
        SET_CMOS_RISING_EDGE(0);
        SET_CMOS_FALLING_EDGE(1);
        SET_TG_PIXEL_CLK_DIVIDER(1);
        SET_CMOS_DATA_LATCH(1);
    }

    iHV_Mirror = read_cmos_sensor(0x04) & 0xFC;
    switch (pSensor_Config_Data->image_mirror) {
    case IMAGE_NORMAL:
        iHV_Mirror |= 0x00;
        if (g_bVideoMode == KAL_TRUE) {
            SET_CAMERA_INPUT_ORDER(INPUT_ORDER_CbYCrY1);
            iStartX = 0;
            iStartY = 1;
        }else {
            SET_CAMERA_INPUT_ORDER(INPUT_ORDER_CbYCrY1);
            iStartX = 0;
            iStartY = 1;
        }
        break;

    case IMAGE_HV_MIRROR:
        iHV_Mirror |= 0x03;
        if (g_bVideoMode == KAL_TRUE) {
            SET_CAMERA_INPUT_ORDER(INPUT_ORDER_CbYCrY1);
            iStartX = 0;
            iStartY = 1;
        }else {
            SET_CAMERA_INPUT_ORDER(INPUT_ORDER_CbYCrY1);
            iStartX = 0;
            iStartY = 1;
        }
        break;

    default:
        ASSERT(0);
    }
    write_cmos_sensor(0x04, iHV_Mirror);

    pImage_Window->grab_start_x = iStartX;
    pImage_Window->grab_start_y = iStartY;
    pImage_Window->exposure_window_width = IMAGE_SENSOR_VGA_WIDTH - iStartX;
    pImage_Window->exposure_window_height = IMAGE_SENSOR_VGA_HEIGHT - iStartY;

    for (iRetry = 0; iRetry < iBound; iRetry++) {
        /********************************
        *   0x7F[0] = 1 when AE stable  *
        ********************************/
        if ((read_cmos_sensor(0x7F) & 0x01) != 0) {
            break;
        }
    }
}   /* SIV100A_Preview */

/*************************************************************************
* FUNCTION
*   SID201A_Capture
*
* DESCRIPTION
*   This function configures the sensor to capture mode.
*
* PARAMETERS
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_Capture(image_sensor_exposure_window_struct *pImage_Window, image_sensor_config_struct *pSensor_Config_Data)
{
    kal_uint8 iStartX = 0, iStartY = 1, iTemp;
    kal_uint32 iExp;

    g_bCaptureMode = KAL_TRUE;

    if (pSensor_Config_Data->frame_rate == 0xF0) {
        /************************************
        *   Webcam mode, AE/AWB still on    *
        ************************************/
        ConfigVBlank(WEBCAM_MODE_VBLANK, CAM_BANDING_50HZ);
        ConfigHBlank(WEBCAM_MODE_HBLANK, CAM_BANDING_50HZ);
    }else {
        /********************************
        *   Normal camera capture mode  *
        ********************************/
        write_cmos_sensor(0x40, 0x00);  // disable AE
        write_cmos_sensor(0x60, 0x00);  // disable AWB
        if (pImage_Window->image_target_width <= IMAGE_SENSOR_VGA_WIDTH &&
            pImage_Window->image_target_height <= IMAGE_SENSOR_VGA_HEIGHT) {
            /********************************************************
            *   This part captures image size equal to or under VGA *
            ********************************************************/
            if (pImage_Window->digital_zoom_factor >= (ISP_DIGITAL_ZOOM_INTERVAL << 1)) {
                iTemp = read_cmos_sensor(0x04) & 0xF3;
                write_cmos_sensor(0x04, iTemp | 0x04);  // set CLK divider = 1/4
                SET_TG_PIXEL_CLK_DIVIDER(3);
                SET_CMOS_DATA_LATCH(2);

                iExp = (read_cmos_sensor(0x30) << 8) | read_cmos_sensor(0x31);
                iTemp = (read_cmos_sensor(0x14) & 0x07) + 1;
                if (iExp == 1) {
                    iTemp >>= 1;
                    write_cmos_sensor(0x14, (read_cmos_sensor(0x14) & 0xF8) | iTemp);
                    write_cmos_sensor(0x30, 0x00);
                    write_cmos_sensor(0x31, 0x01);
                }else {
                    iExp = (((iExp << 3) + iTemp) >> 1);
                    write_cmos_sensor(0x30, (iExp >> 11) & 0x00FF);
                    write_cmos_sensor(0x31, (iExp >> 3) & 0x00FF);
                    write_cmos_sensor(0x14, (read_cmos_sensor(0x14) & 0xF8) | (iExp & 0x0007));
                }
            }
        }else if (pImage_Window->image_target_width > IMAGE_SENSOR_VGA_WIDTH &&
                  pImage_Window->image_target_height > IMAGE_SENSOR_VGA_HEIGHT) {
            /********************************************
            *   This part captures image size over VGA  *
            ********************************************/
            iTemp = read_cmos_sensor(0x04) & 0xF3;
            write_cmos_sensor(0x04, iTemp | 0x0C);  // set CLK divider = 1/16 

            SET_TG_PIXEL_CLK_DIVIDER(15);
            SET_CMOS_DATA_LATCH(8);
 
            iExp = (read_cmos_sensor(0x30) << 8) | read_cmos_sensor(0x31);
            iExp += 4;  // round
            
            if (pImage_Window->digital_zoom_factor >= (ISP_DIGITAL_ZOOM_INTERVAL << 1)) {
                /********************************************************
                *   Capture SXGA resolution with zoom factor over 2x    *
                ********************************************************/
                ConfigHBlank(CP_1M_MODE_ZOOM_HBLANK, CAM_BANDING_50HZ);
                if (g_bNightMode == KAL_TRUE) {
                    if (g_iBanding == CAM_BANDING_50HZ) {
                        iExp = iExp * (PV_MODE_HVP_PERIOD + PV_MODE_HBLANK_50HZ_NIGHT) / (PV_MODE_HVP_PERIOD + CP_1M_MODE_ZOOM_HBLANK);
                    }else {
                        iExp = iExp * (PV_MODE_HVP_PERIOD + PV_MODE_HBLANK_60HZ_NIGHT) / (PV_MODE_HVP_PERIOD + CP_1M_MODE_ZOOM_HBLANK);
                    }
                }else {
                    if (g_iBanding == CAM_BANDING_50HZ) {
                        iExp = iExp * (PV_MODE_HVP_PERIOD + PV_MODE_HBLANK_50HZ_NORMAL) / (PV_MODE_HVP_PERIOD + CP_1M_MODE_ZOOM_HBLANK);
                    }else {
                        iExp = iExp * (PV_MODE_HVP_PERIOD + PV_MODE_HBLANK_60HZ_NORMAL) / (PV_MODE_HVP_PERIOD + CP_1M_MODE_ZOOM_HBLANK);
                    }
                }
            }

            //iTemp = (read_cmos_sensor(0x14) & 0x07) + 1; // remove this line. This register does not use.
            if (iExp <= 8) {               
                //iTemp >>= 1; 
                //write_cmos_sensor(0x14, 0x00); 
                write_cmos_sensor(0x30, 0x00); 
                write_cmos_sensor(0x31, 0x01); 
            }else {
                iExp >>= 3;    // iExp / 8 
                if (iExp < 1) { // make sure nonzero exposure
                    iExp = 1;
                }

                write_cmos_sensor(0x30, (iExp >> 8) & 0x00FF); 
                write_cmos_sensor(0x31,  iExp & 0x00FF); 
                //write_cmos_sensor(0x14, 0x00); 
            } 
        }
    }

    pImage_Window->grab_start_x = iStartX;
    pImage_Window->grab_start_y = iStartY;
    pImage_Window->exposure_window_width = IMAGE_SENSOR_VGA_WIDTH - iStartX;
    pImage_Window->exposure_window_height = IMAGE_SENSOR_VGA_HEIGHT - iStartY;
}   /* SIV100A_Capture() */

/*************************************************************************
* FUNCTION
*   SIV100A_WriteReg
*
* DESCRIPTION
*   This function set the register of SIV100A.
*
* PARAMETERS
*   iAddr : the register index of SIV100A
*   iPara : setting parameter of the specified register of SIV100A
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_WriteReg(kal_uint32 iAddr, kal_uint32 iPara)
{
    write_cmos_sensor(iAddr, iPara);
}   /* SIV100A_WriteReg() */

/*************************************************************************
* FUNCTION
*   read_cmos_sensor
*
* DESCRIPTION
*   This function read parameter of specified register from SIV100A.
*
* PARAMETERS
*   iAddr: the register index of SIV100A
*
* RETURNS
*   the data that read from SIV100A
*
* GLOBALS AFFECTED
*
*************************************************************************/
kal_uint32 SIV100A_ReadReg(kal_uint32 iAddr)
{
    return read_cmos_sensor(iAddr);
}   /* SIV100A_ReadReg() */

/*************************************************************************
* FUNCTION
*   SIV100A_SetShutter
*
* DESCRIPTION
*   This function set e-shutter of SIV100A to change exposure time.
*
* PARAMETERS
*   shutter : exposured lines
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_SetShutter(kal_uint16 shutter)
{
}   /* SIV100A_SetShutter */

/*************************************************************************
* FUNCTION
*   SIV100A_SetGain
*
* DESCRIPTION
*   This function is to set global gain to sensor.
*
* PARAMETERS
*   iGain : sensor global gain(base: 0x40)
*
* RETURNS
*   the actually gain set to sensor.
*
* GLOBALS AFFECTED
*
*************************************************************************/
kal_uint16 SIV100A_SetGain(kal_uint16 iGain)
{
    return iGain;
}   /* SIV100A_SetGain */

/*************************************************************************
* FUNCTION
*   SIV100A_NightMode
*
* DESCRIPTION
*   This function switch on/off night mode of SIV100A.
*
* PARAMETERS
*   None
*
* RETURNS
*   None
*
* GLOBALS AFFECTED
*
*************************************************************************/
void SIV100A_NightMode(kal_bool bEnable)
{
    static kal_uint32 iDelay = 0x000FFFFF;
    volatile kal_uint32 iI = 0;

    g_bNightMode = bEnable;

    if (g_bCaptureMode == KAL_TRUE) {
        return;
    }

    /************************************************************
    *   AE must be off to do the following mode change setting. *
    *   If not off, the covered EV range will be the same for   *
    *   normal/night modes.                                     *
    ************************************************************/
    write_cmos_sensor(0x40, 0x00);

    /********************************************************
    *   MUST delay after turn off AE.                       *
    *   If no such delay, AE will not work after re-enable  *
    ********************************************************/
    for (iI = 0; iI < iDelay; iI++);

    if (bEnable == KAL_TRUE) {
        if (g_bVideoMode == KAL_TRUE) { // video preview mode
            if (g_iBanding == CAM_BANDING_50HZ) {
                ConfigVBlank(VIDEO_MODE_VBLANK_50HZ_NIGHT, CAM_BANDING_50HZ);
                ConfigHBlank(VIDEO_MODE_HBLANK_50HZ_NIGHT, CAM_BANDING_50HZ);
                write_cmos_sensor(0x33, VIDEO_MODE_FRCNT_50HZ_NIGHT);
                write_cmos_sensor(0x34, VIDEO_MODE_STSTN_50HZ_NIGHT);
            }else {
                ConfigVBlank(VIDEO_MODE_VBLANK_60HZ_NIGHT, CAM_BANDING_60HZ);
                ConfigHBlank(VIDEO_MODE_HBLANK_60HZ_NIGHT, CAM_BANDING_60HZ);
                write_cmos_sensor(0x33, VIDEO_MODE_FRCNT_60HZ_NIGHT);
                write_cmos_sensor(0x34, VIDEO_MODE_STSTN_60HZ_NIGHT);
            }
        }else { // camera preview mode
            if (g_iBanding == CAM_BANDING_50HZ) {
                ConfigVBlank(PV_MODE_VBLANK_50HZ_NIGHT, CAM_BANDING_50HZ);
                ConfigHBlank(PV_MODE_HBLANK_50HZ_NIGHT, CAM_BANDING_50HZ);
                write_cmos_sensor(0x33, PV_MODE_FRCNT_50HZ_NIGHT);
                write_cmos_sensor(0x34, PV_MODE_STSTN_50HZ_NIGHT);
            }else {
                ConfigVBlank(PV_MODE_VBLANK_60HZ_NIGHT, CAM_BANDING_60HZ);
                ConfigHBlank(PV_MODE_HBLANK_60HZ_NIGHT, CAM_BANDING_60HZ);
                write_cmos_sensor(0x33, PV_MODE_FRCNT_60HZ_NIGHT);
                write_cmos_sensor(0x34, PV_MODE_STSTN_60HZ_NIGHT);
            }
        }
    }else {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -