Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 585b8ae2 authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "ASoC: codecs: add 32bit capture support in codec"

parents 136a397b 63b5522f
Loading
Loading
Loading
Loading
+135 −0
Original line number Original line Diff line number Diff line
@@ -3391,6 +3391,8 @@ struct asm_softvolume_params {


#define ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V3 0x00010DDC
#define ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V3 0x00010DDC


#define ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V4 0x0001320C

#define ASM_MEDIA_FMT_EVRCB_FS 0x00010BEF
#define ASM_MEDIA_FMT_EVRCB_FS 0x00010BEF


#define ASM_MEDIA_FMT_EVRCWB_FS 0x00010BF0
#define ASM_MEDIA_FMT_EVRCWB_FS 0x00010BF0
@@ -3493,6 +3495,56 @@ struct asm_multi_channel_pcm_fmt_blk_v3 {
 */
 */
} __packed;
} __packed;


struct asm_multi_channel_pcm_fmt_blk_v4 {
	uint16_t                num_channels;
/*
 * Number of channels
 * Supported values: 1 to 8
 */

	uint16_t                bits_per_sample;
/*
 * Number of bits per sample per channel
 * Supported values: 16, 24, 32
 */

	uint32_t                sample_rate;
/*
 * Number of samples per second
 * Supported values: 2000 to 48000, 96000,192000 Hz
 */

	uint16_t                is_signed;
/* Flag that indicates that PCM samples are signed (1) */

	uint16_t                sample_word_size;
/*
 * Size in bits of the word that holds a sample of a channel.
 * Supported values: 12,24,32
 */

	uint8_t                 channel_mapping[8];
/*
 * Each element, i, in the array describes channel i inside the buffer where
 * 0 <= i < num_channels. Unused channels are set to 0.
 */
	uint16_t                endianness;
/*
 * Flag to indicate the endianness of the pcm sample
 * Supported values: 0 - Little endian (all other formats)
 *                   1 - Big endian (AIFF)
 */
	uint16_t                mode;
/*
 * Mode to provide additional info about the pcm input data.
 * Supported values: 0 - Default QFs (Q15 for 16b, Q23 for packed 24b,
 *                       Q31 for unpacked 24b or 32b)
 *                  15 - for 16 bit
 *                  23 - for 24b packed or 8.24 format
 *                  31 - for 24b unpacked or 32bit
 */
} __packed;

/*
/*
 * Payload of the multichannel PCM configuration parameters in
 * Payload of the multichannel PCM configuration parameters in
 * the ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V3 media format.
 * the ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V3 media format.
@@ -3503,6 +3555,16 @@ struct asm_multi_channel_pcm_fmt_blk_param_v3 {
	struct asm_multi_channel_pcm_fmt_blk_v3 param;
	struct asm_multi_channel_pcm_fmt_blk_v3 param;
} __packed;
} __packed;


/*
 * Payload of the multichannel PCM configuration parameters in
 * the ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V4 media format.
 */
struct asm_multi_channel_pcm_fmt_blk_param_v4 {
	struct apr_hdr hdr;
	struct asm_data_cmd_media_fmt_update_v2 fmt_blk;
	struct asm_multi_channel_pcm_fmt_blk_v4 param;
} __packed;

