Commit 63e1968a authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull sound fixes from Takashi Iwai:
 "A collection of small, mostly device-specific fixes.

  The significant one is the regression fix for USB-audio implicit
  feedback devices due to the incorrect frame size calculation, which
  landed in 5.8 and stable trees.

  In addition, a few usual HD-audio and USB-audio quirks, Intel HDMI
  fixes, ASoC fsl and rt5682 fixes, as well as the fix in
  compress-offload partial drain operation"

* tag 'sound-5.8-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound:
  ALSA: compress: fix partial_drain completion state
  ALSA: usb-audio: Add implicit feedback quirk for RTX6001
  ALSA: usb-audio: add quirk for MacroSilicon MS2109
  ALSA: hda/realtek: Enable headset mic of Acer Veriton N4660G with ALC269VC
  ALSA: hda/realtek: Enable headset mic of Acer C20-820 with ALC269VC
  ALSA: hda/realtek - Enable audio jacks of Acer vCopperbox with ALC269VC
  ALSA: hda/realtek - Fix Lenovo Thinkpad X1 Carbon 7th quirk subdevice id
  ALSA: hda/hdmi: improve debug traces for stream lookups
  ALSA: hda/hdmi: fix failures at PCM open on Intel ICL and later
  ALSA: opl3: fix infoleak in opl3
  ALSA: usb-audio: Replace s/frame/packet/ where appropriate
  ALSA: usb-audio: Fix packet size calculation
  AsoC: amd: add missing snd- module prefix to the acp3x-rn driver kernel module
  ALSA: hda - let hs_mic be picked ahead of hp_mic
  ASoC: rt5682: fix the pop noise while OMTP type headset plugin
  ASoC: fsl_mqs: Fix unchecked return value for clk_prepare_enable
  ASoC: fsl_mqs: Don't check clock is NULL before calling clk API
