1 // SPDX-License-Identifier: GPL-2.0+ 2 /* I2C support for Dialog DA9063 3 * 4 * Copyright 2012 Dialog Semiconductor Ltd. 5 * Copyright 2013 Philipp Zabel, Pengutronix 6 * 7 * Author: Krystian Garbaciak, Dialog Semiconductor 8 */ 9 10 #include <linux/kernel.h> 11 #include <linux/module.h> 12 #include <linux/i2c.h> 13 #include <linux/regmap.h> 14 #include <linux/delay.h> 15 #include <linux/slab.h> 16 #include <linux/err.h> 17 18 #include <linux/mfd/core.h> 19 #include <linux/mfd/da9063/core.h> 20 #include <linux/mfd/da9063/pdata.h> 21 #include <linux/mfd/da9063/registers.h> 22 23 #include <linux/of.h> 24 #include <linux/regulator/of_regulator.h> 25 26 static const struct regmap_range da9063_ad_readable_ranges[] = { 27 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_AD_REG_SECOND_D), 28 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 29 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 30 regmap_reg_range(DA9063_REG_T_OFFSET, DA9063_AD_REG_GP_ID_19), 31 regmap_reg_range(DA9063_REG_CHIP_ID, DA9063_REG_CHIP_VARIANT), 32 }; 33 34 static const struct regmap_range da9063_ad_writeable_ranges[] = { 35 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_PAGE_CON), 36 regmap_reg_range(DA9063_REG_FAULT_LOG, DA9063_REG_VSYS_MON), 37 regmap_reg_range(DA9063_REG_COUNT_S, DA9063_AD_REG_ALARM_Y), 38 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 39 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 40 regmap_reg_range(DA9063_REG_CONFIG_I, DA9063_AD_REG_MON_REG_4), 41 regmap_reg_range(DA9063_AD_REG_GP_ID_0, DA9063_AD_REG_GP_ID_19), 42 }; 43 44 static const struct regmap_range da9063_ad_volatile_ranges[] = { 45 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_EVENT_D), 46 regmap_reg_range(DA9063_REG_CONTROL_A, DA9063_REG_CONTROL_B), 47 regmap_reg_range(DA9063_REG_CONTROL_E, DA9063_REG_CONTROL_F), 48 regmap_reg_range(DA9063_REG_BCORE2_CONT, DA9063_REG_LDO11_CONT), 49 regmap_reg_range(DA9063_REG_DVC_1, DA9063_REG_ADC_MAN), 50 regmap_reg_range(DA9063_REG_ADC_RES_L, DA9063_AD_REG_SECOND_D), 51 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_SEQ), 52 regmap_reg_range(DA9063_REG_EN_32K, DA9063_REG_EN_32K), 53 regmap_reg_range(DA9063_AD_REG_MON_REG_5, DA9063_AD_REG_MON_REG_6), 54 }; 55 56 static const struct regmap_access_table da9063_ad_readable_table = { 57 .yes_ranges = da9063_ad_readable_ranges, 58 .n_yes_ranges = ARRAY_SIZE(da9063_ad_readable_ranges), 59 }; 60 61 static const struct regmap_access_table da9063_ad_writeable_table = { 62 .yes_ranges = da9063_ad_writeable_ranges, 63 .n_yes_ranges = ARRAY_SIZE(da9063_ad_writeable_ranges), 64 }; 65 66 static const struct regmap_access_table da9063_ad_volatile_table = { 67 .yes_ranges = da9063_ad_volatile_ranges, 68 .n_yes_ranges = ARRAY_SIZE(da9063_ad_volatile_ranges), 69 }; 70 71 static const struct regmap_range da9063_bb_readable_ranges[] = { 72 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_BB_REG_SECOND_D), 73 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 74 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 75 regmap_reg_range(DA9063_REG_T_OFFSET, DA9063_BB_REG_GP_ID_19), 76 regmap_reg_range(DA9063_REG_CHIP_ID, DA9063_REG_CHIP_VARIANT), 77 }; 78 79 static const struct regmap_range da9063_bb_writeable_ranges[] = { 80 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_PAGE_CON), 81 regmap_reg_range(DA9063_REG_FAULT_LOG, DA9063_REG_VSYS_MON), 82 regmap_reg_range(DA9063_REG_COUNT_S, DA9063_BB_REG_ALARM_Y), 83 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 84 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 85 regmap_reg_range(DA9063_REG_CONFIG_I, DA9063_BB_REG_MON_REG_4), 86 regmap_reg_range(DA9063_BB_REG_GP_ID_0, DA9063_BB_REG_GP_ID_19), 87 }; 88 89 static const struct regmap_range da9063_bb_volatile_ranges[] = { 90 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_EVENT_D), 91 regmap_reg_range(DA9063_REG_CONTROL_A, DA9063_REG_CONTROL_B), 92 regmap_reg_range(DA9063_REG_CONTROL_E, DA9063_REG_CONTROL_F), 93 regmap_reg_range(DA9063_REG_BCORE2_CONT, DA9063_REG_LDO11_CONT), 94 regmap_reg_range(DA9063_REG_DVC_1, DA9063_REG_ADC_MAN), 95 regmap_reg_range(DA9063_REG_ADC_RES_L, DA9063_BB_REG_SECOND_D), 96 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_SEQ), 97 regmap_reg_range(DA9063_REG_EN_32K, DA9063_REG_EN_32K), 98 regmap_reg_range(DA9063_BB_REG_MON_REG_5, DA9063_BB_REG_MON_REG_6), 99 }; 100 101 static const struct regmap_access_table da9063_bb_readable_table = { 102 .yes_ranges = da9063_bb_readable_ranges, 103 .n_yes_ranges = ARRAY_SIZE(da9063_bb_readable_ranges), 104 }; 105 106 static const struct regmap_access_table da9063_bb_writeable_table = { 107 .yes_ranges = da9063_bb_writeable_ranges, 108 .n_yes_ranges = ARRAY_SIZE(da9063_bb_writeable_ranges), 109 }; 110 111 static const struct regmap_access_table da9063_bb_volatile_table = { 112 .yes_ranges = da9063_bb_volatile_ranges, 113 .n_yes_ranges = ARRAY_SIZE(da9063_bb_volatile_ranges), 114 }; 115 116 static const struct regmap_range da9063l_bb_readable_ranges[] = { 117 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_MON_A10_RES), 118 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 119 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 120 regmap_reg_range(DA9063_REG_T_OFFSET, DA9063_BB_REG_GP_ID_19), 121 regmap_reg_range(DA9063_REG_CHIP_ID, DA9063_REG_CHIP_VARIANT), 122 }; 123 124 static const struct regmap_range da9063l_bb_writeable_ranges[] = { 125 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_PAGE_CON), 126 regmap_reg_range(DA9063_REG_FAULT_LOG, DA9063_REG_VSYS_MON), 127 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_ID_32_31), 128 regmap_reg_range(DA9063_REG_SEQ_A, DA9063_REG_AUTO3_LOW), 129 regmap_reg_range(DA9063_REG_CONFIG_I, DA9063_BB_REG_MON_REG_4), 130 regmap_reg_range(DA9063_BB_REG_GP_ID_0, DA9063_BB_REG_GP_ID_19), 131 }; 132 133 static const struct regmap_range da9063l_bb_volatile_ranges[] = { 134 regmap_reg_range(DA9063_REG_PAGE_CON, DA9063_REG_EVENT_D), 135 regmap_reg_range(DA9063_REG_CONTROL_A, DA9063_REG_CONTROL_B), 136 regmap_reg_range(DA9063_REG_CONTROL_E, DA9063_REG_CONTROL_F), 137 regmap_reg_range(DA9063_REG_BCORE2_CONT, DA9063_REG_LDO11_CONT), 138 regmap_reg_range(DA9063_REG_DVC_1, DA9063_REG_ADC_MAN), 139 regmap_reg_range(DA9063_REG_ADC_RES_L, DA9063_REG_MON_A10_RES), 140 regmap_reg_range(DA9063_REG_SEQ, DA9063_REG_SEQ), 141 regmap_reg_range(DA9063_REG_EN_32K, DA9063_REG_EN_32K), 142 regmap_reg_range(DA9063_BB_REG_MON_REG_5, DA9063_BB_REG_MON_REG_6), 143 }; 144 145 static const struct regmap_access_table da9063l_bb_readable_table = { 146 .yes_ranges = da9063l_bb_readable_ranges, 147 .n_yes_ranges = ARRAY_SIZE(da9063l_bb_readable_ranges), 148 }; 149 150 static const struct regmap_access_table da9063l_bb_writeable_table = { 151 .yes_ranges = da9063l_bb_writeable_ranges, 152 .n_yes_ranges = ARRAY_SIZE(da9063l_bb_writeable_ranges), 153 }; 154 155 static const struct regmap_access_table da9063l_bb_volatile_table = { 156 .yes_ranges = da9063l_bb_volatile_ranges, 157 .n_yes_ranges = ARRAY_SIZE(da9063l_bb_volatile_ranges), 158 }; 159 160 static const struct regmap_range_cfg da9063_range_cfg[] = { 161 { 162 .range_min = DA9063_REG_PAGE_CON, 163 .range_max = DA9063_REG_CHIP_VARIANT, 164 .selector_reg = DA9063_REG_PAGE_CON, 165 .selector_mask = 1 << DA9063_I2C_PAGE_SEL_SHIFT, 166 .selector_shift = DA9063_I2C_PAGE_SEL_SHIFT, 167 .window_start = 0, 168 .window_len = 256, 169 } 170 }; 171 172 static struct regmap_config da9063_regmap_config = { 173 .reg_bits = 8, 174 .val_bits = 8, 175 .ranges = da9063_range_cfg, 176 .num_ranges = ARRAY_SIZE(da9063_range_cfg), 177 .max_register = DA9063_REG_CHIP_VARIANT, 178 179 .cache_type = REGCACHE_RBTREE, 180 }; 181 182 static const struct of_device_id da9063_dt_ids[] = { 183 { .compatible = "dlg,da9063", }, 184 { .compatible = "dlg,da9063l", }, 185 { } 186 }; 187 MODULE_DEVICE_TABLE(of, da9063_dt_ids); 188 static int da9063_i2c_probe(struct i2c_client *i2c, 189 const struct i2c_device_id *id) 190 { 191 struct da9063 *da9063; 192 int ret; 193 194 da9063 = devm_kzalloc(&i2c->dev, sizeof(struct da9063), GFP_KERNEL); 195 if (da9063 == NULL) 196 return -ENOMEM; 197 198 i2c_set_clientdata(i2c, da9063); 199 da9063->dev = &i2c->dev; 200 da9063->chip_irq = i2c->irq; 201 da9063->type = id->driver_data; 202 203 if (da9063->variant_code == PMIC_DA9063_AD) { 204 da9063_regmap_config.rd_table = &da9063_ad_readable_table; 205 da9063_regmap_config.wr_table = &da9063_ad_writeable_table; 206 da9063_regmap_config.volatile_table = &da9063_ad_volatile_table; 207 } else if (da9063->type == PMIC_TYPE_DA9063L) { 208 da9063_regmap_config.rd_table = &da9063l_bb_readable_table; 209 da9063_regmap_config.wr_table = &da9063l_bb_writeable_table; 210 da9063_regmap_config.volatile_table = &da9063l_bb_volatile_table; 211 } else { 212 da9063_regmap_config.rd_table = &da9063_bb_readable_table; 213 da9063_regmap_config.wr_table = &da9063_bb_writeable_table; 214 da9063_regmap_config.volatile_table = &da9063_bb_volatile_table; 215 } 216 217 da9063->regmap = devm_regmap_init_i2c(i2c, &da9063_regmap_config); 218 if (IS_ERR(da9063->regmap)) { 219 ret = PTR_ERR(da9063->regmap); 220 dev_err(da9063->dev, "Failed to allocate register map: %d\n", 221 ret); 222 return ret; 223 } 224 225 return da9063_device_init(da9063, i2c->irq); 226 } 227 228 static const struct i2c_device_id da9063_i2c_id[] = { 229 { "da9063", PMIC_TYPE_DA9063 }, 230 { "da9063l", PMIC_TYPE_DA9063L }, 231 {}, 232 }; 233 MODULE_DEVICE_TABLE(i2c, da9063_i2c_id); 234 235 static struct i2c_driver da9063_i2c_driver = { 236 .driver = { 237 .name = "da9063", 238 .of_match_table = of_match_ptr(da9063_dt_ids), 239 }, 240 .probe = da9063_i2c_probe, 241 .id_table = da9063_i2c_id, 242 }; 243 244 module_i2c_driver(da9063_i2c_driver); 245