struct asm_stream_cmd_set_encdec_param {
struct asm_stream_cmd_set_encdec_param {
	u32                  param_id;
	u32                  param_id;
	/* ID of the parameter. */
	/* ID of the parameter. */
@@ -3538,6 +3600,79 @@ struct asm_dec_ddp_endp_param_v2 {
	int endp_param_value;
	int endp_param_value;
} __packed;
} __packed;


/*
 * Payload of the multichannel PCM encoder configuration parameters in
 * the ASM_MEDIA_FMT_MULTI_CHANNEL_PCM_V4 media format.
 */

struct asm_multi_channel_pcm_enc_cfg_v4 {
	struct apr_hdr hdr;
	struct asm_stream_cmd_set_encdec_param encdec;
	struct asm_enc_cfg_blk_param_v2 encblk;
	uint16_t num_channels;
	/*
	 * Number of PCM channels.
	 * @values
	 * - 0 -- Native mode
	 * - 1 -- 8 channels
	 * Native mode indicates that encoding must be performed with the number
	 * of channels at the input.
	 */
	uint16_t  bits_per_sample;
	/*
	 * Number of bits per sample per channel.
	 * @values 16, 24
	 */
	uint32_t  sample_rate;
	/*
	 * Number of samples per second.
	 * @values 0, 8000 to 48000 Hz
	 * A value of 0 indicates the native sampling rate. Encoding is
	 * performed at the input sampling rate.
	 */
	uint16_t  is_signed;
	/*
	 * Flag that indicates the PCM samples are signed (1). Currently, only
	 * signed PCM samples are supported.
	 */
	uint16_t    sample_word_size;
	/*
	 * The size in bits of the word that holds a sample of a channel.
	 * @values 16, 24, 32
	 * 16-bit samples are always placed in 16-bit words:
	 * sample_word_size = 1.
	 * 24-bit samples can be placed in 32-bit words or in consecutive
	 * 24-bit words.
	 * - If sample_word_size = 32, 24-bit samples are placed in the
	 * most significant 24 bits of a 32-bit word.
	 * - If sample_word_size = 24, 24-bit samples are placed in
	 * 24-bit words. @tablebulletend
	 */
	uint8_t   channel_mapping[8];
	/*
	 * Channel mapping array expected at the encoder output.
	 *  Channel[i] mapping describes channel i inside the buffer, where
	 *  0 @le i < num_channels. All valid used channels must be present at
	 *  the beginning of the array.
	 * If Native mode is set for the channels, this field is ignored.
	 * @values See Section @xref{dox:PcmChannelDefs}
	 */
	uint16_t                endianness;
	/*
	 * Flag to indicate the endianness of the pcm sample
	 * Supported values: 0 - Little endian (all other formats)
	 *                   1 - Big endian (AIFF)
	 */
	uint16_t                mode;
	/*
	 * Mode to provide additional info about the pcm input data.
	 * Supported values: 0 - Default QFs (Q15 for 16b, Q23 for packed 24b,
	 *                       Q31 for unpacked 24b or 32b)
	 *                  15 - for 16 bit
	 *                  23 - for 24b packed or 8.24 format
	 *                  31 - for 24b unpacked or 32bit
	 */
} __packed;


/*
/*
 * Payload of the multichannel PCM encoder configuration parameters in
 * Payload of the multichannel PCM encoder configuration parameters in
+59 −0
Original line number Original line Diff line number Diff line
@@ -103,6 +103,24 @@
#define ASM_SHIFT_GAPLESS_MODE_FLAG	31
#define ASM_SHIFT_GAPLESS_MODE_FLAG	31
#define ASM_SHIFT_LAST_BUFFER_FLAG	30
#define ASM_SHIFT_LAST_BUFFER_FLAG	30


#define ASM_LITTLE_ENDIAN 0
#define ASM_BIG_ENDIAN 1

/* PCM_MEDIA_FORMAT_Version */
enum {
	PCM_MEDIA_FORMAT_V2 = 0,
	PCM_MEDIA_FORMAT_V3,
	PCM_MEDIA_FORMAT_V4,
};

/* PCM format modes in DSP */
enum {
	DEFAULT_QF = 0,
	Q15 = 15,
	Q23 = 23,
	Q31 = 31,
};

/* payload structure bytes */
/* payload structure bytes */
#define READDONE_IDX_STATUS 0
#define READDONE_IDX_STATUS 0
#define READDONE_IDX_BUFADD_LSW 1
#define READDONE_IDX_BUFADD_LSW 1
@@ -270,6 +288,9 @@ int q6asm_open_shared_io(struct audio_client *ac,
int q6asm_open_write_v3(struct audio_client *ac, uint32_t format,
int q6asm_open_write_v3(struct audio_client *ac, uint32_t format,
			uint16_t bits_per_sample);
			uint16_t bits_per_sample);


int q6asm_open_write_v4(struct audio_client *ac, uint32_t format,
			uint16_t bits_per_sample);

int q6asm_stream_open_write_v2(struct audio_client *ac, uint32_t format,
int q6asm_stream_open_write_v2(struct audio_client *ac, uint32_t format,
			       uint16_t bits_per_sample, int32_t stream_id,
			       uint16_t bits_per_sample, int32_t stream_id,
			       bool is_gapless_mode);
			       bool is_gapless_mode);
@@ -278,6 +299,10 @@ int q6asm_stream_open_write_v3(struct audio_client *ac, uint32_t format,
			       uint16_t bits_per_sample, int32_t stream_id,
			       uint16_t bits_per_sample, int32_t stream_id,
			       bool is_gapless_mode);
			       bool is_gapless_mode);


int q6asm_stream_open_write_v4(struct audio_client *ac, uint32_t format,
			       uint16_t bits_per_sample, int32_t stream_id,
			       bool is_gapless_mode);

int q6asm_open_write_compressed(struct audio_client *ac, uint32_t format,
int q6asm_open_write_compressed(struct audio_client *ac, uint32_t format,
				uint32_t passthrough_flag);
				uint32_t passthrough_flag);


@@ -386,6 +411,13 @@ int q6asm_enc_cfg_blk_pcm_v3(struct audio_client *ac,
			     bool use_back_flavor, u8 *channel_map,
			     bool use_back_flavor, u8 *channel_map,
			     uint16_t sample_word_size);
			     uint16_t sample_word_size);


