Linux Audio

Check our new training course

Loading...
v6.2
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Regulator driver for TI TPS6586x
  4 *
  5 * Copyright (C) 2010 Compulab Ltd.
  6 * Author: Mike Rapoport <mike@compulab.co.il>
  7 *
  8 * Based on da903x
  9 * Copyright (C) 2006-2008 Marvell International Ltd.
 10 * Copyright (C) 2008 Compulab Ltd.
 
 
 
 
 11 */
 12
 13#include <linux/kernel.h>
 14#include <linux/module.h>
 15#include <linux/init.h>
 16#include <linux/err.h>
 17#include <linux/of.h>
 18#include <linux/slab.h>
 19#include <linux/platform_device.h>
 20#include <linux/regulator/driver.h>
 21#include <linux/regulator/machine.h>
 22#include <linux/regulator/of_regulator.h>
 23#include <linux/mfd/tps6586x.h>
 24
 25/* supply control and voltage setting  */
 26#define TPS6586X_SUPPLYENA	0x10
 27#define TPS6586X_SUPPLYENB	0x11
 28#define TPS6586X_SUPPLYENC	0x12
 29#define TPS6586X_SUPPLYEND	0x13
 30#define TPS6586X_SUPPLYENE	0x14
 31#define TPS6586X_VCC1		0x20
 32#define TPS6586X_VCC2		0x21
 33#define TPS6586X_SM1V1		0x23
 34#define TPS6586X_SM1V2		0x24
 35#define TPS6586X_SM1SL		0x25
 36#define TPS6586X_SM0V1		0x26
 37#define TPS6586X_SM0V2		0x27
 38#define TPS6586X_SM0SL		0x28
 39#define TPS6586X_LDO2AV1	0x29
 40#define TPS6586X_LDO2AV2	0x2A
 41#define TPS6586X_LDO2BV1	0x2F
 42#define TPS6586X_LDO2BV2	0x30
 43#define TPS6586X_LDO4V1		0x32
 44#define TPS6586X_LDO4V2		0x33
 45
 46/* converter settings  */
 47#define TPS6586X_SUPPLYV1	0x41
 48#define TPS6586X_SUPPLYV2	0x42
 49#define TPS6586X_SUPPLYV3	0x43
 50#define TPS6586X_SUPPLYV4	0x44
 51#define TPS6586X_SUPPLYV5	0x45
 52#define TPS6586X_SUPPLYV6	0x46
 53#define TPS6586X_SMODE1		0x47
 54#define TPS6586X_SMODE2		0x48
 55
 56struct tps6586x_regulator {
 57	struct regulator_desc desc;
 58
 
 
 
 59	int enable_bit[2];
 60	int enable_reg[2];
 61};
 62
 63static const struct regulator_ops tps6586x_rw_regulator_ops = {
 64	.list_voltage = regulator_list_voltage_table,
 65	.map_voltage = regulator_map_voltage_ascend,
 66	.get_voltage_sel = regulator_get_voltage_sel_regmap,
 67	.set_voltage_sel = regulator_set_voltage_sel_regmap,
 68
 69	.is_enabled = regulator_is_enabled_regmap,
 70	.enable = regulator_enable_regmap,
 71	.disable = regulator_disable_regmap,
 72};
 73
 74static const struct regulator_ops tps6586x_rw_linear_regulator_ops = {
 75	.list_voltage = regulator_list_voltage_linear,
 76	.get_voltage_sel = regulator_get_voltage_sel_regmap,
 77	.set_voltage_sel = regulator_set_voltage_sel_regmap,
 78
 79	.is_enabled = regulator_is_enabled_regmap,
 80	.enable = regulator_enable_regmap,
 81	.disable = regulator_disable_regmap,
 82};
 83
 84static const struct regulator_ops tps6586x_ro_regulator_ops = {
 85	.list_voltage = regulator_list_voltage_table,
 86	.map_voltage = regulator_map_voltage_ascend,
 87	.get_voltage_sel = regulator_get_voltage_sel_regmap,
 88
 89	.is_enabled = regulator_is_enabled_regmap,
 90	.enable = regulator_enable_regmap,
 91	.disable = regulator_disable_regmap,
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 92};
 93
 94static const struct regulator_ops tps6586x_sys_regulator_ops = {
 
 95};
 96
 97static const unsigned int tps6586x_ldo0_voltages[] = {
 98	1200000, 1500000, 1800000, 2500000, 2700000, 2850000, 3100000, 3300000,
 
 
 
 99};
