Commit 08bd31ec authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull sound fixes from Takashi Iwai:
 "It became more than wished, partly because of vacations. But all
  changes are fairly device-specific and should be safe to apply:

   - A regression fix for Oops at ASoC HD-audio probe

   - A series of TAS2781 HD-audio codec fixes

   - A random build regression fix with SPI helpers

   - Minor endianness fix for USB-audio mixer code

   - ASoC FSL driver error handling fix

   - ASoC Mediatek driver register fix

   - A series of ASoC meson g12a driver fixes

   - A few usual HD-audio oneliner quirks"

* tag 'sound-6.7-final' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound:
  ALSA: hda/realtek: Fix mute and mic-mute LEDs for HP ProBook 440 G6
  ASoC: meson: g12a-tohdmitx: Fix event generation for S/PDIF mux
  ASoC: meson: g12a-toacodec: Fix event generation
  ASoC: meson: g12a-tohdmitx: Validate written enum values
  ASoC: meson: g12a-toacodec: Validate written enum values
  ASoC: SOF: Intel: hda-codec: Delay the codec device registration
  ALSA: hda: cs35l41: fix building without CONFIG_SPI
  ALSA: hda/realtek: fix mute/micmute LEDs for a HP ZBook
  ALSA: hda/realtek: enable SND_PCI_QUIRK for hp pavilion 14-ec1xxx series
  ASoC: mediatek: mt8186: fix AUD_PAD_TOP register and offset
  ALSA: scarlett2: Convert meter levels from little-endian
  ALSA: hda/tas2781: remove sound controls in unbind
  ALSA: hda/tas2781: move set_drv_data outside tasdevice_init
  ALSA: hda/tas2781: fix typos in comment
  ALSA: hda/tas2781: do not use regcache
  ASoC: fsl_rpmsg: Fix error handler with pm_runtime_enable