int q6asm_enc_cfg_blk_pcm_v4(struct audio_client *ac,
			     uint32_t rate, uint32_t channels,
			     uint16_t bits_per_sample, bool use_default_chmap,
			     bool use_back_flavor, u8 *channel_map,
			     uint16_t sample_word_size, uint16_t endianness,
			     uint16_t mode);

int q6asm_enc_cfg_blk_pcm_format_support(struct audio_client *ac,
int q6asm_enc_cfg_blk_pcm_format_support(struct audio_client *ac,
			uint32_t rate, uint32_t channels,
			uint32_t rate, uint32_t channels,
			uint16_t bits_per_sample);
			uint16_t bits_per_sample);
@@ -395,6 +427,13 @@ int q6asm_enc_cfg_blk_pcm_format_support_v3(struct audio_client *ac,
					    uint16_t bits_per_sample,
					    uint16_t bits_per_sample,
					    uint16_t sample_word_size);
					    uint16_t sample_word_size);


int q6asm_enc_cfg_blk_pcm_format_support_v4(struct audio_client *ac,
					    uint32_t rate, uint32_t channels,
					    uint16_t bits_per_sample,
					    uint16_t sample_word_size,
					    uint16_t endianness,
					    uint16_t mode);

int q6asm_set_encdec_chan_map(struct audio_client *ac,
int q6asm_set_encdec_chan_map(struct audio_client *ac,
		uint32_t num_channels);
		uint32_t num_channels);


@@ -444,6 +483,17 @@ int q6asm_media_format_block_pcm_format_support_v3(struct audio_client *ac,
						   char *channel_map,
						   char *channel_map,
						   uint16_t sample_word_size);
						   uint16_t sample_word_size);


int q6asm_media_format_block_pcm_format_support_v4(struct audio_client *ac,
						   uint32_t rate,
						   uint32_t channels,
						   uint16_t bits_per_sample,
						   int stream_id,
						   bool use_default_chmap,
						   char *channel_map,
						   uint16_t sample_word_size,
						   uint16_t endianness,
						   uint16_t mode);

int q6asm_media_format_block_multi_ch_pcm(struct audio_client *ac,
int q6asm_media_format_block_multi_ch_pcm(struct audio_client *ac,
			uint32_t rate, uint32_t channels,
			uint32_t rate, uint32_t channels,
			bool use_default_chmap, char *channel_map);
			bool use_default_chmap, char *channel_map);
@@ -461,6 +511,15 @@ int q6asm_media_format_block_multi_ch_pcm_v3(struct audio_client *ac,
					     uint16_t bits_per_sample,
					     uint16_t bits_per_sample,
					     uint16_t sample_word_size);
					     uint16_t sample_word_size);


