/* * at24.c - handle most I2C EEPROMs * * Copyright (C) 2005-2007 David Brownell * Copyright (C) 2008 Wolfram Sang, Pengutronix * * 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. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #define EEPROM_ATTR(_name) \ { \ .attr = { .name = #_name, .mode = 0444 }, \ .show = _name##_show, \ } struct i2c_client *this_client; static const struct i2c_device_id at24_ids[] = { { "24c16", 0 }, { /* END OF LIST */ } }; MODULE_DEVICE_TABLE(i2c, at24_ids); static int eeprom_i2c_rxdata(char *rxdata, int length) { int ret; struct i2c_msg msgs[] = { { .addr = this_client->addr, .flags = 0, .len = 1, .buf = &rxdata[0], }, { .addr = this_client->addr, .flags = I2C_M_RD, .len = length, .buf = &rxdata[1], }, }; ret = i2c_transfer(this_client->adapter, msgs, 2); if (ret < 0) pr_info("%s i2c read eeprom error: %d\n", __func__, ret); return ret; } static int eeprom_i2c_txdata(char *txdata, int length) { int ret; struct i2c_msg msg[] = { { .addr = this_client->addr, .flags = 0, .len = length, .buf = txdata, }, }; ret = i2c_transfer(this_client->adapter, msg, 1); if (ret < 0) pr_err("%s i2c write eeprom error: %d\n", __func__, ret); return 0; } static ssize_t read_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf) { u8 rxdata[4]; rxdata[0] = 0x1; eeprom_i2c_rxdata(rxdata, 3); return sprintf(buf, "Read data : 0x%x, 0x%x, 0x%x, 0x%x\n", rxdata[0], rxdata[1], rxdata[2], rxdata[3]); } static ssize_t write_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf) { static u8 txdata[4] = {0x1, 0xAA, 0xBB, 0xCC}; txdata[1]++; txdata[2]++; txdata[3]++; eeprom_i2c_txdata(txdata, 4); return sprintf(buf, "Write data: 0x%x, 0x%x, 0x%x, 0x%x\n", txdata[0], txdata[1], txdata[2], txdata[3]); } static struct kobj_attribute read = EEPROM_ATTR(read); static struct kobj_attribute write = EEPROM_ATTR(write); static const struct attribute *test_attrs[] = { &read.attr, &write.attr, NULL, }; static int at24_probe(struct i2c_client *client, const struct i2c_device_id *id) { int err; this_client = client; pr_debug("1..at24_probe\n); err = sysfs_create_files(&client->dev.kobj, test_attrs); pr_debug("2..at24_probe\n); if (err) pr_debug("sysfs_create_files failed\n"); pr_debug("3..at24_probe\n); return 0; } static int at24_remove(struct i2c_client *client) { sysfs_remove_files(&client->dev.kobj, test_attrs); return 0; } /*-------------------------------------------------------------------------*/ static struct i2c_driver at24_driver = { .driver = { .name = "at24", .owner = THIS_MODULE, }, .probe = at24_probe, .remove = at24_remove, .id_table = at24_ids, }; static int __init at24_init(void) { pr_debug("%d----%d\n", __func__, __LINE__); return i2c_add_driver(&at24_driver); } module_init(at24_init); static void __exit at24_exit(void) { pr_debug("%s()%d\n", __func__, __LINE__); i2c_del_driver(&at24_driver); } module_exit(at24_exit); MODULE_DESCRIPTION("24C16 simple test"); MODULE_AUTHOR("pannan"); MODULE_LICENSE("GPL");