parents 6ec4476a f79a732a
Loading
Loading
Loading
Loading
+9 −1
Original line number Diff line number Diff line
@@ -66,6 +66,7 @@ struct snd_compr_runtime {
 * @direction: stream direction, playback/recording
 * @metadata_set: metadata set flag, true when set
 * @next_track: has userspace signal next track transition, true when set
 * @partial_drain: undergoing partial_drain for stream, true when set
 * @private_data: pointer to DSP private data
 * @dma_buffer: allocated buffer if any
 */
@@ -78,6 +79,7 @@ struct snd_compr_stream {
	enum snd_compr_direction direction;
	bool metadata_set;
	bool next_track;
	bool partial_drain;
	void *private_data;
	struct snd_dma_buffer dma_buffer;
};
@@ -182,7 +184,13 @@ static inline void snd_compr_drain_notify(struct snd_compr_stream *stream)
	if (snd_BUG_ON(!stream))
		return;

	/* for partial_drain case we are back to running state on success */
	if (stream->partial_drain) {
		stream->runtime->state = SNDRV_PCM_STATE_RUNNING;
		stream->partial_drain = false; /* clear this flag as well */
	} else {
		stream->runtime->state = SNDRV_PCM_STATE_SETUP;
	}

	wake_up(&stream->runtime->sleep);
}
+4 −0
Original line number Diff line number Diff line
@@ -764,6 +764,9 @@ static int snd_compr_stop(struct snd_compr_stream *stream)

	retval = stream->ops->trigger(stream, SNDRV_PCM_TRIGGER_STOP);
	if (!retval) {
		/* clear flags and stop any drain wait */
		stream->partial_drain = false;
		stream->metadata_set = false;
		snd_compr_drain_notify(stream);
		stream->runtime->total_bytes_available = 0;
		stream->runtime->total_bytes_transferred = 0;
@@ -921,6 +924,7 @@ static int snd_compr_partial_drain(struct snd_compr_stream *stream)
	if (stream->next_track == false)
		return -EPERM;

	stream->partial_drain = true;
	retval = stream->ops->trigger(stream, SND_COMPR_TRIGGER_PARTIAL_DRAIN);
	if (retval) {
		pr_debug("Partial drain returned failure\n");
+2 −0
Original line number Diff line number Diff line
@@ -91,6 +91,8 @@ int snd_opl3_ioctl(struct snd_hwdep * hw, struct file *file,
		{
			struct snd_dm_fm_info info;

			memset(&info, 0, sizeof(info));

			info.fm_mode = opl3->fm_mode;
			info.rhythm = opl3->rhythm;
			if (copy_to_user(argp, &info, sizeof(struct snd_dm_fm_info)))
+6 −0
Original line number Diff line number Diff line
@@ -72,6 +72,12 @@ static int compare_input_type(const void *ap, const void *bp)
	if (a->type != b->type)
		return (int)(a->type - b->type);

	/* If has both hs_mic and hp_mic, pick the hs_mic ahead of hp_mic. */
	if (a->is_headset_mic && b->is_headphone_mic)
		return -1; /* don't swap */
	else if (a->is_headphone_mic && b->is_headset_mic)
		return 1; /* swap */

	/* In case one has boost and the other one has not,
	   pick the one with boost first. */
	return (int)(b->has_boost_on_pin - a->has_boost_on_pin);
+26 −15
Original line number Diff line number Diff line
@@ -259,7 +259,7 @@ static int hinfo_to_pcm_index(struct hda_codec *codec,
		if (get_pcm_rec(spec, pcm_idx)->stream == hinfo)
			return pcm_idx;

	codec_warn(codec, "HDMI: hinfo %p not registered\n", hinfo);
	codec_warn(codec, "HDMI: hinfo %p not tied to a PCM\n", hinfo);
	return -EINVAL;
}

@@ -277,7 +277,8 @@ static int hinfo_to_pin_index(struct hda_codec *codec,
			return pin_idx;
	}

	codec_dbg(codec, "HDMI: hinfo %p not registered\n", hinfo);
	codec_dbg(codec, "HDMI: hinfo %p (pcm %d) not registered\n", hinfo,
		  hinfo_to_pcm_index(codec, hinfo));
	return -EINVAL;
}

@@ -1804,33 +1805,43 @@ static int hdmi_add_cvt(struct hda_codec *codec, hda_nid_t cvt_nid)

static int hdmi_parse_codec(struct hda_codec *codec)
{
	hda_nid_t nid;
	hda_nid_t start_nid;
	unsigned int caps;
	int i, nodes;

	nodes = snd_hda_get_sub_nodes(codec, codec->core.afg, &nid);
	if (!nid || nodes < 0) {
	nodes = snd_hda_get_sub_nodes(codec, codec->core.afg, &start_nid);
	if (!start_nid || nodes < 0) {
		codec_warn(codec, "HDMI: failed to get afg sub nodes\n");
		return -EINVAL;
	}

	for (i = 0; i < nodes; i++, nid++) {
		unsigned int caps;
		unsigned int type;
	/*
	 * hdmi_add_pin() assumes total amount of converters to
	 * be known, so first discover all converters
	 */
	for (i = 0; i < nodes; i++) {
		hda_nid_t nid = start_nid + i;

		caps = get_wcaps(codec, nid);
		type = get_wcaps_type(caps);

		if (!(caps & AC_WCAP_DIGITAL))
			continue;

		switch (type) {
		case AC_WID_AUD_OUT:
		if (get_wcaps_type(caps) == AC_WID_AUD_OUT)
			hdmi_add_cvt(codec, nid);
			break;
		case AC_WID_PIN:
			hdmi_add_pin(codec, nid);
			break;
	}

	/* discover audio pins */
	for (i = 0; i < nodes; i++) {
		hda_nid_t nid = start_nid + i;

		caps = get_wcaps(codec, nid);

		if (!(caps & AC_WCAP_DIGITAL))
			continue;

		if (get_wcaps_type(caps) == AC_WID_PIN)
			hdmi_add_pin(codec, nid);
	}

	return 0;
Loading