int q6asm_media_format_block_multi_ch_pcm_v4(struct audio_client *ac,
					     uint32_t rate, uint32_t channels,
					     bool use_default_chmap,
					     char *channel_map,
					     uint16_t bits_per_sample,
					     uint16_t sample_word_size,
					     uint16_t endianness,
					     uint16_t mode);

int q6asm_media_format_block_aac(struct audio_client *ac,
int q6asm_media_format_block_aac(struct audio_client *ac,
			struct asm_aac_cfg *cfg);
			struct asm_aac_cfg *cfg);


+15 −3
Original line number Original line Diff line number Diff line
@@ -49,7 +49,8 @@
			SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_48000)
			SNDRV_PCM_RATE_32000 | SNDRV_PCM_RATE_48000)
#define MSM8X16_WCD_FORMATS (SNDRV_PCM_FMTBIT_S16_LE |\
#define MSM8X16_WCD_FORMATS (SNDRV_PCM_FMTBIT_S16_LE |\
		SNDRV_PCM_FMTBIT_S24_LE |\
		SNDRV_PCM_FMTBIT_S24_LE |\
		SNDRV_PCM_FMTBIT_S24_3LE)
		SNDRV_PCM_FMTBIT_S24_3LE |\
		SNDRV_PCM_FMTBIT_S32_LE)


#define NUM_INTERPOLATORS	3
#define NUM_INTERPOLATORS	3
#define BITS_PER_REG		8
#define BITS_PER_REG		8
@@ -4745,13 +4746,24 @@ static int msm8x16_wcd_hw_params(struct snd_pcm_substream *substream,
	}
	}
	switch (params_format(params)) {
	switch (params_format(params)) {
	case SNDRV_PCM_FORMAT_S16_LE:
	case SNDRV_PCM_FORMAT_S16_LE:
		if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
			snd_soc_update_bits(dai->codec,
			snd_soc_update_bits(dai->codec,
				MSM8X16_WCD_A_CDC_CLK_RX_I2S_CTL, 0x20, 0x20);
				MSM8X16_WCD_A_CDC_CLK_RX_I2S_CTL, 0x20, 0x20);
		} else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
			snd_soc_update_bits(dai->codec,
				MSM8X16_WCD_A_CDC_CLK_TX_I2S_CTL, 0x20, 0x20);
		}
		break;
		break;
	case SNDRV_PCM_FORMAT_S24_LE:
	case SNDRV_PCM_FORMAT_S24_LE:
	case SNDRV_PCM_FORMAT_S24_3LE:
	case SNDRV_PCM_FORMAT_S24_3LE:
	case SNDRV_PCM_FORMAT_S32_LE:
		if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
			snd_soc_update_bits(dai->codec,
			snd_soc_update_bits(dai->codec,
				MSM8X16_WCD_A_CDC_CLK_RX_I2S_CTL, 0x20, 0x00);
				MSM8X16_WCD_A_CDC_CLK_RX_I2S_CTL, 0x20, 0x00);
		} else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
			snd_soc_update_bits(dai->codec,
				MSM8X16_WCD_A_CDC_CLK_TX_I2S_CTL, 0x20, 0x00);
		}
		break;
		break;
	default:
	default:
		dev_err(dai->codec->dev, "%s: wrong format selected\n",
		dev_err(dai->codec->dev, "%s: wrong format selected\n",
+25 −11
Original line number Original line Diff line number Diff line
@@ -108,7 +108,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -140,7 +141,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -223,7 +225,9 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
			.rates = (SNDRV_PCM_RATE_8000_192000|
			.rates = (SNDRV_PCM_RATE_8000_192000|
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE),
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -255,7 +259,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 0,
			.channels_min = 0,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -288,7 +293,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -320,7 +326,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -372,7 +379,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -2118,7 +2126,10 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
			.aif_name = "MM_UL9",
			.aif_name = "MM_UL9",
			.rates = (SNDRV_PCM_RATE_8000_48000|
			.rates = (SNDRV_PCM_RATE_8000_48000|
				  SNDRV_PCM_RATE_KNOT),
				  SNDRV_PCM_RATE_KNOT),
			.formats = SNDRV_PCM_FMTBIT_S16_LE,
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -2513,7 +2524,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -2532,7 +2544,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
@@ -2551,7 +2564,8 @@ static struct snd_soc_dai_driver msm_fe_dais[] = {
					SNDRV_PCM_RATE_KNOT),
					SNDRV_PCM_RATE_KNOT),
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
			.formats = (SNDRV_PCM_FMTBIT_S16_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_LE |
				    SNDRV_PCM_FMTBIT_S24_3LE),
				    SNDRV_PCM_FMTBIT_S24_3LE |
				    SNDRV_PCM_FMTBIT_S32_LE),
			.channels_min = 1,
			.channels_min = 1,
			.channels_max = 8,
			.channels_max = 8,
			.rate_min =     8000,
			.rate_min =     8000,
+74 −11
Original line number Original line Diff line number Diff line
@@ -68,6 +68,9 @@ static int msm_vi_feed_tx_ch = 2;
static int mi2s_rx_bit_format = SNDRV_PCM_FORMAT_S16_LE;
static int mi2s_rx_bit_format = SNDRV_PCM_FORMAT_S16_LE;
static int mi2s_rx_bits_per_sample = 16;
static int mi2s_rx_bits_per_sample = 16;
static int mi2s_rx_sample_rate = SAMPLING_RATE_48KHZ;
static int mi2s_rx_sample_rate = SAMPLING_RATE_48KHZ;
static int mi2s_tx_bit_format = SNDRV_PCM_FORMAT_S16_LE;
static int mi2s_tx_bits_per_sample = 16;
static int mi2s_tx_sample_rate = SAMPLING_RATE_48KHZ;


static atomic_t quat_mi2s_clk_ref;
static atomic_t quat_mi2s_clk_ref;
static atomic_t quin_mi2s_clk_ref;
static atomic_t quin_mi2s_clk_ref;
@@ -161,7 +164,8 @@ static struct afe_clk_set wsa_ana_clk = {
	0,
	0,
};
};