100
101static const unsigned int tps6586x_ldo_voltages[] = {
102	1250000, 1500000, 1800000, 2500000, 2700000, 2850000, 3100000, 3300000,
 
 
 
103};
104
105static const unsigned int tps658640_rtc_voltages[] = {
106	2500000, 2850000, 3100000, 3300000,
 
 
 
107};
108
109#define TPS6586X_REGULATOR(_id, _ops, _pin_name, vdata, vreg, shift, nbits, \
110			   ereg0, ebit0, ereg1, ebit1, goreg, gobit)	\
111	.desc	= {							\
112		.supply_name = _pin_name,				\
113		.name	= "REG-" #_id,					\
114		.ops	= &tps6586x_## _ops ## _regulator_ops,		\
115		.type	= REGULATOR_VOLTAGE,				\
116		.id	= TPS6586X_ID_##_id,				\
117		.n_voltages = ARRAY_SIZE(vdata##_voltages),		\
118		.volt_table = vdata##_voltages,				\
119		.owner	= THIS_MODULE,					\
120		.enable_reg = TPS6586X_SUPPLY##ereg0,			\
121		.enable_mask = 1 << (ebit0),				\
122		.vsel_reg = TPS6586X_##vreg,				\
123		.vsel_mask = ((1 << (nbits)) - 1) << (shift),		\
124		.apply_reg = (goreg),				\
125		.apply_bit = (gobit),				\
126	},								\
 
 
 
127	.enable_reg[0]	= TPS6586X_SUPPLY##ereg0,			\
128	.enable_bit[0]	= (ebit0),					\
129	.enable_reg[1]	= TPS6586X_SUPPLY##ereg1,			\
130	.enable_bit[1]	= (ebit1),
 
131
132#define TPS6586X_REGULATOR_LINEAR(_id, _ops, _pin_name, n_volt, min_uv,	\
133				  uv_step, vreg, shift, nbits, ereg0,	\
134				  ebit0, ereg1, ebit1, goreg, gobit)	\
135	.desc	= {							\
136		.supply_name = _pin_name,				\
137		.name	= "REG-" #_id,					\
138		.ops	= &tps6586x_## _ops ## _regulator_ops,		\
139		.type	= REGULATOR_VOLTAGE,				\
140		.id	= TPS6586X_ID_##_id,				\
141		.n_voltages = n_volt,					\
142		.min_uV = min_uv,					\
143		.uV_step = uv_step,					\
144		.owner	= THIS_MODULE,					\
145		.enable_reg = TPS6586X_SUPPLY##ereg0,			\
146		.enable_mask = 1 << (ebit0),				\
147		.vsel_reg = TPS6586X_##vreg,				\
148		.vsel_mask = ((1 << (nbits)) - 1) << (shift),		\
149		.apply_reg = (goreg),				\
150		.apply_bit = (gobit),				\
151	},								\
152	.enable_reg[0]	= TPS6586X_SUPPLY##ereg0,			\
153	.enable_bit[0]	= (ebit0),					\
154	.enable_reg[1]	= TPS6586X_SUPPLY##ereg1,			\
155	.enable_bit[1]	= (ebit1),
156
157#define TPS6586X_LDO(_id, _pname, vdata, vreg, shift, nbits,		\
158		     ereg0, ebit0, ereg1, ebit1)			\
159{									\
160	TPS6586X_REGULATOR(_id, rw, _pname, vdata, vreg, shift, nbits,	\
161			   ereg0, ebit0, ereg1, ebit1, 0, 0)		\
162}
163
164#define TPS6586X_LDO_LINEAR(_id, _pname, n_volt, min_uv, uv_step, vreg,	\
165			    shift, nbits, ereg0, ebit0, ereg1, ebit1)	\
166{									\
167	TPS6586X_REGULATOR_LINEAR(_id, rw_linear, _pname, n_volt,	\
168				  min_uv, uv_step, vreg, shift, nbits,	\
169				  ereg0, ebit0, ereg1, ebit1, 0, 0)	\
170}
171
172#define TPS6586X_FIXED_LDO(_id, _pname, vdata, vreg, shift, nbits,	\
173			  ereg0, ebit0, ereg1, ebit1)			\
174{									\
175	TPS6586X_REGULATOR(_id, ro, _pname, vdata, vreg, shift, nbits,	\
176			   ereg0, ebit0, ereg1, ebit1, 0, 0)		\
177}
178
179#define TPS6586X_DVM(_id, _pname, n_volt, min_uv, uv_step, vreg, shift,	\
180		     nbits, ereg0, ebit0, ereg1, ebit1, goreg, gobit)	\
181{									\
182	TPS6586X_REGULATOR_LINEAR(_id, rw_linear, _pname, n_volt,	\
183				  min_uv, uv_step, vreg, shift, nbits,	\
184				  ereg0, ebit0, ereg1, ebit1, goreg,	\
185				  gobit)				\
186}
187
188#define TPS6586X_SYS_REGULATOR()					\
189{									\
190	.desc	= {							\
191		.supply_name = "sys",					\
192		.name	= "REG-SYS",					\
193		.ops	= &tps6586x_sys_regulator_ops,			\
194		.type	= REGULATOR_VOLTAGE,				\
195		.id	= TPS6586X_ID_SYS,				\
196		.owner	= THIS_MODULE,					\
197	},								\
198}
199
200static struct tps6586x_regulator tps6586x_regulator[] = {
201	TPS6586X_SYS_REGULATOR(),
202	TPS6586X_LDO(LDO_0, "vinldo01", tps6586x_ldo0, SUPPLYV1, 5, 3, ENC, 0,
203					END, 0),
204	TPS6586X_LDO(LDO_3, "vinldo23", tps6586x_ldo, SUPPLYV4, 0, 3, ENC, 2,
205					END, 2),
206	TPS6586X_LDO(LDO_5, "REG-SYS", tps6586x_ldo, SUPPLYV6, 0, 3, ENE, 6,
207					ENE, 6),
208	TPS6586X_LDO(LDO_6, "vinldo678", tps6586x_ldo, SUPPLYV3, 0, 3, ENC, 4,
209					END, 4),
210	TPS6586X_LDO(LDO_7, "vinldo678", tps6586x_ldo, SUPPLYV3, 3, 3, ENC, 5,
211					END, 5),
212	TPS6586X_LDO(LDO_8, "vinldo678", tps6586x_ldo, SUPPLYV2, 5, 3, ENC, 6,
213					END, 6),
214	TPS6586X_LDO(LDO_9, "vinldo9", tps6586x_ldo, SUPPLYV6, 3, 3, ENE, 7,
215					ENE, 7),
216	TPS6586X_LDO(LDO_RTC, "REG-SYS", tps6586x_ldo, SUPPLYV4, 3, 3, V4, 7,
217					V4, 7),
218	TPS6586X_LDO_LINEAR(LDO_1, "vinldo01", 32, 725000, 25000, SUPPLYV1,
219			    0, 5, ENC, 1, END, 1),
220	TPS6586X_LDO_LINEAR(SM_2, "vin-sm2", 32, 3000000, 50000, SUPPLYV2,
221			    0, 5, ENC, 7, END, 7),
222	TPS6586X_DVM(LDO_2, "vinldo23", 32, 725000, 25000, LDO2BV1, 0, 5,
223		     ENA, 3, ENB, 3, TPS6586X_VCC2, BIT(6)),
224	TPS6586X_DVM(LDO_4, "vinldo4", 32, 1700000, 25000, LDO4V1, 0, 5,
225		     ENC, 3, END, 3, TPS6586X_VCC1, BIT(6)),
226	TPS6586X_DVM(SM_0, "vin-sm0", 32, 725000, 25000, SM0V1, 0, 5,
227		     ENA, 1, ENB, 1, TPS6586X_VCC1, BIT(2)),
228	TPS6586X_DVM(SM_1, "vin-sm1", 32, 725000, 25000, SM1V1, 0, 5,
229		     ENA, 0, ENB, 0, TPS6586X_VCC1, BIT(0)),
230};
231
232static struct tps6586x_regulator tps658623_regulator[] = {
233	TPS6586X_LDO_LINEAR(SM_2, "vin-sm2", 32, 1700000, 25000, SUPPLYV2,
234			    0, 5, ENC, 7, END, 7),
235};
236
237static struct tps6586x_regulator tps658640_regulator[] = {
238	TPS6586X_LDO(LDO_3, "vinldo23", tps6586x_ldo0, SUPPLYV4, 0, 3,
239					ENC, 2, END, 2),
240	TPS6586X_LDO(LDO_5, "REG-SYS", tps6586x_ldo0, SUPPLYV6, 0, 3,
241					ENE, 6, ENE, 6),
242	TPS6586X_LDO(LDO_6, "vinldo678", tps6586x_ldo0, SUPPLYV3, 0, 3,
243					ENC, 4, END, 4),
244	TPS6586X_LDO(LDO_7, "vinldo678", tps6586x_ldo0, SUPPLYV3, 3, 3,
245					ENC, 5, END, 5),
246	TPS6586X_LDO(LDO_8, "vinldo678", tps6586x_ldo0, SUPPLYV2, 5, 3,
247					ENC, 6, END, 6),
248	TPS6586X_LDO(LDO_9, "vinldo9", tps6586x_ldo0, SUPPLYV6, 3, 3,
249					ENE, 7, ENE, 7),
250	TPS6586X_LDO_LINEAR(SM_2, "vin-sm2", 32, 2150000, 50000, SUPPLYV2,
251			    0, 5, ENC, 7, END, 7),
252
253	TPS6586X_FIXED_LDO(LDO_RTC, "REG-SYS", tps658640_rtc, SUPPLYV4, 3, 2,
254					V4, 7, V4, 7),
255};
256
257static struct tps6586x_regulator tps658643_regulator[] = {
258	TPS6586X_LDO_LINEAR(SM_2, "vin-sm2", 32, 1025000, 25000, SUPPLYV2,
259			    0, 5, ENC, 7, END, 7),
260};
261
262/*
263 * TPS6586X has 2 enable bits that are OR'ed to determine the actual
264 * regulator state. Clearing one of this bits allows switching
265 * regulator on and of with single register write.
266 */
267static inline int tps6586x_regulator_preinit(struct device *parent,
268					     struct tps6586x_regulator *ri)
269{
270	uint8_t val1, val2;
271	int ret;
272
273	if (ri->enable_reg[0] == ri->enable_reg[1] &&
274	    ri->enable_bit[0] == ri->enable_bit[1])
275			return 0;
276
277	ret = tps6586x_read(parent, ri->enable_reg[0], &val1);
278	if (ret)
279		return ret;
280
281	ret = tps6586x_read(parent, ri->enable_reg[1], &val2);
282	if (ret)
283		return ret;
284
285	if (!(val2 & (1 << ri->enable_bit[1])))
286		return 0;
287
288	/*
289	 * The regulator is on, but it's enabled with the bit we don't
290	 * want to use, so we switch the enable bits
291	 */
292	if (!(val1 & (1 << ri->enable_bit[0]))) {
293		ret = tps6586x_set_bits(parent, ri->enable_reg[0],
294					1 << ri->enable_bit[0]);
295		if (ret)
296			return ret;
297	}
298
299	return tps6586x_clr_bits(parent, ri->enable_reg[1],
300				 1 << ri->enable_bit[1]);
301}
302
303static int tps6586x_regulator_set_slew_rate(struct platform_device *pdev,
304			int id, struct regulator_init_data *p)
305{
306	struct device *parent = pdev->dev.parent;
 
307	struct tps6586x_settings *setting = p->driver_data;
308	uint8_t reg;
309
310	if (setting == NULL)
311		return 0;
312
313	if (!(setting->slew_rate & TPS6586X_SLEW_RATE_SET))
314		return 0;
315
316	/* only SM0 and SM1 can have the slew rate settings */
317	switch (id) {
318	case TPS6586X_ID_SM_0:
319		reg = TPS6586X_SM0SL;
320		break;
321	case TPS6586X_ID_SM_1:
322		reg = TPS6586X_SM1SL;
323		break;
324	default:
325		dev_err(&pdev->dev, "Only SM0/SM1 can set slew rate\n");
326		return -EINVAL;
327	}
328
329	return tps6586x_write(parent, reg,
330			setting->slew_rate & TPS6586X_SLEW_RATE_MASK);
331}
332
333static struct tps6586x_regulator *find_regulator_info(int id, int version)
334{
335	struct tps6586x_regulator *ri;
336	struct tps6586x_regulator *table = NULL;
337	int num;
338	int i;
339
340	switch (version) {
341	case TPS658623:
342	case TPS658624:
343		table = tps658623_regulator;
344		num = ARRAY_SIZE(tps658623_regulator);
345		break;
346	case TPS658640:
347	case TPS658640v2:
348		table = tps658640_regulator;
349		num = ARRAY_SIZE(tps658640_regulator);
350		break;
351	case TPS658643:
352		table = tps658643_regulator;
353		num = ARRAY_SIZE(tps658643_regulator);
354		break;
355	}
356
357	/* Search version specific table first */
358	if (table) {
359		for (i = 0; i < num; i++) {
360			ri = &table[i];
361			if (ri->desc.id == id)
362				return ri;
363		}
364	}
365
366	for (i = 0; i < ARRAY_SIZE(tps6586x_regulator); i++) {
367		ri = &tps6586x_regulator[i];
368		if (ri->desc.id == id)
369			return ri;
370	}
371	return NULL;
372}
373
374#ifdef CONFIG_OF
375static struct of_regulator_match tps6586x_matches[] = {
376	{ .name = "sys",     .driver_data = (void *)TPS6586X_ID_SYS     },
377	{ .name = "sm0",     .driver_data = (void *)TPS6586X_ID_SM_0    },
378	{ .name = "sm1",     .driver_data = (void *)TPS6586X_ID_SM_1    },
379	{ .name = "sm2",     .driver_data = (void *)TPS6586X_ID_SM_2    },
380	{ .name = "ldo0",    .driver_data = (void *)TPS6586X_ID_LDO_0   },
381	{ .name = "ldo1",    .driver_data = (void *)TPS6586X_ID_LDO_1   },
382	{ .name = "ldo2",    .driver_data = (void *)TPS6586X_ID_LDO_2   },
383	{ .name = "ldo3",    .driver_data = (void *)TPS6586X_ID_LDO_3   },
384	{ .name = "ldo4",    .driver_data = (void *)TPS6586X_ID_LDO_4   },
385	{ .name = "ldo5",    .driver_data = (void *)TPS6586X_ID_LDO_5   },
386	{ .name = "ldo6",    .driver_data = (void *)TPS6586X_ID_LDO_6   },
387	{ .name = "ldo7",    .driver_data = (void *)TPS6586X_ID_LDO_7   },
388	{ .name = "ldo8",    .driver_data = (void *)TPS6586X_ID_LDO_8   },
389	{ .name = "ldo9",    .driver_data = (void *)TPS6586X_ID_LDO_9   },
390	{ .name = "ldo_rtc", .driver_data = (void *)TPS6586X_ID_LDO_RTC },
391};
392
393static struct tps6586x_platform_data *tps6586x_parse_regulator_dt(
394		struct platform_device *pdev,
395		struct of_regulator_match **tps6586x_reg_matches)
396{
397	const unsigned int num = ARRAY_SIZE(tps6586x_matches);
398	struct device_node *np = pdev->dev.parent->of_node;
399	struct device_node *regs;
400	const char *sys_rail = NULL;
401	unsigned int i;
402	struct tps6586x_platform_data *pdata;
403	int err;
404
405	regs = of_get_child_by_name(np, "regulators");
406	if (!regs) {
407		dev_err(&pdev->dev, "regulator node not found\n");
408		return NULL;
409	}
410
411	err = of_regulator_match(&pdev->dev, regs, tps6586x_matches, num);
412	of_node_put(regs);
413	if (err < 0) {
414		dev_err(&pdev->dev, "Regulator match failed, e %d\n", err);
415		return NULL;
416	}
417
418	pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
419	if (!pdata)
420		return NULL;
421
422	for (i = 0; i < num; i++) {
423		uintptr_t id;
424		if (!tps6586x_matches[i].init_data)
425			continue;
426
427		pdata->reg_init_data[i] = tps6586x_matches[i].init_data;
428		id = (uintptr_t)tps6586x_matches[i].driver_data;
429		if (id == TPS6586X_ID_SYS)
430			sys_rail = pdata->reg_init_data[i]->constraints.name;
431
432		if ((id == TPS6586X_ID_LDO_5) || (id == TPS6586X_ID_LDO_RTC))
433			pdata->reg_init_data[i]->supply_regulator = sys_rail;
434	}
435	*tps6586x_reg_matches = tps6586x_matches;
436	return pdata;
437}
438#else
439static struct tps6586x_platform_data *tps6586x_parse_regulator_dt(
440		struct platform_device *pdev,
441		struct of_regulator_match **tps6586x_reg_matches)
442{
443	*tps6586x_reg_matches = NULL;
444	return NULL;
445}
446#endif
447
448static int tps6586x_regulator_probe(struct platform_device *pdev)
449{
450	struct tps6586x_regulator *ri = NULL;
451	struct regulator_config config = { };
452	struct regulator_dev *rdev;
453	struct regulator_init_data *reg_data;
454	struct tps6586x_platform_data *pdata;
455	struct of_regulator_match *tps6586x_reg_matches = NULL;
456	int version;
457	int id;
458	int err;
459
460	dev_dbg(&pdev->dev, "Probing regulator\n");
461
462	pdata = dev_get_platdata(pdev->dev.parent);
463	if ((!pdata) && (pdev->dev.parent->of_node))
464		pdata = tps6586x_parse_regulator_dt(pdev,
465					&tps6586x_reg_matches);
466
467	if (!pdata) {
468		dev_err(&pdev->dev, "Platform data not available, exiting\n");
469		return -ENODEV;
470	}
471
472	version = tps6586x_get_version(pdev->dev.parent);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
473
474	for (id = 0; id < TPS6586X_ID_MAX_REGULATOR; ++id) {
475		reg_data = pdata->reg_init_data[id];
476
477		ri = find_regulator_info(id, version);
 
478
479		if (!ri) {
480			dev_err(&pdev->dev, "invalid regulator ID specified\n");
481			return -EINVAL;
482		}
483
484		err = tps6586x_regulator_preinit(pdev->dev.parent, ri);
485		if (err) {
486			dev_err(&pdev->dev,
487				"regulator %d preinit failed, e %d\n", id, err);
488			return err;
489		}
490
491		config.dev = pdev->dev.parent;
492		config.init_data = reg_data;
493		config.driver_data = ri;
494
495		if (tps6586x_reg_matches)
496			config.of_node = tps6586x_reg_matches[id].of_node;
497
498		rdev = devm_regulator_register(&pdev->dev, &ri->desc, &config);
499		if (IS_ERR(rdev)) {
500			dev_err(&pdev->dev, "failed to register regulator %s\n",
501					ri->desc.name);
502			return PTR_ERR(rdev);
503		}
504
505		if (reg_data) {
506			err = tps6586x_regulator_set_slew_rate(pdev, id,
507					reg_data);
508			if (err < 0) {
509				dev_err(&pdev->dev,
510					"Slew rate config failed, e %d\n", err);
511				return err;
512			}
513		}
514	}
515
516	platform_set_drvdata(pdev, rdev);
517	return 0;
518}
519
520static struct platform_driver tps6586x_regulator_driver = {
521	.driver	= {
522		.name	= "tps6586x-regulator",
 
523	},
524	.probe		= tps6586x_regulator_probe,
 
525};
526
527static int __init tps6586x_regulator_init(void)
528{
529	return platform_driver_register(&tps6586x_regulator_driver);
530}
531subsys_initcall(tps6586x_regulator_init);
532
533static void __exit tps6586x_regulator_exit(void)
534{
535	platform_driver_unregister(&tps6586x_regulator_driver);
536}
537module_exit(tps6586x_regulator_exit);
538
539MODULE_LICENSE("GPL");
540MODULE_AUTHOR("Mike Rapoport <mike@compulab.co.il>");
541MODULE_DESCRIPTION("Regulator Driver for TI TPS6586X PMIC");
542MODULE_ALIAS("platform:tps6586x-regulator");
v3.5.6
 
  1/*
  2 * Regulator driver for TI TPS6586x
  3 *
  4 * Copyright (C) 2010 Compulab Ltd.
  5 * Author: Mike Rapoport <mike@compulab.co.il>
  6 *
  7 * Based on da903x
  8 * Copyright (C) 2006-2008 Marvell International Ltd.
  9 * Copyright (C) 2008 Compulab Ltd.
 10 *
 11 * This program is free software; you can redistribute it and/or modify
 12 * it under the terms of the GNU General Public License version 2 as
 13 * published by the Free Software Foundation.
 14 */
 15
 16#include <linux/kernel.h>
 17#include <linux/module.h>
 18#include <linux/init.h>
 19#include <linux/err.h>
 
 20#include <linux/slab.h>
 21#include <linux/platform_device.h>
 22#include <linux/regulator/driver.h>
 23#include <linux/regulator/machine.h>
 
 24#include <linux/mfd/tps6586x.h>
 25
 26/* supply control and voltage setting  */
 27#define TPS6586X_SUPPLYENA	0x10
 28#define TPS6586X_SUPPLYENB	0x11
 29#define TPS6586X_SUPPLYENC	0x12
 30#define TPS6586X_SUPPLYEND	0x13
 31#define TPS6586X_SUPPLYENE	0x14
 32#define TPS6586X_VCC1		0x20
 33#define TPS6586X_VCC2		0x21
 34#define TPS6586X_SM1V1		0x23
 35#define TPS6586X_SM1V2		0x24
 36#define TPS6586X_SM1SL		0x25
 37#define TPS6586X_SM0V1		0x26
 38#define TPS6586X_SM0V2		0x27
 39#define TPS6586X_SM0SL		0x28
 40#define TPS6586X_LDO2AV1	0x29
 41#define TPS6586X_LDO2AV2	0x2A
 42#define TPS6586X_LDO2BV1	0x2F
 43#define TPS6586X_LDO2BV2	0x30
 44#define TPS6586X_LDO4V1		0x32
 45#define TPS6586X_LDO4V2		0x33
 46
 47/* converter settings  */
 48#define TPS6586X_SUPPLYV1	0x41
 49#define TPS6586X_SUPPLYV2	0x42
 50#define TPS6586X_SUPPLYV3	0x43
 51#define TPS6586X_SUPPLYV4	0x44
 52#define TPS6586X_SUPPLYV5	0x45
 53#define TPS6586X_SUPPLYV6	0x46
 54#define TPS6586X_SMODE1		0x47
 55#define TPS6586X_SMODE2		0x48
 56
 57struct tps6586x_regulator {
 58	struct regulator_desc desc;
 59
 60	int volt_reg;
 61	int volt_shift;
 62	int volt_nbits;
 63	int enable_bit[2];
 64	int enable_reg[2];
 
 65
 66	int *voltages;
 
 
 
 
 
 
 
 
 
 67
 68	/* for DVM regulators */
 69	int go_reg;
 70	int go_bit;
 
 
 
 
 
 71};
 72
 73static inline struct device *to_tps6586x_dev(struct regulator_dev *rdev)
 74{
 75	return rdev_get_dev(rdev)->parent->parent;
 76}
 77
 78static int tps6586x_list_voltage(struct regulator_dev *rdev, unsigned selector)
 79{
 80	struct tps6586x_regulator *info = rdev_get_drvdata(rdev);
 81	int rid = rdev_get_id(rdev);
 82
 83	/* LDO0 has minimal voltage 1.2V rather than 1.25V */
 84	if ((rid == TPS6586X_ID_LDO_0) && (selector == 0))
 85		return (info->voltages[0] - 50) * 1000;
 86
 87	return info->voltages[selector] * 1000;
 88}
 89
 90
 91static int tps6586x_set_voltage_sel(struct regulator_dev *rdev,
 92				    unsigned selector)
 93{
 94	struct tps6586x_regulator *ri = rdev_get_drvdata(rdev);
 95	struct device *parent = to_tps6586x_dev(rdev);
 96	int ret, val, rid = rdev_get_id(rdev);
 97	uint8_t mask;
 98
 99	val = selector << ri->volt_shift;
100	mask = ((1 << ri->volt_nbits) - 1) << ri->volt_shift;
101
102	ret = tps6586x_update(parent, ri->volt_reg, val, mask);
103	if (ret)
104		return ret;
105
106	/* Update go bit for DVM regulators */
107	switch (rid) {
108	case TPS6586X_ID_LDO_2:
109	case TPS6586X_ID_LDO_4:
110	case TPS6586X_ID_SM_0:
111	case TPS6586X_ID_SM_1:
112		ret = tps6586x_set_bits(parent, ri->go_reg, 1 << ri->go_bit);
113		break;
114	}
115	return ret;
116}
117
118static int tps6586x_get_voltage_sel(struct regulator_dev *rdev)
119{
120	struct tps6586x_regulator *ri = rdev_get_drvdata(rdev);
121	struct device *parent = to_tps6586x_dev(rdev);
122	uint8_t val, mask;
123	int ret;
124
125	ret = tps6586x_read(parent, ri->volt_reg, &val);
126	if (ret)
127		return ret;
128
129	mask = ((1 << ri->volt_nbits) - 1) << ri->volt_shift;
130	val = (val & mask) >> ri->volt_shift;
131
132	if (val >= ri->desc.n_voltages)
133		BUG();
134
135	return val;
136}
137
138static int tps6586x_regulator_enable(struct regulator_dev *rdev)
139{
140	struct tps6586x_regulator *ri = rdev_get_drvdata(rdev);
141	struct device *parent = to_tps6586x_dev(rdev);
142
143	return tps6586x_set_bits(parent, ri->enable_reg[0],
144				 1 << ri->enable_bit[0]);
145}
146
147static int tps6586x_regulator_disable(struct regulator_dev *rdev)
148{
149	struct tps6586x_regulator *ri = rdev_get_drvdata(rdev);
150	struct device *parent = to_tps6586x_dev(rdev);
151
152	return tps6586x_clr_bits(parent, ri->enable_reg[0],
153				 1 << ri->enable_bit[0]);
154}
155
156static int tps6586x_regulator_is_enabled(struct regulator_dev *rdev)
157{
158	struct tps6586x_regulator *ri = rdev_get_drvdata(rdev);
159	struct device *parent = to_tps6586x_dev(rdev);
160	uint8_t reg_val;
161	int ret;
162
163	ret = tps6586x_read(parent, ri->enable_reg[0], &reg_val);
164	if (ret)
165		return ret;
166
167	return !!(reg_val & (1 << ri->enable_bit[0]));
168}
169
170static struct regulator_ops tps6586x_regulator_ops = {
171	.list_voltage = tps6586x_list_voltage,
172	.get_voltage_sel = tps6586x_get_voltage_sel,
173	.set_voltage_sel = tps6586x_set_voltage_sel,
174
175	.is_enabled = tps6586x_regulator_is_enabled,
176	.enable = tps6586x_regulator_enable,
177	.disable = tps6586x_regulator_disable,
178};
179
180static int tps6586x_ldo_voltages[] = {
181	1250, 1500, 1800, 2500, 2700, 2850, 3100, 3300,
182};
183
184static int tps6586x_ldo4_voltages[] = {
185	1700, 1725, 1750, 1775, 1800, 1825, 1850, 1875,
186	1900, 1925, 1950, 1975, 2000, 2025, 2050, 2075,
187	2100, 2125, 2150, 2175, 2200, 2225, 2250, 2275,
188	2300, 2325, 2350, 2375, 2400, 2425, 2450, 2475,
189};
190
191static int tps6586x_sm2_voltages[] = {
192	3000, 3050, 3100, 3150, 3200, 3250, 3300, 3350,
193	3400, 3450, 3500, 3550, 3600, 3650, 3700, 3750,
194	3800, 3850, 3900, 3950, 4000, 4050, 4100, 4150,
195	4200, 4250, 4300, 4350, 4400, 4450, 4500, 4550,
196};
197
198static int tps6586x_dvm_voltages[] = {
199	 725,  750,  775,  800,  825,  850,  875,  900,
200	 925,  950,  975, 1000, 1025, 1050, 1075, 1100,
201	1125, 1150, 1175, 1200, 1225, 1250, 1275, 1300,
202	1325, 1350, 1375, 1400, 1425, 1450, 1475, 1500,
203};
204
205#define TPS6586X_REGULATOR(_id, vdata, vreg, shift, nbits,		\
206			   ereg0, ebit0, ereg1, ebit1)			\
207	.desc	= {							\
 
208		.name	= "REG-" #_id,					\
209		.ops	= &tps6586x_regulator_ops,			\
210		.type	= REGULATOR_VOLTAGE,				\
211		.id	= TPS6586X_ID_##_id,				\
212		.n_voltages = ARRAY_SIZE(tps6586x_##vdata##_voltages),	\
 
213		.owner	= THIS_MODULE,					\
 
 
 
 
 
 
214	},								\
215	.volt_reg	= TPS6586X_##vreg,				\
216	.volt_shift	= (shift),					\
217	.volt_nbits	= (nbits),					\
218	.enable_reg[0]	= TPS6586X_SUPPLY##ereg0,			\
219	.enable_bit[0]	= (ebit0),					\
220	.enable_reg[1]	= TPS6586X_SUPPLY##ereg1,			\
221	.enable_bit[1]	= (ebit1),					\
222	.voltages	= tps6586x_##vdata##_voltages,
223
224#define TPS6586X_REGULATOR_DVM_GOREG(goreg, gobit)			\
225	.go_reg = TPS6586X_##goreg,					\
226	.go_bit = (gobit),
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
227
228#define TPS6586X_LDO(_id, vdata, vreg, shift, nbits,			\
229		     ereg0, ebit0, ereg1, ebit1)			\
230{									\
231	TPS6586X_REGULATOR(_id, vdata, vreg, shift, nbits,		\
232			   ereg0, ebit0, ereg1, ebit1)			\
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
233}
234
235#define TPS6586X_DVM(_id, vdata, vreg, shift, nbits,			\
236		     ereg0, ebit0, ereg1, ebit1, goreg, gobit)		\
237{									\
238	TPS6586X_REGULATOR(_id, vdata, vreg, shift, nbits,		\
239			   ereg0, ebit0, ereg1, ebit1)			\
240	TPS6586X_REGULATOR_DVM_GOREG(goreg, gobit)			\
 
 
 
 
 
 
 
 
 
 
 
 
 
241}
242
243static struct tps6586x_regulator tps6586x_regulator[] = {
244	TPS6586X_LDO(LDO_0, ldo, SUPPLYV1, 5, 3, ENC, 0, END, 0),
245	TPS6586X_LDO(LDO_3, ldo, SUPPLYV4, 0, 3, ENC, 2, END, 2),
246	TPS6586X_LDO(LDO_5, ldo, SUPPLYV6, 0, 3, ENE, 6, ENE, 6),
247	TPS6586X_LDO(LDO_6, ldo, SUPPLYV3, 0, 3, ENC, 4, END, 4),
248	TPS6586X_LDO(LDO_7, ldo, SUPPLYV3, 3, 3, ENC, 5, END, 5),
249	TPS6586X_LDO(LDO_8, ldo, SUPPLYV2, 5, 3, ENC, 6, END, 6),
250	TPS6586X_LDO(LDO_9, ldo, SUPPLYV6, 3, 3, ENE, 7, ENE, 7),
251	TPS6586X_LDO(LDO_RTC, ldo, SUPPLYV4, 3, 3, V4, 7, V4, 7),
252	TPS6586X_LDO(LDO_1, dvm, SUPPLYV1, 0, 5, ENC, 1, END, 1),
253	TPS6586X_LDO(SM_2, sm2, SUPPLYV2, 0, 5, ENC, 7, END, 7),
254
255	TPS6586X_DVM(LDO_2, dvm, LDO2BV1, 0, 5, ENA, 3, ENB, 3, VCC2, 6),
256	TPS6586X_DVM(LDO_4, ldo4, LDO4V1, 0, 5, ENC, 3, END, 3, VCC1, 6),
257	TPS6586X_DVM(SM_0, dvm, SM0V1, 0, 5, ENA, 1, ENB, 1, VCC1, 2),
258	TPS6586X_DVM(SM_1, dvm, SM1V1, 0, 5, ENA, 0, ENB, 0, VCC1, 0),
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
259};
260
261/*
262 * TPS6586X has 2 enable bits that are OR'ed to determine the actual
263 * regulator state. Clearing one of this bits allows switching
264 * regulator on and of with single register write.
265 */
266static inline int tps6586x_regulator_preinit(struct device *parent,
267					     struct tps6586x_regulator *ri)
268{
269	uint8_t val1, val2;
270	int ret;
271
272	if (ri->enable_reg[0] == ri->enable_reg[1] &&
273	    ri->enable_bit[0] == ri->enable_bit[1])
274			return 0;
275
276	ret = tps6586x_read(parent, ri->enable_reg[0], &val1);
277	if (ret)
278		return ret;
279
280	ret = tps6586x_read(parent, ri->enable_reg[1], &val2);
281	if (ret)
282		return ret;
283
284	if (!(val2 & (1 << ri->enable_bit[1])))
285		return 0;
286
287	/*
288	 * The regulator is on, but it's enabled with the bit we don't
289	 * want to use, so we switch the enable bits
290	 */
291	if (!(val1 & (1 << ri->enable_bit[0]))) {
292		ret = tps6586x_set_bits(parent, ri->enable_reg[0],
293					1 << ri->enable_bit[0]);
294		if (ret)
295			return ret;
296	}
297
298	return tps6586x_clr_bits(parent, ri->enable_reg[1],
299				 1 << ri->enable_bit[1]);
300}
301
302static int tps6586x_regulator_set_slew_rate(struct platform_device *pdev)
 
