Linux Audio

Check our new training course

Loading...
Note: File does not exist in v3.1.
  1// SPDX-License-Identifier: GPL-2.0-only
  2/*
  3 * Core MFD support for Cirrus Logic Madera codecs
  4 *
  5 * Copyright (C) 2015-2018 Cirrus Logic
  6 */
  7
  8#include <linux/device.h>
  9#include <linux/delay.h>
 10#include <linux/err.h>
 11#include <linux/gpio.h>
 12#include <linux/mfd/core.h>
 13#include <linux/module.h>
 14#include <linux/mutex.h>
 15#include <linux/notifier.h>
 16#include <linux/of.h>
 17#include <linux/of_gpio.h>
 18#include <linux/platform_device.h>
 19#include <linux/pm_runtime.h>
 20#include <linux/regmap.h>
 21#include <linux/regulator/consumer.h>
 22#include <linux/regulator/machine.h>
 23#include <linux/regulator/of_regulator.h>
 24
 25#include <linux/mfd/madera/core.h>
 26#include <linux/mfd/madera/registers.h>
 27
 28#include "madera.h"
 29
 30#define CS47L15_SILICON_ID	0x6370
 31#define CS47L35_SILICON_ID	0x6360
 32#define CS47L85_SILICON_ID	0x6338
 33#define CS47L90_SILICON_ID	0x6364
 34#define CS47L92_SILICON_ID	0x6371
 35
 36#define MADERA_32KZ_MCLK2	1
 37
 38#define MADERA_RESET_MIN_US	2000
 39#define MADERA_RESET_MAX_US	3000
 40
 41#define ERRATA_DCVDD_MIN_US	10000
 42#define ERRATA_DCVDD_MAX_US	15000
 43
 44static const char * const madera_core_supplies[] = {
 45	"AVDD",
 46	"DBVDD1",
 47};
 48
 49static const struct mfd_cell madera_ldo1_devs[] = {
 50	{
 51		.name = "madera-ldo1",
 52		.level = MFD_DEP_LEVEL_HIGH,
 53	},
 54};
 55
 56static const char * const cs47l15_supplies[] = {
 57	"MICVDD",
 58	"CPVDD1",
 59	"SPKVDD",
 60};
 61
 62static const struct mfd_cell cs47l15_devs[] = {
 63	{ .name = "madera-pinctrl", },
 64	{ .name = "madera-irq", },
 65	{ .name = "madera-gpio", },
 66	{
 67		.name = "madera-extcon",
 68		.parent_supplies = cs47l15_supplies,
 69		.num_parent_supplies = 1, /* We only need MICVDD */
 70	},
 71	{
 72		.name = "cs47l15-codec",
 73		.parent_supplies = cs47l15_supplies,
 74		.num_parent_supplies = ARRAY_SIZE(cs47l15_supplies),
 75	},
 76};
 77
 78static const char * const cs47l35_supplies[] = {
 79	"MICVDD",
 80	"DBVDD2",
 81	"CPVDD1",
 82	"CPVDD2",
 83	"SPKVDD",
 84};
 85
 86static const struct mfd_cell cs47l35_devs[] = {
 87	{ .name = "madera-pinctrl", },
 88	{ .name = "madera-irq", },
 89	{ .name = "madera-micsupp", },
 90	{ .name = "madera-gpio", },
 91	{
 92		.name = "madera-extcon",
 93		.parent_supplies = cs47l35_supplies,
 94		.num_parent_supplies = 1, /* We only need MICVDD */
 95	},
 96	{
 97		.name = "cs47l35-codec",
 98		.parent_supplies = cs47l35_supplies,
 99		.num_parent_supplies = ARRAY_SIZE(cs47l35_supplies),
100	},
101};
102
103static const char * const cs47l85_supplies[] = {
104	"MICVDD",
105	"DBVDD2",
106	"DBVDD3",
107	"DBVDD4",
108	"CPVDD1",
109	"CPVDD2",
110	"SPKVDDL",
111	"SPKVDDR",
112};
113
114static const struct mfd_cell cs47l85_devs[] = {
115	{ .name = "madera-pinctrl", },
116	{ .name = "madera-irq", },
117	{ .name = "madera-micsupp", },
118	{ .name = "madera-gpio", },
119	{
120		.name = "madera-extcon",
121		.parent_supplies = cs47l85_supplies,
122		.num_parent_supplies = 1, /* We only need MICVDD */
123	},
124	{
125		.name = "cs47l85-codec",
126		.parent_supplies = cs47l85_supplies,
127		.num_parent_supplies = ARRAY_SIZE(cs47l85_supplies),
128	},
129};
130
131static const char * const cs47l90_supplies[] = {
132	"MICVDD",
133	"DBVDD2",
134	"DBVDD3",
135	"DBVDD4",
136	"CPVDD1",
137	"CPVDD2",
138};
139
140static const struct mfd_cell cs47l90_devs[] = {
141	{ .name = "madera-pinctrl", },
142	{ .name = "madera-irq", },
143	{ .name = "madera-micsupp", },
144	{ .name = "madera-gpio", },
145	{
146		.name = "madera-extcon",
147		.parent_supplies = cs47l90_supplies,
148		.num_parent_supplies = 1, /* We only need MICVDD */
149	},
150	{
151		.name = "cs47l90-codec",
152		.parent_supplies = cs47l90_supplies,
153		.num_parent_supplies = ARRAY_SIZE(cs47l90_supplies),
154	},
155};
156
157static const char * const cs47l92_supplies[] = {
158	"MICVDD",
159	"CPVDD1",
160	"CPVDD2",
161};
162
163static const struct mfd_cell cs47l92_devs[] = {
164	{ .name = "madera-pinctrl", },
165	{ .name = "madera-irq", },
166	{ .name = "madera-micsupp", },
167	{ .name = "madera-gpio", },
168	{
169		.name = "madera-extcon",
170		.parent_supplies = cs47l92_supplies,
171		.num_parent_supplies = 1, /* We only need MICVDD */
172	},
173	{
174		.name = "cs47l92-codec",
175		.parent_supplies = cs47l92_supplies,
176		.num_parent_supplies = ARRAY_SIZE(cs47l92_supplies),
177	},
178};
179
180/* Used by madera-i2c and madera-spi drivers */
181const char *madera_name_from_type(enum madera_type type)
182{
183	switch (type) {
184	case CS47L15:
185		return "CS47L15";
186	case CS47L35:
187		return "CS47L35";
188	case CS47L85:
189		return "CS47L85";
190	case CS47L90:
191		return "CS47L90";
192	case CS47L91:
193		return "CS47L91";
194	case CS42L92:
195		return "CS42L92";
196	case CS47L92:
197		return "CS47L92";
198	case CS47L93:
199		return "CS47L93";
200	case WM1840:
201		return "WM1840";
202	default:
203		return "Unknown";
204	}
205}
206EXPORT_SYMBOL_GPL(madera_name_from_type);
207
208#define MADERA_BOOT_POLL_INTERVAL_USEC		5000
209#define MADERA_BOOT_POLL_TIMEOUT_USEC		25000
210
211static int madera_wait_for_boot_noack(struct madera *madera)
212{
213	ktime_t timeout;
214	unsigned int val = 0;
215	int ret = 0;
216
217	/*
218	 * We can't use an interrupt as we need to runtime resume to do so,
219	 * so we poll the status bit. This won't race with the interrupt
220	 * handler because it will be blocked on runtime resume.
221	 * The chip could NAK a read request while it is booting so ignore
222	 * errors from regmap_read.
223	 */
224	timeout = ktime_add_us(ktime_get(), MADERA_BOOT_POLL_TIMEOUT_USEC);
225	regmap_read(madera->regmap, MADERA_IRQ1_RAW_STATUS_1, &val);
226	while (!(val & MADERA_BOOT_DONE_STS1) &&
227	       !ktime_after(ktime_get(), timeout)) {
228		usleep_range(MADERA_BOOT_POLL_INTERVAL_USEC / 2,
229			     MADERA_BOOT_POLL_INTERVAL_USEC);
230		regmap_read(madera->regmap, MADERA_IRQ1_RAW_STATUS_1, &val);
231	}
232
233	if (!(val & MADERA_BOOT_DONE_STS1)) {
234		dev_err(madera->dev, "Polling BOOT_DONE_STS timed out\n");
235		ret = -ETIMEDOUT;
236	}
237
238	return ret;
239}
240
241static int madera_wait_for_boot(struct madera *madera)
242{
243	int ret = madera_wait_for_boot_noack(madera);
244
245	/*
246	 * BOOT_DONE defaults to unmasked on boot so we must ack it.
247	 * Do this even after a timeout to avoid interrupt storms.
248	 */
249	regmap_write(madera->regmap, MADERA_IRQ1_STATUS_1,
250		     MADERA_BOOT_DONE_EINT1);
251
252	pm_runtime_mark_last_busy(madera->dev);
253
254	return ret;
255}
256
257static int madera_soft_reset(struct madera *madera)
258{
259	int ret;
260
261	ret = regmap_write(madera->regmap, MADERA_SOFTWARE_RESET, 0);
262	if (ret != 0) {
263		dev_err(madera->dev, "Failed to soft reset device: %d\n", ret);
264		return ret;
265	}
266
267	/* Allow time for internal clocks to startup after reset */
268	usleep_range(MADERA_RESET_MIN_US, MADERA_RESET_MAX_US);
269
270	return 0;
271}
272
273static void madera_enable_hard_reset(struct madera *madera)
274{
275	/*
276	 * There are many existing out-of-tree users of these codecs that we
277	 * can't break so preserve the expected behaviour of setting the line
278	 * low to assert reset.
279	 */
280	gpiod_set_raw_value_cansleep(madera->pdata.reset, 0);
281}
282
283static void madera_disable_hard_reset(struct madera *madera)
284{
285	gpiod_set_raw_value_cansleep(madera->pdata.reset, 1);
286
287	usleep_range(MADERA_RESET_MIN_US, MADERA_RESET_MAX_US);
288}
289
290static int __maybe_unused madera_runtime_resume(struct device *dev)
291{
292	struct madera *madera = dev_get_drvdata(dev);
293	int ret;
294
295	dev_dbg(dev, "Leaving sleep mode\n");
296
297	if (!madera->reset_errata)
298		madera_enable_hard_reset(madera);
299
300	ret = regulator_enable(madera->dcvdd);
301	if (ret) {
302		dev_err(dev, "Failed to enable DCVDD: %d\n", ret);
303		return ret;
304	}
305
306	regcache_cache_only(madera->regmap, false);
307	regcache_cache_only(madera->regmap_32bit, false);
308
309	if (madera->reset_errata)
310		usleep_range(ERRATA_DCVDD_MIN_US, ERRATA_DCVDD_MAX_US);
311	else
312		madera_disable_hard_reset(madera);
313
314	if (!madera->pdata.reset || madera->reset_errata) {
315		ret = madera_wait_for_boot(madera);
316		if (ret)
317			goto err;
318
319		ret = madera_soft_reset(madera);
320		if (ret) {
321			dev_err(dev, "Failed to reset: %d\n", ret);
322			goto err;
323		}
324	}
325
326	ret = madera_wait_for_boot(madera);
327	if (ret)
328		goto err;
329
330	ret = regcache_sync(madera->regmap);
331	if (ret) {
332		dev_err(dev, "Failed to restore 16-bit register cache\n");
333		goto err;
334	}
335
336	ret = regcache_sync(madera->regmap_32bit);
337	if (ret) {
338		dev_err(dev, "Failed to restore 32-bit register cache\n");
339		goto err;
340	}
341
342	return 0;
343
344err:
345	regcache_cache_only(madera->regmap_32bit, true);
346	regcache_cache_only(madera->regmap, true);
347	regulator_disable(madera->dcvdd);
348
349	return ret;
350}
351
352static int __maybe_unused madera_runtime_suspend(struct device *dev)
353{
354	struct madera *madera = dev_get_drvdata(dev);
355
356	dev_dbg(madera->dev, "Entering sleep mode\n");
357
358	regcache_cache_only(madera->regmap, true);
359	regcache_mark_dirty(madera->regmap);
360	regcache_cache_only(madera->regmap_32bit, true);
361	regcache_mark_dirty(madera->regmap_32bit);
362
363	regulator_disable(madera->dcvdd);
364
365	return 0;
366}
367
368const struct dev_pm_ops madera_pm_ops = {
369	SET_RUNTIME_PM_OPS(madera_runtime_suspend,
370			   madera_runtime_resume,
371			   NULL)
372};
373EXPORT_SYMBOL_GPL(madera_pm_ops);
374
375const struct of_device_id madera_of_match[] = {
376	{ .compatible = "cirrus,cs47l15", .data = (void *)CS47L15 },
377	{ .compatible = "cirrus,cs47l35", .data = (void *)CS47L35 },
378	{ .compatible = "cirrus,cs47l85", .data = (void *)CS47L85 },
379	{ .compatible = "cirrus,cs47l90", .data = (void *)CS47L90 },
380	{ .compatible = "cirrus,cs47l91", .data = (void *)CS47L91 },
381	{ .compatible = "cirrus,cs42l92", .data = (void *)CS42L92 },
382	{ .compatible = "cirrus,cs47l92", .data = (void *)CS47L92 },
383	{ .compatible = "cirrus,cs47l93", .data = (void *)CS47L93 },
384	{ .compatible = "cirrus,wm1840", .data = (void *)WM1840 },
385	{}
386};
387MODULE_DEVICE_TABLE(of, madera_of_match);
388EXPORT_SYMBOL_GPL(madera_of_match);
389
390static int madera_get_reset_gpio(struct madera *madera)
391{
392	struct gpio_desc *reset;
393
394	if (madera->pdata.reset)
395		return 0;
396
397	reset = devm_gpiod_get_optional(madera->dev, "reset", GPIOD_OUT_LOW);
398	if (IS_ERR(reset))
399		return dev_err_probe(madera->dev, PTR_ERR(reset),
400				"Failed to request /RESET");
401
402	/*
403	 * A hard reset is needed for full reset of the chip. We allow running
404	 * without hard reset only because it can be useful for early
405	 * prototyping and some debugging, but we need to warn it's not ideal.
406	 */
407	if (!reset)
408		dev_warn(madera->dev,
409			 "Running without reset GPIO is not recommended\n");
410
411	madera->pdata.reset = reset;
412
413	return 0;
414}
415
416static void madera_set_micbias_info(struct madera *madera)
417{
418	/*
419	 * num_childbias is an array because future codecs can have different
420	 * childbiases for each micbias. Unspecified values default to 0.
421	 */
422	switch (madera->type) {
423	case CS47L15:
424		madera->num_micbias = 1;
425		madera->num_childbias[0] = 3;
426		return;
427	case CS47L35:
428		madera->num_micbias = 2;
429		madera->num_childbias[0] = 2;
430		madera->num_childbias[1] = 2;
431		return;
432	case CS47L85:
433	case WM1840:
434		madera->num_micbias = 4;
435		/* no child biases */
436		return;
437	case CS47L90:
438	case CS47L91:
439		madera->num_micbias = 2;
440		madera->num_childbias[0] = 4;
441		madera->num_childbias[1] = 4;
442		return;
443	case CS42L92:
444	case CS47L92:
445	case CS47L93:
446		madera->num_micbias = 2;
447		madera->num_childbias[0] = 4;
448		madera->num_childbias[1] = 2;
449		return;
450	default:
451		return;
452	}
453}
454
455int madera_dev_init(struct madera *madera)
456{
457	struct device *dev = madera->dev;
458	unsigned int hwid;
459	int (*patch_fn)(struct madera *) = NULL;
460	const struct mfd_cell *mfd_devs;
461	int n_devs = 0;
462	int i, ret;
463
464	dev_set_drvdata(madera->dev, madera);
465	BLOCKING_INIT_NOTIFIER_HEAD(&madera->notifier);
466	mutex_init(&madera->dapm_ptr_lock);
467
468	madera_set_micbias_info(madera);
469
470	/*
471	 * We need writable hw config info that all children can share.
472	 * Simplest to take one shared copy of pdata struct.
473	 */
474	if (dev_get_platdata(madera->dev)) {
475		memcpy(&madera->pdata, dev_get_platdata(madera->dev),
476		       sizeof(madera->pdata));
477	}
478
479	madera->mclk[MADERA_MCLK1].id = "mclk1";
480	madera->mclk[MADERA_MCLK2].id = "mclk2";
481	madera->mclk[MADERA_MCLK3].id = "mclk3";
482
483	ret = devm_clk_bulk_get_optional(madera->dev, ARRAY_SIZE(madera->mclk),
484					 madera->mclk);
485	if (ret) {
486		dev_err(madera->dev, "Failed to get clocks: %d\n", ret);
487		return ret;
488	}
489
490	/* Not using devm_clk_get to prevent breakage of existing DTs */
491	if (!madera->mclk[MADERA_MCLK2].clk)
492		dev_warn(madera->dev, "Missing MCLK2, requires 32kHz clock\n");
493
494	ret = madera_get_reset_gpio(madera);
495	if (ret)
496		return ret;
497
498	regcache_cache_only(madera->regmap, true);
499	regcache_cache_only(madera->regmap_32bit, true);
500
501	for (i = 0; i < ARRAY_SIZE(madera_core_supplies); i++)
502		madera->core_supplies[i].supply = madera_core_supplies[i];
503
504	madera->num_core_supplies = ARRAY_SIZE(madera_core_supplies);
505
506	/*
507	 * On some codecs DCVDD could be supplied by the internal LDO1.
508	 * For those we must add the LDO1 driver before requesting DCVDD
509	 * No devm_ because we need to control shutdown order of children.
510	 */
511	switch (madera->type) {
512	case CS47L15:
513		madera->reset_errata = true;
514		break;
515	case CS47L35:
516	case CS47L90:
517	case CS47L91:
518	case CS42L92:
519	case CS47L92:
520	case CS47L93:
521		break;
522	case CS47L85:
523	case WM1840:
524		ret = mfd_add_devices(madera->dev, PLATFORM_DEVID_NONE,
525				      madera_ldo1_devs,
526				      ARRAY_SIZE(madera_ldo1_devs),
527				      NULL, 0, NULL);
528		if (ret) {
529			dev_err(dev, "Failed to add LDO1 child: %d\n", ret);
530			return ret;
531		}
532		break;
533	default:
534		/* No point continuing if the type is unknown */
535		dev_err(madera->dev, "Unknown device type %d\n", madera->type);
536		return -ENODEV;
537	}
538
539	ret = devm_regulator_bulk_get(dev, madera->num_core_supplies,
540				      madera->core_supplies);
541	if (ret) {
542		dev_err(dev, "Failed to request core supplies: %d\n", ret);
543		goto err_devs;
544	}
545
546	/*
547	 * Don't use devres here. If the regulator is one of our children it
548	 * will already have been removed before devres cleanup on this mfd
549	 * driver tries to call put() on it. We need control of shutdown order.
550	 */
551	madera->dcvdd = regulator_get(madera->dev, "DCVDD");
552	if (IS_ERR(madera->dcvdd)) {
553		ret = PTR_ERR(madera->dcvdd);
554		dev_err(dev, "Failed to request DCVDD: %d\n", ret);
555		goto err_devs;
556	}
557
558	ret = regulator_bulk_enable(madera->num_core_supplies,
559				    madera->core_supplies);
560	if (ret) {
561		dev_err(dev, "Failed to enable core supplies: %d\n", ret);
562		goto err_dcvdd;
563	}
564
565	if (madera->reset_errata)
566		madera_disable_hard_reset(madera);
567
568	ret = regulator_enable(madera->dcvdd);
569	if (ret) {
570		dev_err(dev, "Failed to enable DCVDD: %d\n", ret);
571		goto err_enable;
572	}
573
574	if (madera->reset_errata)
575		usleep_range(ERRATA_DCVDD_MIN_US, ERRATA_DCVDD_MAX_US);
576	else
577		madera_disable_hard_reset(madera);
578
579	regcache_cache_only(madera->regmap, false);
580	regcache_cache_only(madera->regmap_32bit, false);
581
582	ret = madera_wait_for_boot_noack(madera);
583	if (ret) {
584		dev_err(madera->dev, "Device failed initial boot: %d\n", ret);
585		goto err_reset;
586	}
587
588	/*
589	 * Now we can power up and verify that this is a chip we know about
590	 * before we start doing any writes to its registers.
591	 */
592	ret = regmap_read(madera->regmap, MADERA_SOFTWARE_RESET, &hwid);
593	if (ret) {
594		dev_err(dev, "Failed to read ID register: %d\n", ret);
595		goto err_reset;
596	}
597
598	switch (hwid) {
599	case CS47L15_SILICON_ID:
600		if (IS_ENABLED(CONFIG_MFD_CS47L15)) {
601			switch (madera->type) {
602			case CS47L15:
603				patch_fn = &cs47l15_patch;
604				mfd_devs = cs47l15_devs;
605				n_devs = ARRAY_SIZE(cs47l15_devs);
606				break;
607			default:
608				break;
609			}
610		}
611		break;
612	case CS47L35_SILICON_ID:
613		if (IS_ENABLED(CONFIG_MFD_CS47L35)) {
614			switch (madera->type) {
615			case CS47L35:
616				patch_fn = cs47l35_patch;
617				mfd_devs = cs47l35_devs;
618				n_devs = ARRAY_SIZE(cs47l35_devs);
619				break;
620			default:
621				break;
622			}
623		}
624		break;
625	case CS47L85_SILICON_ID:
626		if (IS_ENABLED(CONFIG_MFD_CS47L85)) {
627			switch (madera->type) {
628			case CS47L85:
629			case WM1840:
630				patch_fn = cs47l85_patch;
631				mfd_devs = cs47l85_devs;
632				n_devs = ARRAY_SIZE(cs47l85_devs);
633				break;
634			default:
635				break;
636			}
637		}
638		break;
639	case CS47L90_SILICON_ID:
640		if (IS_ENABLED(CONFIG_MFD_CS47L90)) {
641			switch (madera->type) {
642			case CS47L90:
643			case CS47L91:
644				patch_fn = cs47l90_patch;
645				mfd_devs = cs47l90_devs;
646				n_devs = ARRAY_SIZE(cs47l90_devs);
647				break;
648			default:
649				break;
650			}
651		}
652		break;
653	case CS47L92_SILICON_ID:
654		if (IS_ENABLED(CONFIG_MFD_CS47L92)) {
655			switch (madera->type) {
656			case CS42L92:
657			case CS47L92:
658			case CS47L93:
659				patch_fn = cs47l92_patch;
660				mfd_devs = cs47l92_devs;
661				n_devs = ARRAY_SIZE(cs47l92_devs);
662				break;
663			default:
664				break;
665			}
666		}
667		break;
668	default:
669		dev_err(madera->dev, "Unknown device ID: %x\n", hwid);
670		ret = -EINVAL;
671		goto err_reset;
672	}
673
674	if (!n_devs) {
675		dev_err(madera->dev, "Device ID 0x%x not a %s\n", hwid,
676			madera->type_name);
677		ret = -ENODEV;
678		goto err_reset;
679	}
680
681	/*
682	 * It looks like a device we support. If we don't have a hard reset
683	 * we can now attempt a soft reset.
684	 */
685	if (!madera->pdata.reset || madera->reset_errata) {
686		ret = madera_soft_reset(madera);
687		if (ret)
688			goto err_reset;
689	}
690
691	ret = madera_wait_for_boot(madera);
692	if (ret) {
693		dev_err(madera->dev, "Failed to clear boot done: %d\n", ret);
694		goto err_reset;
695	}
696
697	ret = regmap_read(madera->regmap, MADERA_HARDWARE_REVISION,
698			  &madera->rev);
699	if (ret) {
700		dev_err(dev, "Failed to read revision register: %d\n", ret);
701		goto err_reset;
702	}
703	madera->rev &= MADERA_HW_REVISION_MASK;
704
705	dev_info(dev, "%s silicon revision %d\n", madera->type_name,
706		 madera->rev);
707
708	/* Apply hardware patch */
709	if (patch_fn) {
710		ret = patch_fn(madera);
711		if (ret) {
712			dev_err(madera->dev, "Failed to apply patch %d\n", ret);
713			goto err_reset;
714		}
715	}
716
717	/* Init 32k clock sourced from MCLK2 */
718	ret = clk_prepare_enable(madera->mclk[MADERA_MCLK2].clk);
719	if (ret) {
720		dev_err(madera->dev, "Failed to enable 32k clock: %d\n", ret);
721		goto err_reset;
722	}
723
724	ret = regmap_update_bits(madera->regmap,
725			MADERA_CLOCK_32K_1,
726			MADERA_CLK_32K_ENA_MASK | MADERA_CLK_32K_SRC_MASK,
727			MADERA_CLK_32K_ENA | MADERA_32KZ_MCLK2);
728	if (ret) {
729		dev_err(madera->dev, "Failed to init 32k clock: %d\n", ret);
730		goto err_clock;
731	}
732
733	pm_runtime_set_active(madera->dev);
734	pm_runtime_enable(madera->dev);
735	pm_runtime_set_autosuspend_delay(madera->dev, 100);
736	pm_runtime_use_autosuspend(madera->dev);
737
738	/* No devm_ because we need to control shutdown order of children */
739	ret = mfd_add_devices(madera->dev, PLATFORM_DEVID_NONE,
740			      mfd_devs, n_devs,
741			      NULL, 0, NULL);
742	if (ret) {
743		dev_err(madera->dev, "Failed to add subdevices: %d\n", ret);
744		goto err_pm_runtime;
745	}
746
747	return 0;
748
749err_pm_runtime:
750	pm_runtime_disable(madera->dev);
751err_clock:
752	clk_disable_unprepare(madera->mclk[MADERA_MCLK2].clk);
753err_reset:
754	madera_enable_hard_reset(madera);
755	regulator_disable(madera->dcvdd);
756err_enable:
757	regulator_bulk_disable(madera->num_core_supplies,
758			       madera->core_supplies);
759err_dcvdd:
760	regulator_put(madera->dcvdd);
761err_devs:
762	mfd_remove_devices(dev);
763
764	return ret;
765}
766EXPORT_SYMBOL_GPL(madera_dev_init);
767
768int madera_dev_exit(struct madera *madera)
769{
770	/* Prevent any IRQs being serviced while we clean up */
771	disable_irq(madera->irq);
772
773	pm_runtime_get_sync(madera->dev);
774
775	mfd_remove_devices(madera->dev);
776
777	pm_runtime_disable(madera->dev);
778
779	regulator_disable(madera->dcvdd);
780	regulator_put(madera->dcvdd);
781
782	mfd_remove_devices_late(madera->dev);
783
784	pm_runtime_set_suspended(madera->dev);
785	pm_runtime_put_noidle(madera->dev);
786
787	clk_disable_unprepare(madera->mclk[MADERA_MCLK2].clk);
788
789	madera_enable_hard_reset(madera);
790
791	regulator_bulk_disable(madera->num_core_supplies,
792			       madera->core_supplies);
793	return 0;
794}
795EXPORT_SYMBOL_GPL(madera_dev_exit);
796
797MODULE_DESCRIPTION("Madera core MFD driver");
798MODULE_AUTHOR("Richard Fitzgerald <rf@opensource.cirrus.com>");
799MODULE_LICENSE("GPL v2");