static char const *rx_bit_format_text[] = {"S16_LE", "S24_LE", "S24_3LE"};
static char const *bit_format_text[] = {"S16_LE", "S24_LE", "S24_3LE",
					"S32_LE"};
static const char *const mi2s_ch_text[] = {"One", "Two"};
static const char *const mi2s_ch_text[] = {"One", "Two"};
static const char *const loopback_mclk_text[] = {"DISABLE", "ENABLE"};
static const char *const loopback_mclk_text[] = {"DISABLE", "ENABLE"};
static const char *const btsco_rate_text[] = {"BTSCO_RATE_8KHZ",
static const char *const btsco_rate_text[] = {"BTSCO_RATE_8KHZ",
@@ -389,7 +393,7 @@ static int msm_tx_be_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,


	pr_debug("%s(), channel:%d\n", __func__, msm_ter_mi2s_tx_ch);
	pr_debug("%s(), channel:%d\n", __func__, msm_ter_mi2s_tx_ch);
	param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
	param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
			SNDRV_PCM_FORMAT_S16_LE);
			mi2s_tx_bit_format);
	rate->min = rate->max = 48000;
	rate->min = rate->max = 48000;
	channels->min = channels->max = msm_ter_mi2s_tx_ch;
	channels->min = channels->max = msm_ter_mi2s_tx_ch;


@@ -480,7 +484,7 @@ static int msm_mi2s_snd_hw_params(struct snd_pcm_substream *substream,
			       mi2s_rx_bit_format);
			       mi2s_rx_bit_format);
	else
	else
		param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
		param_set_mask(params, SNDRV_PCM_HW_PARAM_FORMAT,
			       SNDRV_PCM_FORMAT_S16_LE);
			       mi2s_tx_bit_format);
	return 0;
	return 0;
}
}


@@ -549,7 +553,7 @@ static bool is_mi2s_rx_port(int port_id)
	return ret;
	return ret;
}
}


