Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Probe problem when writing a I2C device driver

I am a newbie in writing linux device driver, forgive me if anything stupid a asked and my poor English^^
I am trying to write a driver for a touch panel, which communicate with CPU via I2C.
I tried to add a device driver into linux platform, and the register was success, I mean the driver was loaded, but the probe function didn't fired up!!

Above is partial code of the driver i wrote.

static int i2c_ts_probe(struct i2c_client *client, const struct i2c_device_id * id) {  
    /* ... */  
}

static int i2c_ts_remove(struct i2c_client *client) {  
    /* ... */  
}

static const struct i2c_device_id i2c_ts_id[] = {  
    {"Capacitive TS", 0},  
    { }  
};  
MODULE_DEVICE_TABLE(i2c, i2c_ts_id);  

static struct i2c_driver i2c_ts = {  
    .id_table = i2c_ts_id,  
    .probe = i2c_ts_probe,  
    .remove = i1c_ts_remobe,  
    .driver = {  
        .name = "i2c_ts",  
    },  
};

static int __init i2c_ts_init(void) {  
    return i2c_add_driver(&i2c_ts);  
}

static int __init i2c_ts_exit(void) {  
    return i2c_del_driver(&i2c_ts);  
}  

module_init(i2c_ts_init);
module_exit(i2c_ts_exit);

Above is partial code in platform (/kernel/arch/arm/mach-pxa/saarb.c) used for registering the i2c device.

static struct i2c_board_info i2c_board_info_ts[] = {
    {  
        .type = i2c_ts,  
        .irq = IRQ_GPIO(mfp_to_gpio(MFP_PIN_GPIO0)),  
    },  
};

static void __init saarb_init(void) {  
    ...  
    i2c_register_board_info(0, ARRAY_AND_SIZE(i2c_board_info_ts));  
    ...  
}

any suggestion and comment will be welcome, thanks^^

like image 766
ChengYing Avatar asked Jun 10 '10 13:06

ChengYing


People also ask

What is I2C probe?

The probe() function is a part of the struct i2c_driver structure, and is executed anytime, once an I2C device is instantiated. It is responsible for the following tasks: Check whether the device is the one you expected.

What is probe in device driver?

The probe routine specifies a physical device ID as a device node property so that the bus driver can find the appropriate device driver for this device node. Note that the device ID is bus class specific.

How do I download I2C HID driver?

Locate and double click on the Human Interface Devices option. Right-click on the I2C HID Device and select Update driver from the context menu. Select the Search automatically for drivers option as Windows will find the best drivers on your system.


2 Answers

So that the linux device/driver model can probe your driver, there must be a device requesting it: this is achieved by comparing the name of the driver ("i2c_ts") and the type of the device in the i2c_board_info struct. In your case I guess the type is not equal to "i2c_ts".

So I would suggest that you use the I2C_BOARD_INFO macro to instantiate your device, as documented in Documentation/i2c/instantiating_devices.

static struct i2c_board_info i2c_board_info_ts[] = {
    {  
         I2C_BOARD_INFO("i2c_ts", 0x12),  
         .irq = IRQ_GPIO(mfp_to_gpio(MFP_PIN_GPIO0)),  
    },
};

static void __init saarb_init(void) {  
    ...  
    i2c_register_board_info(0, ARRAY_AND_SIZE(i2c_board_info_ts));  
    ... 
}

You had also not given an address to your device, and I2C_BOARD_INFO needs it. Read the datasheet of your touchscreen to know what that address is.

Finally, as suggested above, be sure that i2c_ts_id is correct. I am not sure it plays a role in the device/module association mechanism in the kernel, but I would say it's far less confusing it they all share the same name.

like image 119
Longfield Avatar answered Oct 03 '22 17:10

Longfield


Probe method will only be called when the device matches the driver name.As you have mentioned your driver name as 'i2c_ts' please check your device tree for the device name.Both should be same.

like image 34
a.saurabh Avatar answered Oct 03 '22 17:10

a.saurabh