aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/rtc/rtc-ds1307.c67
1 files changed, 63 insertions, 4 deletions
diff --git a/drivers/rtc/rtc-ds1307.c b/drivers/rtc/rtc-ds1307.c
index f03d5ba96db1..bb43cf703efc 100644
--- a/drivers/rtc/rtc-ds1307.c
+++ b/drivers/rtc/rtc-ds1307.c
@@ -126,9 +126,14 @@ struct chip_desc {
126 u16 nvram_offset; 126 u16 nvram_offset;
127 u16 nvram_size; 127 u16 nvram_size;
128 u16 trickle_charger_reg; 128 u16 trickle_charger_reg;
129 u8 trickle_charger_setup;
130 u8 (*do_trickle_setup)(struct i2c_client *, uint32_t, bool);
129}; 131};
130 132
131static const struct chip_desc chips[last_ds_type] = { 133static u8 do_trickle_setup_ds1339(struct i2c_client *,
134 uint32_t ohms, bool diode);
135
136static struct chip_desc chips[last_ds_type] = {
132 [ds_1307] = { 137 [ds_1307] = {
133 .nvram_offset = 8, 138 .nvram_offset = 8,
134 .nvram_size = 56, 139 .nvram_size = 56,
@@ -143,6 +148,7 @@ static const struct chip_desc chips[last_ds_type] = {
143 [ds_1339] = { 148 [ds_1339] = {
144 .alarm = 1, 149 .alarm = 1,
145 .trickle_charger_reg = 0x10, 150 .trickle_charger_reg = 0x10,
151 .do_trickle_setup = &do_trickle_setup_ds1339,
146 }, 152 },
147 [ds_1340] = { 153 [ds_1340] = {
148 .trickle_charger_reg = 0x08, 154 .trickle_charger_reg = 0x08,
@@ -833,15 +839,58 @@ ds1307_nvram_write(struct file *filp, struct kobject *kobj,
833 return count; 839 return count;
834} 840}
835 841
842
836/*----------------------------------------------------------------------*/ 843/*----------------------------------------------------------------------*/
837 844
845static u8 do_trickle_setup_ds1339(struct i2c_client *client,
846 uint32_t ohms, bool diode)
847{
848 u8 setup = (diode) ? DS1307_TRICKLE_CHARGER_DIODE :
849 DS1307_TRICKLE_CHARGER_NO_DIODE;
850
851 switch (ohms) {
852 case 250:
853 setup |= DS1307_TRICKLE_CHARGER_250_OHM;
854 break;
855 case 2000:
856 setup |= DS1307_TRICKLE_CHARGER_2K_OHM;
857 break;
858 case 4000:
859 setup |= DS1307_TRICKLE_CHARGER_4K_OHM;
860 break;
861 default:
862 dev_warn(&client->dev,
863 "Unsupported ohm value %u in dt\n", ohms);
864 return 0;
865 }
866 return setup;
867}
868
869static void ds1307_trickle_of_init(struct i2c_client *client,
870 struct chip_desc *chip)
871{
872 uint32_t ohms = 0;
873 bool diode = true;
874
875 if (!chip->do_trickle_setup)
876 goto out;
877 if (of_property_read_u32(client->dev.of_node, "trickle-resistor-ohms" , &ohms))
878 goto out;
879 if (of_property_read_bool(client->dev.of_node, "trickle-diode-disable"))
880 diode = false;
881 chip->trickle_charger_setup = chip->do_trickle_setup(client,
882 ohms, diode);
883out:
884 return;
885}
886
838static int ds1307_probe(struct i2c_client *client, 887static int ds1307_probe(struct i2c_client *client,
839 const struct i2c_device_id *id) 888 const struct i2c_device_id *id)
840{ 889{
841 struct ds1307 *ds1307; 890 struct ds1307 *ds1307;
842 int err = -ENODEV; 891 int err = -ENODEV;
843 int tmp; 892 int tmp;
844 const struct chip_desc *chip = &chips[id->driver_data]; 893 struct chip_desc *chip = &chips[id->driver_data];
845 struct i2c_adapter *adapter = to_i2c_adapter(client->dev.parent); 894 struct i2c_adapter *adapter = to_i2c_adapter(client->dev.parent);
846 bool want_irq = false; 895 bool want_irq = false;
847 unsigned char *buf; 896 unsigned char *buf;
@@ -866,9 +915,19 @@ static int ds1307_probe(struct i2c_client *client,
866 ds1307->client = client; 915 ds1307->client = client;
867 ds1307->type = id->driver_data; 916 ds1307->type = id->driver_data;
868 917
869 if (pdata && pdata->trickle_charger_setup && chip->trickle_charger_reg) 918 if (!pdata && client->dev.of_node)
919 ds1307_trickle_of_init(client, chip);
920 else if (pdata && pdata->trickle_charger_setup)
921 chip->trickle_charger_setup = pdata->trickle_charger_setup;
922
923 if (chip->trickle_charger_setup && chip->trickle_charger_reg) {
924 dev_dbg(&client->dev, "writing trickle charger info 0x%x to 0x%x\n",
925 DS13XX_TRICKLE_CHARGER_MAGIC | chip->trickle_charger_setup,
926 chip->trickle_charger_reg);
870 i2c_smbus_write_byte_data(client, chip->trickle_charger_reg, 927 i2c_smbus_write_byte_data(client, chip->trickle_charger_reg,
871 DS13XX_TRICKLE_CHARGER_MAGIC | pdata->trickle_charger_setup); 928 DS13XX_TRICKLE_CHARGER_MAGIC |
929 chip->trickle_charger_setup);
930 }
872 931
873 buf = ds1307->regs; 932 buf = ds1307->regs;
874 if (i2c_check_functionality(adapter, I2C_FUNC_SMBUS_I2C_BLOCK)) { 933 if (i2c_check_functionality(adapter, I2C_FUNC_SMBUS_I2C_BLOCK)) {