static uint32_t get_mi2s_rx_clk_val(int port_id)
static uint32_t get_mi2s_clk_val(int port_id)
{
{
	uint32_t clk_val = 0;
	uint32_t clk_val = 0;


@@ -559,8 +563,10 @@ static uint32_t get_mi2s_rx_clk_val(int port_id)
	 */
	 */
	if (is_mi2s_rx_port(port_id))
	if (is_mi2s_rx_port(port_id))
		clk_val = (mi2s_rx_sample_rate * mi2s_rx_bits_per_sample * 2);
		clk_val = (mi2s_rx_sample_rate * mi2s_rx_bits_per_sample * 2);
	else
		clk_val = (mi2s_tx_sample_rate * mi2s_tx_bits_per_sample * 2);


	pr_debug("%s: MI2S Rx bit clock value: 0x%0x\n", __func__, clk_val);
	pr_debug("%s: MI2S bit clock value: 0x%0x\n", __func__, clk_val);
	return clk_val;
	return clk_val;
}
}


@@ -581,7 +587,7 @@ static int msm_mi2s_sclk_ctl(struct snd_pcm_substream *substream, bool enable)
		if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
		if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
			if (pdata->afe_clk_ver == AFE_CLK_VERSION_V1) {
			if (pdata->afe_clk_ver == AFE_CLK_VERSION_V1) {
				mi2s_rx_clk_v1.clk_val1 =
				mi2s_rx_clk_v1.clk_val1 =
						get_mi2s_rx_clk_val(port_id);
						get_mi2s_clk_val(port_id);
				ret = afe_set_lpass_clock(port_id,
				ret = afe_set_lpass_clock(port_id,
							&mi2s_rx_clk_v1);
							&mi2s_rx_clk_v1);
			} else {
			} else {
@@ -589,14 +595,14 @@ static int msm_mi2s_sclk_ctl(struct snd_pcm_substream *substream, bool enable)
				mi2s_rx_clk.clk_id =
				mi2s_rx_clk.clk_id =
						msm8952_get_clk_id(port_id);
						msm8952_get_clk_id(port_id);
				mi2s_rx_clk.clk_freq_in_hz =
				mi2s_rx_clk.clk_freq_in_hz =
						get_mi2s_rx_clk_val(port_id);
						get_mi2s_clk_val(port_id);
				ret = afe_set_lpass_clock_v2(port_id,
				ret = afe_set_lpass_clock_v2(port_id,
							&mi2s_rx_clk);
							&mi2s_rx_clk);
			}
			}
		} else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
		} else if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
			if (pdata->afe_clk_ver == AFE_CLK_VERSION_V1) {
			if (pdata->afe_clk_ver == AFE_CLK_VERSION_V1) {
				mi2s_tx_clk_v1.clk_val1 =
				mi2s_tx_clk_v1.clk_val1 =
						Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ;
						get_mi2s_clk_val(port_id);
				ret = afe_set_lpass_clock(port_id,
				ret = afe_set_lpass_clock(port_id,
							&mi2s_tx_clk_v1);
							&mi2s_tx_clk_v1);
			} else {
			} else {
@@ -604,7 +610,7 @@ static int msm_mi2s_sclk_ctl(struct snd_pcm_substream *substream, bool enable)
				mi2s_tx_clk.clk_id =
				mi2s_tx_clk.clk_id =
						msm8952_get_clk_id(port_id);
						msm8952_get_clk_id(port_id);
				mi2s_tx_clk.clk_freq_in_hz =
				mi2s_tx_clk.clk_freq_in_hz =
						Q6AFE_LPASS_IBIT_CLK_1_P536_MHZ;
						get_mi2s_clk_val(port_id);
				ret = afe_set_lpass_clock_v2(port_id,
				ret = afe_set_lpass_clock_v2(port_id,
							&mi2s_tx_clk);
							&mi2s_tx_clk);
			}
			}
@@ -790,6 +796,61 @@ static int mi2s_rx_bit_format_put(struct snd_kcontrol *kcontrol,
	return 0;
	return 0;
}
}