303{
304	struct device *parent = pdev->dev.parent;
305	struct regulator_init_data *p = pdev->dev.platform_data;
306	struct tps6586x_settings *setting = p->driver_data;
307	uint8_t reg;
308
309	if (setting == NULL)
310		return 0;
311
312	if (!(setting->slew_rate & TPS6586X_SLEW_RATE_SET))
313		return 0;
314
315	/* only SM0 and SM1 can have the slew rate settings */
316	switch (pdev->id) {
317	case TPS6586X_ID_SM_0:
318		reg = TPS6586X_SM0SL;
319		break;
320	case TPS6586X_ID_SM_1:
321		reg = TPS6586X_SM1SL;
322		break;
323	default:
324		dev_warn(&pdev->dev, "Only SM0/SM1 can set slew rate\n");
325		return -EINVAL;
326	}
327
328	return tps6586x_write(parent, reg,
329			setting->slew_rate & TPS6586X_SLEW_RATE_MASK);
330}
331
332static inline struct tps6586x_regulator *find_regulator_info(int id)
333{
334	struct tps6586x_regulator *ri;
 
 
335	int i;
336
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
337	for (i = 0; i < ARRAY_SIZE(tps6586x_regulator); i++) {
338		ri = &tps6586x_regulator[i];
339		if (ri->desc.id == id)
340			return ri;
341	}
342	return NULL;
343}
344
345static int __devinit tps6586x_regulator_probe(struct platform_device *pdev)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
346{
347	struct tps6586x_regulator *ri = NULL;
348	struct regulator_config config = { };
349	struct regulator_dev *rdev;
350	int id = pdev->id;
 
 
 
 
351	int err;
352
353	dev_dbg(&pdev->dev, "Probing regulator %d\n", id);
354
355	ri = find_regulator_info(id);
356	if (ri == NULL) {
357		dev_err(&pdev->dev, "invalid regulator ID specified\n");
358		return -EINVAL;
 
 
 
 
359	}
360
361	err = tps6586x_regulator_preinit(pdev->dev.parent, ri);
362	if (err)
363		return err;
364
365	config.dev = &pdev->dev;
366	config.of_node = pdev->dev.of_node;
367	config.init_data = pdev->dev.platform_data;
368	config.driver_data = ri;
369
370	rdev = regulator_register(&ri->desc, &config);
371	if (IS_ERR(rdev)) {
372		dev_err(&pdev->dev, "failed to register regulator %s\n",
373				ri->desc.name);
374		return PTR_ERR(rdev);
375	}
376
377	platform_set_drvdata(pdev, rdev);
 
378
379	return tps6586x_regulator_set_slew_rate(pdev);
380}
381
382static int __devexit tps6586x_regulator_remove(struct platform_device *pdev)
383{
384	struct regulator_dev *rdev = platform_get_drvdata(pdev);
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
385
386	regulator_unregister(rdev);
387	return 0;
388}
389
390static struct platform_driver tps6586x_regulator_driver = {
391	.driver	= {
392		.name	= "tps6586x-regulator",
393		.owner	= THIS_MODULE,
394	},
395	.probe		= tps6586x_regulator_probe,
396	.remove		= __devexit_p(tps6586x_regulator_remove),
397};
398
399static int __init tps6586x_regulator_init(void)
400{
401	return platform_driver_register(&tps6586x_regulator_driver);
402}
403subsys_initcall(tps6586x_regulator_init);
404
405static void __exit tps6586x_regulator_exit(void)
406{
407	platform_driver_unregister(&tps6586x_regulator_driver);
408}
409module_exit(tps6586x_regulator_exit);
410
411MODULE_LICENSE("GPL");
412MODULE_AUTHOR("Mike Rapoport <mike@compulab.co.il>");
413MODULE_DESCRIPTION("Regulator Driver for TI TPS6586X PMIC");
414MODULE_ALIAS("platform:tps6586x-regulator");