parents 5939a693 b6ce6e6c
Loading
Loading
Loading
Loading
+1 −3
Original line number Diff line number Diff line
@@ -211,7 +211,6 @@ static int generic_dsd_config(struct cs35l41_hda *cs35l41, struct device *physde
	if (cfg->bus == SPI) {
		cs35l41->index = id;

#if IS_ENABLED(CONFIG_SPI)
		/*
		 * Manually set the Chip Select for the second amp <cs_gpio_index> in the node.
		 * This is only supported for systems with 2 amps, since we cannot expand the
@@ -220,7 +219,7 @@ static int generic_dsd_config(struct cs35l41_hda *cs35l41, struct device *physde
		 * uses a native chip select), to ensure the second amp does not clash with the
		 * first.
		 */
		if (cfg->cs_gpio_index >= 0) {
		if (IS_ENABLED(CONFIG_SPI) && cfg->cs_gpio_index >= 0) {
			spi = to_spi_device(cs35l41->dev);

			if (cfg->num_amps != 2) {
@@ -251,7 +250,6 @@ static int generic_dsd_config(struct cs35l41_hda *cs35l41, struct device *physde
				spi_setup(spi);
			}
		}
#endif
	} else {
		if (cfg->num_amps > 2)
			/*
+3 −0
Original line number Diff line number Diff line
@@ -9799,6 +9799,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = {
	SND_PCI_QUIRK(0x103c, 0x84da, "HP OMEN dc0019-ur", ALC295_FIXUP_HP_OMEN),
	SND_PCI_QUIRK(0x103c, 0x84e7, "HP Pavilion 15", ALC269_FIXUP_HP_MUTE_LED_MIC3),
	SND_PCI_QUIRK(0x103c, 0x8519, "HP Spectre x360 15-df0xxx", ALC285_FIXUP_HP_SPECTRE_X360),
	SND_PCI_QUIRK(0x103c, 0x8537, "HP ProBook 440 G6", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF),
	SND_PCI_QUIRK(0x103c, 0x860f, "HP ZBook 15 G6", ALC285_FIXUP_HP_GPIO_AMP_INIT),
	SND_PCI_QUIRK(0x103c, 0x861f, "HP Elite Dragonfly G1", ALC285_FIXUP_HP_GPIO_AMP_INIT),
	SND_PCI_QUIRK(0x103c, 0x869d, "HP", ALC236_FIXUP_HP_MUTE_LED),
@@ -9881,6 +9882,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = {
	SND_PCI_QUIRK(0x103c, 0x89c6, "Zbook Fury 17 G9", ALC245_FIXUP_CS35L41_SPI_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x89ca, "HP", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF),
	SND_PCI_QUIRK(0x103c, 0x89d3, "HP EliteBook 645 G9 (MB 89D2)", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF),
	SND_PCI_QUIRK(0x103c, 0x8a0f, "HP Pavilion 14-ec1xxx", ALC287_FIXUP_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8a20, "HP Laptop 15s-fq5xxx", ALC236_FIXUP_HP_MUTE_LED_COEFBIT2),
	SND_PCI_QUIRK(0x103c, 0x8a25, "HP Victus 16-d1xxx (MB 8A25)", ALC245_FIXUP_HP_MUTE_LED_COEFBIT),
	SND_PCI_QUIRK(0x103c, 0x8a78, "HP Dev One", ALC285_FIXUP_HP_LIMIT_INT_MIC_BOOST),
@@ -9925,6 +9927,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = {
	SND_PCI_QUIRK(0x103c, 0x8c70, "HP EliteBook 835 G11", ALC287_FIXUP_CS35L41_I2C_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8c71, "HP EliteBook 845 G11", ALC287_FIXUP_CS35L41_I2C_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8c72, "HP EliteBook 865 G11", ALC287_FIXUP_CS35L41_I2C_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8c96, "HP", ALC236_FIXUP_HP_MUTE_LED_MICMUTE_VREF),
	SND_PCI_QUIRK(0x103c, 0x8ca4, "HP ZBook Fury", ALC245_FIXUP_CS35L41_SPI_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8ca7, "HP ZBook Fury", ALC245_FIXUP_CS35L41_SPI_2_HP_GPIO_LED),
	SND_PCI_QUIRK(0x103c, 0x8cf5, "HP ZBook Studio 16", ALC245_FIXUP_CS35L41_SPI_4_HP_GPIO_LED),
+134 −110
Original line number Diff line number Diff line
@@ -65,6 +65,15 @@ enum calib_data {
	CALIB_MAX
};

struct tas2781_hda {
	struct device *dev;
	struct tasdevice_priv *priv;
	struct snd_kcontrol *dsp_prog_ctl;
	struct snd_kcontrol *dsp_conf_ctl;
	struct snd_kcontrol *prof_ctl;
	struct snd_kcontrol *snd_ctls[3];
};

static int tas2781_get_i2c_res(struct acpi_resource *ares, void *data)
{
	struct tasdevice_priv *tas_priv = data;
@@ -125,26 +134,26 @@ static int tas2781_read_acpi(struct tasdevice_priv *p, const char *hid)

static void tas2781_hda_playback_hook(struct device *dev, int action)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);

	dev_dbg(tas_priv->dev, "%s: action = %d\n", __func__, action);
	dev_dbg(tas_hda->dev, "%s: action = %d\n", __func__, action);
	switch (action) {
	case HDA_GEN_PCM_ACT_OPEN:
		pm_runtime_get_sync(dev);
		mutex_lock(&tas_priv->codec_lock);
		tasdevice_tuning_switch(tas_priv, 0);
		mutex_unlock(&tas_priv->codec_lock);
		mutex_lock(&tas_hda->priv->codec_lock);
		tasdevice_tuning_switch(tas_hda->priv, 0);
		mutex_unlock(&tas_hda->priv->codec_lock);
		break;
	case HDA_GEN_PCM_ACT_CLOSE:
		mutex_lock(&tas_priv->codec_lock);
		tasdevice_tuning_switch(tas_priv, 1);
		mutex_unlock(&tas_priv->codec_lock);
		mutex_lock(&tas_hda->priv->codec_lock);
		tasdevice_tuning_switch(tas_hda->priv, 1);
		mutex_unlock(&tas_hda->priv->codec_lock);

		pm_runtime_mark_last_busy(dev);
		pm_runtime_put_autosuspend(dev);
		break;
	default:
		dev_dbg(tas_priv->dev, "Playback action not supported: %d\n",
		dev_dbg(tas_hda->dev, "Playback action not supported: %d\n",
			action);
		break;
	}
@@ -421,9 +430,9 @@ static void tas2781_apply_calib(struct tasdevice_priv *tas_priv)
	}
}

/* Update the calibrate data, including speaker impedance, f0, etc, into algo.
/* Update the calibration data, including speaker impedance, f0, etc, into algo.
 * Calibrate data is done by manufacturer in the factory. These data are used
 * by Algo for calucating the speaker temperature, speaker membrance excursion
 * by Algo for calculating the speaker temperature, speaker membrane excursion
 * and f0 in real time during playback.
 */
static int tas2781_save_calibration(struct tasdevice_priv *tas_priv)
@@ -477,9 +486,28 @@ static int tas2781_save_calibration(struct tasdevice_priv *tas_priv)
	return 0;
}

static void tas2781_hda_remove_controls(struct tas2781_hda *tas_hda)
{
	struct hda_codec *codec = tas_hda->priv->codec;

	if (tas_hda->dsp_prog_ctl)
		snd_ctl_remove(codec->card, tas_hda->dsp_prog_ctl);

	if (tas_hda->dsp_conf_ctl)
		snd_ctl_remove(codec->card, tas_hda->dsp_conf_ctl);

	for (int i = ARRAY_SIZE(tas_hda->snd_ctls) - 1; i >= 0; i--)
		if (tas_hda->snd_ctls[i])
			snd_ctl_remove(codec->card, tas_hda->snd_ctls[i]);

	if (tas_hda->prof_ctl)
		snd_ctl_remove(codec->card, tas_hda->prof_ctl);
}

static void tasdev_fw_ready(const struct firmware *fmw, void *context)
{
	struct tasdevice_priv *tas_priv = context;
	struct tas2781_hda *tas_hda = dev_get_drvdata(tas_priv->dev);
	struct hda_codec *codec = tas_priv->codec;
	int i, ret;

@@ -490,8 +518,8 @@ static void tasdev_fw_ready(const struct firmware *fmw, void *context)
	if (ret)
		goto out;

	ret = snd_ctl_add(codec->card,
		snd_ctl_new1(&tas2781_prof_ctrl, tas_priv));
	tas_hda->prof_ctl = snd_ctl_new1(&tas2781_prof_ctrl, tas_priv);
	ret = snd_ctl_add(codec->card, tas_hda->prof_ctl);
	if (ret) {
		dev_err(tas_priv->dev,
			"Failed to add KControl %s = %d\n",
@@ -500,8 +528,9 @@ static void tasdev_fw_ready(const struct firmware *fmw, void *context)
	}

	for (i = 0; i < ARRAY_SIZE(tas2781_snd_controls); i++) {
		ret = snd_ctl_add(codec->card,
			snd_ctl_new1(&tas2781_snd_controls[i], tas_priv));
		tas_hda->snd_ctls[i] = snd_ctl_new1(&tas2781_snd_controls[i],
			tas_priv);
		ret = snd_ctl_add(codec->card, tas_hda->snd_ctls[i]);
		if (ret) {
			dev_err(tas_priv->dev,
				"Failed to add KControl %s = %d\n",
@@ -523,8 +552,9 @@ static void tasdev_fw_ready(const struct firmware *fmw, void *context)
		goto out;
	}

	ret = snd_ctl_add(codec->card,
		snd_ctl_new1(&tas2781_dsp_prog_ctrl, tas_priv));
	tas_hda->dsp_prog_ctl = snd_ctl_new1(&tas2781_dsp_prog_ctrl,
		tas_priv);
	ret = snd_ctl_add(codec->card, tas_hda->dsp_prog_ctl);
	if (ret) {
		dev_err(tas_priv->dev,
			"Failed to add KControl %s = %d\n",
@@ -532,8 +562,9 @@ static void tasdev_fw_ready(const struct firmware *fmw, void *context)
		goto out;
	}

	ret = snd_ctl_add(codec->card,
		snd_ctl_new1(&tas2781_dsp_conf_ctrl, tas_priv));
	tas_hda->dsp_conf_ctl = snd_ctl_new1(&tas2781_dsp_conf_ctrl,
		tas_priv);
	ret = snd_ctl_add(codec->card, tas_hda->dsp_conf_ctl);
	if (ret) {
		dev_err(tas_priv->dev,
			"Failed to add KControl %s = %d\n",
@@ -554,27 +585,27 @@ static void tasdev_fw_ready(const struct firmware *fmw, void *context)
	tas2781_save_calibration(tas_priv);

out:
	mutex_unlock(&tas_priv->codec_lock);
	mutex_unlock(&tas_hda->priv->codec_lock);
	if (fmw)
		release_firmware(fmw);
	pm_runtime_mark_last_busy(tas_priv->dev);
	pm_runtime_put_autosuspend(tas_priv->dev);
	pm_runtime_mark_last_busy(tas_hda->dev);
	pm_runtime_put_autosuspend(tas_hda->dev);
}

static int tas2781_hda_bind(struct device *dev, struct device *master,
	void *master_data)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	struct hda_component *comps = master_data;
	struct hda_codec *codec;
	unsigned int subid;
	int ret;

	if (!comps || tas_priv->index < 0 ||
		tas_priv->index >= HDA_MAX_COMPONENTS)
	if (!comps || tas_hda->priv->index < 0 ||
		tas_hda->priv->index >= HDA_MAX_COMPONENTS)
		return -EINVAL;

	comps = &comps[tas_priv->index];
	comps = &comps[tas_hda->priv->index];
	if (comps->dev)
		return -EBUSY;

@@ -583,10 +614,10 @@ static int tas2781_hda_bind(struct device *dev, struct device *master,

	switch (subid) {
	case 0x17aa:
		tas_priv->catlog_id = LENOVO;
		tas_hda->priv->catlog_id = LENOVO;
		break;
	default:
		tas_priv->catlog_id = OTHERS;
		tas_hda->priv->catlog_id = OTHERS;
		break;
	}

@@ -596,7 +627,7 @@ static int tas2781_hda_bind(struct device *dev, struct device *master,

	strscpy(comps->name, dev_name(dev), sizeof(comps->name));

	ret = tascodec_init(tas_priv, codec, tasdev_fw_ready);
	ret = tascodec_init(tas_hda->priv, codec, tasdev_fw_ready);
	if (!ret)
		comps->playback_hook = tas2781_hda_playback_hook;

@@ -609,9 +640,9 @@ static int tas2781_hda_bind(struct device *dev, struct device *master,
static void tas2781_hda_unbind(struct device *dev,
	struct device *master, void *master_data)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	struct hda_component *comps = master_data;
	comps = &comps[tas_priv->index];
	comps = &comps[tas_hda->priv->index];

	if (comps->dev == dev) {
		comps->dev = NULL;
@@ -619,10 +650,12 @@ static void tas2781_hda_unbind(struct device *dev,
		comps->playback_hook = NULL;
	}

	tasdevice_config_info_remove(tas_priv);
	tasdevice_dsp_remove(tas_priv);
	tas2781_hda_remove_controls(tas_hda);

	tas_priv->fw_state = TASDEVICE_DSP_FW_PENDING;
	tasdevice_config_info_remove(tas_hda->priv);
	tasdevice_dsp_remove(tas_hda->priv);

	tas_hda->priv->fw_state = TASDEVICE_DSP_FW_PENDING;
}

static const struct component_ops tas2781_hda_comp_ops = {
@@ -632,21 +665,21 @@ static const struct component_ops tas2781_hda_comp_ops = {

static void tas2781_hda_remove(struct device *dev)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);

	pm_runtime_get_sync(tas_priv->dev);
	pm_runtime_disable(tas_priv->dev);
	pm_runtime_get_sync(tas_hda->dev);
	pm_runtime_disable(tas_hda->dev);

	component_del(tas_priv->dev, &tas2781_hda_comp_ops);
	component_del(tas_hda->dev, &tas2781_hda_comp_ops);

	pm_runtime_put_noidle(tas_priv->dev);
	pm_runtime_put_noidle(tas_hda->dev);

	tasdevice_remove(tas_priv);
	tasdevice_remove(tas_hda->priv);
}

static int tas2781_hda_i2c_probe(struct i2c_client *clt)
{
	struct tasdevice_priv *tas_priv;
	struct tas2781_hda *tas_hda;
	const char *device_name;
	int ret;

@@ -655,35 +688,42 @@ static int tas2781_hda_i2c_probe(struct i2c_client *clt)
	else
		return -ENODEV;

	tas_priv = tasdevice_kzalloc(clt);
	if (!tas_priv)
	tas_hda = devm_kzalloc(&clt->dev, sizeof(*tas_hda), GFP_KERNEL);
	if (!tas_hda)
		return -ENOMEM;

	dev_set_drvdata(&clt->dev, tas_hda);
	tas_hda->dev = &clt->dev;

	tas_hda->priv = tasdevice_kzalloc(clt);
	if (!tas_hda->priv)
		return -ENOMEM;

	tas_priv->irq_info.irq = clt->irq;
	ret = tas2781_read_acpi(tas_priv, device_name);
	tas_hda->priv->irq_info.irq = clt->irq;
	ret = tas2781_read_acpi(tas_hda->priv, device_name);
	if (ret)
		return dev_err_probe(tas_priv->dev, ret,
		return dev_err_probe(tas_hda->dev, ret,
			"Platform not supported\n");

	ret = tasdevice_init(tas_priv);
	ret = tasdevice_init(tas_hda->priv);
	if (ret)
		goto err;

	pm_runtime_set_autosuspend_delay(tas_priv->dev, 3000);
	pm_runtime_use_autosuspend(tas_priv->dev);
	pm_runtime_mark_last_busy(tas_priv->dev);
	pm_runtime_set_active(tas_priv->dev);
	pm_runtime_get_noresume(tas_priv->dev);
	pm_runtime_enable(tas_priv->dev);
	pm_runtime_set_autosuspend_delay(tas_hda->dev, 3000);
	pm_runtime_use_autosuspend(tas_hda->dev);
	pm_runtime_mark_last_busy(tas_hda->dev);
	pm_runtime_set_active(tas_hda->dev);
	pm_runtime_get_noresume(tas_hda->dev);
	pm_runtime_enable(tas_hda->dev);

	pm_runtime_put_autosuspend(tas_priv->dev);
	pm_runtime_put_autosuspend(tas_hda->dev);

	tas2781_reset(tas_priv);
	tas2781_reset(tas_hda->priv);

	ret = component_add(tas_priv->dev, &tas2781_hda_comp_ops);
	ret = component_add(tas_hda->dev, &tas2781_hda_comp_ops);
	if (ret) {
		dev_err(tas_priv->dev, "Register component failed: %d\n", ret);
		pm_runtime_disable(tas_priv->dev);
		dev_err(tas_hda->dev, "Register component failed: %d\n", ret);
		pm_runtime_disable(tas_hda->dev);
	}

err:
@@ -699,81 +739,65 @@ static void tas2781_hda_i2c_remove(struct i2c_client *clt)

static int tas2781_runtime_suspend(struct device *dev)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	int i;

	dev_dbg(tas_priv->dev, "Runtime Suspend\n");
	dev_dbg(tas_hda->dev, "Runtime Suspend\n");

	mutex_lock(&tas_priv->codec_lock);
	mutex_lock(&tas_hda->priv->codec_lock);

	if (tas_priv->playback_started) {
		tasdevice_tuning_switch(tas_priv, 1);
		tas_priv->playback_started = false;
	if (tas_hda->priv->playback_started) {
		tasdevice_tuning_switch(tas_hda->priv, 1);
		tas_hda->priv->playback_started = false;
	}

	for (i = 0; i < tas_priv->ndev; i++) {
		tas_priv->tasdevice[i].cur_book = -1;
		tas_priv->tasdevice[i].cur_prog = -1;
		tas_priv->tasdevice[i].cur_conf = -1;
	for (i = 0; i < tas_hda->priv->ndev; i++) {
		tas_hda->priv->tasdevice[i].cur_book = -1;
		tas_hda->priv->tasdevice[i].cur_prog = -1;
		tas_hda->priv->tasdevice[i].cur_conf = -1;
	}

	regcache_cache_only(tas_priv->regmap, true);
	regcache_mark_dirty(tas_priv->regmap);

	mutex_unlock(&tas_priv->codec_lock);
	mutex_unlock(&tas_hda->priv->codec_lock);

	return 0;
}

static int tas2781_runtime_resume(struct device *dev)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	unsigned long calib_data_sz =
		tas_priv->ndev * TASDEVICE_SPEAKER_CALIBRATION_SIZE;
	int ret;
		tas_hda->priv->ndev * TASDEVICE_SPEAKER_CALIBRATION_SIZE;

	dev_dbg(tas_priv->dev, "Runtime Resume\n");
	dev_dbg(tas_hda->dev, "Runtime Resume\n");

	mutex_lock(&tas_priv->codec_lock);
	mutex_lock(&tas_hda->priv->codec_lock);

	regcache_cache_only(tas_priv->regmap, false);
	ret = regcache_sync(tas_priv->regmap);
	if (ret) {
		dev_err(tas_priv->dev,
			"Failed to restore register cache: %d\n", ret);
		goto out;
	}

	tasdevice_prmg_load(tas_priv, tas_priv->cur_prog);
	tasdevice_prmg_load(tas_hda->priv, tas_hda->priv->cur_prog);

	/* If calibrated data occurs error, dsp will still works with default
	 * calibrated data inside algo.
	 */
	if (tas_priv->cali_data.total_sz > calib_data_sz)
		tas2781_apply_calib(tas_priv);
	if (tas_hda->priv->cali_data.total_sz > calib_data_sz)
		tas2781_apply_calib(tas_hda->priv);

out:
	mutex_unlock(&tas_priv->codec_lock);
	mutex_unlock(&tas_hda->priv->codec_lock);

	return ret;
	return 0;
}

static int tas2781_system_suspend(struct device *dev)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	int ret;

	dev_dbg(tas_priv->dev, "System Suspend\n");
	dev_dbg(tas_hda->priv->dev, "System Suspend\n");

	ret = pm_runtime_force_suspend(dev);
	if (ret)
		return ret;

	/* Shutdown chip before system suspend */
	regcache_cache_only(tas_priv->regmap, false);
	tasdevice_tuning_switch(tas_priv, 1);
	regcache_cache_only(tas_priv->regmap, true);
	regcache_mark_dirty(tas_priv->regmap);
	tasdevice_tuning_switch(tas_hda->priv, 1);

	/*
	 * Reset GPIO may be shared, so cannot reset here.
@@ -784,33 +808,33 @@ static int tas2781_system_suspend(struct device *dev)

static int tas2781_system_resume(struct device *dev)
{
	struct tasdevice_priv *tas_priv = dev_get_drvdata(dev);
	struct tas2781_hda *tas_hda = dev_get_drvdata(dev);
	unsigned long calib_data_sz =
		tas_priv->ndev * TASDEVICE_SPEAKER_CALIBRATION_SIZE;
		tas_hda->priv->ndev * TASDEVICE_SPEAKER_CALIBRATION_SIZE;
	int i, ret;

	dev_dbg(tas_priv->dev, "System Resume\n");
	dev_info(tas_hda->priv->dev, "System Resume\n");

	ret = pm_runtime_force_resume(dev);
	if (ret)
		return ret;

	mutex_lock(&tas_priv->codec_lock);
	mutex_lock(&tas_hda->priv->codec_lock);

	for (i = 0; i < tas_priv->ndev; i++) {
		tas_priv->tasdevice[i].cur_book = -1;
		tas_priv->tasdevice[i].cur_prog = -1;
		tas_priv->tasdevice[i].cur_conf = -1;
	for (i = 0; i < tas_hda->priv->ndev; i++) {
		tas_hda->priv->tasdevice[i].cur_book = -1;
		tas_hda->priv->tasdevice[i].cur_prog = -1;
		tas_hda->priv->tasdevice[i].cur_conf = -1;
	}
	tas2781_reset(tas_priv);
	tasdevice_prmg_load(tas_priv, tas_priv->cur_prog);
	tas2781_reset(tas_hda->priv);
	tasdevice_prmg_load(tas_hda->priv, tas_hda->priv->cur_prog);

	/* If calibrated data occurs error, dsp will still work with default
	 * calibrated data inside algo.
	 */
	if (tas_priv->cali_data.total_sz > calib_data_sz)
		tas2781_apply_calib(tas_priv);
	mutex_unlock(&tas_priv->codec_lock);
	if (tas_hda->priv->cali_data.total_sz > calib_data_sz)
		tas2781_apply_calib(tas_hda->priv);
	mutex_unlock(&tas_hda->priv->codec_lock);

	return 0;
}
+1 −3
Original line number Diff line number Diff line
@@ -39,7 +39,7 @@ static const struct regmap_range_cfg tasdevice_ranges[] = {
static const struct regmap_config tasdevice_regmap = {
	.reg_bits = 8,
	.val_bits = 8,
	.cache_type = REGCACHE_RBTREE,
	.cache_type = REGCACHE_NONE,
	.ranges = tasdevice_ranges,
	.num_ranges = ARRAY_SIZE(tasdevice_ranges),
	.max_register = 256 * 128,
@@ -316,8 +316,6 @@ int tasdevice_init(struct tasdevice_priv *tas_priv)
		tas_priv->tasdevice[i].cur_conf = -1;
	}

	dev_set_drvdata(tas_priv->dev, tas_priv);

	mutex_init(&tas_priv->codec_lock);

out:
+2 −0
Original line number Diff line number Diff line
@@ -689,6 +689,8 @@ static int tasdevice_i2c_probe(struct i2c_client *i2c)
	if (!tas_priv)
		return -ENOMEM;

	dev_set_drvdata(&i2c->dev, tas_priv);

	if (ACPI_HANDLE(&i2c->dev)) {
		acpi_id = acpi_match_device(i2c->dev.driver->acpi_match_table,
				&i2c->dev);
Loading