Linux Audio

Check our new training course

Loading...
v5.9
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Copyright (C) 2017 Spreadtrum Communications Inc.
  4 */
  5
  6#include <linux/interrupt.h>
  7#include <linux/kernel.h>
  8#include <linux/module.h>
  9#include <linux/mfd/core.h>
 10#include <linux/mfd/sc27xx-pmic.h>
 11#include <linux/of_device.h>
 12#include <linux/of_platform.h>
 13#include <linux/regmap.h>
 14#include <linux/spi/spi.h>
 15#include <uapi/linux/usb/charger.h>
 16
 17#define SPRD_PMIC_INT_MASK_STATUS	0x0
 18#define SPRD_PMIC_INT_RAW_STATUS	0x4
 19#define SPRD_PMIC_INT_EN		0x8
 20
 
 
 
 21#define SPRD_SC2731_IRQ_BASE		0x140
 22#define SPRD_SC2731_IRQ_NUMS		16
 23#define SPRD_SC2731_CHG_DET		0xedc
 24
 25/* PMIC charger detection definition */
 26#define SPRD_PMIC_CHG_DET_DELAY_US	200000
 27#define SPRD_PMIC_CHG_DET_TIMEOUT	2000000
 28#define SPRD_PMIC_CHG_DET_DONE		BIT(11)
 29#define SPRD_PMIC_SDP_TYPE		BIT(7)
 30#define SPRD_PMIC_DCP_TYPE		BIT(6)
 31#define SPRD_PMIC_CDP_TYPE		BIT(5)
 32#define SPRD_PMIC_CHG_TYPE_MASK		GENMASK(7, 5)
 33
 34struct sprd_pmic {
 35	struct regmap *regmap;
 36	struct device *dev;
 37	struct regmap_irq *irqs;
 38	struct regmap_irq_chip irq_chip;
 39	struct regmap_irq_chip_data *irq_data;
 40	const struct sprd_pmic_data *pdata;
 41	int irq;
 42};
 43
 44struct sprd_pmic_data {
 45	u32 irq_base;
 46	u32 num_irqs;
 47	u32 charger_det;
 48};
 49
 50/*
 51 * Since different PMICs of SC27xx series can have different interrupt
 52 * base address and irq number, we should save irq number and irq base
 53 * in the device data structure.
 54 */
 
 
 
 
 
 
 55static const struct sprd_pmic_data sc2731_data = {
 56	.irq_base = SPRD_SC2731_IRQ_BASE,
 57	.num_irqs = SPRD_SC2731_IRQ_NUMS,
 58	.charger_det = SPRD_SC2731_CHG_DET,
 59};
 60
 61enum usb_charger_type sprd_pmic_detect_charger_type(struct device *dev)
 62{
 63	struct spi_device *spi = to_spi_device(dev);
 64	struct sprd_pmic *ddata = spi_get_drvdata(spi);
 65	const struct sprd_pmic_data *pdata = ddata->pdata;
 66	enum usb_charger_type type;
 67	u32 val;
 68	int ret;
 69
 70	ret = regmap_read_poll_timeout(ddata->regmap, pdata->charger_det, val,
 71				       (val & SPRD_PMIC_CHG_DET_DONE),
 72				       SPRD_PMIC_CHG_DET_DELAY_US,
 73				       SPRD_PMIC_CHG_DET_TIMEOUT);
 74	if (ret) {
 75		dev_err(&spi->dev, "failed to detect charger type\n");
 76		return UNKNOWN_TYPE;
 77	}
 78
 79	switch (val & SPRD_PMIC_CHG_TYPE_MASK) {
 80	case SPRD_PMIC_CDP_TYPE:
 81		type = CDP_TYPE;
 82		break;
 83	case SPRD_PMIC_DCP_TYPE:
 84		type = DCP_TYPE;
 85		break;
 86	case SPRD_PMIC_SDP_TYPE:
 87		type = SDP_TYPE;
 88		break;
 89	default:
 90		type = UNKNOWN_TYPE;
 91		break;
 92	}
 93
 94	return type;
 95}
 96EXPORT_SYMBOL_GPL(sprd_pmic_detect_charger_type);
 97
 98static int sprd_pmic_spi_write(void *context, const void *data, size_t count)
 99{
100	struct device *dev = context;
101	struct spi_device *spi = to_spi_device(dev);
102
103	return spi_write(spi, data, count);
104}
105
106static int sprd_pmic_spi_read(void *context,
107			      const void *reg, size_t reg_size,
108			      void *val, size_t val_size)
109{
110	struct device *dev = context;
111	struct spi_device *spi = to_spi_device(dev);
112	u32 rx_buf[2] = { 0 };
113	int ret;
114
115	/* Now we only support one PMIC register to read every time. */
116	if (reg_size != sizeof(u32) || val_size != sizeof(u32))
117		return -EINVAL;
118
119	/* Copy address to read from into first element of SPI buffer. */
120	memcpy(rx_buf, reg, sizeof(u32));
121	ret = spi_read(spi, rx_buf, 1);
122	if (ret < 0)
123		return ret;
124
125	memcpy(val, rx_buf, val_size);
126	return 0;
127}
128
129static struct regmap_bus sprd_pmic_regmap = {
130	.write = sprd_pmic_spi_write,
131	.read = sprd_pmic_spi_read,
132	.reg_format_endian_default = REGMAP_ENDIAN_NATIVE,
133	.val_format_endian_default = REGMAP_ENDIAN_NATIVE,
134};
135
136static const struct regmap_config sprd_pmic_config = {
137	.reg_bits = 32,
138	.val_bits = 32,
139	.reg_stride = 4,
140	.max_register = 0xffff,
141};
142
143static int sprd_pmic_probe(struct spi_device *spi)
144{
145	struct sprd_pmic *ddata;
146	const struct sprd_pmic_data *pdata;
147	int ret, i;
148
149	pdata = of_device_get_match_data(&spi->dev);
150	if (!pdata) {
151		dev_err(&spi->dev, "No matching driver data found\n");
152		return -EINVAL;
153	}
154
155	ddata = devm_kzalloc(&spi->dev, sizeof(*ddata), GFP_KERNEL);
156	if (!ddata)
157		return -ENOMEM;
158
159	ddata->regmap = devm_regmap_init(&spi->dev, &sprd_pmic_regmap,
160					 &spi->dev, &sprd_pmic_config);
161	if (IS_ERR(ddata->regmap)) {
162		ret = PTR_ERR(ddata->regmap);
163		dev_err(&spi->dev, "Failed to allocate register map %d\n", ret);
164		return ret;
165	}
166
167	spi_set_drvdata(spi, ddata);
168	ddata->dev = &spi->dev;
169	ddata->irq = spi->irq;
170	ddata->pdata = pdata;
171
172	ddata->irq_chip.name = dev_name(&spi->dev);
173	ddata->irq_chip.status_base =
174		pdata->irq_base + SPRD_PMIC_INT_MASK_STATUS;
175	ddata->irq_chip.mask_base = pdata->irq_base + SPRD_PMIC_INT_EN;
176	ddata->irq_chip.ack_base = 0;
177	ddata->irq_chip.num_regs = 1;
178	ddata->irq_chip.num_irqs = pdata->num_irqs;
179	ddata->irq_chip.mask_invert = true;
180
181	ddata->irqs = devm_kcalloc(&spi->dev,
182				   pdata->num_irqs, sizeof(struct regmap_irq),
183				   GFP_KERNEL);
184	if (!ddata->irqs)
185		return -ENOMEM;
186
187	ddata->irq_chip.irqs = ddata->irqs;
188	for (i = 0; i < pdata->num_irqs; i++)
189		ddata->irqs[i].mask = BIT(i);
190
191	ret = devm_regmap_add_irq_chip(&spi->dev, ddata->regmap, ddata->irq,
192				       IRQF_ONESHOT | IRQF_NO_SUSPEND, 0,
193				       &ddata->irq_chip, &ddata->irq_data);
194	if (ret) {
195		dev_err(&spi->dev, "Failed to add PMIC irq chip %d\n", ret);
196		return ret;
197	}
198
199	ret = devm_of_platform_populate(&spi->dev);
200	if (ret) {
201		dev_err(&spi->dev, "Failed to populate sub-devices %d\n", ret);
202		return ret;
203	}
204
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
205	return 0;
206}
207
 
 
 
