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

📄 ov9653.c

📁 嵌入式linux系统下hi3510平台的osd开发源码
💻 C
📖 第 1 页 / 共 2 页
字号:
/*   extdrv/peripheral/dc/ov9653.c
 *
 *
 * Copyright (c) 2006 Hisilicon Co., Ltd.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.
 *
 *
 * History:
 *     04-Apr-2006 create this file
 *
 */
#include <linux/string.h>
#include <linux/slab.h>

#include <linux/module.h>
#include <linux/config.h>
#include <linux/errno.h>
#include <linux/miscdevice.h>
#include <linux/fcntl.h>

#include <linux/init.h>
#include <linux/delay.h>
#include <linux/proc_fs.h>
#include <linux/workqueue.h>
#include <asm/uaccess.h>
#include <asm/system.h>
#include <asm/io.h>

#include "ov9653.h"
#include "gpio_i2c.h"

/* ov9653 i2c slaver address micro-definition. */
#define I2C_OV9653     0x60

#define DC_COM1 0x4
#define DC_COM2 0x9
#define DC_CLKRC 0x11
#define DC_COM7 0x12
#define DC_COM10 0x15
#define DC_MVFP 0x1E
#define DC_COM11 0x3B
#define DC_COM15 0x40
#define DC_PID 0x0A
#define DC_VER 0x0B

static int out_mode = 0;
/* 
 *  ov9653's output format set routine.
 *
 *  @param mode: ov9653's output format
 *
 *  @return value:0-- set success; 1-- set error. 
 *
 */

static unsigned int dc_mode_set(dc_output_set mode)
{
    switch(mode)
    {
        case DC_MODE_CCIR656:
            gpio_i2c_write(I2C_OV9653, DC_COM1, 0x40);
        break;
        
        case DC_MODE_VGA:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x40);
        break;
        
        case DC_MODE_CIF:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x20);
            
        break;
        
        case DC_MODE_QVGA:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x10);
        break;
        
        case DC_MODE_QCIF:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x08);
        break;
        
        case DC_MODE_QQVGA:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x10);
            gpio_i2c_write(I2C_OV9653, DC_COM1, 0x20);
        break;
        
        case DC_MODE_QQCIF:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x08);
            gpio_i2c_write(I2C_OV9653, DC_COM1, 0x20);
        break;
        
        case DC_MODE_RGB:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x04);
            gpio_i2c_write(I2C_OV9653, DC_COM15, 0x00);
        break;
        
        case DC_MODE_RGB565:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x04);
            gpio_i2c_write(I2C_OV9653, DC_COM15, 0x10);
        break;
        
        case DC_MODE_RGB555:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x04);
            gpio_i2c_write(I2C_OV9653, DC_COM15, 0x30);
        break;
        
        case DC_MODE_RGBRAW:
            gpio_i2c_write(I2C_OV9653, DC_COM7, 0x05);
        break;
        
        default:
            return 1;
    
    }
    return 0;
}

/* 
 *  ov9653's output format get routine.
 *
 *  @return value: mode of ov9653's output format
 *
 */

static unsigned int dc_mode_get(void)
{
    unsigned int regvalue,regvalue1,reg_mode = DC_MODE_CCIR656;
    regvalue = gpio_sccb_read(I2C_OV9653, DC_COM1);
    if((regvalue & 0x40) == 0x40)
    {
        reg_mode = DC_MODE_CCIR656;
        return reg_mode;
    }
    regvalue = gpio_sccb_read(I2C_OV9653, DC_COM7);
    if((regvalue & 0x40) == 0x40)
    {
        reg_mode = DC_MODE_VGA;
        return reg_mode;
    }
    else if((regvalue & 0x20) == 0x20)
    {
        reg_mode = DC_MODE_CIF;
        return reg_mode;
    }
    else if((regvalue & 0x10) == 0x10)
    {
        reg_mode = DC_MODE_QVGA;
        return reg_mode;
    }
    else if((regvalue & 0x08) == 0x08)
    {
        reg_mode = DC_MODE_QCIF;
        return reg_mode;
    }
    else if((regvalue & 0x05) == 0x05)
    {
        reg_mode = DC_MODE_RGBRAW;
        return reg_mode;
    }
    else if(regvalue == 0x0) 
    {
        reg_mode = DC_MODE_SXGA;
        return reg_mode;    
    }
    regvalue1 =  gpio_sccb_read(I2C_OV9653, DC_COM1);
    if(((regvalue & 0x10) == 0x10) && ((regvalue1 & 0x20) == 0x20))
    {
        reg_mode = DC_MODE_QQVGA;
        return reg_mode;
    }
    else if(((regvalue & 0x08) == 0x08) && ((regvalue1 & 0x20) == 0x20))
    {
        reg_mode = DC_MODE_QQCIF;
        return reg_mode;
    }
    regvalue1 =  gpio_sccb_read(I2C_OV9653, DC_COM15);
    if(((regvalue & 0x04) == 0x04) && (regvalue1 == 0x00))
    {
        reg_mode = DC_MODE_RGB;
        return reg_mode;
    }
    else if(((regvalue & 0x04) == 0x04) && ((regvalue1 & 0x10) == 0x10))
    {
        reg_mode = DC_MODE_RGB565;
        return reg_mode;
    }  
    else if(((regvalue & 0x04) == 0x04) && ((regvalue1 & 0x30) == 0x30))
    {
        reg_mode = DC_MODE_RGB555;
        return reg_mode;
    } 
    return reg_mode;
}

