cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

arizona.c (72009B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * arizona.c - Wolfson Arizona class device shared support
      4 *
      5 * Copyright 2012 Wolfson Microelectronics plc
      6 *
      7 * Author: Mark Brown <broonie@opensource.wolfsonmicro.com>
      8 */
      9
     10#include <linux/delay.h>
     11#include <linux/gcd.h>
     12#include <linux/module.h>
     13#include <linux/of.h>
     14#include <linux/pm_runtime.h>
     15#include <sound/pcm.h>
     16#include <sound/pcm_params.h>
     17#include <sound/tlv.h>
     18
     19#include <linux/mfd/arizona/core.h>
     20#include <linux/mfd/arizona/registers.h>
     21
     22#include "arizona.h"
     23
     24#define ARIZONA_AIF_BCLK_CTRL                   0x00
     25#define ARIZONA_AIF_TX_PIN_CTRL                 0x01
     26#define ARIZONA_AIF_RX_PIN_CTRL                 0x02
     27#define ARIZONA_AIF_RATE_CTRL                   0x03
     28#define ARIZONA_AIF_FORMAT                      0x04
     29#define ARIZONA_AIF_TX_BCLK_RATE                0x05
     30#define ARIZONA_AIF_RX_BCLK_RATE                0x06
     31#define ARIZONA_AIF_FRAME_CTRL_1                0x07
     32#define ARIZONA_AIF_FRAME_CTRL_2                0x08
     33#define ARIZONA_AIF_FRAME_CTRL_3                0x09
     34#define ARIZONA_AIF_FRAME_CTRL_4                0x0A
     35#define ARIZONA_AIF_FRAME_CTRL_5                0x0B
     36#define ARIZONA_AIF_FRAME_CTRL_6                0x0C
     37#define ARIZONA_AIF_FRAME_CTRL_7                0x0D
     38#define ARIZONA_AIF_FRAME_CTRL_8                0x0E
     39#define ARIZONA_AIF_FRAME_CTRL_9                0x0F
     40#define ARIZONA_AIF_FRAME_CTRL_10               0x10
     41#define ARIZONA_AIF_FRAME_CTRL_11               0x11
     42#define ARIZONA_AIF_FRAME_CTRL_12               0x12
     43#define ARIZONA_AIF_FRAME_CTRL_13               0x13
     44#define ARIZONA_AIF_FRAME_CTRL_14               0x14
     45#define ARIZONA_AIF_FRAME_CTRL_15               0x15
     46#define ARIZONA_AIF_FRAME_CTRL_16               0x16
     47#define ARIZONA_AIF_FRAME_CTRL_17               0x17
     48#define ARIZONA_AIF_FRAME_CTRL_18               0x18
     49#define ARIZONA_AIF_TX_ENABLES                  0x19
     50#define ARIZONA_AIF_RX_ENABLES                  0x1A
     51#define ARIZONA_AIF_FORCE_WRITE                 0x1B
     52
     53#define ARIZONA_FLL_VCO_CORNER 141900000
     54#define ARIZONA_FLL_MAX_FREF   13500000
     55#define ARIZONA_FLL_MIN_FVCO   90000000
     56#define ARIZONA_FLL_MAX_FRATIO 16
     57#define ARIZONA_FLL_MAX_REFDIV 8
     58#define ARIZONA_FLL_MIN_OUTDIV 2
     59#define ARIZONA_FLL_MAX_OUTDIV 7
     60
     61#define ARIZONA_FMT_DSP_MODE_A          0
     62#define ARIZONA_FMT_DSP_MODE_B          1
     63#define ARIZONA_FMT_I2S_MODE            2
     64#define ARIZONA_FMT_LEFT_JUSTIFIED_MODE 3
     65
     66#define arizona_fll_err(_fll, fmt, ...) \
     67	dev_err(_fll->arizona->dev, "FLL%d: " fmt, _fll->id, ##__VA_ARGS__)
     68#define arizona_fll_warn(_fll, fmt, ...) \
     69	dev_warn(_fll->arizona->dev, "FLL%d: " fmt, _fll->id, ##__VA_ARGS__)
     70#define arizona_fll_dbg(_fll, fmt, ...) \
     71	dev_dbg(_fll->arizona->dev, "FLL%d: " fmt, _fll->id, ##__VA_ARGS__)
     72
     73#define arizona_aif_err(_dai, fmt, ...) \
     74	dev_err(_dai->dev, "AIF%d: " fmt, _dai->id, ##__VA_ARGS__)
     75#define arizona_aif_warn(_dai, fmt, ...) \
     76	dev_warn(_dai->dev, "AIF%d: " fmt, _dai->id, ##__VA_ARGS__)
     77#define arizona_aif_dbg(_dai, fmt, ...) \
     78	dev_dbg(_dai->dev, "AIF%d: " fmt, _dai->id, ##__VA_ARGS__)
     79
     80static int arizona_spk_ev(struct snd_soc_dapm_widget *w,
     81			  struct snd_kcontrol *kcontrol,
     82			  int event)
     83{
     84	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
     85	struct arizona *arizona = dev_get_drvdata(component->dev->parent);
     86	int val;
     87
     88	switch (event) {
     89	case SND_SOC_DAPM_POST_PMU:
     90		val = snd_soc_component_read(component,
     91					       ARIZONA_INTERRUPT_RAW_STATUS_3);
     92		if (val & ARIZONA_SPK_OVERHEAT_STS) {
     93			dev_crit(arizona->dev,
     94				 "Speaker not enabled due to temperature\n");
     95			return -EBUSY;
     96		}
     97
     98		regmap_update_bits_async(arizona->regmap,
     99					 ARIZONA_OUTPUT_ENABLES_1,
    100					 1 << w->shift, 1 << w->shift);
    101		break;
    102	case SND_SOC_DAPM_PRE_PMD:
    103		regmap_update_bits_async(arizona->regmap,
    104					 ARIZONA_OUTPUT_ENABLES_1,
    105					 1 << w->shift, 0);
    106		break;
    107	default:
    108		break;
    109	}
    110
    111	return arizona_out_ev(w, kcontrol, event);
    112}
    113
    114static irqreturn_t arizona_thermal_warn(int irq, void *data)
    115{
    116	struct arizona *arizona = data;
    117	unsigned int val;
    118	int ret;
    119
    120	ret = regmap_read(arizona->regmap, ARIZONA_INTERRUPT_RAW_STATUS_3,
    121			  &val);
    122	if (ret != 0) {
    123		dev_err(arizona->dev, "Failed to read thermal status: %d\n",
    124			ret);
    125	} else if (val & ARIZONA_SPK_OVERHEAT_WARN_STS) {
    126		dev_crit(arizona->dev, "Thermal warning\n");
    127	}
    128
    129	return IRQ_HANDLED;
    130}
    131
    132static irqreturn_t arizona_thermal_shutdown(int irq, void *data)
    133{
    134	struct arizona *arizona = data;
    135	unsigned int val;
    136	int ret;
    137
    138	ret = regmap_read(arizona->regmap, ARIZONA_INTERRUPT_RAW_STATUS_3,
    139			  &val);
    140	if (ret != 0) {
    141		dev_err(arizona->dev, "Failed to read thermal status: %d\n",
    142			ret);
    143	} else if (val & ARIZONA_SPK_OVERHEAT_STS) {
    144		dev_crit(arizona->dev, "Thermal shutdown\n");
    145		ret = regmap_update_bits(arizona->regmap,
    146					 ARIZONA_OUTPUT_ENABLES_1,
    147					 ARIZONA_OUT4L_ENA |
    148					 ARIZONA_OUT4R_ENA, 0);
    149		if (ret != 0)
    150			dev_crit(arizona->dev,
    151				 "Failed to disable speaker outputs: %d\n",
    152				 ret);
    153	}
    154
    155	return IRQ_HANDLED;
    156}
    157
    158static const struct snd_soc_dapm_widget arizona_spkl =
    159	SND_SOC_DAPM_PGA_E("OUT4L", SND_SOC_NOPM,
    160			   ARIZONA_OUT4L_ENA_SHIFT, 0, NULL, 0, arizona_spk_ev,
    161			   SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
    162			   SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD);
    163
    164static const struct snd_soc_dapm_widget arizona_spkr =
    165	SND_SOC_DAPM_PGA_E("OUT4R", SND_SOC_NOPM,
    166			   ARIZONA_OUT4R_ENA_SHIFT, 0, NULL, 0, arizona_spk_ev,
    167			   SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU |
    168			   SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD);
    169
    170int arizona_init_spk(struct snd_soc_component *component)
    171{
    172	struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component);
    173	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    174	struct arizona *arizona = priv->arizona;
    175	int ret;
    176
    177	ret = snd_soc_dapm_new_controls(dapm, &arizona_spkl, 1);
    178	if (ret != 0)
    179		return ret;
    180
    181	switch (arizona->type) {
    182	case WM8997:
    183	case CS47L24:
    184	case WM1831:
    185		break;
    186	default:
    187		ret = snd_soc_dapm_new_controls(dapm, &arizona_spkr, 1);
    188		if (ret != 0)
    189			return ret;
    190		break;
    191	}
    192
    193	return 0;
    194}
    195EXPORT_SYMBOL_GPL(arizona_init_spk);
    196
    197int arizona_init_spk_irqs(struct arizona *arizona)
    198{
    199	int ret;
    200
    201	ret = arizona_request_irq(arizona, ARIZONA_IRQ_SPK_OVERHEAT_WARN,
    202				  "Thermal warning", arizona_thermal_warn,
    203				  arizona);
    204	if (ret != 0)
    205		dev_err(arizona->dev,
    206			"Failed to get thermal warning IRQ: %d\n",
    207			ret);
    208
    209	ret = arizona_request_irq(arizona, ARIZONA_IRQ_SPK_OVERHEAT,
    210				  "Thermal shutdown", arizona_thermal_shutdown,
    211				  arizona);
    212	if (ret != 0)
    213		dev_err(arizona->dev,
    214			"Failed to get thermal shutdown IRQ: %d\n",
    215			ret);
    216
    217	return 0;
    218}
    219EXPORT_SYMBOL_GPL(arizona_init_spk_irqs);
    220
    221int arizona_free_spk_irqs(struct arizona *arizona)
    222{
    223	arizona_free_irq(arizona, ARIZONA_IRQ_SPK_OVERHEAT_WARN, arizona);
    224	arizona_free_irq(arizona, ARIZONA_IRQ_SPK_OVERHEAT, arizona);
    225
    226	return 0;
    227}
    228EXPORT_SYMBOL_GPL(arizona_free_spk_irqs);
    229
    230static const struct snd_soc_dapm_route arizona_mono_routes[] = {
    231	{ "OUT1R", NULL, "OUT1L" },
    232	{ "OUT2R", NULL, "OUT2L" },
    233	{ "OUT3R", NULL, "OUT3L" },
    234	{ "OUT4R", NULL, "OUT4L" },
    235	{ "OUT5R", NULL, "OUT5L" },
    236	{ "OUT6R", NULL, "OUT6L" },
    237};
    238
    239int arizona_init_mono(struct snd_soc_component *component)
    240{
    241	struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component);
    242	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    243	struct arizona *arizona = priv->arizona;
    244	int i;
    245
    246	for (i = 0; i < ARIZONA_MAX_OUTPUT; ++i) {
    247		if (arizona->pdata.out_mono[i])
    248			snd_soc_dapm_add_routes(dapm,
    249						&arizona_mono_routes[i], 1);
    250	}
    251
    252	return 0;
    253}
    254EXPORT_SYMBOL_GPL(arizona_init_mono);
    255
    256int arizona_init_gpio(struct snd_soc_component *component)
    257{
    258	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    259	struct arizona *arizona = priv->arizona;
    260	int i;
    261
    262	switch (arizona->type) {
    263	case WM5110:
    264	case WM8280:
    265		snd_soc_component_disable_pin(component,
    266					      "DRC2 Signal Activity");
    267		break;
    268	default:
    269		break;
    270	}
    271
    272	snd_soc_component_disable_pin(component, "DRC1 Signal Activity");
    273
    274	for (i = 0; i < ARRAY_SIZE(arizona->pdata.gpio_defaults); i++) {
    275		switch (arizona->pdata.gpio_defaults[i] & ARIZONA_GPN_FN_MASK) {
    276		case ARIZONA_GP_FN_DRC1_SIGNAL_DETECT:
    277			snd_soc_component_enable_pin(component,
    278						     "DRC1 Signal Activity");
    279			break;
    280		case ARIZONA_GP_FN_DRC2_SIGNAL_DETECT:
    281			snd_soc_component_enable_pin(component,
    282						     "DRC2 Signal Activity");
    283			break;
    284		default:
    285			break;
    286		}
    287	}
    288
    289	return 0;
    290}
    291EXPORT_SYMBOL_GPL(arizona_init_gpio);
    292
    293int arizona_init_common(struct arizona *arizona)
    294{
    295	struct arizona_pdata *pdata = &arizona->pdata;
    296	unsigned int val, mask;
    297	int i;
    298
    299	BLOCKING_INIT_NOTIFIER_HEAD(&arizona->notifier);
    300
    301	for (i = 0; i < ARIZONA_MAX_OUTPUT; ++i) {
    302		/* Default is 0 so noop with defaults */
    303		if (pdata->out_mono[i])
    304			val = ARIZONA_OUT1_MONO;
    305		else
    306			val = 0;
    307
    308		regmap_update_bits(arizona->regmap,
    309				   ARIZONA_OUTPUT_PATH_CONFIG_1L + (i * 8),
    310				   ARIZONA_OUT1_MONO, val);
    311	}
    312
    313	for (i = 0; i < ARIZONA_MAX_PDM_SPK; i++) {
    314		if (pdata->spk_mute[i])
    315			regmap_update_bits(arizona->regmap,
    316					   ARIZONA_PDM_SPK1_CTRL_1 + (i * 2),
    317					   ARIZONA_SPK1_MUTE_ENDIAN_MASK |
    318					   ARIZONA_SPK1_MUTE_SEQ1_MASK,
    319					   pdata->spk_mute[i]);
    320
    321		if (pdata->spk_fmt[i])
    322			regmap_update_bits(arizona->regmap,
    323					   ARIZONA_PDM_SPK1_CTRL_2 + (i * 2),
    324					   ARIZONA_SPK1_FMT_MASK,
    325					   pdata->spk_fmt[i]);
    326	}
    327
    328	for (i = 0; i < ARIZONA_MAX_INPUT; i++) {
    329		/* Default for both is 0 so noop with defaults */
    330		val = pdata->dmic_ref[i] << ARIZONA_IN1_DMIC_SUP_SHIFT;
    331		if (pdata->inmode[i] & ARIZONA_INMODE_DMIC)
    332			val |= 1 << ARIZONA_IN1_MODE_SHIFT;
    333
    334		switch (arizona->type) {
    335		case WM8998:
    336		case WM1814:
    337			regmap_update_bits(arizona->regmap,
    338				ARIZONA_ADC_DIGITAL_VOLUME_1L + (i * 8),
    339				ARIZONA_IN1L_SRC_SE_MASK,
    340				(pdata->inmode[i] & ARIZONA_INMODE_SE)
    341					<< ARIZONA_IN1L_SRC_SE_SHIFT);
    342
    343			regmap_update_bits(arizona->regmap,
    344				ARIZONA_ADC_DIGITAL_VOLUME_1R + (i * 8),
    345				ARIZONA_IN1R_SRC_SE_MASK,
    346				(pdata->inmode[i] & ARIZONA_INMODE_SE)
    347					<< ARIZONA_IN1R_SRC_SE_SHIFT);
    348
    349			mask = ARIZONA_IN1_DMIC_SUP_MASK |
    350			       ARIZONA_IN1_MODE_MASK;
    351			break;
    352		default:
    353			if (pdata->inmode[i] & ARIZONA_INMODE_SE)
    354				val |= 1 << ARIZONA_IN1_SINGLE_ENDED_SHIFT;
    355
    356			mask = ARIZONA_IN1_DMIC_SUP_MASK |
    357			       ARIZONA_IN1_MODE_MASK |
    358			       ARIZONA_IN1_SINGLE_ENDED_MASK;
    359			break;
    360		}
    361
    362		regmap_update_bits(arizona->regmap,
    363				   ARIZONA_IN1L_CONTROL + (i * 8),
    364				   mask, val);
    365	}
    366
    367	return 0;
    368}
    369EXPORT_SYMBOL_GPL(arizona_init_common);
    370
    371int arizona_init_vol_limit(struct arizona *arizona)
    372{
    373	int i;
    374
    375	for (i = 0; i < ARRAY_SIZE(arizona->pdata.out_vol_limit); ++i) {
    376		if (arizona->pdata.out_vol_limit[i])
    377			regmap_update_bits(arizona->regmap,
    378					   ARIZONA_DAC_VOLUME_LIMIT_1L + i * 4,
    379					   ARIZONA_OUT1L_VOL_LIM_MASK,
    380					   arizona->pdata.out_vol_limit[i]);
    381	}
    382
    383	return 0;
    384}
    385EXPORT_SYMBOL_GPL(arizona_init_vol_limit);
    386
    387const char * const arizona_mixer_texts[ARIZONA_NUM_MIXER_INPUTS] = {
    388	"None",
    389	"Tone Generator 1",
    390	"Tone Generator 2",
    391	"Haptics",
    392	"AEC",
    393	"AEC2",
    394	"Mic Mute Mixer",
    395	"Noise Generator",
    396	"IN1L",
    397	"IN1R",
    398	"IN2L",
    399	"IN2R",
    400	"IN3L",
    401	"IN3R",
    402	"IN4L",
    403	"IN4R",
    404	"AIF1RX1",
    405	"AIF1RX2",
    406	"AIF1RX3",
    407	"AIF1RX4",
    408	"AIF1RX5",
    409	"AIF1RX6",
    410	"AIF1RX7",
    411	"AIF1RX8",
    412	"AIF2RX1",
    413	"AIF2RX2",
    414	"AIF2RX3",
    415	"AIF2RX4",
    416	"AIF2RX5",
    417	"AIF2RX6",
    418	"AIF3RX1",
    419	"AIF3RX2",
    420	"SLIMRX1",
    421	"SLIMRX2",
    422	"SLIMRX3",
    423	"SLIMRX4",
    424	"SLIMRX5",
    425	"SLIMRX6",
    426	"SLIMRX7",
    427	"SLIMRX8",
    428	"EQ1",
    429	"EQ2",
    430	"EQ3",
    431	"EQ4",
    432	"DRC1L",
    433	"DRC1R",
    434	"DRC2L",
    435	"DRC2R",
    436	"LHPF1",
    437	"LHPF2",
    438	"LHPF3",
    439	"LHPF4",
    440	"DSP1.1",
    441	"DSP1.2",
    442	"DSP1.3",
    443	"DSP1.4",
    444	"DSP1.5",
    445	"DSP1.6",
    446	"DSP2.1",
    447	"DSP2.2",
    448	"DSP2.3",
    449	"DSP2.4",
    450	"DSP2.5",
    451	"DSP2.6",
    452	"DSP3.1",
    453	"DSP3.2",
    454	"DSP3.3",
    455	"DSP3.4",
    456	"DSP3.5",
    457	"DSP3.6",
    458	"DSP4.1",
    459	"DSP4.2",
    460	"DSP4.3",
    461	"DSP4.4",
    462	"DSP4.5",
    463	"DSP4.6",
    464	"ASRC1L",
    465	"ASRC1R",
    466	"ASRC2L",
    467	"ASRC2R",
    468	"ISRC1INT1",
    469	"ISRC1INT2",
    470	"ISRC1INT3",
    471	"ISRC1INT4",
    472	"ISRC1DEC1",
    473	"ISRC1DEC2",
    474	"ISRC1DEC3",
    475	"ISRC1DEC4",
    476	"ISRC2INT1",
    477	"ISRC2INT2",
    478	"ISRC2INT3",
    479	"ISRC2INT4",
    480	"ISRC2DEC1",
    481	"ISRC2DEC2",
    482	"ISRC2DEC3",
    483	"ISRC2DEC4",
    484	"ISRC3INT1",
    485	"ISRC3INT2",
    486	"ISRC3INT3",
    487	"ISRC3INT4",
    488	"ISRC3DEC1",
    489	"ISRC3DEC2",
    490	"ISRC3DEC3",
    491	"ISRC3DEC4",
    492};
    493EXPORT_SYMBOL_GPL(arizona_mixer_texts);
    494
    495unsigned int arizona_mixer_values[ARIZONA_NUM_MIXER_INPUTS] = {
    496	0x00,  /* None */
    497	0x04,  /* Tone */
    498	0x05,
    499	0x06,  /* Haptics */
    500	0x08,  /* AEC */
    501	0x09,  /* AEC2 */
    502	0x0c,  /* Noise mixer */
    503	0x0d,  /* Comfort noise */
    504	0x10,  /* IN1L */
    505	0x11,
    506	0x12,
    507	0x13,
    508	0x14,
    509	0x15,
    510	0x16,
    511	0x17,
    512	0x20,  /* AIF1RX1 */
    513	0x21,
    514	0x22,
    515	0x23,
    516	0x24,
    517	0x25,
    518	0x26,
    519	0x27,
    520	0x28,  /* AIF2RX1 */
    521	0x29,
    522	0x2a,
    523	0x2b,
    524	0x2c,
    525	0x2d,
    526	0x30,  /* AIF3RX1 */
    527	0x31,
    528	0x38,  /* SLIMRX1 */
    529	0x39,
    530	0x3a,
    531	0x3b,
    532	0x3c,
    533	0x3d,
    534	0x3e,
    535	0x3f,
    536	0x50,  /* EQ1 */
    537	0x51,
    538	0x52,
    539	0x53,
    540	0x58,  /* DRC1L */
    541	0x59,
    542	0x5a,
    543	0x5b,
    544	0x60,  /* LHPF1 */
    545	0x61,
    546	0x62,
    547	0x63,
    548	0x68,  /* DSP1.1 */
    549	0x69,
    550	0x6a,
    551	0x6b,
    552	0x6c,
    553	0x6d,
    554	0x70,  /* DSP2.1 */
    555	0x71,
    556	0x72,
    557	0x73,
    558	0x74,
    559	0x75,
    560	0x78,  /* DSP3.1 */
    561	0x79,
    562	0x7a,
    563	0x7b,
    564	0x7c,
    565	0x7d,
    566	0x80,  /* DSP4.1 */
    567	0x81,
    568	0x82,
    569	0x83,
    570	0x84,
    571	0x85,
    572	0x90,  /* ASRC1L */
    573	0x91,
    574	0x92,
    575	0x93,
    576	0xa0,  /* ISRC1INT1 */
    577	0xa1,
    578	0xa2,
    579	0xa3,
    580	0xa4,  /* ISRC1DEC1 */
    581	0xa5,
    582	0xa6,
    583	0xa7,
    584	0xa8,  /* ISRC2DEC1 */
    585	0xa9,
    586	0xaa,
    587	0xab,
    588	0xac,  /* ISRC2INT1 */
    589	0xad,
    590	0xae,
    591	0xaf,
    592	0xb0,  /* ISRC3DEC1 */
    593	0xb1,
    594	0xb2,
    595	0xb3,
    596	0xb4,  /* ISRC3INT1 */
    597	0xb5,
    598	0xb6,
    599	0xb7,
    600};
    601EXPORT_SYMBOL_GPL(arizona_mixer_values);
    602
    603const DECLARE_TLV_DB_SCALE(arizona_mixer_tlv, -3200, 100, 0);
    604EXPORT_SYMBOL_GPL(arizona_mixer_tlv);
    605
    606const char * const arizona_sample_rate_text[ARIZONA_SAMPLE_RATE_ENUM_SIZE] = {
    607	"12kHz", "24kHz", "48kHz", "96kHz", "192kHz",
    608	"11.025kHz", "22.05kHz", "44.1kHz", "88.2kHz", "176.4kHz",
    609	"4kHz", "8kHz", "16kHz", "32kHz",
    610};
    611EXPORT_SYMBOL_GPL(arizona_sample_rate_text);
    612
    613const unsigned int arizona_sample_rate_val[ARIZONA_SAMPLE_RATE_ENUM_SIZE] = {
    614	0x01, 0x02, 0x03, 0x04, 0x05, 0x09, 0x0A, 0x0B, 0x0C, 0x0D,
    615	0x10, 0x11, 0x12, 0x13,
    616};
    617EXPORT_SYMBOL_GPL(arizona_sample_rate_val);
    618
    619const char *arizona_sample_rate_val_to_name(unsigned int rate_val)
    620{
    621	int i;
    622
    623	for (i = 0; i < ARRAY_SIZE(arizona_sample_rate_val); ++i) {
    624		if (arizona_sample_rate_val[i] == rate_val)
    625			return arizona_sample_rate_text[i];
    626	}
    627
    628	return "Illegal";
    629}
    630EXPORT_SYMBOL_GPL(arizona_sample_rate_val_to_name);
    631
    632const char * const arizona_rate_text[ARIZONA_RATE_ENUM_SIZE] = {
    633	"SYNCCLK rate", "8kHz", "16kHz", "ASYNCCLK rate",
    634};
    635EXPORT_SYMBOL_GPL(arizona_rate_text);
    636
    637const unsigned int arizona_rate_val[ARIZONA_RATE_ENUM_SIZE] = {
    638	0, 1, 2, 8,
    639};
    640EXPORT_SYMBOL_GPL(arizona_rate_val);
    641
    642const struct soc_enum arizona_isrc_fsh[] = {
    643	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_1_CTRL_1,
    644			      ARIZONA_ISRC1_FSH_SHIFT, 0xf,
    645			      ARIZONA_RATE_ENUM_SIZE,
    646			      arizona_rate_text, arizona_rate_val),
    647	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_2_CTRL_1,
    648			      ARIZONA_ISRC2_FSH_SHIFT, 0xf,
    649			      ARIZONA_RATE_ENUM_SIZE,
    650			      arizona_rate_text, arizona_rate_val),
    651	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_3_CTRL_1,
    652			      ARIZONA_ISRC3_FSH_SHIFT, 0xf,
    653			      ARIZONA_RATE_ENUM_SIZE,
    654			      arizona_rate_text, arizona_rate_val),
    655};
    656EXPORT_SYMBOL_GPL(arizona_isrc_fsh);
    657
    658const struct soc_enum arizona_isrc_fsl[] = {
    659	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_1_CTRL_2,
    660			      ARIZONA_ISRC1_FSL_SHIFT, 0xf,
    661			      ARIZONA_RATE_ENUM_SIZE,
    662			      arizona_rate_text, arizona_rate_val),
    663	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_2_CTRL_2,
    664			      ARIZONA_ISRC2_FSL_SHIFT, 0xf,
    665			      ARIZONA_RATE_ENUM_SIZE,
    666			      arizona_rate_text, arizona_rate_val),
    667	SOC_VALUE_ENUM_SINGLE(ARIZONA_ISRC_3_CTRL_2,
    668			      ARIZONA_ISRC3_FSL_SHIFT, 0xf,
    669			      ARIZONA_RATE_ENUM_SIZE,
    670			      arizona_rate_text, arizona_rate_val),
    671};
    672EXPORT_SYMBOL_GPL(arizona_isrc_fsl);
    673
    674const struct soc_enum arizona_asrc_rate1 =
    675	SOC_VALUE_ENUM_SINGLE(ARIZONA_ASRC_RATE1,
    676			      ARIZONA_ASRC_RATE1_SHIFT, 0xf,
    677			      ARIZONA_RATE_ENUM_SIZE - 1,
    678			      arizona_rate_text, arizona_rate_val);
    679EXPORT_SYMBOL_GPL(arizona_asrc_rate1);
    680
    681static const char * const arizona_vol_ramp_text[] = {
    682	"0ms/6dB", "0.5ms/6dB", "1ms/6dB", "2ms/6dB", "4ms/6dB", "8ms/6dB",
    683	"15ms/6dB", "30ms/6dB",
    684};
    685
    686SOC_ENUM_SINGLE_DECL(arizona_in_vd_ramp,
    687		     ARIZONA_INPUT_VOLUME_RAMP,
    688		     ARIZONA_IN_VD_RAMP_SHIFT,
    689		     arizona_vol_ramp_text);
    690EXPORT_SYMBOL_GPL(arizona_in_vd_ramp);
    691
    692SOC_ENUM_SINGLE_DECL(arizona_in_vi_ramp,
    693		     ARIZONA_INPUT_VOLUME_RAMP,
    694		     ARIZONA_IN_VI_RAMP_SHIFT,
    695		     arizona_vol_ramp_text);
    696EXPORT_SYMBOL_GPL(arizona_in_vi_ramp);
    697
    698SOC_ENUM_SINGLE_DECL(arizona_out_vd_ramp,
    699		     ARIZONA_OUTPUT_VOLUME_RAMP,
    700		     ARIZONA_OUT_VD_RAMP_SHIFT,
    701		     arizona_vol_ramp_text);
    702EXPORT_SYMBOL_GPL(arizona_out_vd_ramp);
    703
    704SOC_ENUM_SINGLE_DECL(arizona_out_vi_ramp,
    705		     ARIZONA_OUTPUT_VOLUME_RAMP,
    706		     ARIZONA_OUT_VI_RAMP_SHIFT,
    707		     arizona_vol_ramp_text);
    708EXPORT_SYMBOL_GPL(arizona_out_vi_ramp);
    709
    710static const char * const arizona_lhpf_mode_text[] = {
    711	"Low-pass", "High-pass"
    712};
    713
    714SOC_ENUM_SINGLE_DECL(arizona_lhpf1_mode,
    715		     ARIZONA_HPLPF1_1,
    716		     ARIZONA_LHPF1_MODE_SHIFT,
    717		     arizona_lhpf_mode_text);
    718EXPORT_SYMBOL_GPL(arizona_lhpf1_mode);
    719
    720SOC_ENUM_SINGLE_DECL(arizona_lhpf2_mode,
    721		     ARIZONA_HPLPF2_1,
    722		     ARIZONA_LHPF2_MODE_SHIFT,
    723		     arizona_lhpf_mode_text);
    724EXPORT_SYMBOL_GPL(arizona_lhpf2_mode);
    725
    726SOC_ENUM_SINGLE_DECL(arizona_lhpf3_mode,
    727		     ARIZONA_HPLPF3_1,
    728		     ARIZONA_LHPF3_MODE_SHIFT,
    729		     arizona_lhpf_mode_text);
    730EXPORT_SYMBOL_GPL(arizona_lhpf3_mode);
    731
    732SOC_ENUM_SINGLE_DECL(arizona_lhpf4_mode,
    733		     ARIZONA_HPLPF4_1,
    734		     ARIZONA_LHPF4_MODE_SHIFT,
    735		     arizona_lhpf_mode_text);
    736EXPORT_SYMBOL_GPL(arizona_lhpf4_mode);
    737
    738static const char * const arizona_ng_hold_text[] = {
    739	"30ms", "120ms", "250ms", "500ms",
    740};
    741
    742SOC_ENUM_SINGLE_DECL(arizona_ng_hold,
    743		     ARIZONA_NOISE_GATE_CONTROL,
    744		     ARIZONA_NGATE_HOLD_SHIFT,
    745		     arizona_ng_hold_text);
    746EXPORT_SYMBOL_GPL(arizona_ng_hold);
    747
    748static const char * const arizona_in_hpf_cut_text[] = {
    749	"2.5Hz", "5Hz", "10Hz", "20Hz", "40Hz"
    750};
    751
    752SOC_ENUM_SINGLE_DECL(arizona_in_hpf_cut_enum,
    753		     ARIZONA_HPF_CONTROL,
    754		     ARIZONA_IN_HPF_CUT_SHIFT,
    755		     arizona_in_hpf_cut_text);
    756EXPORT_SYMBOL_GPL(arizona_in_hpf_cut_enum);
    757
    758static const char * const arizona_in_dmic_osr_text[] = {
    759	"1.536MHz", "3.072MHz", "6.144MHz", "768kHz",
    760};
    761
    762const struct soc_enum arizona_in_dmic_osr[] = {
    763	SOC_ENUM_SINGLE(ARIZONA_IN1L_CONTROL, ARIZONA_IN1_OSR_SHIFT,
    764			ARRAY_SIZE(arizona_in_dmic_osr_text),
    765			arizona_in_dmic_osr_text),
    766	SOC_ENUM_SINGLE(ARIZONA_IN2L_CONTROL, ARIZONA_IN2_OSR_SHIFT,
    767			ARRAY_SIZE(arizona_in_dmic_osr_text),
    768			arizona_in_dmic_osr_text),
    769	SOC_ENUM_SINGLE(ARIZONA_IN3L_CONTROL, ARIZONA_IN3_OSR_SHIFT,
    770			ARRAY_SIZE(arizona_in_dmic_osr_text),
    771			arizona_in_dmic_osr_text),
    772	SOC_ENUM_SINGLE(ARIZONA_IN4L_CONTROL, ARIZONA_IN4_OSR_SHIFT,
    773			ARRAY_SIZE(arizona_in_dmic_osr_text),
    774			arizona_in_dmic_osr_text),
    775};
    776EXPORT_SYMBOL_GPL(arizona_in_dmic_osr);
    777
    778static const char * const arizona_anc_input_src_text[] = {
    779	"None", "IN1", "IN2", "IN3", "IN4",
    780};
    781
    782static const char * const arizona_anc_channel_src_text[] = {
    783	"None", "Left", "Right", "Combine",
    784};
    785
    786const struct soc_enum arizona_anc_input_src[] = {
    787	SOC_ENUM_SINGLE(ARIZONA_ANC_SRC,
    788			ARIZONA_IN_RXANCL_SEL_SHIFT,
    789			ARRAY_SIZE(arizona_anc_input_src_text),
    790			arizona_anc_input_src_text),
    791	SOC_ENUM_SINGLE(ARIZONA_FCL_ADC_REFORMATTER_CONTROL,
    792			ARIZONA_FCL_MIC_MODE_SEL_SHIFT,
    793			ARRAY_SIZE(arizona_anc_channel_src_text),
    794			arizona_anc_channel_src_text),
    795	SOC_ENUM_SINGLE(ARIZONA_ANC_SRC,
    796			ARIZONA_IN_RXANCR_SEL_SHIFT,
    797			ARRAY_SIZE(arizona_anc_input_src_text),
    798			arizona_anc_input_src_text),
    799	SOC_ENUM_SINGLE(ARIZONA_FCR_ADC_REFORMATTER_CONTROL,
    800			ARIZONA_FCR_MIC_MODE_SEL_SHIFT,
    801			ARRAY_SIZE(arizona_anc_channel_src_text),
    802			arizona_anc_channel_src_text),
    803};
    804EXPORT_SYMBOL_GPL(arizona_anc_input_src);
    805
    806static const char * const arizona_anc_ng_texts[] = {
    807	"None",
    808	"Internal",
    809	"External",
    810};
    811
    812SOC_ENUM_SINGLE_DECL(arizona_anc_ng_enum, SND_SOC_NOPM, 0,
    813		     arizona_anc_ng_texts);
    814EXPORT_SYMBOL_GPL(arizona_anc_ng_enum);
    815
    816static const char * const arizona_output_anc_src_text[] = {
    817	"None", "RXANCL", "RXANCR",
    818};
    819
    820const struct soc_enum arizona_output_anc_src[] = {
    821	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_1L,
    822			ARIZONA_OUT1L_ANC_SRC_SHIFT,
    823			ARRAY_SIZE(arizona_output_anc_src_text),
    824			arizona_output_anc_src_text),
    825	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_1R,
    826			ARIZONA_OUT1R_ANC_SRC_SHIFT,
    827			ARRAY_SIZE(arizona_output_anc_src_text),
    828			arizona_output_anc_src_text),
    829	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_2L,
    830			ARIZONA_OUT2L_ANC_SRC_SHIFT,
    831			ARRAY_SIZE(arizona_output_anc_src_text),
    832			arizona_output_anc_src_text),
    833	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_2R,
    834			ARIZONA_OUT2R_ANC_SRC_SHIFT,
    835			ARRAY_SIZE(arizona_output_anc_src_text),
    836			arizona_output_anc_src_text),
    837	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_3L,
    838			ARIZONA_OUT3L_ANC_SRC_SHIFT,
    839			ARRAY_SIZE(arizona_output_anc_src_text),
    840			arizona_output_anc_src_text),
    841	SOC_ENUM_SINGLE(ARIZONA_DAC_VOLUME_LIMIT_3R,
    842			ARIZONA_OUT3R_ANC_SRC_SHIFT,
    843			ARRAY_SIZE(arizona_output_anc_src_text),
    844			arizona_output_anc_src_text),
    845	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_4L,
    846			ARIZONA_OUT4L_ANC_SRC_SHIFT,
    847			ARRAY_SIZE(arizona_output_anc_src_text),
    848			arizona_output_anc_src_text),
    849	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_4R,
    850			ARIZONA_OUT4R_ANC_SRC_SHIFT,
    851			ARRAY_SIZE(arizona_output_anc_src_text),
    852			arizona_output_anc_src_text),
    853	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_5L,
    854			ARIZONA_OUT5L_ANC_SRC_SHIFT,
    855			ARRAY_SIZE(arizona_output_anc_src_text),
    856			arizona_output_anc_src_text),
    857	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_5R,
    858			ARIZONA_OUT5R_ANC_SRC_SHIFT,
    859			ARRAY_SIZE(arizona_output_anc_src_text),
    860			arizona_output_anc_src_text),
    861	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_6L,
    862			ARIZONA_OUT6L_ANC_SRC_SHIFT,
    863			ARRAY_SIZE(arizona_output_anc_src_text),
    864			arizona_output_anc_src_text),
    865	SOC_ENUM_SINGLE(ARIZONA_OUTPUT_PATH_CONFIG_6R,
    866			ARIZONA_OUT6R_ANC_SRC_SHIFT,
    867			ARRAY_SIZE(arizona_output_anc_src_text),
    868			arizona_output_anc_src_text),
    869};
    870EXPORT_SYMBOL_GPL(arizona_output_anc_src);
    871
    872const struct snd_kcontrol_new arizona_voice_trigger_switch[] = {
    873	SOC_DAPM_SINGLE("Switch", SND_SOC_NOPM, 0, 1, 0),
    874	SOC_DAPM_SINGLE("Switch", SND_SOC_NOPM, 1, 1, 0),
    875	SOC_DAPM_SINGLE("Switch", SND_SOC_NOPM, 2, 1, 0),
    876	SOC_DAPM_SINGLE("Switch", SND_SOC_NOPM, 3, 1, 0),
    877};
    878EXPORT_SYMBOL_GPL(arizona_voice_trigger_switch);
    879
    880static void arizona_in_set_vu(struct snd_soc_component *component, int ena)
    881{
    882	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    883	unsigned int val;
    884	int i;
    885
    886	if (ena)
    887		val = ARIZONA_IN_VU;
    888	else
    889		val = 0;
    890
    891	for (i = 0; i < priv->num_inputs; i++)
    892		snd_soc_component_update_bits(component,
    893				    ARIZONA_ADC_DIGITAL_VOLUME_1L + (i * 4),
    894				    ARIZONA_IN_VU, val);
    895}
    896
    897bool arizona_input_analog(struct snd_soc_component *component, int shift)
    898{
    899	unsigned int reg = ARIZONA_IN1L_CONTROL + ((shift / 2) * 8);
    900	unsigned int val = snd_soc_component_read(component, reg);
    901
    902	return !(val & ARIZONA_IN1_MODE_MASK);
    903}
    904EXPORT_SYMBOL_GPL(arizona_input_analog);
    905
    906int arizona_in_ev(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol,
    907		  int event)
    908{
    909	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
    910	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    911	unsigned int reg;
    912
    913	if (w->shift % 2)
    914		reg = ARIZONA_ADC_DIGITAL_VOLUME_1L + ((w->shift / 2) * 8);
    915	else
    916		reg = ARIZONA_ADC_DIGITAL_VOLUME_1R + ((w->shift / 2) * 8);
    917
    918	switch (event) {
    919	case SND_SOC_DAPM_PRE_PMU:
    920		priv->in_pending++;
    921		break;
    922	case SND_SOC_DAPM_POST_PMU:
    923		snd_soc_component_update_bits(component, reg,
    924					      ARIZONA_IN1L_MUTE, 0);
    925
    926		/* If this is the last input pending then allow VU */
    927		priv->in_pending--;
    928		if (priv->in_pending == 0) {
    929			msleep(1);
    930			arizona_in_set_vu(component, 1);
    931		}
    932		break;
    933	case SND_SOC_DAPM_PRE_PMD:
    934		snd_soc_component_update_bits(component, reg,
    935				    ARIZONA_IN1L_MUTE | ARIZONA_IN_VU,
    936				    ARIZONA_IN1L_MUTE | ARIZONA_IN_VU);
    937		break;
    938	case SND_SOC_DAPM_POST_PMD:
    939		/* Disable volume updates if no inputs are enabled */
    940		reg = snd_soc_component_read(component, ARIZONA_INPUT_ENABLES);
    941		if (reg == 0)
    942			arizona_in_set_vu(component, 0);
    943		break;
    944	default:
    945		break;
    946	}
    947
    948	return 0;
    949}
    950EXPORT_SYMBOL_GPL(arizona_in_ev);
    951
    952int arizona_out_ev(struct snd_soc_dapm_widget *w,
    953		   struct snd_kcontrol *kcontrol,
    954		   int event)
    955{
    956	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
    957	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
    958	struct arizona *arizona = priv->arizona;
    959
    960	switch (event) {
    961	case SND_SOC_DAPM_PRE_PMU:
    962		switch (w->shift) {
    963		case ARIZONA_OUT1L_ENA_SHIFT:
    964		case ARIZONA_OUT1R_ENA_SHIFT:
    965		case ARIZONA_OUT2L_ENA_SHIFT:
    966		case ARIZONA_OUT2R_ENA_SHIFT:
    967		case ARIZONA_OUT3L_ENA_SHIFT:
    968		case ARIZONA_OUT3R_ENA_SHIFT:
    969			priv->out_up_pending++;
    970			priv->out_up_delay += 17;
    971			break;
    972		case ARIZONA_OUT4L_ENA_SHIFT:
    973		case ARIZONA_OUT4R_ENA_SHIFT:
    974			priv->out_up_pending++;
    975			switch (arizona->type) {
    976			case WM5102:
    977			case WM8997:
    978				break;
    979			default:
    980				priv->out_up_delay += 10;
    981				break;
    982			}
    983			break;
    984		default:
    985			break;
    986		}
    987		break;
    988	case SND_SOC_DAPM_POST_PMU:
    989		switch (w->shift) {
    990		case ARIZONA_OUT1L_ENA_SHIFT:
    991		case ARIZONA_OUT1R_ENA_SHIFT:
    992		case ARIZONA_OUT2L_ENA_SHIFT:
    993		case ARIZONA_OUT2R_ENA_SHIFT:
    994		case ARIZONA_OUT3L_ENA_SHIFT:
    995		case ARIZONA_OUT3R_ENA_SHIFT:
    996		case ARIZONA_OUT4L_ENA_SHIFT:
    997		case ARIZONA_OUT4R_ENA_SHIFT:
    998			priv->out_up_pending--;
    999			if (!priv->out_up_pending && priv->out_up_delay) {
   1000				dev_dbg(component->dev, "Power up delay: %d\n",
   1001					priv->out_up_delay);
   1002				msleep(priv->out_up_delay);
   1003				priv->out_up_delay = 0;
   1004			}
   1005			break;
   1006
   1007		default:
   1008			break;
   1009		}
   1010		break;
   1011	case SND_SOC_DAPM_PRE_PMD:
   1012		switch (w->shift) {
   1013		case ARIZONA_OUT1L_ENA_SHIFT:
   1014		case ARIZONA_OUT1R_ENA_SHIFT:
   1015		case ARIZONA_OUT2L_ENA_SHIFT:
   1016		case ARIZONA_OUT2R_ENA_SHIFT:
   1017		case ARIZONA_OUT3L_ENA_SHIFT:
   1018		case ARIZONA_OUT3R_ENA_SHIFT:
   1019			priv->out_down_pending++;
   1020			priv->out_down_delay++;
   1021			break;
   1022		case ARIZONA_OUT4L_ENA_SHIFT:
   1023		case ARIZONA_OUT4R_ENA_SHIFT:
   1024			priv->out_down_pending++;
   1025			switch (arizona->type) {
   1026			case WM5102:
   1027			case WM8997:
   1028				break;
   1029			case WM8998:
   1030			case WM1814:
   1031				priv->out_down_delay += 5;
   1032				break;
   1033			default:
   1034				priv->out_down_delay++;
   1035				break;
   1036			}
   1037			break;
   1038		default:
   1039			break;
   1040		}
   1041		break;
   1042	case SND_SOC_DAPM_POST_PMD:
   1043		switch (w->shift) {
   1044		case ARIZONA_OUT1L_ENA_SHIFT:
   1045		case ARIZONA_OUT1R_ENA_SHIFT:
   1046		case ARIZONA_OUT2L_ENA_SHIFT:
   1047		case ARIZONA_OUT2R_ENA_SHIFT:
   1048		case ARIZONA_OUT3L_ENA_SHIFT:
   1049		case ARIZONA_OUT3R_ENA_SHIFT:
   1050		case ARIZONA_OUT4L_ENA_SHIFT:
   1051		case ARIZONA_OUT4R_ENA_SHIFT:
   1052			priv->out_down_pending--;
   1053			if (!priv->out_down_pending && priv->out_down_delay) {
   1054				dev_dbg(component->dev, "Power down delay: %d\n",
   1055					priv->out_down_delay);
   1056				msleep(priv->out_down_delay);
   1057				priv->out_down_delay = 0;
   1058			}
   1059			break;
   1060		default:
   1061			break;
   1062		}
   1063		break;
   1064	default:
   1065		break;
   1066	}
   1067
   1068	return 0;
   1069}
   1070EXPORT_SYMBOL_GPL(arizona_out_ev);
   1071
   1072int arizona_hp_ev(struct snd_soc_dapm_widget *w, struct snd_kcontrol *kcontrol,
   1073		  int event)
   1074{
   1075	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
   1076	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1077	struct arizona *arizona = priv->arizona;
   1078	unsigned int mask = 1 << w->shift;
   1079	unsigned int val;
   1080
   1081	switch (event) {
   1082	case SND_SOC_DAPM_POST_PMU:
   1083		val = mask;
   1084		break;
   1085	case SND_SOC_DAPM_PRE_PMD:
   1086		val = 0;
   1087		break;
   1088	case SND_SOC_DAPM_PRE_PMU:
   1089	case SND_SOC_DAPM_POST_PMD:
   1090		return arizona_out_ev(w, kcontrol, event);
   1091	default:
   1092		return -EINVAL;
   1093	}
   1094
   1095	/* Store the desired state for the HP outputs */
   1096	priv->arizona->hp_ena &= ~mask;
   1097	priv->arizona->hp_ena |= val;
   1098
   1099	/* Force off if HPDET clamp is active */
   1100	if (priv->arizona->hpdet_clamp)
   1101		val = 0;
   1102
   1103	regmap_update_bits_async(arizona->regmap, ARIZONA_OUTPUT_ENABLES_1,
   1104				 mask, val);
   1105
   1106	return arizona_out_ev(w, kcontrol, event);
   1107}
   1108EXPORT_SYMBOL_GPL(arizona_hp_ev);
   1109
   1110static int arizona_dvfs_enable(struct snd_soc_component *component)
   1111{
   1112	const struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1113	struct arizona *arizona = priv->arizona;
   1114	int ret;
   1115
   1116	ret = regulator_set_voltage(arizona->dcvdd, 1800000, 1800000);
   1117	if (ret) {
   1118		dev_err(component->dev, "Failed to boost DCVDD: %d\n", ret);
   1119		return ret;
   1120	}
   1121
   1122	ret = regmap_update_bits(arizona->regmap,
   1123				 ARIZONA_DYNAMIC_FREQUENCY_SCALING_1,
   1124				 ARIZONA_SUBSYS_MAX_FREQ,
   1125				 ARIZONA_SUBSYS_MAX_FREQ);
   1126	if (ret) {
   1127		dev_err(component->dev, "Failed to enable subsys max: %d\n", ret);
   1128		regulator_set_voltage(arizona->dcvdd, 1200000, 1800000);
   1129		return ret;
   1130	}
   1131
   1132	return 0;
   1133}
   1134
   1135static int arizona_dvfs_disable(struct snd_soc_component *component)
   1136{
   1137	const struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1138	struct arizona *arizona = priv->arizona;
   1139	int ret;
   1140
   1141	ret = regmap_update_bits(arizona->regmap,
   1142				 ARIZONA_DYNAMIC_FREQUENCY_SCALING_1,
   1143				 ARIZONA_SUBSYS_MAX_FREQ, 0);
   1144	if (ret) {
   1145		dev_err(component->dev, "Failed to disable subsys max: %d\n", ret);
   1146		return ret;
   1147	}
   1148
   1149	ret = regulator_set_voltage(arizona->dcvdd, 1200000, 1800000);
   1150	if (ret) {
   1151		dev_err(component->dev, "Failed to unboost DCVDD: %d\n", ret);
   1152		return ret;
   1153	}
   1154
   1155	return 0;
   1156}
   1157
   1158int arizona_dvfs_up(struct snd_soc_component *component, unsigned int flags)
   1159{
   1160	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1161	int ret = 0;
   1162
   1163	mutex_lock(&priv->dvfs_lock);
   1164
   1165	if (!priv->dvfs_cached && !priv->dvfs_reqs) {
   1166		ret = arizona_dvfs_enable(component);
   1167		if (ret)
   1168			goto err;
   1169	}
   1170
   1171	priv->dvfs_reqs |= flags;
   1172err:
   1173	mutex_unlock(&priv->dvfs_lock);
   1174	return ret;
   1175}
   1176EXPORT_SYMBOL_GPL(arizona_dvfs_up);
   1177
   1178int arizona_dvfs_down(struct snd_soc_component *component, unsigned int flags)
   1179{
   1180	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1181	unsigned int old_reqs;
   1182	int ret = 0;
   1183
   1184	mutex_lock(&priv->dvfs_lock);
   1185
   1186	old_reqs = priv->dvfs_reqs;
   1187	priv->dvfs_reqs &= ~flags;
   1188
   1189	if (!priv->dvfs_cached && old_reqs && !priv->dvfs_reqs)
   1190		ret = arizona_dvfs_disable(component);
   1191
   1192	mutex_unlock(&priv->dvfs_lock);
   1193	return ret;
   1194}
   1195EXPORT_SYMBOL_GPL(arizona_dvfs_down);
   1196
   1197int arizona_dvfs_sysclk_ev(struct snd_soc_dapm_widget *w,
   1198			   struct snd_kcontrol *kcontrol, int event)
   1199{
   1200	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
   1201	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1202	int ret = 0;
   1203
   1204	mutex_lock(&priv->dvfs_lock);
   1205
   1206	switch (event) {
   1207	case SND_SOC_DAPM_POST_PMU:
   1208		if (priv->dvfs_reqs)
   1209			ret = arizona_dvfs_enable(component);
   1210
   1211		priv->dvfs_cached = false;
   1212		break;
   1213	case SND_SOC_DAPM_PRE_PMD:
   1214		/* We must ensure DVFS is disabled before the codec goes into
   1215		 * suspend so that we are never in an illegal state of DVFS
   1216		 * enabled without enough DCVDD
   1217		 */
   1218		priv->dvfs_cached = true;
   1219
   1220		if (priv->dvfs_reqs)
   1221			ret = arizona_dvfs_disable(component);
   1222		break;
   1223	default:
   1224		break;
   1225	}
   1226
   1227	mutex_unlock(&priv->dvfs_lock);
   1228	return ret;
   1229}
   1230EXPORT_SYMBOL_GPL(arizona_dvfs_sysclk_ev);
   1231
   1232void arizona_init_dvfs(struct arizona_priv *priv)
   1233{
   1234	mutex_init(&priv->dvfs_lock);
   1235}
   1236EXPORT_SYMBOL_GPL(arizona_init_dvfs);
   1237
   1238int arizona_anc_ev(struct snd_soc_dapm_widget *w,
   1239		   struct snd_kcontrol *kcontrol,
   1240		   int event)
   1241{
   1242	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
   1243	unsigned int val;
   1244
   1245	switch (event) {
   1246	case SND_SOC_DAPM_POST_PMU:
   1247		val = 1 << w->shift;
   1248		break;
   1249	case SND_SOC_DAPM_PRE_PMD:
   1250		val = 1 << (w->shift + 1);
   1251		break;
   1252	default:
   1253		return 0;
   1254	}
   1255
   1256	snd_soc_component_write(component, ARIZONA_CLOCK_CONTROL, val);
   1257
   1258	return 0;
   1259}
   1260EXPORT_SYMBOL_GPL(arizona_anc_ev);
   1261
   1262static unsigned int arizona_opclk_ref_48k_rates[] = {
   1263	6144000,
   1264	12288000,
   1265	24576000,
   1266	49152000,
   1267};
   1268
   1269static unsigned int arizona_opclk_ref_44k1_rates[] = {
   1270	5644800,
   1271	11289600,
   1272	22579200,
   1273	45158400,
   1274};
   1275
   1276static int arizona_set_opclk(struct snd_soc_component *component,
   1277			     unsigned int clk, unsigned int freq)
   1278{
   1279	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1280	unsigned int reg;
   1281	unsigned int *rates;
   1282	int ref, div, refclk;
   1283
   1284	switch (clk) {
   1285	case ARIZONA_CLK_OPCLK:
   1286		reg = ARIZONA_OUTPUT_SYSTEM_CLOCK;
   1287		refclk = priv->sysclk;
   1288		break;
   1289	case ARIZONA_CLK_ASYNC_OPCLK:
   1290		reg = ARIZONA_OUTPUT_ASYNC_CLOCK;
   1291		refclk = priv->asyncclk;
   1292		break;
   1293	default:
   1294		return -EINVAL;
   1295	}
   1296
   1297	if (refclk % 8000)
   1298		rates = arizona_opclk_ref_44k1_rates;
   1299	else
   1300		rates = arizona_opclk_ref_48k_rates;
   1301
   1302	for (ref = 0; ref < ARRAY_SIZE(arizona_opclk_ref_48k_rates) &&
   1303	     rates[ref] <= refclk; ref++) {
   1304		div = 1;
   1305		while (rates[ref] / div >= freq && div < 32) {
   1306			if (rates[ref] / div == freq) {
   1307				dev_dbg(component->dev, "Configured %dHz OPCLK\n",
   1308					freq);
   1309				snd_soc_component_update_bits(component, reg,
   1310						    ARIZONA_OPCLK_DIV_MASK |
   1311						    ARIZONA_OPCLK_SEL_MASK,
   1312						    (div <<
   1313						     ARIZONA_OPCLK_DIV_SHIFT) |
   1314						    ref);
   1315				return 0;
   1316			}
   1317			div++;
   1318		}
   1319	}
   1320
   1321	dev_err(component->dev, "Unable to generate %dHz OPCLK\n", freq);
   1322	return -EINVAL;
   1323}
   1324
   1325int arizona_clk_ev(struct snd_soc_dapm_widget *w,
   1326		   struct snd_kcontrol *kcontrol, int event)
   1327{
   1328	struct snd_soc_component *component = snd_soc_dapm_to_component(w->dapm);
   1329	struct arizona *arizona = dev_get_drvdata(component->dev->parent);
   1330	unsigned int val;
   1331	int clk_idx;
   1332	int ret;
   1333
   1334	ret = regmap_read(arizona->regmap, w->reg, &val);
   1335	if (ret) {
   1336		dev_err(component->dev, "Failed to check clock source: %d\n", ret);
   1337		return ret;
   1338	}
   1339
   1340	val = (val & ARIZONA_SYSCLK_SRC_MASK) >> ARIZONA_SYSCLK_SRC_SHIFT;
   1341
   1342	switch (val) {
   1343	case ARIZONA_CLK_SRC_MCLK1:
   1344		clk_idx = ARIZONA_MCLK1;
   1345		break;
   1346	case ARIZONA_CLK_SRC_MCLK2:
   1347		clk_idx = ARIZONA_MCLK2;
   1348		break;
   1349	default:
   1350		return 0;
   1351	}
   1352
   1353	switch (event) {
   1354	case SND_SOC_DAPM_PRE_PMU:
   1355		return clk_prepare_enable(arizona->mclk[clk_idx]);
   1356	case SND_SOC_DAPM_POST_PMD:
   1357		clk_disable_unprepare(arizona->mclk[clk_idx]);
   1358		return 0;
   1359	default:
   1360		return 0;
   1361	}
   1362}
   1363EXPORT_SYMBOL_GPL(arizona_clk_ev);
   1364
   1365int arizona_set_sysclk(struct snd_soc_component *component, int clk_id,
   1366		       int source, unsigned int freq, int dir)
   1367{
   1368	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1369	struct arizona *arizona = priv->arizona;
   1370	char *name;
   1371	unsigned int reg;
   1372	unsigned int mask = ARIZONA_SYSCLK_FREQ_MASK | ARIZONA_SYSCLK_SRC_MASK;
   1373	unsigned int val = source << ARIZONA_SYSCLK_SRC_SHIFT;
   1374	int *clk;
   1375
   1376	switch (clk_id) {
   1377	case ARIZONA_CLK_SYSCLK:
   1378		name = "SYSCLK";
   1379		reg = ARIZONA_SYSTEM_CLOCK_1;
   1380		clk = &priv->sysclk;
   1381		mask |= ARIZONA_SYSCLK_FRAC;
   1382		break;
   1383	case ARIZONA_CLK_ASYNCCLK:
   1384		name = "ASYNCCLK";
   1385		reg = ARIZONA_ASYNC_CLOCK_1;
   1386		clk = &priv->asyncclk;
   1387		break;
   1388	case ARIZONA_CLK_OPCLK:
   1389	case ARIZONA_CLK_ASYNC_OPCLK:
   1390		return arizona_set_opclk(component, clk_id, freq);
   1391	default:
   1392		return -EINVAL;
   1393	}
   1394
   1395	switch (freq) {
   1396	case  5644800:
   1397	case  6144000:
   1398		break;
   1399	case 11289600:
   1400	case 12288000:
   1401		val |= ARIZONA_CLK_12MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1402		break;
   1403	case 22579200:
   1404	case 24576000:
   1405		val |= ARIZONA_CLK_24MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1406		break;
   1407	case 45158400:
   1408	case 49152000:
   1409		val |= ARIZONA_CLK_49MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1410		break;
   1411	case 67737600:
   1412	case 73728000:
   1413		val |= ARIZONA_CLK_73MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1414		break;
   1415	case 90316800:
   1416	case 98304000:
   1417		val |= ARIZONA_CLK_98MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1418		break;
   1419	case 135475200:
   1420	case 147456000:
   1421		val |= ARIZONA_CLK_147MHZ << ARIZONA_SYSCLK_FREQ_SHIFT;
   1422		break;
   1423	case 0:
   1424		dev_dbg(arizona->dev, "%s cleared\n", name);
   1425		*clk = freq;
   1426		return 0;
   1427	default:
   1428		return -EINVAL;
   1429	}
   1430
   1431	*clk = freq;
   1432
   1433	if (freq % 6144000)
   1434		val |= ARIZONA_SYSCLK_FRAC;
   1435
   1436	dev_dbg(arizona->dev, "%s set to %uHz", name, freq);
   1437
   1438	return regmap_update_bits(arizona->regmap, reg, mask, val);
   1439}
   1440EXPORT_SYMBOL_GPL(arizona_set_sysclk);
   1441
   1442static int arizona_set_fmt(struct snd_soc_dai *dai, unsigned int fmt)
   1443{
   1444	struct snd_soc_component *component = dai->component;
   1445	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1446	struct arizona *arizona = priv->arizona;
   1447	int lrclk, bclk, mode, base;
   1448
   1449	base = dai->driver->base;
   1450
   1451	lrclk = 0;
   1452	bclk = 0;
   1453
   1454	switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
   1455	case SND_SOC_DAIFMT_DSP_A:
   1456		mode = ARIZONA_FMT_DSP_MODE_A;
   1457		break;
   1458	case SND_SOC_DAIFMT_DSP_B:
   1459		if ((fmt & SND_SOC_DAIFMT_MASTER_MASK)
   1460				!= SND_SOC_DAIFMT_CBM_CFM) {
   1461			arizona_aif_err(dai, "DSP_B not valid in slave mode\n");
   1462			return -EINVAL;
   1463		}
   1464		mode = ARIZONA_FMT_DSP_MODE_B;
   1465		break;
   1466	case SND_SOC_DAIFMT_I2S:
   1467		mode = ARIZONA_FMT_I2S_MODE;
   1468		break;
   1469	case SND_SOC_DAIFMT_LEFT_J:
   1470		if ((fmt & SND_SOC_DAIFMT_MASTER_MASK)
   1471				!= SND_SOC_DAIFMT_CBM_CFM) {
   1472			arizona_aif_err(dai, "LEFT_J not valid in slave mode\n");
   1473			return -EINVAL;
   1474		}
   1475		mode = ARIZONA_FMT_LEFT_JUSTIFIED_MODE;
   1476		break;
   1477	default:
   1478		arizona_aif_err(dai, "Unsupported DAI format %d\n",
   1479				fmt & SND_SOC_DAIFMT_FORMAT_MASK);
   1480		return -EINVAL;
   1481	}
   1482
   1483	switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) {
   1484	case SND_SOC_DAIFMT_CBS_CFS:
   1485		break;
   1486	case SND_SOC_DAIFMT_CBS_CFM:
   1487		lrclk |= ARIZONA_AIF1TX_LRCLK_MSTR;
   1488		break;
   1489	case SND_SOC_DAIFMT_CBM_CFS:
   1490		bclk |= ARIZONA_AIF1_BCLK_MSTR;
   1491		break;
   1492	case SND_SOC_DAIFMT_CBM_CFM:
   1493		bclk |= ARIZONA_AIF1_BCLK_MSTR;
   1494		lrclk |= ARIZONA_AIF1TX_LRCLK_MSTR;
   1495		break;
   1496	default:
   1497		arizona_aif_err(dai, "Unsupported master mode %d\n",
   1498				fmt & SND_SOC_DAIFMT_MASTER_MASK);
   1499		return -EINVAL;
   1500	}
   1501
   1502	switch (fmt & SND_SOC_DAIFMT_INV_MASK) {
   1503	case SND_SOC_DAIFMT_NB_NF:
   1504		break;
   1505	case SND_SOC_DAIFMT_IB_IF:
   1506		bclk |= ARIZONA_AIF1_BCLK_INV;
   1507		lrclk |= ARIZONA_AIF1TX_LRCLK_INV;
   1508		break;
   1509	case SND_SOC_DAIFMT_IB_NF:
   1510		bclk |= ARIZONA_AIF1_BCLK_INV;
   1511		break;
   1512	case SND_SOC_DAIFMT_NB_IF:
   1513		lrclk |= ARIZONA_AIF1TX_LRCLK_INV;
   1514		break;
   1515	default:
   1516		return -EINVAL;
   1517	}
   1518
   1519	regmap_update_bits_async(arizona->regmap, base + ARIZONA_AIF_BCLK_CTRL,
   1520				 ARIZONA_AIF1_BCLK_INV |
   1521				 ARIZONA_AIF1_BCLK_MSTR,
   1522				 bclk);
   1523	regmap_update_bits_async(arizona->regmap, base + ARIZONA_AIF_TX_PIN_CTRL,
   1524				 ARIZONA_AIF1TX_LRCLK_INV |
   1525				 ARIZONA_AIF1TX_LRCLK_MSTR, lrclk);
   1526	regmap_update_bits_async(arizona->regmap,
   1527				 base + ARIZONA_AIF_RX_PIN_CTRL,
   1528				 ARIZONA_AIF1RX_LRCLK_INV |
   1529				 ARIZONA_AIF1RX_LRCLK_MSTR, lrclk);
   1530	regmap_update_bits(arizona->regmap, base + ARIZONA_AIF_FORMAT,
   1531			   ARIZONA_AIF1_FMT_MASK, mode);
   1532
   1533	return 0;
   1534}
   1535
   1536static const int arizona_48k_bclk_rates[] = {
   1537	-1,
   1538	48000,
   1539	64000,
   1540	96000,
   1541	128000,
   1542	192000,
   1543	256000,
   1544	384000,
   1545	512000,
   1546	768000,
   1547	1024000,
   1548	1536000,
   1549	2048000,
   1550	3072000,
   1551	4096000,
   1552	6144000,
   1553	8192000,
   1554	12288000,
   1555	24576000,
   1556};
   1557
   1558static const int arizona_44k1_bclk_rates[] = {
   1559	-1,
   1560	44100,
   1561	58800,
   1562	88200,
   1563	117600,
   1564	177640,
   1565	235200,
   1566	352800,
   1567	470400,
   1568	705600,
   1569	940800,
   1570	1411200,
   1571	1881600,
   1572	2822400,
   1573	3763200,
   1574	5644800,
   1575	7526400,
   1576	11289600,
   1577	22579200,
   1578};
   1579
   1580static const unsigned int arizona_sr_vals[] = {
   1581	0,
   1582	12000,
   1583	24000,
   1584	48000,
   1585	96000,
   1586	192000,
   1587	384000,
   1588	768000,
   1589	0,
   1590	11025,
   1591	22050,
   1592	44100,
   1593	88200,
   1594	176400,
   1595	352800,
   1596	705600,
   1597	4000,
   1598	8000,
   1599	16000,
   1600	32000,
   1601	64000,
   1602	128000,
   1603	256000,
   1604	512000,
   1605};
   1606
   1607#define ARIZONA_48K_RATE_MASK	0x0F003E
   1608#define ARIZONA_44K1_RATE_MASK	0x003E00
   1609#define ARIZONA_RATE_MASK	(ARIZONA_48K_RATE_MASK | ARIZONA_44K1_RATE_MASK)
   1610
   1611static const struct snd_pcm_hw_constraint_list arizona_constraint = {
   1612	.count	= ARRAY_SIZE(arizona_sr_vals),
   1613	.list	= arizona_sr_vals,
   1614};
   1615
   1616static int arizona_startup(struct snd_pcm_substream *substream,
   1617			   struct snd_soc_dai *dai)
   1618{
   1619	struct snd_soc_component *component = dai->component;
   1620	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1621	struct arizona_dai_priv *dai_priv = &priv->dai[dai->id - 1];
   1622	unsigned int base_rate;
   1623
   1624	if (!substream->runtime)
   1625		return 0;
   1626
   1627	switch (dai_priv->clk) {
   1628	case ARIZONA_CLK_SYSCLK:
   1629		base_rate = priv->sysclk;
   1630		break;
   1631	case ARIZONA_CLK_ASYNCCLK:
   1632		base_rate = priv->asyncclk;
   1633		break;
   1634	default:
   1635		return 0;
   1636	}
   1637
   1638	if (base_rate == 0)
   1639		dai_priv->constraint.mask = ARIZONA_RATE_MASK;
   1640	else if (base_rate % 8000)
   1641		dai_priv->constraint.mask = ARIZONA_44K1_RATE_MASK;
   1642	else
   1643		dai_priv->constraint.mask = ARIZONA_48K_RATE_MASK;
   1644
   1645	return snd_pcm_hw_constraint_list(substream->runtime, 0,
   1646					  SNDRV_PCM_HW_PARAM_RATE,
   1647					  &dai_priv->constraint);
   1648}
   1649
   1650static void arizona_wm5102_set_dac_comp(struct snd_soc_component *component,
   1651					unsigned int rate)
   1652{
   1653	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1654	struct arizona *arizona = priv->arizona;
   1655	struct reg_sequence dac_comp[] = {
   1656		{ 0x80, 0x3 },
   1657		{ ARIZONA_DAC_COMP_1, 0 },
   1658		{ ARIZONA_DAC_COMP_2, 0 },
   1659		{ 0x80, 0x0 },
   1660	};
   1661
   1662	mutex_lock(&arizona->dac_comp_lock);
   1663
   1664	dac_comp[1].def = arizona->dac_comp_coeff;
   1665	if (rate >= 176400)
   1666		dac_comp[2].def = arizona->dac_comp_enabled;
   1667
   1668	mutex_unlock(&arizona->dac_comp_lock);
   1669
   1670	regmap_multi_reg_write(arizona->regmap,
   1671			       dac_comp,
   1672			       ARRAY_SIZE(dac_comp));
   1673}
   1674
   1675static int arizona_hw_params_rate(struct snd_pcm_substream *substream,
   1676				  struct snd_pcm_hw_params *params,
   1677				  struct snd_soc_dai *dai)
   1678{
   1679	struct snd_soc_component *component = dai->component;
   1680	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1681	struct arizona_dai_priv *dai_priv = &priv->dai[dai->id - 1];
   1682	int base = dai->driver->base;
   1683	int i, sr_val, ret;
   1684
   1685	/*
   1686	 * We will need to be more flexible than this in future,
   1687	 * currently we use a single sample rate for SYSCLK.
   1688	 */
   1689	for (i = 0; i < ARRAY_SIZE(arizona_sr_vals); i++)
   1690		if (arizona_sr_vals[i] == params_rate(params))
   1691			break;
   1692	if (i == ARRAY_SIZE(arizona_sr_vals)) {
   1693		arizona_aif_err(dai, "Unsupported sample rate %dHz\n",
   1694				params_rate(params));
   1695		return -EINVAL;
   1696	}
   1697	sr_val = i;
   1698
   1699	switch (priv->arizona->type) {
   1700	case WM5102:
   1701	case WM8997:
   1702		if (arizona_sr_vals[sr_val] >= 88200)
   1703			ret = arizona_dvfs_up(component, ARIZONA_DVFS_SR1_RQ);
   1704		else
   1705			ret = arizona_dvfs_down(component, ARIZONA_DVFS_SR1_RQ);
   1706
   1707		if (ret) {
   1708			arizona_aif_err(dai, "Failed to change DVFS %d\n", ret);
   1709			return ret;
   1710		}
   1711		break;
   1712	default:
   1713		break;
   1714	}
   1715
   1716	switch (dai_priv->clk) {
   1717	case ARIZONA_CLK_SYSCLK:
   1718		switch (priv->arizona->type) {
   1719		case WM5102:
   1720			arizona_wm5102_set_dac_comp(component,
   1721						    params_rate(params));
   1722			break;
   1723		default:
   1724			break;
   1725		}
   1726
   1727		snd_soc_component_update_bits(component, ARIZONA_SAMPLE_RATE_1,
   1728					      ARIZONA_SAMPLE_RATE_1_MASK,
   1729					      sr_val);
   1730		if (base)
   1731			snd_soc_component_update_bits(component,
   1732					base + ARIZONA_AIF_RATE_CTRL,
   1733					ARIZONA_AIF1_RATE_MASK, 0);
   1734		break;
   1735	case ARIZONA_CLK_ASYNCCLK:
   1736		snd_soc_component_update_bits(component,
   1737					      ARIZONA_ASYNC_SAMPLE_RATE_1,
   1738					      ARIZONA_ASYNC_SAMPLE_RATE_1_MASK,
   1739					      sr_val);
   1740		if (base)
   1741			snd_soc_component_update_bits(component,
   1742					base + ARIZONA_AIF_RATE_CTRL,
   1743					ARIZONA_AIF1_RATE_MASK,
   1744					8 << ARIZONA_AIF1_RATE_SHIFT);
   1745		break;
   1746	default:
   1747		arizona_aif_err(dai, "Invalid clock %d\n", dai_priv->clk);
   1748		return -EINVAL;
   1749	}
   1750
   1751	return 0;
   1752}
   1753
   1754static bool arizona_aif_cfg_changed(struct snd_soc_component *component,
   1755				    int base, int bclk, int lrclk, int frame)
   1756{
   1757	int val;
   1758
   1759	val = snd_soc_component_read(component, base + ARIZONA_AIF_BCLK_CTRL);
   1760	if (bclk != (val & ARIZONA_AIF1_BCLK_FREQ_MASK))
   1761		return true;
   1762
   1763	val = snd_soc_component_read(component, base + ARIZONA_AIF_TX_BCLK_RATE);
   1764	if (lrclk != (val & ARIZONA_AIF1TX_BCPF_MASK))
   1765		return true;
   1766
   1767	val = snd_soc_component_read(component, base + ARIZONA_AIF_FRAME_CTRL_1);
   1768	if (frame != (val & (ARIZONA_AIF1TX_WL_MASK |
   1769			     ARIZONA_AIF1TX_SLOT_LEN_MASK)))
   1770		return true;
   1771
   1772	return false;
   1773}
   1774
   1775static int arizona_hw_params(struct snd_pcm_substream *substream,
   1776			     struct snd_pcm_hw_params *params,
   1777			     struct snd_soc_dai *dai)
   1778{
   1779	struct snd_soc_component *component = dai->component;
   1780	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1781	struct arizona *arizona = priv->arizona;
   1782	int base = dai->driver->base;
   1783	const int *rates;
   1784	int i, ret, val;
   1785	int channels = params_channels(params);
   1786	int chan_limit = arizona->pdata.max_channels_clocked[dai->id - 1];
   1787	int tdm_width = arizona->tdm_width[dai->id - 1];
   1788	int tdm_slots = arizona->tdm_slots[dai->id - 1];
   1789	int bclk, lrclk, wl, frame, bclk_target;
   1790	bool reconfig;
   1791	unsigned int aif_tx_state, aif_rx_state;
   1792
   1793	if (params_rate(params) % 4000)
   1794		rates = &arizona_44k1_bclk_rates[0];
   1795	else
   1796		rates = &arizona_48k_bclk_rates[0];
   1797
   1798	wl = params_width(params);
   1799
   1800	if (tdm_slots) {
   1801		arizona_aif_dbg(dai, "Configuring for %d %d bit TDM slots\n",
   1802				tdm_slots, tdm_width);
   1803		bclk_target = tdm_slots * tdm_width * params_rate(params);
   1804		channels = tdm_slots;
   1805	} else {
   1806		bclk_target = snd_soc_params_to_bclk(params);
   1807		tdm_width = wl;
   1808	}
   1809
   1810	if (chan_limit && chan_limit < channels) {
   1811		arizona_aif_dbg(dai, "Limiting to %d channels\n", chan_limit);
   1812		bclk_target /= channels;
   1813		bclk_target *= chan_limit;
   1814	}
   1815
   1816	/* Force multiple of 2 channels for I2S mode */
   1817	val = snd_soc_component_read(component, base + ARIZONA_AIF_FORMAT);
   1818	val &= ARIZONA_AIF1_FMT_MASK;
   1819	if ((channels & 1) && (val == ARIZONA_FMT_I2S_MODE)) {
   1820		arizona_aif_dbg(dai, "Forcing stereo mode\n");
   1821		bclk_target /= channels;
   1822		bclk_target *= channels + 1;
   1823	}
   1824
   1825	for (i = 0; i < ARRAY_SIZE(arizona_44k1_bclk_rates); i++) {
   1826		if (rates[i] >= bclk_target &&
   1827		    rates[i] % params_rate(params) == 0) {
   1828			bclk = i;
   1829			break;
   1830		}
   1831	}
   1832	if (i == ARRAY_SIZE(arizona_44k1_bclk_rates)) {
   1833		arizona_aif_err(dai, "Unsupported sample rate %dHz\n",
   1834				params_rate(params));
   1835		return -EINVAL;
   1836	}
   1837
   1838	lrclk = rates[bclk] / params_rate(params);
   1839
   1840	arizona_aif_dbg(dai, "BCLK %dHz LRCLK %dHz\n",
   1841			rates[bclk], rates[bclk] / lrclk);
   1842
   1843	frame = wl << ARIZONA_AIF1TX_WL_SHIFT | tdm_width;
   1844
   1845	reconfig = arizona_aif_cfg_changed(component, base, bclk, lrclk, frame);
   1846
   1847	if (reconfig) {
   1848		/* Save AIF TX/RX state */
   1849		aif_tx_state = snd_soc_component_read(component,
   1850					    base + ARIZONA_AIF_TX_ENABLES);
   1851		aif_rx_state = snd_soc_component_read(component,
   1852					    base + ARIZONA_AIF_RX_ENABLES);
   1853		/* Disable AIF TX/RX before reconfiguring it */
   1854		regmap_update_bits_async(arizona->regmap,
   1855					 base + ARIZONA_AIF_TX_ENABLES,
   1856					 0xff, 0x0);
   1857		regmap_update_bits(arizona->regmap,
   1858				   base + ARIZONA_AIF_RX_ENABLES, 0xff, 0x0);
   1859	}
   1860
   1861	ret = arizona_hw_params_rate(substream, params, dai);
   1862	if (ret != 0)
   1863		goto restore_aif;
   1864
   1865	if (reconfig) {
   1866		regmap_update_bits_async(arizona->regmap,
   1867					 base + ARIZONA_AIF_BCLK_CTRL,
   1868					 ARIZONA_AIF1_BCLK_FREQ_MASK, bclk);
   1869		regmap_update_bits_async(arizona->regmap,
   1870					 base + ARIZONA_AIF_TX_BCLK_RATE,
   1871					 ARIZONA_AIF1TX_BCPF_MASK, lrclk);
   1872		regmap_update_bits_async(arizona->regmap,
   1873					 base + ARIZONA_AIF_RX_BCLK_RATE,
   1874					 ARIZONA_AIF1RX_BCPF_MASK, lrclk);
   1875		regmap_update_bits_async(arizona->regmap,
   1876					 base + ARIZONA_AIF_FRAME_CTRL_1,
   1877					 ARIZONA_AIF1TX_WL_MASK |
   1878					 ARIZONA_AIF1TX_SLOT_LEN_MASK, frame);
   1879		regmap_update_bits(arizona->regmap,
   1880				   base + ARIZONA_AIF_FRAME_CTRL_2,
   1881				   ARIZONA_AIF1RX_WL_MASK |
   1882				   ARIZONA_AIF1RX_SLOT_LEN_MASK, frame);
   1883	}
   1884
   1885restore_aif:
   1886	if (reconfig) {
   1887		/* Restore AIF TX/RX state */
   1888		regmap_update_bits_async(arizona->regmap,
   1889					 base + ARIZONA_AIF_TX_ENABLES,
   1890					 0xff, aif_tx_state);
   1891		regmap_update_bits(arizona->regmap,
   1892				   base + ARIZONA_AIF_RX_ENABLES,
   1893				   0xff, aif_rx_state);
   1894	}
   1895	return ret;
   1896}
   1897
   1898static const char *arizona_dai_clk_str(int clk_id)
   1899{
   1900	switch (clk_id) {
   1901	case ARIZONA_CLK_SYSCLK:
   1902		return "SYSCLK";
   1903	case ARIZONA_CLK_ASYNCCLK:
   1904		return "ASYNCCLK";
   1905	default:
   1906		return "Unknown clock";
   1907	}
   1908}
   1909
   1910static int arizona_dai_set_sysclk(struct snd_soc_dai *dai,
   1911				  int clk_id, unsigned int freq, int dir)
   1912{
   1913	struct snd_soc_component *component = dai->component;
   1914	struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component);
   1915	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1916	struct arizona_dai_priv *dai_priv = &priv->dai[dai->id - 1];
   1917	struct snd_soc_dapm_route routes[2];
   1918
   1919	switch (clk_id) {
   1920	case ARIZONA_CLK_SYSCLK:
   1921	case ARIZONA_CLK_ASYNCCLK:
   1922		break;
   1923	default:
   1924		return -EINVAL;
   1925	}
   1926
   1927	if (clk_id == dai_priv->clk)
   1928		return 0;
   1929
   1930	if (snd_soc_dai_active(dai)) {
   1931		dev_err(component->dev, "Can't change clock on active DAI %d\n",
   1932			dai->id);
   1933		return -EBUSY;
   1934	}
   1935
   1936	dev_dbg(component->dev, "Setting AIF%d to %s\n", dai->id + 1,
   1937		arizona_dai_clk_str(clk_id));
   1938
   1939	memset(&routes, 0, sizeof(routes));
   1940	routes[0].sink = dai->driver->capture.stream_name;
   1941	routes[1].sink = dai->driver->playback.stream_name;
   1942
   1943	routes[0].source = arizona_dai_clk_str(dai_priv->clk);
   1944	routes[1].source = arizona_dai_clk_str(dai_priv->clk);
   1945	snd_soc_dapm_del_routes(dapm, routes, ARRAY_SIZE(routes));
   1946
   1947	routes[0].source = arizona_dai_clk_str(clk_id);
   1948	routes[1].source = arizona_dai_clk_str(clk_id);
   1949	snd_soc_dapm_add_routes(dapm, routes, ARRAY_SIZE(routes));
   1950
   1951	dai_priv->clk = clk_id;
   1952
   1953	return snd_soc_dapm_sync(dapm);
   1954}
   1955
   1956static int arizona_set_tristate(struct snd_soc_dai *dai, int tristate)
   1957{
   1958	struct snd_soc_component *component = dai->component;
   1959	int base = dai->driver->base;
   1960	unsigned int reg;
   1961
   1962	if (tristate)
   1963		reg = ARIZONA_AIF1_TRI;
   1964	else
   1965		reg = 0;
   1966
   1967	return snd_soc_component_update_bits(component,
   1968					     base + ARIZONA_AIF_RATE_CTRL,
   1969					     ARIZONA_AIF1_TRI, reg);
   1970}
   1971
   1972static void arizona_set_channels_to_mask(struct snd_soc_dai *dai,
   1973					 unsigned int base,
   1974					 int channels, unsigned int mask)
   1975{
   1976	struct snd_soc_component *component = dai->component;
   1977	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   1978	struct arizona *arizona = priv->arizona;
   1979	int slot, i;
   1980
   1981	for (i = 0; i < channels; ++i) {
   1982		slot = ffs(mask) - 1;
   1983		if (slot < 0)
   1984			return;
   1985
   1986		regmap_write(arizona->regmap, base + i, slot);
   1987
   1988		mask &= ~(1 << slot);
   1989	}
   1990
   1991	if (mask)
   1992		arizona_aif_warn(dai, "Too many channels in TDM mask\n");
   1993}
   1994
   1995static int arizona_set_tdm_slot(struct snd_soc_dai *dai, unsigned int tx_mask,
   1996				unsigned int rx_mask, int slots, int slot_width)
   1997{
   1998	struct snd_soc_component *component = dai->component;
   1999	struct arizona_priv *priv = snd_soc_component_get_drvdata(component);
   2000	struct arizona *arizona = priv->arizona;
   2001	int base = dai->driver->base;
   2002	int rx_max_chan = dai->driver->playback.channels_max;
   2003	int tx_max_chan = dai->driver->capture.channels_max;
   2004
   2005	/* Only support TDM for the physical AIFs */
   2006	if (dai->id > ARIZONA_MAX_AIF)
   2007		return -ENOTSUPP;
   2008
   2009	if (slots == 0) {
   2010		tx_mask = (1 << tx_max_chan) - 1;
   2011		rx_mask = (1 << rx_max_chan) - 1;
   2012	}
   2013
   2014	arizona_set_channels_to_mask(dai, base + ARIZONA_AIF_FRAME_CTRL_3,
   2015				     tx_max_chan, tx_mask);
   2016	arizona_set_channels_to_mask(dai, base + ARIZONA_AIF_FRAME_CTRL_11,
   2017				     rx_max_chan, rx_mask);
   2018
   2019	arizona->tdm_width[dai->id - 1] = slot_width;
   2020	arizona->tdm_slots[dai->id - 1] = slots;
   2021
   2022	return 0;
   2023}
   2024
   2025const struct snd_soc_dai_ops arizona_dai_ops = {
   2026	.startup = arizona_startup,
   2027	.set_fmt = arizona_set_fmt,
   2028	.set_tdm_slot = arizona_set_tdm_slot,
   2029	.hw_params = arizona_hw_params,
   2030	.set_sysclk = arizona_dai_set_sysclk,
   2031	.set_tristate = arizona_set_tristate,
   2032};
   2033EXPORT_SYMBOL_GPL(arizona_dai_ops);
   2034
   2035const struct snd_soc_dai_ops arizona_simple_dai_ops = {
   2036	.startup = arizona_startup,
   2037	.hw_params = arizona_hw_params_rate,
   2038	.set_sysclk = arizona_dai_set_sysclk,
   2039};
   2040EXPORT_SYMBOL_GPL(arizona_simple_dai_ops);
   2041
   2042int arizona_init_dai(struct arizona_priv *priv, int id)
   2043{
   2044	struct arizona_dai_priv *dai_priv = &priv->dai[id];
   2045
   2046	dai_priv->clk = ARIZONA_CLK_SYSCLK;
   2047	dai_priv->constraint = arizona_constraint;
   2048
   2049	return 0;
   2050}
   2051EXPORT_SYMBOL_GPL(arizona_init_dai);
   2052
   2053static struct {
   2054	unsigned int min;
   2055	unsigned int max;
   2056	u16 fratio;
   2057	int ratio;
   2058} fll_fratios[] = {
   2059	{       0,    64000, 4, 16 },
   2060	{   64000,   128000, 3,  8 },
   2061	{  128000,   256000, 2,  4 },
   2062	{  256000,  1000000, 1,  2 },
   2063	{ 1000000, 13500000, 0,  1 },
   2064};
   2065
   2066static const unsigned int pseudo_fref_max[ARIZONA_FLL_MAX_FRATIO] = {
   2067	13500000,
   2068	 6144000,
   2069	 6144000,
   2070	 3072000,
   2071	 3072000,
   2072	 2822400,
   2073	 2822400,
   2074	 1536000,
   2075	 1536000,
   2076	 1536000,
   2077	 1536000,
   2078	 1536000,
   2079	 1536000,
   2080	 1536000,
   2081	 1536000,
   2082	  768000,
   2083};
   2084
   2085static struct {
   2086	unsigned int min;
   2087	unsigned int max;
   2088	u16 gain;
   2089} fll_gains[] = {
   2090	{       0,   256000, 0 },
   2091	{  256000,  1000000, 2 },
   2092	{ 1000000, 13500000, 4 },
   2093};
   2094
   2095struct arizona_fll_cfg {
   2096	int n;
   2097	unsigned int theta;
   2098	unsigned int lambda;
   2099	int refdiv;
   2100	int outdiv;
   2101	int fratio;
   2102	int gain;
   2103};
   2104
   2105static int arizona_validate_fll(struct arizona_fll *fll,
   2106				unsigned int Fref,
   2107				unsigned int Fout)
   2108{
   2109	unsigned int Fvco_min;
   2110
   2111	if (fll->fout && Fout != fll->fout) {
   2112		arizona_fll_err(fll,
   2113				"Can't change output on active FLL\n");
   2114		return -EINVAL;
   2115	}
   2116
   2117	if (Fref / ARIZONA_FLL_MAX_REFDIV > ARIZONA_FLL_MAX_FREF) {
   2118		arizona_fll_err(fll,
   2119				"Can't scale %dMHz in to <=13.5MHz\n",
   2120				Fref);
   2121		return -EINVAL;
   2122	}
   2123
   2124	Fvco_min = ARIZONA_FLL_MIN_FVCO * fll->vco_mult;
   2125	if (Fout * ARIZONA_FLL_MAX_OUTDIV < Fvco_min) {
   2126		arizona_fll_err(fll, "No FLL_OUTDIV for Fout=%uHz\n",
   2127				Fout);
   2128		return -EINVAL;
   2129	}
   2130
   2131	return 0;
   2132}
   2133
   2134static int arizona_find_fratio(unsigned int Fref, int *fratio)
   2135{
   2136	int i;
   2137
   2138	/* Find an appropriate FLL_FRATIO */
   2139	for (i = 0; i < ARRAY_SIZE(fll_fratios); i++) {
   2140		if (fll_fratios[i].min <= Fref && Fref <= fll_fratios[i].max) {
   2141			if (fratio)
   2142				*fratio = fll_fratios[i].fratio;
   2143			return fll_fratios[i].ratio;
   2144		}
   2145	}
   2146
   2147	return -EINVAL;
   2148}
   2149
   2150static int arizona_calc_fratio(struct arizona_fll *fll,
   2151			       struct arizona_fll_cfg *cfg,
   2152			       unsigned int target,
   2153			       unsigned int Fref, bool sync)
   2154{
   2155	int init_ratio, ratio;
   2156	int refdiv, div;
   2157
   2158	/* Fref must be <=13.5MHz, find initial refdiv */
   2159	div = 1;
   2160	cfg->refdiv = 0;
   2161	while (Fref > ARIZONA_FLL_MAX_FREF) {
   2162		div *= 2;
   2163		Fref /= 2;
   2164		cfg->refdiv++;
   2165
   2166		if (div > ARIZONA_FLL_MAX_REFDIV)
   2167			return -EINVAL;
   2168	}
   2169
   2170	/* Find an appropriate FLL_FRATIO */
   2171	init_ratio = arizona_find_fratio(Fref, &cfg->fratio);
   2172	if (init_ratio < 0) {
   2173		arizona_fll_err(fll, "Unable to find FRATIO for Fref=%uHz\n",
   2174				Fref);
   2175		return init_ratio;
   2176	}
   2177
   2178	switch (fll->arizona->type) {
   2179	case WM5102:
   2180	case WM8997:
   2181		return init_ratio;
   2182	case WM5110:
   2183	case WM8280:
   2184		if (fll->arizona->rev < 3 || sync)
   2185			return init_ratio;
   2186		break;
   2187	default:
   2188		if (sync)
   2189			return init_ratio;
   2190		break;
   2191	}
   2192
   2193	cfg->fratio = init_ratio - 1;
   2194
   2195	/* Adjust FRATIO/refdiv to avoid integer mode if possible */
   2196	refdiv = cfg->refdiv;
   2197
   2198	arizona_fll_dbg(fll, "pseudo: initial ratio=%u fref=%u refdiv=%u\n",
   2199			init_ratio, Fref, refdiv);
   2200
   2201	while (div <= ARIZONA_FLL_MAX_REFDIV) {
   2202		/* start from init_ratio because this may already give a
   2203		 * fractional N.K
   2204		 */
   2205		for (ratio = init_ratio; ratio > 0; ratio--) {
   2206			if (target % (ratio * Fref)) {
   2207				cfg->refdiv = refdiv;
   2208				cfg->fratio = ratio - 1;
   2209				arizona_fll_dbg(fll,
   2210					"pseudo: found fref=%u refdiv=%d(%d) ratio=%d\n",
   2211					Fref, refdiv, div, ratio);
   2212				return ratio;
   2213			}
   2214		}
   2215
   2216		for (ratio = init_ratio + 1; ratio <= ARIZONA_FLL_MAX_FRATIO;
   2217		     ratio++) {
   2218			if ((ARIZONA_FLL_VCO_CORNER / 2) /
   2219			    (fll->vco_mult * ratio) < Fref) {
   2220				arizona_fll_dbg(fll, "pseudo: hit VCO corner\n");
   2221				break;
   2222			}
   2223
   2224			if (Fref > pseudo_fref_max[ratio - 1]) {
   2225				arizona_fll_dbg(fll,
   2226					"pseudo: exceeded max fref(%u) for ratio=%u\n",
   2227					pseudo_fref_max[ratio - 1],
   2228					ratio);
   2229				break;
   2230			}
   2231
   2232			if (target % (ratio * Fref)) {
   2233				cfg->refdiv = refdiv;
   2234				cfg->fratio = ratio - 1;
   2235				arizona_fll_dbg(fll,
   2236					"pseudo: found fref=%u refdiv=%d(%d) ratio=%d\n",
   2237					Fref, refdiv, div, ratio);
   2238				return ratio;
   2239			}
   2240		}
   2241
   2242		div *= 2;
   2243		Fref /= 2;
   2244		refdiv++;
   2245		init_ratio = arizona_find_fratio(Fref, NULL);
   2246		arizona_fll_dbg(fll,
   2247				"pseudo: change fref=%u refdiv=%d(%d) ratio=%u\n",
   2248				Fref, refdiv, div, init_ratio);
   2249	}
   2250
   2251	arizona_fll_warn(fll, "Falling back to integer mode operation\n");
   2252	return cfg->fratio + 1;
   2253}
   2254
   2255static int arizona_calc_fll(struct arizona_fll *fll,
   2256			    struct arizona_fll_cfg *cfg,
   2257			    unsigned int Fref, bool sync)
   2258{
   2259	unsigned int target, div, gcd_fll;
   2260	int i, ratio;
   2261
   2262	arizona_fll_dbg(fll, "Fref=%u Fout=%u\n", Fref, fll->fout);
   2263
   2264	/* Fvco should be over the targt; don't check the upper bound */
   2265	div = ARIZONA_FLL_MIN_OUTDIV;
   2266	while (fll->fout * div < ARIZONA_FLL_MIN_FVCO * fll->vco_mult) {
   2267		div++;
   2268		if (div > ARIZONA_FLL_MAX_OUTDIV)
   2269			return -EINVAL;
   2270	}
   2271	target = fll->fout * div / fll->vco_mult;
   2272	cfg->outdiv = div;
   2273
   2274	arizona_fll_dbg(fll, "Fvco=%dHz\n", target);
   2275
   2276	/* Find an appropriate FLL_FRATIO and refdiv */
   2277	ratio = arizona_calc_fratio(fll, cfg, target, Fref, sync);
   2278	if (ratio < 0)
   2279		return ratio;
   2280
   2281	/* Apply the division for our remaining calculations */
   2282	Fref = Fref / (1 << cfg->refdiv);
   2283
   2284	cfg->n = target / (ratio * Fref);
   2285
   2286	if (target % (ratio * Fref)) {
   2287		gcd_fll = gcd(target, ratio * Fref);
   2288		arizona_fll_dbg(fll, "GCD=%u\n", gcd_fll);
   2289
   2290		cfg->theta = (target - (cfg->n * ratio * Fref))
   2291			/ gcd_fll;
   2292		cfg->lambda = (ratio * Fref) / gcd_fll;
   2293	} else {
   2294		cfg->theta = 0;
   2295		cfg->lambda = 0;
   2296	}
   2297
   2298	/* Round down to 16bit range with cost of accuracy lost.
   2299	 * Denominator must be bigger than numerator so we only
   2300	 * take care of it.
   2301	 */
   2302	while (cfg->lambda >= (1 << 16)) {
   2303		cfg->theta >>= 1;
   2304		cfg->lambda >>= 1;
   2305	}
   2306
   2307	for (i = 0; i < ARRAY_SIZE(fll_gains); i++) {
   2308		if (fll_gains[i].min <= Fref && Fref <= fll_gains[i].max) {
   2309			cfg->gain = fll_gains[i].gain;
   2310			break;
   2311		}
   2312	}
   2313	if (i == ARRAY_SIZE(fll_gains)) {
   2314		arizona_fll_err(fll, "Unable to find gain for Fref=%uHz\n",
   2315				Fref);
   2316		return -EINVAL;
   2317	}
   2318
   2319	arizona_fll_dbg(fll, "N=%d THETA=%d LAMBDA=%d\n",
   2320			cfg->n, cfg->theta, cfg->lambda);
   2321	arizona_fll_dbg(fll, "FRATIO=0x%x(%d) OUTDIV=%d REFCLK_DIV=0x%x(%d)\n",
   2322			cfg->fratio, ratio, cfg->outdiv,
   2323			cfg->refdiv, 1 << cfg->refdiv);
   2324	arizona_fll_dbg(fll, "GAIN=0x%x(%d)\n", cfg->gain, 1 << cfg->gain);
   2325
   2326	return 0;
   2327}
   2328
   2329static void arizona_apply_fll(struct arizona *arizona, unsigned int base,
   2330			      struct arizona_fll_cfg *cfg, int source,
   2331			      bool sync)
   2332{
   2333	regmap_update_bits_async(arizona->regmap, base + 3,
   2334				 ARIZONA_FLL1_THETA_MASK, cfg->theta);
   2335	regmap_update_bits_async(arizona->regmap, base + 4,
   2336				 ARIZONA_FLL1_LAMBDA_MASK, cfg->lambda);
   2337	regmap_update_bits_async(arizona->regmap, base + 5,
   2338				 ARIZONA_FLL1_FRATIO_MASK,
   2339				 cfg->fratio << ARIZONA_FLL1_FRATIO_SHIFT);
   2340	regmap_update_bits_async(arizona->regmap, base + 6,
   2341				 ARIZONA_FLL1_CLK_REF_DIV_MASK |
   2342				 ARIZONA_FLL1_CLK_REF_SRC_MASK,
   2343				 cfg->refdiv << ARIZONA_FLL1_CLK_REF_DIV_SHIFT |
   2344				 source << ARIZONA_FLL1_CLK_REF_SRC_SHIFT);
   2345
   2346	if (sync) {
   2347		regmap_update_bits(arizona->regmap, base + 0x7,
   2348				   ARIZONA_FLL1_GAIN_MASK,
   2349				   cfg->gain << ARIZONA_FLL1_GAIN_SHIFT);
   2350	} else {
   2351		regmap_update_bits(arizona->regmap, base + 0x5,
   2352				   ARIZONA_FLL1_OUTDIV_MASK,
   2353				   cfg->outdiv << ARIZONA_FLL1_OUTDIV_SHIFT);
   2354		regmap_update_bits(arizona->regmap, base + 0x9,
   2355				   ARIZONA_FLL1_GAIN_MASK,
   2356				   cfg->gain << ARIZONA_FLL1_GAIN_SHIFT);
   2357	}
   2358
   2359	regmap_update_bits_async(arizona->regmap, base + 2,
   2360				 ARIZONA_FLL1_CTRL_UPD | ARIZONA_FLL1_N_MASK,
   2361				 ARIZONA_FLL1_CTRL_UPD | cfg->n);
   2362}
   2363
   2364static int arizona_is_enabled_fll(struct arizona_fll *fll, int base)
   2365{
   2366	struct arizona *arizona = fll->arizona;
   2367	unsigned int reg;
   2368	int ret;
   2369
   2370	ret = regmap_read(arizona->regmap, base + 1, &reg);
   2371	if (ret != 0) {
   2372		arizona_fll_err(fll, "Failed to read current state: %d\n",
   2373				ret);
   2374		return ret;
   2375	}
   2376
   2377	return reg & ARIZONA_FLL1_ENA;
   2378}
   2379
   2380static int arizona_set_fll_clks(struct arizona_fll *fll, int base, bool ena)
   2381{
   2382	struct arizona *arizona = fll->arizona;
   2383	unsigned int val;
   2384	struct clk *clk;
   2385	int ret;
   2386
   2387	ret = regmap_read(arizona->regmap, base + 6, &val);
   2388	if (ret != 0) {
   2389		arizona_fll_err(fll, "Failed to read current source: %d\n",
   2390				ret);
   2391		return ret;
   2392	}
   2393
   2394	val &= ARIZONA_FLL1_CLK_REF_SRC_MASK;
   2395	val >>= ARIZONA_FLL1_CLK_REF_SRC_SHIFT;
   2396
   2397	switch (val) {
   2398	case ARIZONA_FLL_SRC_MCLK1:
   2399		clk = arizona->mclk[ARIZONA_MCLK1];
   2400		break;
   2401	case ARIZONA_FLL_SRC_MCLK2:
   2402		clk = arizona->mclk[ARIZONA_MCLK2];
   2403		break;
   2404	default:
   2405		return 0;
   2406	}
   2407
   2408	if (ena) {
   2409		return clk_prepare_enable(clk);
   2410	} else {
   2411		clk_disable_unprepare(clk);
   2412		return 0;
   2413	}
   2414}
   2415
   2416static int arizona_enable_fll(struct arizona_fll *fll)
   2417{
   2418	struct arizona *arizona = fll->arizona;
   2419	bool use_sync = false;
   2420	int already_enabled = arizona_is_enabled_fll(fll, fll->base);
   2421	int sync_enabled = arizona_is_enabled_fll(fll, fll->base + 0x10);
   2422	struct arizona_fll_cfg cfg;
   2423	int i;
   2424	unsigned int val;
   2425
   2426	if (already_enabled < 0)
   2427		return already_enabled;
   2428	if (sync_enabled < 0)
   2429		return sync_enabled;
   2430
   2431	if (already_enabled) {
   2432		/* Facilitate smooth refclk across the transition */
   2433		regmap_update_bits(fll->arizona->regmap, fll->base + 1,
   2434				   ARIZONA_FLL1_FREERUN, ARIZONA_FLL1_FREERUN);
   2435		udelay(32);
   2436		regmap_update_bits_async(fll->arizona->regmap, fll->base + 0x9,
   2437					 ARIZONA_FLL1_GAIN_MASK, 0);
   2438
   2439		if (arizona_is_enabled_fll(fll, fll->base + 0x10) > 0)
   2440			arizona_set_fll_clks(fll, fll->base + 0x10, false);
   2441		arizona_set_fll_clks(fll, fll->base, false);
   2442	}
   2443
   2444	/*
   2445	 * If we have both REFCLK and SYNCCLK then enable both,
   2446	 * otherwise apply the SYNCCLK settings to REFCLK.
   2447	 */
   2448	if (fll->ref_src >= 0 && fll->ref_freq &&
   2449	    fll->ref_src != fll->sync_src) {
   2450		arizona_calc_fll(fll, &cfg, fll->ref_freq, false);
   2451
   2452		/* Ref path hardcodes lambda to 65536 when sync is on */
   2453		if (fll->sync_src >= 0 && cfg.lambda)
   2454			cfg.theta = (cfg.theta * (1 << 16)) / cfg.lambda;
   2455
   2456		arizona_apply_fll(arizona, fll->base, &cfg, fll->ref_src,
   2457				  false);
   2458		if (fll->sync_src >= 0) {
   2459			arizona_calc_fll(fll, &cfg, fll->sync_freq, true);
   2460
   2461			arizona_apply_fll(arizona, fll->base + 0x10, &cfg,
   2462					  fll->sync_src, true);
   2463			use_sync = true;
   2464		}
   2465	} else if (fll->sync_src >= 0) {
   2466		arizona_calc_fll(fll, &cfg, fll->sync_freq, false);
   2467
   2468		arizona_apply_fll(arizona, fll->base, &cfg,
   2469				  fll->sync_src, false);
   2470
   2471		regmap_update_bits_async(arizona->regmap, fll->base + 0x11,
   2472					 ARIZONA_FLL1_SYNC_ENA, 0);
   2473	} else {
   2474		arizona_fll_err(fll, "No clocks provided\n");
   2475		return -EINVAL;
   2476	}
   2477
   2478	if (already_enabled && !!sync_enabled != use_sync)
   2479		arizona_fll_warn(fll, "Synchroniser changed on active FLL\n");
   2480
   2481	/*
   2482	 * Increase the bandwidth if we're not using a low frequency
   2483	 * sync source.
   2484	 */
   2485	if (use_sync && fll->sync_freq > 100000)
   2486		regmap_update_bits_async(arizona->regmap, fll->base + 0x17,
   2487					 ARIZONA_FLL1_SYNC_BW, 0);
   2488	else
   2489		regmap_update_bits_async(arizona->regmap, fll->base + 0x17,
   2490					 ARIZONA_FLL1_SYNC_BW,
   2491					 ARIZONA_FLL1_SYNC_BW);
   2492
   2493	if (!already_enabled)
   2494		pm_runtime_get_sync(arizona->dev);
   2495
   2496	if (use_sync) {
   2497		arizona_set_fll_clks(fll, fll->base + 0x10, true);
   2498		regmap_update_bits_async(arizona->regmap, fll->base + 0x11,
   2499					 ARIZONA_FLL1_SYNC_ENA,
   2500					 ARIZONA_FLL1_SYNC_ENA);
   2501	}
   2502	arizona_set_fll_clks(fll, fll->base, true);
   2503	regmap_update_bits_async(arizona->regmap, fll->base + 1,
   2504				 ARIZONA_FLL1_ENA, ARIZONA_FLL1_ENA);
   2505
   2506	if (already_enabled)
   2507		regmap_update_bits_async(arizona->regmap, fll->base + 1,
   2508					 ARIZONA_FLL1_FREERUN, 0);
   2509
   2510	arizona_fll_dbg(fll, "Waiting for FLL lock...\n");
   2511	val = 0;
   2512	for (i = 0; i < 15; i++) {
   2513		if (i < 5)
   2514			usleep_range(200, 400);
   2515		else
   2516			msleep(20);
   2517
   2518		regmap_read(arizona->regmap,
   2519			    ARIZONA_INTERRUPT_RAW_STATUS_5,
   2520			    &val);
   2521		if (val & (ARIZONA_FLL1_CLOCK_OK_STS << (fll->id - 1)))
   2522			break;
   2523	}
   2524	if (i == 15)
   2525		arizona_fll_warn(fll, "Timed out waiting for lock\n");
   2526	else
   2527		arizona_fll_dbg(fll, "FLL locked (%d polls)\n", i);
   2528
   2529	return 0;
   2530}
   2531
   2532static void arizona_disable_fll(struct arizona_fll *fll)
   2533{
   2534	struct arizona *arizona = fll->arizona;
   2535	bool ref_change, sync_change;
   2536
   2537	regmap_update_bits_async(arizona->regmap, fll->base + 1,
   2538				 ARIZONA_FLL1_FREERUN, ARIZONA_FLL1_FREERUN);
   2539	regmap_update_bits_check(arizona->regmap, fll->base + 1,
   2540				 ARIZONA_FLL1_ENA, 0, &ref_change);
   2541	regmap_update_bits_check(arizona->regmap, fll->base + 0x11,
   2542				 ARIZONA_FLL1_SYNC_ENA, 0, &sync_change);
   2543	regmap_update_bits_async(arizona->regmap, fll->base + 1,
   2544				 ARIZONA_FLL1_FREERUN, 0);
   2545
   2546	if (sync_change)
   2547		arizona_set_fll_clks(fll, fll->base + 0x10, false);
   2548
   2549	if (ref_change) {
   2550		arizona_set_fll_clks(fll, fll->base, false);
   2551		pm_runtime_put_autosuspend(arizona->dev);
   2552	}
   2553}
   2554
   2555int arizona_set_fll_refclk(struct arizona_fll *fll, int source,
   2556			   unsigned int Fref, unsigned int Fout)
   2557{
   2558	int ret = 0;
   2559
   2560	if (fll->ref_src == source && fll->ref_freq == Fref)
   2561		return 0;
   2562
   2563	if (fll->fout && Fref > 0) {
   2564		ret = arizona_validate_fll(fll, Fref, fll->fout);
   2565		if (ret != 0)
   2566			return ret;
   2567	}
   2568
   2569	fll->ref_src = source;
   2570	fll->ref_freq = Fref;
   2571
   2572	if (fll->fout && Fref > 0)
   2573		ret = arizona_enable_fll(fll);
   2574
   2575	return ret;
   2576}
   2577EXPORT_SYMBOL_GPL(arizona_set_fll_refclk);
   2578
   2579int arizona_set_fll(struct arizona_fll *fll, int source,
   2580		    unsigned int Fref, unsigned int Fout)
   2581{
   2582	int ret = 0;
   2583
   2584	if (fll->sync_src == source &&
   2585	    fll->sync_freq == Fref && fll->fout == Fout)
   2586		return 0;
   2587
   2588	if (Fout) {
   2589		if (fll->ref_src >= 0) {
   2590			ret = arizona_validate_fll(fll, fll->ref_freq, Fout);
   2591			if (ret != 0)
   2592				return ret;
   2593		}
   2594
   2595		ret = arizona_validate_fll(fll, Fref, Fout);
   2596		if (ret != 0)
   2597			return ret;
   2598	}
   2599
   2600	fll->sync_src = source;
   2601	fll->sync_freq = Fref;
   2602	fll->fout = Fout;
   2603
   2604	if (Fout)
   2605		ret = arizona_enable_fll(fll);
   2606	else
   2607		arizona_disable_fll(fll);
   2608
   2609	return ret;
   2610}
   2611EXPORT_SYMBOL_GPL(arizona_set_fll);
   2612
   2613int arizona_init_fll(struct arizona *arizona, int id, int base, int lock_irq,
   2614		     int ok_irq, struct arizona_fll *fll)
   2615{
   2616	unsigned int val;
   2617
   2618	fll->id = id;
   2619	fll->base = base;
   2620	fll->arizona = arizona;
   2621	fll->sync_src = ARIZONA_FLL_SRC_NONE;
   2622
   2623	/* Configure default refclk to 32kHz if we have one */
   2624	regmap_read(arizona->regmap, ARIZONA_CLOCK_32K_1, &val);
   2625	switch (val & ARIZONA_CLK_32K_SRC_MASK) {
   2626	case ARIZONA_CLK_SRC_MCLK1:
   2627	case ARIZONA_CLK_SRC_MCLK2:
   2628		fll->ref_src = val & ARIZONA_CLK_32K_SRC_MASK;
   2629		break;
   2630	default:
   2631		fll->ref_src = ARIZONA_FLL_SRC_NONE;
   2632	}
   2633	fll->ref_freq = 32768;
   2634
   2635	snprintf(fll->lock_name, sizeof(fll->lock_name), "FLL%d lock", id);
   2636	snprintf(fll->clock_ok_name, sizeof(fll->clock_ok_name),
   2637		 "FLL%d clock OK", id);
   2638
   2639	regmap_update_bits(arizona->regmap, fll->base + 1,
   2640			   ARIZONA_FLL1_FREERUN, 0);
   2641
   2642	return 0;
   2643}
   2644EXPORT_SYMBOL_GPL(arizona_init_fll);
   2645
   2646/**
   2647 * arizona_set_output_mode - Set the mode of the specified output
   2648 *
   2649 * @component: Device to configure
   2650 * @output: Output number
   2651 * @diff: True to set the output to differential mode
   2652 *
   2653 * Some systems use external analogue switches to connect more
   2654 * analogue devices to the CODEC than are supported by the device.  In
   2655 * some systems this requires changing the switched output from single
   2656 * ended to differential mode dynamically at runtime, an operation
   2657 * supported using this function.
   2658 *
   2659 * Most systems have a single static configuration and should use
   2660 * platform data instead.
   2661 */
   2662int arizona_set_output_mode(struct snd_soc_component *component, int output,
   2663			    bool diff)
   2664{
   2665	unsigned int reg, val;
   2666
   2667	if (output < 1 || output > 6)
   2668		return -EINVAL;
   2669
   2670	reg = ARIZONA_OUTPUT_PATH_CONFIG_1L + (output - 1) * 8;
   2671
   2672	if (diff)
   2673		val = ARIZONA_OUT1_MONO;
   2674	else
   2675		val = 0;
   2676
   2677	return snd_soc_component_update_bits(component, reg,
   2678					     ARIZONA_OUT1_MONO, val);
   2679}
   2680EXPORT_SYMBOL_GPL(arizona_set_output_mode);
   2681
   2682static const struct soc_enum arizona_adsp2_rate_enum[] = {
   2683	SOC_VALUE_ENUM_SINGLE(ARIZONA_DSP1_CONTROL_1,
   2684			      ARIZONA_DSP1_RATE_SHIFT, 0xf,
   2685			      ARIZONA_RATE_ENUM_SIZE,
   2686			      arizona_rate_text, arizona_rate_val),
   2687	SOC_VALUE_ENUM_SINGLE(ARIZONA_DSP2_CONTROL_1,
   2688			      ARIZONA_DSP1_RATE_SHIFT, 0xf,
   2689			      ARIZONA_RATE_ENUM_SIZE,
   2690			      arizona_rate_text, arizona_rate_val),
   2691	SOC_VALUE_ENUM_SINGLE(ARIZONA_DSP3_CONTROL_1,
   2692			      ARIZONA_DSP1_RATE_SHIFT, 0xf,
   2693			      ARIZONA_RATE_ENUM_SIZE,
   2694			      arizona_rate_text, arizona_rate_val),
   2695	SOC_VALUE_ENUM_SINGLE(ARIZONA_DSP4_CONTROL_1,
   2696			      ARIZONA_DSP1_RATE_SHIFT, 0xf,
   2697			      ARIZONA_RATE_ENUM_SIZE,
   2698			      arizona_rate_text, arizona_rate_val),
   2699};
   2700
   2701const struct snd_kcontrol_new arizona_adsp2_rate_controls[] = {
   2702	SOC_ENUM("DSP1 Rate", arizona_adsp2_rate_enum[0]),
   2703	SOC_ENUM("DSP2 Rate", arizona_adsp2_rate_enum[1]),
   2704	SOC_ENUM("DSP3 Rate", arizona_adsp2_rate_enum[2]),
   2705	SOC_ENUM("DSP4 Rate", arizona_adsp2_rate_enum[3]),
   2706};
   2707EXPORT_SYMBOL_GPL(arizona_adsp2_rate_controls);
   2708
   2709static bool arizona_eq_filter_unstable(bool mode, __be16 _a, __be16 _b)
   2710{
   2711	s16 a = be16_to_cpu(_a);
   2712	s16 b = be16_to_cpu(_b);
   2713
   2714	if (!mode) {
   2715		return abs(a) >= 4096;
   2716	} else {
   2717		if (abs(b) >= 4096)
   2718			return true;
   2719
   2720		return (abs((a << 16) / (4096 - b)) >= 4096 << 4);
   2721	}
   2722}
   2723
   2724int arizona_eq_coeff_put(struct snd_kcontrol *kcontrol,
   2725			 struct snd_ctl_elem_value *ucontrol)
   2726{
   2727	struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
   2728	struct arizona *arizona = dev_get_drvdata(component->dev->parent);
   2729	struct soc_bytes *params = (void *)kcontrol->private_value;
   2730	unsigned int val;
   2731	__be16 *data;
   2732	int len;
   2733	int ret;
   2734
   2735	len = params->num_regs * regmap_get_val_bytes(arizona->regmap);
   2736
   2737	data = kmemdup(ucontrol->value.bytes.data, len, GFP_KERNEL | GFP_DMA);
   2738	if (!data)
   2739		return -ENOMEM;
   2740
   2741	data[0] &= cpu_to_be16(ARIZONA_EQ1_B1_MODE);
   2742
   2743	if (arizona_eq_filter_unstable(!!data[0], data[1], data[2]) ||
   2744	    arizona_eq_filter_unstable(true, data[4], data[5]) ||
   2745	    arizona_eq_filter_unstable(true, data[8], data[9]) ||
   2746	    arizona_eq_filter_unstable(true, data[12], data[13]) ||
   2747	    arizona_eq_filter_unstable(false, data[16], data[17])) {
   2748		dev_err(arizona->dev, "Rejecting unstable EQ coefficients\n");
   2749		ret = -EINVAL;
   2750		goto out;
   2751	}
   2752
   2753	ret = regmap_read(arizona->regmap, params->base, &val);
   2754	if (ret != 0)
   2755		goto out;
   2756
   2757	val &= ~ARIZONA_EQ1_B1_MODE;
   2758	data[0] |= cpu_to_be16(val);
   2759
   2760	ret = regmap_raw_write(arizona->regmap, params->base, data, len);
   2761
   2762out:
   2763	kfree(data);
   2764	return ret;
   2765}
   2766EXPORT_SYMBOL_GPL(arizona_eq_coeff_put);
   2767
   2768int arizona_lhpf_coeff_put(struct snd_kcontrol *kcontrol,
   2769			   struct snd_ctl_elem_value *ucontrol)
   2770{
   2771	struct snd_soc_component *component = snd_soc_kcontrol_component(kcontrol);
   2772	struct arizona *arizona = dev_get_drvdata(component->dev->parent);
   2773	__be16 *data = (__be16 *)ucontrol->value.bytes.data;
   2774	s16 val = be16_to_cpu(*data);
   2775
   2776	if (abs(val) >= 4096) {
   2777		dev_err(arizona->dev, "Rejecting unstable LHPF coefficients\n");
   2778		return -EINVAL;
   2779	}
   2780
   2781	return snd_soc_bytes_put(kcontrol, ucontrol);
   2782}
   2783EXPORT_SYMBOL_GPL(arizona_lhpf_coeff_put);
   2784
   2785int arizona_of_get_audio_pdata(struct arizona *arizona)
   2786{
   2787	struct arizona_pdata *pdata = &arizona->pdata;
   2788	struct device_node *np = arizona->dev->of_node;
   2789	struct property *prop;
   2790	const __be32 *cur;
   2791	u32 val;
   2792	u32 pdm_val[ARIZONA_MAX_PDM_SPK];
   2793	int ret;
   2794	int count = 0;
   2795
   2796	count = 0;
   2797	of_property_for_each_u32(np, "wlf,inmode", prop, cur, val) {
   2798		if (count == ARRAY_SIZE(pdata->inmode))
   2799			break;
   2800
   2801		pdata->inmode[count] = val;
   2802		count++;
   2803	}
   2804
   2805	count = 0;
   2806	of_property_for_each_u32(np, "wlf,dmic-ref", prop, cur, val) {
   2807		if (count == ARRAY_SIZE(pdata->dmic_ref))
   2808			break;
   2809
   2810		pdata->dmic_ref[count] = val;
   2811		count++;
   2812	}
   2813
   2814	count = 0;
   2815	of_property_for_each_u32(np, "wlf,out-mono", prop, cur, val) {
   2816		if (count == ARRAY_SIZE(pdata->out_mono))
   2817			break;
   2818
   2819		pdata->out_mono[count] = !!val;
   2820		count++;
   2821	}
   2822
   2823	count = 0;
   2824	of_property_for_each_u32(np, "wlf,max-channels-clocked", prop, cur, val) {
   2825		if (count == ARRAY_SIZE(pdata->max_channels_clocked))
   2826			break;
   2827
   2828		pdata->max_channels_clocked[count] = val;
   2829		count++;
   2830	}
   2831
   2832	count = 0;
   2833	of_property_for_each_u32(np, "wlf,out-volume-limit", prop, cur, val) {
   2834		if (count == ARRAY_SIZE(pdata->out_vol_limit))
   2835			break;
   2836
   2837		pdata->out_vol_limit[count] = val;
   2838		count++;
   2839	}
   2840
   2841	ret = of_property_read_u32_array(np, "wlf,spk-fmt",
   2842					 pdm_val, ARRAY_SIZE(pdm_val));
   2843
   2844	if (ret >= 0)
   2845		for (count = 0; count < ARRAY_SIZE(pdata->spk_fmt); ++count)
   2846			pdata->spk_fmt[count] = pdm_val[count];
   2847
   2848	ret = of_property_read_u32_array(np, "wlf,spk-mute",
   2849					 pdm_val, ARRAY_SIZE(pdm_val));
   2850
   2851	if (ret >= 0)
   2852		for (count = 0; count < ARRAY_SIZE(pdata->spk_mute); ++count)
   2853			pdata->spk_mute[count] = pdm_val[count];
   2854
   2855	return 0;
   2856}
   2857EXPORT_SYMBOL_GPL(arizona_of_get_audio_pdata);
   2858
   2859MODULE_DESCRIPTION("ASoC Wolfson Arizona class device support");
   2860MODULE_AUTHOR("Mark Brown <broonie@opensource.wolfsonmicro.com>");
   2861MODULE_LICENSE("GPL");