static int mi2s_tx_bit_format_put(struct snd_kcontrol *kcontrol,
	struct snd_ctl_elem_value *ucontrol)
{
	switch (ucontrol->value.integer.value[0]) {
	case 3:
		mi2s_tx_bit_format = SNDRV_PCM_FORMAT_S32_LE;
		mi2s_tx_bits_per_sample = 32;
		break;
	case 2:
		mi2s_tx_bit_format = SNDRV_PCM_FORMAT_S24_3LE;
		mi2s_tx_bits_per_sample = 32;
		break;
	case 1:
		mi2s_tx_bit_format = SNDRV_PCM_FORMAT_S24_LE;
		mi2s_tx_bits_per_sample = 32;
		break;
	case 0:
	default:
		mi2s_tx_bit_format = SNDRV_PCM_FORMAT_S16_LE;
		mi2s_tx_bits_per_sample = 16;
		break;
	}
	return 0;
}

static int mi2s_tx_bit_format_get(struct snd_kcontrol *kcontrol,
	struct snd_ctl_elem_value *ucontrol)
{

	switch (mi2s_tx_bit_format) {
	case SNDRV_PCM_FORMAT_S32_LE:
		ucontrol->value.integer.value[0] = 3;
		break;

	case SNDRV_PCM_FORMAT_S24_3LE:
		ucontrol->value.integer.value[0] = 2;
		break;

	case SNDRV_PCM_FORMAT_S24_LE:
		ucontrol->value.integer.value[0] = 1;
		break;

	case SNDRV_PCM_FORMAT_S16_LE:
	default:
		ucontrol->value.integer.value[0] = 0;
		break;
	}

	pr_debug("%s: mi2s_tx_bit_format = %d, ucontrol value = %ld\n",
			__func__, mi2s_tx_bit_format,
			ucontrol->value.integer.value[0]);

	return 0;
}

static int loopback_mclk_get(struct snd_kcontrol *kcontrol,
static int loopback_mclk_get(struct snd_kcontrol *kcontrol,
	struct snd_ctl_elem_value *ucontrol)
	struct snd_ctl_elem_value *ucontrol)
{
{
@@ -988,8 +1049,8 @@ static int msm_vi_feed_tx_ch_put(struct snd_kcontrol *kcontrol,
}
}


static const struct soc_enum msm_snd_enum[] = {
static const struct soc_enum msm_snd_enum[] = {
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(rx_bit_format_text),
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(bit_format_text),
				rx_bit_format_text),
				bit_format_text),
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(mi2s_ch_text),
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(mi2s_ch_text),
				mi2s_ch_text),
				mi2s_ch_text),
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(loopback_mclk_text),
	SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(loopback_mclk_text),
@@ -1007,6 +1068,8 @@ static const struct soc_enum msm_snd_enum[] = {
static const struct snd_kcontrol_new msm_snd_controls[] = {
static const struct snd_kcontrol_new msm_snd_controls[] = {
	SOC_ENUM_EXT("MI2S_RX Format", msm_snd_enum[0],
	SOC_ENUM_EXT("MI2S_RX Format", msm_snd_enum[0],
			mi2s_rx_bit_format_get, mi2s_rx_bit_format_put),
			mi2s_rx_bit_format_get, mi2s_rx_bit_format_put),
	SOC_ENUM_EXT("MI2S_TX Format", msm_snd_enum[0],
			mi2s_tx_bit_format_get, mi2s_tx_bit_format_put),
	SOC_ENUM_EXT("MI2S_TX Channels", msm_snd_enum[1],
	SOC_ENUM_EXT("MI2S_TX Channels", msm_snd_enum[1],
			msm_ter_mi2s_tx_ch_get, msm_ter_mi2s_tx_ch_put),
			msm_ter_mi2s_tx_ch_get, msm_ter_mi2s_tx_ch_put),
	SOC_ENUM_EXT("MI2S_RX Channels", msm_snd_enum[1],
	SOC_ENUM_EXT("MI2S_RX Channels", msm_snd_enum[1],
Loading