/* 
 *  ov9653's output drive capability set routine.
 *
 *  @param zoom: ov9653's output drive capability value
 *
 *  @return value:0-- set success; 1-- set error. 
 *
 */

static unsigned int dc_zoom_set(dc_output_zoom zoom)
{
    switch(zoom)
    {
        case DC_ZOOM_1X:
            gpio_i2c_write(I2C_OV9653, DC_COM2, 0x0);
        break;
        
        case DC_ZOOM_2X:
            gpio_i2c_write(I2C_OV9653, DC_COM2, 0x1);
        break;
        
        case DC_ZOOM_4X:
            gpio_i2c_write(I2C_OV9653, DC_COM2, 0x3);
        break;
        
        default:
            return 1;
    
    }
    return 0;
}

/* 
 *  ov9653's output drive capability get routine.
 *
 *  @return value: ov9653's output drive capability value 
 *
 */

static unsigned int dc_zoom_get(void)
{
    unsigned int regvalue,reg_zoom = DC_ZOOM_1X;
    regvalue = gpio_sccb_read(I2C_OV9653, DC_COM2);
    if(regvalue == 0)
    {   
        reg_zoom = DC_ZOOM_1X;
    }
    else if((regvalue & 0x01) == 0x01)
    {
        reg_zoom = DC_ZOOM_2X;
    } 
    else if((regvalue & 0x03) == 0x03)
    {
        reg_zoom = DC_ZOOM_4X;
    }  
    return reg_zoom;
}

/* 
 *  ov9653's mirror image set routine.
 *
 *  @param mirror: ov9653's mirror image enable or disable
 *
 *  @return value:0-- set success; 1-- set error. 
 *
 */

static unsigned int dc_mirror_set(dc_output_mirror mirror)
{
    switch(mirror)
    {
        case DC_MIRROR_DISABLE:
            gpio_i2c_write(I2C_OV9653, DC_MVFP, 0x0);
        break;
        
        case DC_MIRROR_ENABLE:
          gpio_i2c_write(I2C_OV9653, DC_MVFP, 0x20);
        break;
        
        default:
            return 1;
    
    }
    return 0;
}

/* 
 *  ov9653's mirror image get routine.
 *
 *  @return value: ov9653's mirror image enable or disable
 *
 */

static unsigned int dc_mirror_get(void)
{
    unsigned int regvalue,reg_mirror = DC_MIRROR_DISABLE;
    regvalue = gpio_sccb_read(I2C_OV9653, DC_MVFP);  
    if(regvalue == 0)
    {   
        reg_mirror = DC_MIRROR_DISABLE;
    }
    else if((regvalue & 0x20) == 0x20)
    {
        reg_mirror = DC_MIRROR_ENABLE;
    }   
    return reg_mirror;      
}

/* 
 *  ov9653's night mode set routine.
 *
 *  @param nightmode: ov9653's night mode value
 *
 *  @return value:0-- set success; 1-- set error. 
 *
 */

static unsigned int dc_nightmode_set(dc_output_nightmode nightmode)
{
    switch(nightmode)
    {
        case DC_NIGHTMODE_DISABLE:
            gpio_i2c_write(I2C_OV9653, DC_COM11, 0x00);
        break;
        
        case DC_NIGHTMODE_NORMAL:
            gpio_i2c_write(I2C_OV9653, DC_COM11, 0x80);
        break;
        
        case DC_NIGHTMODE_HALFFRAME:
            gpio_i2c_write(I2C_OV9653, DC_COM11, 0xa0);
        break;
        
        case DC_NIGHTMODE_QUARTFRAME:
            gpio_i2c_write(I2C_OV9653, DC_COM11, 0xc0);
        break;
        
        case DC_NIGHTMODE_OCTFRAME:
            gpio_i2c_write(I2C_OV9653, DC_COM11, 0xe0);
        break;
        
        default:
            return 1;
    
    }
    return 0;
}

