Ov9650 camera driver-Linux kernel v4l2 Architecture Analysis 1

Source: Internet
Author: User

This series is divided into 3-4 articles, because too many articles will be messy.


V4l2 video drivers mainly involve the following knowledge points:

Camera knowledge (You can view the chip manual provided by the camera manufacturer.)

You need to know the features of the selected camera, including the access control method, configuration methods of various parameters, and signal output types.

Camera decoder, controller (The Controller Chip Manual contains camera-related register settings, such as 2410, which mainly sets the relevant control function to enable the chip's internal architecture.)

If the camera outputs analog data, you must be familiar with the decoder configuration. After the digital video signal enters the camera controller, you must be familiar with the operations of the camera controller.

V4l2 API and Data Structure Control (It mainly refers to some v4l2 operations required by the user space, and then the corresponding driver must be implemented at the underlying layer for these operations.)

Before writing a driver, familiarize yourself with the method for accessing v4l2 and the data structure designed by the application.

V4l2 driver architecture (This is the underlying write driver that provides the corresponding access interface for the user space. You can refer to/Drivers/Media/video // zc301/zc301_core.cZc301 video driver code in

It is an example of a very well-developed v4l2 architecture provided by the kernel. It can basically be modified based on it!)

Finally, compile a video driver that complies with v4l2 specifications.


No. 1 camera knowledge


Ov9650 camera. Do not talk about it for the moment. First, let's take a look at the camera decoder, Controller, and the camera controllers of different master chips.


static struct ov9650_reg{unsigned char subaddr;unsigned char value;}regs[] = {/* OV9650 intialization parameter table for VGA application */{0x12, 0x40},// Camera Soft reset. Self cleared after reset.{CHIP_DELAY, 10},{0x11,0x81},{0x6a,0x3e},{0x3b,0x09},{0x13,0xe0},{0x01,0x80},{0x02,0x80},{0x00,0x00},{0x10,0x00},{0x13,0xe5},{0x39,0x43},{0x38,0x12},{0x37,0x91},{0x35,0x91},{0x0e,0xa0},{0x1e,0x04},{0xA8,0x80},{0x14,0x40},{0x04,0x00},{0x0c,0x04},{0x0d,0x80},{0x18,0xc6},{0x17,0x26},{0x32,0xad},{0x03,0x00},{0x1a,0x3d},{0x19,0x01},{0x3f,0xa6},{0x14,0x2e},{0x15,0x10},{0x41,0x02},{0x42,0x08},{0x1b,0x00},{0x16,0x06},{0x33,0xe2},{0x34,0xbf},{0x96,0x04},{0x3a,0x00},{0x8e,0x00},{0x3c,0x77},{0x8B,0x06},{0x94,0x88},{0x95,0x88},{0x40,0xc1},{0x29,0x3f},{0x0f,0x42},{0x3d,0x92},{0x69,0x40},{0x5C,0xb9},{0x5D,0x96},{0x5E,0x10},{0x59,0xc0},{0x5A,0xaf},{0x5B,0x55},{0x43,0xf0},{0x44,0x10},{0x45,0x68},{0x46,0x96},{0x47,0x60},{0x48,0x80},{0x5F,0xe0},{0x60,0x8c},{0x61,0x20},{0xa5,0xd9},{0xa4,0x74},{0x8d,0x02},{0x13,0xe7},{0x4f,0x3a},{0x50,0x3d},{0x51,0x03},{0x52,0x12},{0x53,0x26},{0x54,0x38},{0x55,0x40},{0x56,0x40},{0x57,0x40},{0x58,0x0d},{0x8C,0x23},{0x3E,0x02},{0xa9,0xb8},{0xaa,0x92},{0xab,0x0a},{0x8f,0xdf},{0x90,0x00},{0x91,0x00},{0x9f,0x00},{0xa0,0x00},{0x3A,0x01},{0x24,0x70},{0x25,0x64},{0x26,0xc3},{0x2a,0x00},{0x2b,0x00},{0x6c,0x40},{0x6d,0x30},{0x6e,0x4b},{0x6f,0x60},{0x70,0x70},{0x71,0x70},{0x72,0x70},{0x73,0x70},{0x74,0x60},{0x75,0x60},{0x76,0x50},{0x77,0x48},{0x78,0x3a},{0x79,0x2e},{0x7a,0x28},{0x7b,0x22},{0x7c,0x04},{0x7d,0x07},{0x7e,0x10},{0x7f,0x28},{0x80,0x36},{0x81,0x44},{0x82,0x52},{0x83,0x60},{0x84,0x6c},{0x85,0x78},{0x86,0x8c},{0x87,0x9e},{0x88,0xbb},{0x89,0xd2},{0x8a,0xe6},};



The above is the address of the register that needs to write ov9650 sequentially and the written value (transmitted using I2C subsystem)

The I2C subsystem transmission has been analyzed. The platform device resources can be initialized in the Board file:


1. Modify VI Drivers/I2C/busses/kconfig



Config i2c_s3c2410

Tristate "S3C2410 I2C driver"

Depends on arch_s3c2410 | arch_initi64xx


Say y here to include support for I2C controller in

Samsung S3C2410 Based System-on-chip devices.



Config i2c_s3c2410

Tristate "S3C2410 I2C driver"

Depends on arch_s3c2410 | arch_initi64xx | arch_s5pc100


Say y here to include support for I2C controller in

Samsung S3C2410 Based System-on-chip devices.

2. Configure and re-compile the kernel

$ Make menuconfig

Device Drivers --->

<*> I2C support --->

<*> I2C Device Interface

I2C hardware bus support --->

<*> S3C2410 I2C driver

3. Modify vi arch/ARM/mach-s5pc100/mach-smdkc100.c


View the schematic can know that the camera is connected to the I2C-0 or 1, assuming on 1, according to the schematic modified i2c_devs1 add ov9650 content, mainly ov9650 address, this can be found in the chip manual as 0x60.

Why is it 0x30? I have discussed this in another I2C subsystem analysis. Explanations for links


Static struct i2c_board_info i2c_devs1 [] _ initdata = {




Static struct i2c_board_info i2c_devs1 [] _ initdata = {


I2c_board_info ("ov9650", 0x30 ),




Add information about s5pc100 camera controller platform device. You can view the information in s5pc100 chip manual.

Static struct resource initi_camif_resource [] = {

[0] = {

. Start = 0xee200000,

. End = 0xee200000 + sz_1m-1,

. Flags = ioresource_mem,


[1] = {

. Start = irq_fimc0,

. End = irq_fimc0,

. Flags = ioresource_irq,





Static u64 initi_device_camif_dmamask = 0 xfffffffful;


Struct platform_device initi_device_camif = {

. Name = "s5pc100-camif ",

. ID = 0,

. Num_resources = array_size (initi_camif_resource ),

. Resource = maid,

. Dev = {

. Dma_mask = & cloud_device_camif_dmamask,

. Coherent_dma_mask = 0 xfffffffful




Export_symbol (initi_device_camif );


Register the camera control platform device:

In smdkc100_devices, add


Static struct platform_device * smdkc100_devices [] _ initdata = {

& Amp; initi_device_camif, // Add content



4. Add a Driver (video)

Make menuconfig

Device Drivers --->

<*> Multimedia support --->

<*> Video for Linux

[*] Enable video for Linux API 1 (Deprecated) (new)

[*] Video capture adapters (new) --->

[*] V4l USB devices (new) --->

<*> USB video class (UVC)

[*] UVC input events Device Support (new)

<*> USB zc0301 [p] webcam support (Deprecated)


The device has been registered!


/* Write a register */

Static int ov9650_reg_write (struct i2c_client * client, u8 Reg, u8 Val)


Int ret;

U8 _ Val;

Unsigned char data [2] = {Reg, Val };

Struct i2c_msg MSG = {

. ADDR = client-> ADDR,

. Flags = 0,

. Len = 2,

. Buf = data,


// Construct i2c_msg

Ret = i2c_transfer (client-> adapter, & MSG, 1); // exchange a group of messages between the I2C adapter and the I2C Device

Return 0;





Static void ov9650_init_regs (void)


Int I;

For (I = 0; I <array_size (regs); I ++)



If (regs [I]. subaddr = 0xff)


Mdelay (regs [I]. value );



Ov9650_reg_write (ov9650_client, regs [I]. subaddr, regs [I]. value );



At this point, the camera register has been initialized through the I2C bus.

The next section will explainCamera decoder and controller.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.