208static const struct of_device_id sprd_pmic_match[] = {
 
209	{ .compatible = "sprd,sc2731", .data = &sc2731_data },
210	{},
211};
212MODULE_DEVICE_TABLE(of, sprd_pmic_match);
213
 
 
 
 
 
 
 
214static struct spi_driver sprd_pmic_driver = {
215	.driver = {
216		.name = "sc27xx-pmic",
217		.of_match_table = sprd_pmic_match,
 
218	},
219	.probe = sprd_pmic_probe,
 
220};
221
222static int __init sprd_pmic_init(void)
223{
224	return spi_register_driver(&sprd_pmic_driver);
225}
226subsys_initcall(sprd_pmic_init);
227
228static void __exit sprd_pmic_exit(void)
229{
230	spi_unregister_driver(&sprd_pmic_driver);
231}
232module_exit(sprd_pmic_exit);
233
234MODULE_LICENSE("GPL v2");
235MODULE_DESCRIPTION("Spreadtrum SC27xx PMICs driver");
236MODULE_AUTHOR("Baolin Wang <baolin.wang@spreadtrum.com>");
v6.2
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Copyright (C) 2017 Spreadtrum Communications Inc.
  4 */
  5
  6#include <linux/interrupt.h>
  7#include <linux/kernel.h>
  8#include <linux/module.h>
  9#include <linux/mfd/core.h>
 10#include <linux/mfd/sc27xx-pmic.h>
 11#include <linux/of_device.h>
 12#include <linux/of_platform.h>
 13#include <linux/regmap.h>
 14#include <linux/spi/spi.h>
 15#include <uapi/linux/usb/charger.h>
 16
 17#define SPRD_PMIC_INT_MASK_STATUS	0x0
 18#define SPRD_PMIC_INT_RAW_STATUS	0x4
 19#define SPRD_PMIC_INT_EN		0x8
 20
 21#define SPRD_SC2730_IRQ_BASE		0x80
 22#define SPRD_SC2730_IRQ_NUMS		10
 23#define SPRD_SC2730_CHG_DET		0x1b9c
 24#define SPRD_SC2731_IRQ_BASE		0x140
 25#define SPRD_SC2731_IRQ_NUMS		16
 26#define SPRD_SC2731_CHG_DET		0xedc
 27
 28/* PMIC charger detection definition */
 29#define SPRD_PMIC_CHG_DET_DELAY_US	200000
 30#define SPRD_PMIC_CHG_DET_TIMEOUT	2000000
 31#define SPRD_PMIC_CHG_DET_DONE		BIT(11)
 32#define SPRD_PMIC_SDP_TYPE		BIT(7)
 33#define SPRD_PMIC_DCP_TYPE		BIT(6)
 34#define SPRD_PMIC_CDP_TYPE		BIT(5)
 35#define SPRD_PMIC_CHG_TYPE_MASK		GENMASK(7, 5)
 36
 37struct sprd_pmic {
 38	struct regmap *regmap;
 39	struct device *dev;
 40	struct regmap_irq *irqs;
 41	struct regmap_irq_chip irq_chip;
 42	struct regmap_irq_chip_data *irq_data;
 43	const struct sprd_pmic_data *pdata;
 44	int irq;
 45};
 46
 47struct sprd_pmic_data {
 48	u32 irq_base;
 49	u32 num_irqs;
 50	u32 charger_det;
 51};
 52
 53/*
 54 * Since different PMICs of SC27xx series can have different interrupt
 55 * base address and irq number, we should save irq number and irq base
 56 * in the device data structure.
 57 */
 58static const struct sprd_pmic_data sc2730_data = {
 59	.irq_base = SPRD_SC2730_IRQ_BASE,
 60	.num_irqs = SPRD_SC2730_IRQ_NUMS,
 61	.charger_det = SPRD_SC2730_CHG_DET,
 62};
 63
 64static const struct sprd_pmic_data sc2731_data = {
 65	.irq_base = SPRD_SC2731_IRQ_BASE,
 66	.num_irqs = SPRD_SC2731_IRQ_NUMS,
 67	.charger_det = SPRD_SC2731_CHG_DET,
 68};
 69
 70enum usb_charger_type sprd_pmic_detect_charger_type(struct device *dev)
 71{
 72	struct spi_device *spi = to_spi_device(dev);
 73	struct sprd_pmic *ddata = spi_get_drvdata(spi);
 74	const struct sprd_pmic_data *pdata = ddata->pdata;
 75	enum usb_charger_type type;
 76	u32 val;
 77	int ret;
 78
 79	ret = regmap_read_poll_timeout(ddata->regmap, pdata->charger_det, val,
 80				       (val & SPRD_PMIC_CHG_DET_DONE),
 81				       SPRD_PMIC_CHG_DET_DELAY_US,
 82				       SPRD_PMIC_CHG_DET_TIMEOUT);
 83	if (ret) {
 84		dev_err(&spi->dev, "failed to detect charger type\n");
 85		return UNKNOWN_TYPE;
 86	}
 87
 88	switch (val & SPRD_PMIC_CHG_TYPE_MASK) {
 89	case SPRD_PMIC_CDP_TYPE:
 90		type = CDP_TYPE;
 91		break;
 92	case SPRD_PMIC_DCP_TYPE:
 93		type = DCP_TYPE;
 94		break;
 95	case SPRD_PMIC_SDP_TYPE:
 96		type = SDP_TYPE;
 97		break;
 98	default:
 99		type = UNKNOWN_TYPE;
100		break;
101	}
102
103	return type;
104}
105EXPORT_SYMBOL_GPL(sprd_pmic_detect_charger_type);
106
107static int sprd_pmic_spi_write(void *context, const void *data, size_t count)
108{
109	struct device *dev = context;
110	struct spi_device *spi = to_spi_device(dev);
111
112	return spi_write(spi, data, count);
113}
114
115static int sprd_pmic_spi_read(void *context,
116			      const void *reg, size_t reg_size,
117			      void *val, size_t val_size)
118{
119	struct device *dev = context;
120	struct spi_device *spi = to_spi_device(dev);
121	u32 rx_buf[2] = { 0 };
122	int ret;
123
124	/* Now we only support one PMIC register to read every time. */
125	if (reg_size != sizeof(u32) || val_size != sizeof(u32))
126		return -EINVAL;
127
128	/* Copy address to read from into first element of SPI buffer. */
129	memcpy(rx_buf, reg, sizeof(u32));
130	ret = spi_read(spi, rx_buf, 1);
131	if (ret < 0)
132		return ret;
133
134	memcpy(val, rx_buf, val_size);
135	return 0;
136}
137
138static struct regmap_bus sprd_pmic_regmap = {
139	.write = sprd_pmic_spi_write,
140	.read = sprd_pmic_spi_read,
141	.reg_format_endian_default = REGMAP_ENDIAN_NATIVE,
142	.val_format_endian_default = REGMAP_ENDIAN_NATIVE,
143};
144
145static const struct regmap_config sprd_pmic_config = {
146	.reg_bits = 32,
147	.val_bits = 32,
148	.reg_stride = 4,
149	.max_register = 0xffff,
150};
151
152static int sprd_pmic_probe(struct spi_device *spi)
153{
154	struct sprd_pmic *ddata;
155	const struct sprd_pmic_data *pdata;
156	int ret, i;
157
158	pdata = of_device_get_match_data(&spi->dev);
159	if (!pdata) {
160		dev_err(&spi->dev, "No matching driver data found\n");
161		return -EINVAL;
162	}
163
164	ddata = devm_kzalloc(&spi->dev, sizeof(*ddata), GFP_KERNEL);
165	if (!ddata)
166		return -ENOMEM;
167
168	ddata->regmap = devm_regmap_init(&spi->dev, &sprd_pmic_regmap,
169					 &spi->dev, &sprd_pmic_config);
170	if (IS_ERR(ddata->regmap)) {
171		ret = PTR_ERR(ddata->regmap);
172		dev_err(&spi->dev, "Failed to allocate register map %d\n", ret);
173		return ret;
174	}
175
176	spi_set_drvdata(spi, ddata);
177	ddata->dev = &spi->dev;
178	ddata->irq = spi->irq;
179	ddata->pdata = pdata;
180
181	ddata->irq_chip.name = dev_name(&spi->dev);
182	ddata->irq_chip.status_base =
183		pdata->irq_base + SPRD_PMIC_INT_MASK_STATUS;
184	ddata->irq_chip.unmask_base = pdata->irq_base + SPRD_PMIC_INT_EN;
185	ddata->irq_chip.ack_base = 0;
186	ddata->irq_chip.num_regs = 1;
187	ddata->irq_chip.num_irqs = pdata->num_irqs;
 
188
189	ddata->irqs = devm_kcalloc(&spi->dev,
190				   pdata->num_irqs, sizeof(struct regmap_irq),
191				   GFP_KERNEL);
192	if (!ddata->irqs)
193		return -ENOMEM;
194
195	ddata->irq_chip.irqs = ddata->irqs;
196	for (i = 0; i < pdata->num_irqs; i++)
197		ddata->irqs[i].mask = BIT(i);
198
199	ret = devm_regmap_add_irq_chip(&spi->dev, ddata->regmap, ddata->irq,
200				       IRQF_ONESHOT, 0,
201				       &ddata->irq_chip, &ddata->irq_data);
202	if (ret) {
203		dev_err(&spi->dev, "Failed to add PMIC irq chip %d\n", ret);
204		return ret;
205	}
206
207	ret = devm_of_platform_populate(&spi->dev);
208	if (ret) {
209		dev_err(&spi->dev, "Failed to populate sub-devices %d\n", ret);
210		return ret;
211	}
212
213	device_init_wakeup(&spi->dev, true);
214	return 0;
215}
216
217static int sprd_pmic_suspend(struct device *dev)
218{
219	struct sprd_pmic *ddata = dev_get_drvdata(dev);
220
221	if (device_may_wakeup(dev))
222		enable_irq_wake(ddata->irq);
223
224	return 0;
225}
226
227static int sprd_pmic_resume(struct device *dev)
228{
229	struct sprd_pmic *ddata = dev_get_drvdata(dev);
230
231	if (device_may_wakeup(dev))
232		disable_irq_wake(ddata->irq);
233
234	return 0;
235}
236
237static DEFINE_SIMPLE_DEV_PM_OPS(sprd_pmic_pm_ops,
238				sprd_pmic_suspend, sprd_pmic_resume);
239
240static const struct of_device_id sprd_pmic_match[] = {
241	{ .compatible = "sprd,sc2730", .data = &sc2730_data },
242	{ .compatible = "sprd,sc2731", .data = &sc2731_data },
243	{},
244};
245MODULE_DEVICE_TABLE(of, sprd_pmic_match);
246
247static const struct spi_device_id sprd_pmic_spi_ids[] = {
248	{ .name = "sc2730", .driver_data = (unsigned long)&sc2730_data },
249	{ .name = "sc2731", .driver_data = (unsigned long)&sc2731_data },
250	{},
251};
252MODULE_DEVICE_TABLE(spi, sprd_pmic_spi_ids);
253
254static struct spi_driver sprd_pmic_driver = {
255	.driver = {
256		.name = "sc27xx-pmic",
257		.of_match_table = sprd_pmic_match,
258		.pm = pm_sleep_ptr(&sprd_pmic_pm_ops),
259	},
260	.probe = sprd_pmic_probe,
261	.id_table = sprd_pmic_spi_ids,
262};
263
264static int __init sprd_pmic_init(void)
265{
266	return spi_register_driver(&sprd_pmic_driver);
267}
268subsys_initcall(sprd_pmic_init);
269
270static void __exit sprd_pmic_exit(void)
271{
272	spi_unregister_driver(&sprd_pmic_driver);
273}
274module_exit(sprd_pmic_exit);
275
276MODULE_LICENSE("GPL v2");
277MODULE_DESCRIPTION("Spreadtrum SC27xx PMICs driver");
278MODULE_AUTHOR("Baolin Wang <baolin.wang@spreadtrum.com>");