Linux I2C总线设备驱动模型分析(ov7740)(8)

static int __devinit cmos_ov7740_probe(struct i2c_client *client,
                  const struct i2c_device_id *id)
{
    printk("%s %s %d\n", __FILE__, __FUNCTION__, __LINE__);

/* 2.3 硬件相关 */
    /* 2.3.1 映射相应的寄存器 */
    GPJCON = ioremap(0x560000d0, 4);
    GPJDAT = ioremap(0x560000d4, 4);
    GPJUP = ioremap(0x560000d8, 4);

CISRCFMT = ioremap(0x4F000000, 4);
    CIWDOFST = ioremap(0x4F000004, 4);
    CIGCTRL = ioremap(0x4F000008, 4);
    CIPRCLRSA1 = ioremap(0x4F00006C, 4);
    CIPRCLRSA2 = ioremap(0x4F000070, 4);
    CIPRCLRSA3 = ioremap(0x4F000074, 4);
    CIPRCLRSA4 = ioremap(0x4F000078, 4);
    CIPRTRGFMT = ioremap(0x4F00007C, 4);
    CIPRCTRL = ioremap(0x4F000080, 4);
    CIPRSCPRERATIO = ioremap(0x4F000084, 4);
    CIPRSCPREDST = ioremap(0x4F000088, 4);
    CIPRSCCTRL = ioremap(0x4F00008C, 4);
    CIPRTAREA = ioremap(0x4F000090, 4);
    CIIMGCPT = ioremap(0x4F0000A0, 4);

SRCPND = ioremap(0X4A000000, 4);
    INTPND = ioremap(0X4A000010, 4);
    SUBSRCPND = ioremap(0X4A000018, 4);

/* 2.3.2 设置相应的GPIO用于CAMIF */
    cmos_ov7740_gpio_cfg();

/* 2.3.3 复位一下CAMIF控制器 */
    cmos_ov7740_camif_reset();

/* 2.3.4 设置、使能时钟(使能HCLK、使能并设置CAMCLK = 24MHz) */
    cmos_ov7740_clk_cfg();

/* 2.3.5 复位一下摄像头模块 */
    cmos_ov7740_reset();

/* 2.3.6 通过IIC总线,初始化摄像头模块 */
    cmos_ov7740_client = client;
    cmos_ov7740_init();

/* 2.3.7 注册中断 */
    if (request_irq(IRQ_S3C2440_CAM_C, cmos_ov7740_camif_irq_c, IRQF_DISABLED , "CAM_C", NULL))
        printk("%s:request_irq failed\n", __func__);

if (request_irq(IRQ_S3C2440_CAM_P, cmos_ov7740_camif_irq_p, IRQF_DISABLED , "CAM_P", NULL))
        printk("%s:request_irq failed\n", __func__);
   
   
    /* 2.2.注册 */
        if(video_register_device(&cmos_ov7740_vdev, VFL_TYPE_GRABBER, -1))
        {
            printk("unable to register video device\n");
        }

return 0;
}

static int __devexit cmos_ov7740_remove(struct i2c_client *client)
{
    printk("%s %s %d\n", __FILE__, __FUNCTION__, __LINE__);

iounmap(GPJCON);
    iounmap(GPJDAT);
    iounmap(GPJUP);

iounmap(CISRCFMT);
    iounmap(CIWDOFST);
    iounmap(CIGCTRL);
    iounmap(CIPRCLRSA1);
    iounmap(CIPRCLRSA2);
    iounmap(CIPRCLRSA3);
    iounmap(CIPRCLRSA4);
    iounmap(CIPRTRGFMT);
    iounmap(CIPRCTRL);
    iounmap(CIPRSCPRERATIO);
    iounmap(CIPRSCPREDST);
    iounmap(CIPRSCCTRL);
    iounmap(CIPRTAREA);
    iounmap(CIIMGCPT);
   
    iounmap(SRCPND);
    iounmap(INTPND);
    iounmap(SUBSRCPND);

free_irq(IRQ_S3C2440_CAM_C, NULL);
    free_irq(IRQ_S3C2440_CAM_P, NULL);
    video_unregister_device(&cmos_ov7740_vdev);
    return 0;
}

static const struct i2c_device_id cmos_ov7740_id_table[] = {
    { "cmos_ov7740", 0 },
    {}
};

/* 1.1. 分配、设置一个i2c_driver */
static struct i2c_driver cmos_ov7740_driver = {
    .driver    = {
        .name    = "cmos_ov7740",
        .owner    = THIS_MODULE,
    },
    .probe        = cmos_ov7740_probe,
    .remove        = __devexit_p(cmos_ov7740_remove),
    .id_table    = cmos_ov7740_id_table,
};

static int cmos_ov7740_drv_init(void)
{
    /* 1.2.注册 */
    i2c_add_driver(&cmos_ov7740_driver);

return 0;
}

static void cmos_ov7740_drv_exit(void)
{
    i2c_del_driver(&cmos_ov7740_driver);
}

module_init(cmos_ov7740_drv_init);
module_exit(cmos_ov7740_drv_exit);

MODULE_LICENSE("GPL");

再附一段测试程序,对i2c设备的寄存器进行读写测试:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>


/* i2c_test r addr
 * i2c_test w addr val
 */

void print_usage(char *file)
{
    printf("%s r addr\n", file);
    printf("%s w addr val\n", file);
}

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/124de2ba14b952f5a166e369a62106bb.html