Loading sound/soc/codecs/ab8500-codec.c +46 −33 Original line number Diff line number Diff line Loading @@ -2236,7 +2236,7 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, int slots, int slot_width) { struct snd_soc_codec *codec = dai->codec; unsigned int val, mask, slots_active; unsigned int val, mask, slot, slots_active; mask = BIT(AB8500_DIGIFCONF2_IF0WL0) | BIT(AB8500_DIGIFCONF2_IF0WL1); Loading Loading @@ -2292,27 +2292,34 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, snd_soc_update_bits(codec, AB8500_DIGIFCONF1, mask, val); /* Setup TDM DA according to active tx slots */ if (tx_mask & ~0xff) return -EINVAL; mask = AB8500_DASLOTCONFX_SLTODAX_MASK; tx_mask = tx_mask << AB8500_DA_DATA0_OFFSET; slots_active = hweight32(tx_mask); dev_dbg(dai->codec->dev, "%s: Slots, active, TX: %d\n", __func__, slots_active); switch (slots_active) { case 0: break; case 1: /* Slot 9 -> DA_IN1 & DA_IN3 */ snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, 11); slot = find_first_bit((unsigned long *)&tx_mask, 32); snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, slot); break; case 2: /* Slot 9 -> DA_IN1 & DA_IN3, Slot 11 -> DA_IN2 & DA_IN4 */ snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, 9); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, 9); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, 11); slot = find_first_bit((unsigned long *)&tx_mask, 32); snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, slot); slot = find_next_bit((unsigned long *)&tx_mask, 32, slot + 1); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, slot); break; case 8: dev_dbg(dai->codec->dev, Loading @@ -2327,25 +2334,36 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, } /* Setup TDM AD according to active RX-slots */ if (rx_mask & ~0xff) return -EINVAL; rx_mask = rx_mask << AB8500_AD_DATA0_OFFSET; slots_active = hweight32(rx_mask); dev_dbg(dai->codec->dev, "%s: Slots, active, RX: %d\n", __func__, slots_active); switch (slots_active) { case 0: break; case 1: /* AD_OUT3 -> slot 0 & 1 */ snd_soc_update_bits(codec, AB8500_ADSLOTSEL1, AB8500_MASK_ALL, AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN | AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_ODD); slot = find_first_bit((unsigned long *)&rx_mask, 32); snd_soc_update_bits(codec, AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT3, slot)); break; case 2: /* AD_OUT3 -> slot 0, AD_OUT2 -> slot 1 */ slot = find_first_bit((unsigned long *)&rx_mask, 32); snd_soc_update_bits(codec, AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT3, slot)); slot = find_next_bit((unsigned long *)&rx_mask, 32, slot + 1); snd_soc_update_bits(codec, AB8500_ADSLOTSEL1, AB8500_MASK_ALL, AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN | AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_ODD); AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT2, slot)); break; case 8: dev_dbg(dai->codec->dev, Loading @@ -2362,6 +2380,11 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, return 0; } static const struct snd_soc_dai_ops ab8500_codec_ops = { .set_fmt = ab8500_codec_set_dai_fmt, .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, }; static struct snd_soc_dai_driver ab8500_codec_dai[] = { { .name = "ab8500-codec-dai.0", Loading @@ -2373,12 +2396,7 @@ static struct snd_soc_dai_driver ab8500_codec_dai[] = { .rates = AB8500_SUPPORTED_RATE, .formats = AB8500_SUPPORTED_FMT, }, .ops = (struct snd_soc_dai_ops[]) { { .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, .set_fmt = ab8500_codec_set_dai_fmt, } }, .ops = &ab8500_codec_ops, .symmetric_rates = 1 }, { Loading @@ -2391,12 +2409,7 @@ static struct snd_soc_dai_driver ab8500_codec_dai[] = { .rates = AB8500_SUPPORTED_RATE, .formats = AB8500_SUPPORTED_FMT, }, .ops = (struct snd_soc_dai_ops[]) { { .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, .set_fmt = ab8500_codec_set_dai_fmt, } }, .ops = &ab8500_codec_ops, .symmetric_rates = 1 } }; Loading sound/soc/codecs/ab8500-codec.h +22 −20 Original line number Diff line number Diff line Loading @@ -24,6 +24,13 @@ #define AB8500_SUPPORTED_RATE (SNDRV_PCM_RATE_48000) #define AB8500_SUPPORTED_FMT (SNDRV_PCM_FMTBIT_S16_LE) /* AB8500 interface slot offset definitions */ #define AB8500_AD_DATA0_OFFSET 0 #define AB8500_DA_DATA0_OFFSET 8 #define AB8500_AD_DATA1_OFFSET 16 #define AB8500_DA_DATA1_OFFSET 24 /* AB8500 audio bank (0x0d) register definitions */ #define AB8500_POWERUP 0x00 Loading Loading @@ -73,6 +80,7 @@ #define AB8500_ADSLOTSEL14 0x2C #define AB8500_ADSLOTSEL15 0x2D #define AB8500_ADSLOTSEL16 0x2E #define AB8500_ADSLOTSEL(slot) (AB8500_ADSLOTSEL1 + (slot >> 1)) #define AB8500_ADSLOTHIZCTRL1 0x2F #define AB8500_ADSLOTHIZCTRL2 0x30 #define AB8500_ADSLOTHIZCTRL3 0x31 Loading Loading @@ -144,6 +152,7 @@ #define AB8500_CACHEREGNUM (AB8500_LAST_REG + 1) #define AB8500_MASK_ALL 0xFF #define AB8500_MASK_SLOT(slot) ((slot & 1) ? 0xF0 : 0x0F) #define AB8500_MASK_NONE 0x00 /* AB8500_POWERUP */ Loading Loading @@ -347,28 +356,21 @@ #define AB8500_DIGIFCONF4_IF1WL0 0 /* AB8500_ADSLOTSELX */ #define AB8500_ADSLOTSELX_AD_OUT1_TO_SLOT_ODD 0x00 #define AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_ODD 0x10 #define AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_ODD 0x20 #define AB8500_ADSLOTSELX_AD_OUT4_TO_SLOT_ODD 0x30 #define AB8500_ADSLOTSELX_AD_OUT5_TO_SLOT_ODD 0x40 #define AB8500_ADSLOTSELX_AD_OUT6_TO_SLOT_ODD 0x50 #define AB8500_ADSLOTSELX_AD_OUT7_TO_SLOT_ODD 0x60 #define AB8500_ADSLOTSELX_AD_OUT8_TO_SLOT_ODD 0x70 #define AB8500_ADSLOTSELX_ZEROES_TO_SLOT_ODD 0x80 #define AB8500_ADSLOTSELX_TRISTATE_TO_SLOT_ODD 0xF0 #define AB8500_ADSLOTSELX_AD_OUT1_TO_SLOT_EVEN 0x00 #define AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_EVEN 0x01 #define AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN 0x02 #define AB8500_ADSLOTSELX_AD_OUT4_TO_SLOT_EVEN 0x03 #define AB8500_ADSLOTSELX_AD_OUT5_TO_SLOT_EVEN 0x04 #define AB8500_ADSLOTSELX_AD_OUT6_TO_SLOT_EVEN 0x05 #define AB8500_ADSLOTSELX_AD_OUT7_TO_SLOT_EVEN 0x06 #define AB8500_ADSLOTSELX_AD_OUT8_TO_SLOT_EVEN 0x07 #define AB8500_ADSLOTSELX_ZEROES_TO_SLOT_EVEN 0x08 #define AB8500_ADSLOTSELX_TRISTATE_TO_SLOT_EVEN 0x0F #define AB8500_AD_OUT1 0x0 #define AB8500_AD_OUT2 0x1 #define AB8500_AD_OUT3 0x2 #define AB8500_AD_OUT4 0x3 #define AB8500_AD_OUT5 0x4 #define AB8500_AD_OUT6 0x5 #define AB8500_AD_OUT7 0x6 #define AB8500_AD_OUT8 0x7 #define AB8500_ZEROES 0x8 #define AB8500_TRISTATE 0xF #define AB8500_ADSLOTSELX_EVEN_SHIFT 0 #define AB8500_ADSLOTSELX_ODD_SHIFT 4 #define AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(out, slot) \ ((out) << (((slot) & 1) ? \ AB8500_ADSLOTSELX_ODD_SHIFT : AB8500_ADSLOTSELX_EVEN_SHIFT)) /* AB8500_ADSLOTHIZCTRL1 */ /* AB8500_ADSLOTHIZCTRL2 */ Loading sound/soc/ux500/mop500_ab8500.c +36 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ #include <linux/device.h> #include <linux/io.h> #include <linux/clk.h> #include <linux/mutex.h> #include <sound/soc.h> #include <sound/soc-dapm.h> Loading @@ -24,6 +25,7 @@ #include "ux500_pcm.h" #include "ux500_msp_dai.h" #include "mop500_ab8500.h" #include "../codecs/ab8500-codec.h" #define TX_SLOT_MONO 0x0008 Loading @@ -43,6 +45,12 @@ static unsigned int tx_slots = DEF_TX_SLOTS; static unsigned int rx_slots = DEF_RX_SLOTS; /* Configuration consistency parameters */ static DEFINE_MUTEX(mop500_ab8500_params_lock); static unsigned long mop500_ab8500_usage; static int mop500_ab8500_rate; static int mop500_ab8500_channels; /* Clocks */ static const char * const enum_mclk[] = { "SYSCLK", Loading Loading @@ -230,6 +238,21 @@ static int mop500_ab8500_hw_params(struct snd_pcm_substream *substream, substream->name, substream->number); /* Ensure configuration consistency between DAIs */ mutex_lock(&mop500_ab8500_params_lock); if (mop500_ab8500_usage) { if (mop500_ab8500_rate != params_rate(params) || mop500_ab8500_channels != params_channels(params)) { mutex_unlock(&mop500_ab8500_params_lock); return -EBUSY; } } else { mop500_ab8500_rate = params_rate(params); mop500_ab8500_channels = params_channels(params); } __set_bit(cpu_dai->id, &mop500_ab8500_usage); mutex_unlock(&mop500_ab8500_params_lock); channels = params_channels(params); switch (params_format(params)) { Loading Loading @@ -328,9 +351,22 @@ static int mop500_ab8500_hw_params(struct snd_pcm_substream *substream, return 0; } static int mop500_ab8500_hw_free(struct snd_pcm_substream *substream) { struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_dai *cpu_dai = rtd->cpu_dai; mutex_lock(&mop500_ab8500_params_lock); __clear_bit(cpu_dai->id, &mop500_ab8500_usage); mutex_unlock(&mop500_ab8500_params_lock); return 0; } struct snd_soc_ops mop500_ab8500_ops[] = { { .hw_params = mop500_ab8500_hw_params, .hw_free = mop500_ab8500_hw_free, .startup = mop500_ab8500_startup, .shutdown = mop500_ab8500_shutdown, } Loading sound/soc/ux500/ux500_msp_dai.c +4 −7 Original line number Diff line number Diff line Loading @@ -658,14 +658,11 @@ static int ux500_msp_dai_probe(struct snd_soc_dai *dai) { struct ux500_msp_i2s_drvdata *drvdata = dev_get_drvdata(dai->dev); drvdata->playback_dma_data.dma_cfg = drvdata->msp->dma_cfg_tx; drvdata->capture_dma_data.dma_cfg = drvdata->msp->dma_cfg_rx; dai->playback_dma_data = &drvdata->msp->playback_dma_data; dai->capture_dma_data = &drvdata->msp->capture_dma_data; dai->playback_dma_data = &drvdata->playback_dma_data; dai->capture_dma_data = &drvdata->capture_dma_data; drvdata->playback_dma_data.data_size = drvdata->slot_width; drvdata->capture_dma_data.data_size = drvdata->slot_width; drvdata->msp->playback_dma_data.data_size = drvdata->slot_width; drvdata->msp->capture_dma_data.data_size = drvdata->slot_width; return 0; } Loading sound/soc/ux500/ux500_msp_dai.h +0 −4 Original line number Diff line number Diff line Loading @@ -51,15 +51,11 @@ enum ux500_msp_clock_id { struct ux500_msp_i2s_drvdata { struct ux500_msp *msp; struct regulator *reg_vape; struct ux500_msp_dma_params playback_dma_data; struct ux500_msp_dma_params capture_dma_data; unsigned int fmt; unsigned int tx_mask; unsigned int rx_mask; int slots; int slot_width; u8 configured; int data_delay; /* Clocks */ unsigned int master_clk; Loading Loading
sound/soc/codecs/ab8500-codec.c +46 −33 Original line number Diff line number Diff line Loading @@ -2236,7 +2236,7 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, int slots, int slot_width) { struct snd_soc_codec *codec = dai->codec; unsigned int val, mask, slots_active; unsigned int val, mask, slot, slots_active; mask = BIT(AB8500_DIGIFCONF2_IF0WL0) | BIT(AB8500_DIGIFCONF2_IF0WL1); Loading Loading @@ -2292,27 +2292,34 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, snd_soc_update_bits(codec, AB8500_DIGIFCONF1, mask, val); /* Setup TDM DA according to active tx slots */ if (tx_mask & ~0xff) return -EINVAL; mask = AB8500_DASLOTCONFX_SLTODAX_MASK; tx_mask = tx_mask << AB8500_DA_DATA0_OFFSET; slots_active = hweight32(tx_mask); dev_dbg(dai->codec->dev, "%s: Slots, active, TX: %d\n", __func__, slots_active); switch (slots_active) { case 0: break; case 1: /* Slot 9 -> DA_IN1 & DA_IN3 */ snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, 11); slot = find_first_bit((unsigned long *)&tx_mask, 32); snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, slot); break; case 2: /* Slot 9 -> DA_IN1 & DA_IN3, Slot 11 -> DA_IN2 & DA_IN4 */ snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, 9); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, 9); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, 11); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, 11); slot = find_first_bit((unsigned long *)&tx_mask, 32); snd_soc_update_bits(codec, AB8500_DASLOTCONF1, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF3, mask, slot); slot = find_next_bit((unsigned long *)&tx_mask, 32, slot + 1); snd_soc_update_bits(codec, AB8500_DASLOTCONF2, mask, slot); snd_soc_update_bits(codec, AB8500_DASLOTCONF4, mask, slot); break; case 8: dev_dbg(dai->codec->dev, Loading @@ -2327,25 +2334,36 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, } /* Setup TDM AD according to active RX-slots */ if (rx_mask & ~0xff) return -EINVAL; rx_mask = rx_mask << AB8500_AD_DATA0_OFFSET; slots_active = hweight32(rx_mask); dev_dbg(dai->codec->dev, "%s: Slots, active, RX: %d\n", __func__, slots_active); switch (slots_active) { case 0: break; case 1: /* AD_OUT3 -> slot 0 & 1 */ snd_soc_update_bits(codec, AB8500_ADSLOTSEL1, AB8500_MASK_ALL, AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN | AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_ODD); slot = find_first_bit((unsigned long *)&rx_mask, 32); snd_soc_update_bits(codec, AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT3, slot)); break; case 2: /* AD_OUT3 -> slot 0, AD_OUT2 -> slot 1 */ slot = find_first_bit((unsigned long *)&rx_mask, 32); snd_soc_update_bits(codec, AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT3, slot)); slot = find_next_bit((unsigned long *)&rx_mask, 32, slot + 1); snd_soc_update_bits(codec, AB8500_ADSLOTSEL1, AB8500_MASK_ALL, AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN | AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_ODD); AB8500_ADSLOTSEL(slot), AB8500_MASK_SLOT(slot), AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(AB8500_AD_OUT2, slot)); break; case 8: dev_dbg(dai->codec->dev, Loading @@ -2362,6 +2380,11 @@ static int ab8500_codec_set_dai_tdm_slot(struct snd_soc_dai *dai, return 0; } static const struct snd_soc_dai_ops ab8500_codec_ops = { .set_fmt = ab8500_codec_set_dai_fmt, .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, }; static struct snd_soc_dai_driver ab8500_codec_dai[] = { { .name = "ab8500-codec-dai.0", Loading @@ -2373,12 +2396,7 @@ static struct snd_soc_dai_driver ab8500_codec_dai[] = { .rates = AB8500_SUPPORTED_RATE, .formats = AB8500_SUPPORTED_FMT, }, .ops = (struct snd_soc_dai_ops[]) { { .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, .set_fmt = ab8500_codec_set_dai_fmt, } }, .ops = &ab8500_codec_ops, .symmetric_rates = 1 }, { Loading @@ -2391,12 +2409,7 @@ static struct snd_soc_dai_driver ab8500_codec_dai[] = { .rates = AB8500_SUPPORTED_RATE, .formats = AB8500_SUPPORTED_FMT, }, .ops = (struct snd_soc_dai_ops[]) { { .set_tdm_slot = ab8500_codec_set_dai_tdm_slot, .set_fmt = ab8500_codec_set_dai_fmt, } }, .ops = &ab8500_codec_ops, .symmetric_rates = 1 } }; Loading
sound/soc/codecs/ab8500-codec.h +22 −20 Original line number Diff line number Diff line Loading @@ -24,6 +24,13 @@ #define AB8500_SUPPORTED_RATE (SNDRV_PCM_RATE_48000) #define AB8500_SUPPORTED_FMT (SNDRV_PCM_FMTBIT_S16_LE) /* AB8500 interface slot offset definitions */ #define AB8500_AD_DATA0_OFFSET 0 #define AB8500_DA_DATA0_OFFSET 8 #define AB8500_AD_DATA1_OFFSET 16 #define AB8500_DA_DATA1_OFFSET 24 /* AB8500 audio bank (0x0d) register definitions */ #define AB8500_POWERUP 0x00 Loading Loading @@ -73,6 +80,7 @@ #define AB8500_ADSLOTSEL14 0x2C #define AB8500_ADSLOTSEL15 0x2D #define AB8500_ADSLOTSEL16 0x2E #define AB8500_ADSLOTSEL(slot) (AB8500_ADSLOTSEL1 + (slot >> 1)) #define AB8500_ADSLOTHIZCTRL1 0x2F #define AB8500_ADSLOTHIZCTRL2 0x30 #define AB8500_ADSLOTHIZCTRL3 0x31 Loading Loading @@ -144,6 +152,7 @@ #define AB8500_CACHEREGNUM (AB8500_LAST_REG + 1) #define AB8500_MASK_ALL 0xFF #define AB8500_MASK_SLOT(slot) ((slot & 1) ? 0xF0 : 0x0F) #define AB8500_MASK_NONE 0x00 /* AB8500_POWERUP */ Loading Loading @@ -347,28 +356,21 @@ #define AB8500_DIGIFCONF4_IF1WL0 0 /* AB8500_ADSLOTSELX */ #define AB8500_ADSLOTSELX_AD_OUT1_TO_SLOT_ODD 0x00 #define AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_ODD 0x10 #define AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_ODD 0x20 #define AB8500_ADSLOTSELX_AD_OUT4_TO_SLOT_ODD 0x30 #define AB8500_ADSLOTSELX_AD_OUT5_TO_SLOT_ODD 0x40 #define AB8500_ADSLOTSELX_AD_OUT6_TO_SLOT_ODD 0x50 #define AB8500_ADSLOTSELX_AD_OUT7_TO_SLOT_ODD 0x60 #define AB8500_ADSLOTSELX_AD_OUT8_TO_SLOT_ODD 0x70 #define AB8500_ADSLOTSELX_ZEROES_TO_SLOT_ODD 0x80 #define AB8500_ADSLOTSELX_TRISTATE_TO_SLOT_ODD 0xF0 #define AB8500_ADSLOTSELX_AD_OUT1_TO_SLOT_EVEN 0x00 #define AB8500_ADSLOTSELX_AD_OUT2_TO_SLOT_EVEN 0x01 #define AB8500_ADSLOTSELX_AD_OUT3_TO_SLOT_EVEN 0x02 #define AB8500_ADSLOTSELX_AD_OUT4_TO_SLOT_EVEN 0x03 #define AB8500_ADSLOTSELX_AD_OUT5_TO_SLOT_EVEN 0x04 #define AB8500_ADSLOTSELX_AD_OUT6_TO_SLOT_EVEN 0x05 #define AB8500_ADSLOTSELX_AD_OUT7_TO_SLOT_EVEN 0x06 #define AB8500_ADSLOTSELX_AD_OUT8_TO_SLOT_EVEN 0x07 #define AB8500_ADSLOTSELX_ZEROES_TO_SLOT_EVEN 0x08 #define AB8500_ADSLOTSELX_TRISTATE_TO_SLOT_EVEN 0x0F #define AB8500_AD_OUT1 0x0 #define AB8500_AD_OUT2 0x1 #define AB8500_AD_OUT3 0x2 #define AB8500_AD_OUT4 0x3 #define AB8500_AD_OUT5 0x4 #define AB8500_AD_OUT6 0x5 #define AB8500_AD_OUT7 0x6 #define AB8500_AD_OUT8 0x7 #define AB8500_ZEROES 0x8 #define AB8500_TRISTATE 0xF #define AB8500_ADSLOTSELX_EVEN_SHIFT 0 #define AB8500_ADSLOTSELX_ODD_SHIFT 4 #define AB8500_ADSLOTSELX_AD_OUT_TO_SLOT(out, slot) \ ((out) << (((slot) & 1) ? \ AB8500_ADSLOTSELX_ODD_SHIFT : AB8500_ADSLOTSELX_EVEN_SHIFT)) /* AB8500_ADSLOTHIZCTRL1 */ /* AB8500_ADSLOTHIZCTRL2 */ Loading
sound/soc/ux500/mop500_ab8500.c +36 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ #include <linux/device.h> #include <linux/io.h> #include <linux/clk.h> #include <linux/mutex.h> #include <sound/soc.h> #include <sound/soc-dapm.h> Loading @@ -24,6 +25,7 @@ #include "ux500_pcm.h" #include "ux500_msp_dai.h" #include "mop500_ab8500.h" #include "../codecs/ab8500-codec.h" #define TX_SLOT_MONO 0x0008 Loading @@ -43,6 +45,12 @@ static unsigned int tx_slots = DEF_TX_SLOTS; static unsigned int rx_slots = DEF_RX_SLOTS; /* Configuration consistency parameters */ static DEFINE_MUTEX(mop500_ab8500_params_lock); static unsigned long mop500_ab8500_usage; static int mop500_ab8500_rate; static int mop500_ab8500_channels; /* Clocks */ static const char * const enum_mclk[] = { "SYSCLK", Loading Loading @@ -230,6 +238,21 @@ static int mop500_ab8500_hw_params(struct snd_pcm_substream *substream, substream->name, substream->number); /* Ensure configuration consistency between DAIs */ mutex_lock(&mop500_ab8500_params_lock); if (mop500_ab8500_usage) { if (mop500_ab8500_rate != params_rate(params) || mop500_ab8500_channels != params_channels(params)) { mutex_unlock(&mop500_ab8500_params_lock); return -EBUSY; } } else { mop500_ab8500_rate = params_rate(params); mop500_ab8500_channels = params_channels(params); } __set_bit(cpu_dai->id, &mop500_ab8500_usage); mutex_unlock(&mop500_ab8500_params_lock); channels = params_channels(params); switch (params_format(params)) { Loading Loading @@ -328,9 +351,22 @@ static int mop500_ab8500_hw_params(struct snd_pcm_substream *substream, return 0; } static int mop500_ab8500_hw_free(struct snd_pcm_substream *substream) { struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_dai *cpu_dai = rtd->cpu_dai; mutex_lock(&mop500_ab8500_params_lock); __clear_bit(cpu_dai->id, &mop500_ab8500_usage); mutex_unlock(&mop500_ab8500_params_lock); return 0; } struct snd_soc_ops mop500_ab8500_ops[] = { { .hw_params = mop500_ab8500_hw_params, .hw_free = mop500_ab8500_hw_free, .startup = mop500_ab8500_startup, .shutdown = mop500_ab8500_shutdown, } Loading
sound/soc/ux500/ux500_msp_dai.c +4 −7 Original line number Diff line number Diff line Loading @@ -658,14 +658,11 @@ static int ux500_msp_dai_probe(struct snd_soc_dai *dai) { struct ux500_msp_i2s_drvdata *drvdata = dev_get_drvdata(dai->dev); drvdata->playback_dma_data.dma_cfg = drvdata->msp->dma_cfg_tx; drvdata->capture_dma_data.dma_cfg = drvdata->msp->dma_cfg_rx; dai->playback_dma_data = &drvdata->msp->playback_dma_data; dai->capture_dma_data = &drvdata->msp->capture_dma_data; dai->playback_dma_data = &drvdata->playback_dma_data; dai->capture_dma_data = &drvdata->capture_dma_data; drvdata->playback_dma_data.data_size = drvdata->slot_width; drvdata->capture_dma_data.data_size = drvdata->slot_width; drvdata->msp->playback_dma_data.data_size = drvdata->slot_width; drvdata->msp->capture_dma_data.data_size = drvdata->slot_width; return 0; } Loading
sound/soc/ux500/ux500_msp_dai.h +0 −4 Original line number Diff line number Diff line Loading @@ -51,15 +51,11 @@ enum ux500_msp_clock_id { struct ux500_msp_i2s_drvdata { struct ux500_msp *msp; struct regulator *reg_vape; struct ux500_msp_dma_params playback_dma_data; struct ux500_msp_dma_params capture_dma_data; unsigned int fmt; unsigned int tx_mask; unsigned int rx_mask; int slots; int slot_width; u8 configured; int data_delay; /* Clocks */ unsigned int master_clk; Loading