Unverified Commit 15909885 authored by Krzysztof Kozlowski's avatar Krzysztof Kozlowski Committed by Mark Brown
Browse files

ASoC: qcom: x1e80100: Support boards with two speakers



Some Qualcomm X1E laptops have only two speakers.  Regardless whether
this sound card driver is suitable for them (we could re-use one for
some older SoC), we should set reasonable channel map depending on the
number of channels, not always 4-speaker setup.

This change is necessary for bringing audio support on Lenovo Thinkpad
T14s with Qualcomm X1E78100 and only two speakers.

Signed-off-by: default avatarKrzysztof Kozlowski <krzysztof.kozlowski@linaro.org>
Link: https://patch.msgid.link/20241023124152.130706-1-krzysztof.kozlowski@linaro.org


Signed-off-by: default avatarMark Brown <broonie@kernel.org>
parent 8f5fab53
Loading
Loading
Loading
Loading
+35 −5
Original line number Diff line number Diff line
@@ -95,23 +95,53 @@ static int x1e80100_snd_hw_params(struct snd_pcm_substream *substream,
	return qcom_snd_sdw_hw_params(substream, params, &data->sruntime[cpu_dai->id]);
}

static int x1e80100_snd_hw_map_channels(unsigned int *ch_map, int num)
{
	switch (num) {
	case 1:
		ch_map[0] = PCM_CHANNEL_FC;
		break;
	case 2:
		ch_map[0] = PCM_CHANNEL_FL;
		ch_map[1] = PCM_CHANNEL_FR;
		break;
	case 3:
		ch_map[0] = PCM_CHANNEL_FL;
		ch_map[1] = PCM_CHANNEL_FR;
		ch_map[2] = PCM_CHANNEL_FC;
		break;
	case 4:
		ch_map[0] = PCM_CHANNEL_FL;
		ch_map[1] = PCM_CHANNEL_LB;
		ch_map[2] = PCM_CHANNEL_FR;
		ch_map[3] = PCM_CHANNEL_RB;
		break;
	default:
		return -EINVAL;
	}

	return 0;
}

static int x1e80100_snd_prepare(struct snd_pcm_substream *substream)
{
	struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
	struct snd_soc_dai *cpu_dai = snd_soc_rtd_to_cpu(rtd, 0);
	struct x1e80100_snd_data *data = snd_soc_card_get_drvdata(rtd->card);
	struct sdw_stream_runtime *sruntime = data->sruntime[cpu_dai->id];
	const unsigned int rx_slot[4] = { PCM_CHANNEL_FL,
					  PCM_CHANNEL_LB,
					  PCM_CHANNEL_FR,
					  PCM_CHANNEL_RB };
	unsigned int channels = substream->runtime->channels;
	unsigned int rx_slot[4];
	int ret;

	switch (cpu_dai->id) {
	case WSA_CODEC_DMA_RX_0:
	case WSA_CODEC_DMA_RX_1:
		ret = x1e80100_snd_hw_map_channels(rx_slot, channels);
		if (ret)
			return ret;

		ret = snd_soc_dai_set_channel_map(cpu_dai, 0, NULL,
						  ARRAY_SIZE(rx_slot), rx_slot);
						  channels, rx_slot);
		if (ret)
			return ret;
		break;