/* 
 *  ov9653's night mode get routine.
 *
 *  @return value: ov9653's night mode
 *
 */

static unsigned int dc_nightmode_get(void)
{
    unsigned int regvalue,reg_nightmode = DC_NIGHTMODE_DISABLE;
    regvalue = gpio_sccb_read(I2C_OV9653, DC_COM11);  
    if(regvalue == 0)
    {   
        reg_nightmode = DC_NIGHTMODE_DISABLE;
    }
    else if((regvalue & 0x80) == 0x80)
    {
        reg_nightmode = DC_NIGHTMODE_NORMAL;
    }
    else if((regvalue & 0xa0) == 0xa0)
    {
        reg_nightmode = DC_NIGHTMODE_HALFFRAME;
    }
    else if((regvalue & 0xc0) == 0xc0)
    {
        reg_nightmode = DC_NIGHTMODE_QUARTFRAME;
    }
    else if((regvalue & 0xe0) == 0xe0)
    {
        reg_nightmode = DC_NIGHTMODE_OCTFRAME;
    }   
    return reg_nightmode;      
}

/* 
 *  ov9653's sync set routine.
 *
 *  @param href_or_hsync: set pin definition
 *  @param pclk_mode: PCLK output option
 *  @param pclk_reverse: PCLK reverse
 *  @param href_reverse: HREF reserse
 *  @param vsync_neg: VSYNC negative
 *  @param hsync_neg: HSYNC negative
 *
 *  @return value:0-- set success; 1-- set error. 
 *
 */

static unsigned int dc_syncset
(
    dc_horizontal_mode  href_or_hsync,
    dc_pclk_mode  pclk_mode,
    dc_pclk_rev pclk_reverse,
    dc_href_rev href_reverse,
    dc_vsync_neg vsync_neg,
    dc_hsync_neg  hsync_neg
)
{
    unsigned char reg = 0;
    
    if(href_or_hsync == DC_HSYNC)
        reg |= 0x40;
    else if(href_or_hsync == DC_HREF)
        reg |= 0x00;
    else
    return 1;
    
    if(pclk_mode == DC_PCLK_DISABLE)
        reg |= 0x20;
    else if(pclk_mode == DC_PCLK_ENABLE)
        reg |= 0x00;
    else
    return 1;
    
    if(pclk_reverse == DC_PCLK_REVERSE)
        reg |= 0x10;
    else if(pclk_reverse == DC_PCLK_NORMAL)
        reg |= 0x00;
    else
    return 1;
    
    if(href_reverse == DC_HREF_REVERSE)
        reg |= 0x08;
    else if(href_reverse == DC_HREF_NORMAL)
        reg |= 0x00;
    else
    return 1;
    
    if(vsync_neg == DC_VSYNC_NEGATIVE)
        reg |= 0x02;
    else if(vsync_neg == DC_VSYNC_NORMAL)
        reg |= 0x00;
    else
    return 1;
    
    if(hsync_neg == DC_HSYNC_NEGATIVE)
        reg |= 0x01;
    else if(hsync_neg == DC_HSYNC_NORMAL)
        reg |= 0x00;
    else
    return 1;
    
    gpio_i2c_write(I2C_OV9653, DC_COM10, reg);
    return 0;
}

/* 
 *  ov9653's sync get routine.
 *
 *  @return value: ov9653's sync value
 *
 */

static struct dc_sync_mode * dc_syncget(void)
{
    struct dc_sync_mode *pmode = kmalloc(sizeof(struct dc_sync_mode), GFP_KERNEL);
    unsigned int regvalue;
    regvalue = gpio_sccb_read(I2C_OV9653, DC_COM10);
    if((regvalue & 0x40) == 0x40)
    {   
        pmode->href_or_hsync = DC_HSYNC;
    }
    else if((regvalue & 0x40) == 0x00)
    {
        pmode->href_or_hsync = DC_HREF;
    }
    
    if((regvalue & 0x20) == 0x20)
    {   
        pmode->pclk_mode = DC_PCLK_DISABLE;
    }
    else if((regvalue & 0x20) == 0x00)
    {
        pmode->pclk_mode = DC_PCLK_DISABLE;
    }
    
    if((regvalue & 0x10) == 0x10)
    {   
        pmode->pclk_reverse = DC_PCLK_REVERSE;
    }
    else if((regvalue & 0x10) == 0x00)
    {
        pmode->pclk_reverse = DC_PCLK_NORMAL;
    }
    
    if((regvalue & 0x08) == 0x08)
    {   
        pmode->href_reverse = DC_HREF_REVERSE;
    }
    else if((regvalue & 0x08) == 0x00)
    {
        pmode->href_reverse = DC_HREF_NORMAL;

⌨️ 快捷键说明

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