[RK3288][Android6.0] AT24C02驅動分析及功能增加小結
阿新 • • 發佈:2018-12-22
Platform: Rockchip
OS: Android 6.0
Kernel: 3.10.92
Spec:
網上很多,如
https://wenku.baidu.com/view/0020131fff00bed5b8f31d05.html
驅動:
檔案:
kernel/drivers/misc/eeprom/at24.c
支援at24cxx所有系列,當然也支援at24c02, 這些系列不同的區別僅在於eeprom的大小.
at24_bin_read()和at24_bin_write()
操作路徑 :
/sys/bus/i2c/drivers/at24/5-0050/eeprom
5-0050是表示i2c通道5,地址是0x50,會根據裝置連線i2c埠以及地址變化.
使用:
#echo "at24c02 test" > /sys/bus/i2c/drivers/at24/5-0050/eeprom
#cat /sys/bus/i2c/drivers/at24/5-0050/eeprom
如果需要偏移若干地址讀寫,可以編寫一個ap來操作,可參考:
http://blog.csdn.net/dzw19911024/article/details/53813862
實際案例:
原理圖:
改動如下:
參考:
地址設定:
http://blog.csdn.net/qq_27312943/article/details/53325885
驅動解析:
http://blog.csdn.net/yj4231/article/details/18182775
OS: Android 6.0
Kernel: 3.10.92
Spec:
網上很多,如
https://wenku.baidu.com/view/0020131fff00bed5b8f31d05.html
驅動:
檔案:
kernel/drivers/misc/eeprom/at24.c
支援at24cxx所有系列,當然也支援at24c02, 這些系列不同的區別僅在於eeprom的大小.
驅動可以同時支援多個eeprom同時掛載,但需要修改eeprom的大小,比如支援at24c02,需要將2048改成4096.static const struct i2c_device_id at24_ids[] = { { "24c00", AT24_DEVICE_MAGIC(128 / 8, AT24_FLAG_TAKE8ADDR) }, { "24c01", AT24_DEVICE_MAGIC(1024 / 8, 0) }, { "24c02", AT24_DEVICE_MAGIC(2048 / 8, 0) }, { "spd", AT24_DEVICE_MAGIC(2048 / 8, AT24_FLAG_READONLY | AT24_FLAG_IRUGO) }, { "24c04", AT24_DEVICE_MAGIC(4096 / 8, 0) }, ...... };
static int at24_probe(struct i2c_client *client, const struct i2c_device_id *id)
{
......
num_addresses = DIV_ROUND_UP(chip.byte_len,
(chip.flags & AT24_FLAG_ADDR16) ? 65536 : 256);
......
}
驅動沒有建立字元裝置提供給上層, 而是以sysfs檔案的讀寫方式來操作,對應讀寫操作函式:at24_bin_read()和at24_bin_write()
操作路徑
/sys/bus/i2c/drivers/at24/5-0050/eeprom
5-0050是表示i2c通道5,地址是0x50,會根據裝置連線i2c埠以及地址變化.
使用:
#echo "at24c02 test" > /sys/bus/i2c/drivers/at24/5-0050/eeprom
#cat /sys/bus/i2c/drivers/at24/5-0050/eeprom
如果需要偏移若干地址讀寫,可以編寫一個ap來操作,可參考:
http://blog.csdn.net/dzw19911024/article/details/53813862
實際案例:
原理圖:
改動如下:
diff --git a/arch/arm/boot/dts/rk3288-b.dts b/arch/arm/boot/dts/rk3288-b.dts
index 1ff653a..ad3bc1a 100644
--- a/arch/arm/boot/dts/rk3288-b.dts
+++ b/arch/arm/boot/dts/rk3288-b.dts
@@ -324,6 +324,7 @@
&i2c3 {
status = "okay";
+
};
&i2c4 {
@@ -340,8 +341,14 @@
};
};
+//Kris,170510, add eeprom.
&i2c5 {
- status = "disabled";
+ status = "okay";
+ [email protected] {
+ compatible = "24c02";
+ reg = <0x50>;
+ status = "okay";
+ };
};
&fb {
diff --git a/arch/arm/boot/dts/rk3288-pinctrl.dtsi b/arch/arm/boot/dts/rk3288-pinctrl.dtsi
index a35d4d7..4a4ebc8 100755
--- a/arch/arm/boot/dts/rk3288-pinctrl.dtsi
+++ b/arch/arm/boot/dts/rk3288-pinctrl.dtsi
@@ -404,21 +404,21 @@
gpio7_i2c5 {
i2c5_sda:i2c5-sda {
- rockchip,pins = <EDPHDMII2C_SDA>;
+ rockchip,pins = <I2C5HDMI_SDA>;
rockchip,pull = <VALUE_PULL_NORMAL>;
rockchip,drive = <VALUE_DRV_DEFAULT>;
//rockchip,tristate = <VALUE_TRI_DEFAULT>;
};
i2c5_scl:i2c5-scl {
- rockchip,pins = <EDPHDMII2C_SCL>;
+ rockchip,pins = <I2C5HDMI_SCL>;
rockchip,pull = <VALUE_PULL_NORMAL>;
rockchip,drive = <VALUE_DRV_DEFAULT>;
//rockchip,tristate = <VALUE_TRI_DEFAULT>;
};
i2c5_gpio: i2c5-gpio {
- rockchip,pins = <FUNC_TO_GPIO(EDPHDMII2C_SDA)>, <FUNC_TO_GPIO(EDPHDMII2C_SCL)>;
+ rockchip,pins = <FUNC_TO_GPIO(I2C5HDMI_SDA)>, <FUNC_TO_GPIO(I2C5HDMI_SCL)>;
rockchip,drive = <VALUE_DRV_DEFAULT>;
};
};
diff --git a/arch/arm/configs/rockchip_b_defconfig b/arch/arm/configs/rockchip_b_defconfig
index a7037c2..092dc3c 100644
--- a/arch/arm/configs/rockchip_b_defconfig
+++ b/arch/arm/configs/rockchip_b_defconfig
@@ -662,3 +662,5 @@ CONFIG_CRYPTO_TWOFISH=y
CONFIG_CRYPTO_DEV_ROCKCHIP=y
CONFIG_CRYPTO_DEV_ROCKCHIP_ENCRYPT=y
CONFIG_XMF10411=y
+#Kris,170510, add eeprom
+CONFIG_EEPROM_AT24=y
diff --git a/drivers/misc/eeprom/at24.c b/drivers/misc/eeprom/at24.c
index 2baeec5..a6391a9 100644
--- a/drivers/misc/eeprom/at24.c
+++ b/drivers/misc/eeprom/at24.c
@@ -213,11 +213,15 @@ static ssize_t at24_eeprom_read(struct at24_data *at24, char *buf,
msg[0].addr = client->addr;
msg[0].buf = msgbuf;
msg[0].len = i;
+ //Kris, 170510, set scl_rate.
+ msg[0].scl_rate = 100*1000;
msg[1].addr = client->addr;
msg[1].flags = I2C_M_RD;
msg[1].buf = buf;
msg[1].len = count;
+ //Kris, 170510, set scl_rate.
+ msg[1].scl_rate = 100*1000;
}
/*
@@ -331,6 +335,7 @@ static ssize_t at24_eeprom_write(struct at24_data *at24, const char *buf,
/* Get corresponding I2C address and adjust offset */
client = at24_translate_offset(at24, &offset);
+
/* write_max is at most a page */
if (count > at24->write_max)
count = at24->write_max;
@@ -355,6 +360,8 @@ static ssize_t at24_eeprom_write(struct at24_data *at24, const char *buf,
msg.buf[i++] = offset;
memcpy(&msg.buf[i], buf, count);
msg.len = i + count;
+ //Kris, 170510, set scl_rate.
+ msg.scl_rate = 100*1000;
}
參考:
地址設定:
http://blog.csdn.net/qq_27312943/article/details/53325885
驅動解析:
http://blog.csdn.net/yj4231/article/details/18182775