This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Issue in using MCASP1 on DM8148 Platform

Other Parts Discussed in Thread: DM385

Hi,

I have customized board on which audio amplifier (TFA9879) is connected on mcasp1 of TI814X. Amplifier output is connected to speaker. No audio codec chip is used.


To make playback running I have added one more sound card, and code is added in file sound/soc/davinci/ti81xx-evm.c as below
----------------------------
1)
/* Initialize dai structured */
static struct snd_soc_dai_link ti81xx_speaker_dai = {
      .name = "SPEAKER_SOC_LINK",
      .stream_name = "speaker",
      .cpu_dai_name = "davinci-mcasp.1",
      .platform_name = "davinci-pcm-audio",
      .codec_dai_name = "SPEAKER-DAI-CODEC",
      .codec_name = "speaker-dummy-codec",
      .ops = &ti81xx_evm_ops,
};


2)
/* Initialize sound card structure */
static struct snd_soc_card ti81xx_apeaker_snd_card2 = {
   .name = "TI81XX SOUND2",
   .dai_link = &ti81xx_speaker_dai,
   .num_links = 1,
};


3)
/* Declared the sound card device */
static struct platform_device *ti81xx_pdev2;

4)
/* Created the sound card */

ti81xx_pdev2 = platform_device_alloc("soc-audio", 2);
   if (!ti81xx_pdev2) {
      platform_device_put(ti81xx_pdev0);
      platform_device_put(ti81xx_pdev1);
      return -ENOMEM;
   }

   platform_set_drvdata(ti81xx_pdev2, &ti81xx_ds3_snd_card2);
   ret = platform_device_add(ti81xx_pdev2);
   if (ret) {
      printk(KERN_ERR "Can't add soc platform device\n");
      platform_device_put(ti81xx_pdev0);
      platform_device_put(ti81xx_pdev1);
      platform_device_put(ti81xx_pdev2);
      return ret;
   }

----------------------------

Dummy codec for speaker is initialized from arch/arm/mach-omap2/board-ti8148evm.c

static struct platform_device ti8148_ds3_dummy_codec_device = {
   .name   = "speaker-dummy-codec",
   .id     = -1,
};


static struct platform_device *ti8148_devices[] __initdata = {
   &ti8148_hdmi_audio_device,
   &ti8148_hdmi_codec_device,
   &ti8148_speaker_dummy_codec_device,

----------------------------
mcasp1 is registered in file arch/arm/mach-omap2/devices.c

static u8 speaker_iis_serializer_direction[] = {
    TX_MODE,    RX_MODE,    INACTIVE_MODE,  INACTIVE_MODE,
    INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,
    INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,
    INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,  INACTIVE_MODE,
};

static struct snd_platform_data ds3_speaker_snd_data = {
    .tx_dma_offset  = 0x46400000,
    .rx_dma_offset  = 0x46400000,
    .op_mode    = DAVINCI_MCASP_IIS_MODE,
    .num_serializer = ARRAY_SIZE(ds3_speaker_iis_serializer_direction),
    .tdm_slots  = 2,
    .serial_dir = speaker_iis_serializer_direction,
    .asp_chan_q = EVENTQ_2,
    .version    = MCASP_VERSION_2,
    .txnumevt   = 1,
    .rxnumevt   = 1,
};
  
static struct platform_device speaker_mcasp1_device = {
    .name = "davinci-mcasp", /* driver name */
    .id = 1,
    .dev = {
        .platform_data = &speaker_snd_data,
        },
    .num_resources = ARRAY_SIZE(dm385_mcasp_resource),
    .resource = dm385_mcasp_resource,
    .resource = dm385_mcasp_resource,
};


void __init ti81xx_register_mcasp(int id, struct snd_platform_data *pdata)
{
   if (machine_is_ti8168evm() || machine_is_ti8148evm()
            || machine_is_ti811xevm()) {
      ti81xx_mcasp_device.id = 2;
      ti81xx_mcasp_device.resource = ti81xx_mcasp_resource;
      ti81xx_mcasp_device.num_resources = ARRAY_SIZE(ti81xx_mcasp_resource);
   } else if (machine_is_dm385evm()) {
      ti81xx_mcasp_device.id = 1;
      ti81xx_mcasp_device.resource = dm385_mcasp_resource;
      ti81xx_mcasp_device.num_resources = ARRAY_SIZE(dm385_mcasp_resource);
   } else {
      pr_err("%s: platform not supported\n", __func__);
      return;
   }

   /* TI811x AIC_MCLK is connected to SoC pin MCA2_AHCLKX */
   //omap_mux_init_signal("xref_clk2.mcasp2_ahclkx", 0);
   ti81xx_mcasp_device.dev.platform_data = pdata;
   platform_device_register(&ti81xx_mcasp_device);

#if defined(CONFIG_SND_TI81XX_SOC_EVM)
      platform_device_register(&ti81xx_mcasp0_device);
#endif

   platform_device_register(&speaker_mcasp1_device);
}
----------------------------
Created on dummy codec as below in file sound/soc/codecs/speaker_dummy_codec.c

#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/slab.h>
#include <sound/soc.h>
#include <sound/pcm.h>
#include <sound/initval.h>

static struct snd_soc_codec_driver soc_codec;

static int speaker_hw_params(struct snd_pcm_substream *substream,
             struct snd_pcm_hw_params *params,
             struct snd_soc_dai *dai)
{
   printk(KERN_INFO "%s : %d\n",__func__,__LINE__);
   return 0;
}

static int speaker_mute(struct snd_soc_dai *dai, int mute)
{
   printk(KERN_INFO "%s : %d\n",__func__,__LINE__);
   return 0;
}

static int speaker_set_dai_sysclk(struct snd_soc_dai *codec_dai,
            int clk_id, unsigned int freq, int dir)
{
   printk(KERN_INFO "%s : %d\n",__func__,__LINE__);
   return 0;
}

static int speaker_set_dai_fmt(struct snd_soc_dai *codec_dai,
              unsigned int fmt)
{
   printk(KERN_INFO "%s : %d\n",__func__,__LINE__);
   return 0;
}

static struct snd_soc_dai_ops speaker_dai_ops = {
   .hw_params  = speaker_hw_params,
   .digital_mute  = speaker_mute,
   .set_sysclk = speaker_set_dai_sysclk,
   .set_fmt = speaker_set_dai_fmt,
};


static struct snd_soc_dai_driver ti8148_speaker_dai = {
   .name = "SPEAKER-DAI-CODEC",
   .playback = {
      .stream_name = "Playback",
      .channels_min = 1,
      .channels_max = 1,
      .rates = SNDRV_PCM_RATE_8000
         | SNDRV_PCM_RATE_11025
         | SNDRV_PCM_RATE_16000
         | SNDRV_PCM_RATE_22050
         | SNDRV_PCM_RATE_32000
         | SNDRV_PCM_RATE_44100
         | SNDRV_PCM_RATE_48000
         | SNDRV_PCM_RATE_64000
         | SNDRV_PCM_RATE_88200
         | SNDRV_PCM_RATE_96000,
      .formats = SNDRV_PCM_FMTBIT_S16_LE
         | SNDRV_PCM_FMTBIT_S18_3LE
         | SNDRV_PCM_FMTBIT_S20_3LE
         | SNDRV_PCM_FMTBIT_S24_LE,
   },
   .ops = &speaker_dai_ops,
   .symmetric_rates = 1,
};

static int speaker_codec_probe(struct platform_device *pdev)
{
   int ret;

   ret = snd_soc_register_codec(&pdev->dev, &soc_codec_speaker,
               &ti8148_speaker_dai, 1);
   if (ret < 0)
      printk(KERN_INFO " Speaker Codec Register Failed\n");

   printk(KERN_ALERT "Speaker Dummy Codec Driver Is Probed\n");

   return ret;
}

static int speaker_codec_remove(struct platform_device *pdev)
{
   snd_soc_unregister_codec(&pdev->dev);
   return 0;
}

static struct platform_driver speaker_codec_driver = {
   .probe      = speaker_codec_probe,
   .remove     = speaker_codec_remove,
   .driver     = {
      .name = "speaker-dummy-codec",
      .owner   = THIS_MODULE,
   },
};

static int __init speaker_modinit(void)
{
   return platform_driver_register(&speaker_codec_driver);
}

static void __exit speaker_exit(void)
{
   platform_driver_unregister(&speaker_codec_driver);
}

module_init(speaker_modinit);
module_exit(speaker_exit);
----------------------------


Output of command
aplay -l is,

**** List of PLAYBACK Hardware Devices ****
card 0: SOUND0 [TI81XX SOUND0], device 1: AIC3X tlv320aic3x-hifi-1 []
  Subdevices: 1/1
  Subdevice #0: subdevice #0
card 1: SOUND1 [TI81XX SOUND1], device 0: hdmi HDMI-DAI-CODEC-0 []
  Subdevices: 1/1
  Subdevice #0: subdevice #0
card 2: SOUND2 [TI81XX SOUND2], device 0: ds3_speaker SPEAKER-DAI-CODEC-0 []
  Subdevices: 1/1
  Subdevice #0: subdevice #0

so, my sound card is created successfully.

==========================
Problem:
Now when I play any raw file using command

aplay -Dplughw:2,0 /home/audio.raw
and prob MCA1_AXR0, MCA1_ACLKX, MCA1_AFSX using oscilloscope, I can not see any activity on this lines.

I want to know,

1) if I can use mcasp1 on DM8148 platform, or not?

2) If yes then, I have done some wrong configuration?

3) arch/arm/mach-omap2/devices.c, there is an explicit condition made, to use MCASP2 only in case of TI814XEVM. Is there any reason for this condition? Following is the condition.

void __init ti81xx_register_mcasp(int id, struct snd_platform_data *pdata)
{
   if (machine_is_ti8168evm() || machine_is_ti8148evm()
            || machine_is_ti811xevm()) {
      ti81xx_mcasp_device.id = 2;
      ti81xx_mcasp_device.resource = ti81xx_mcasp_resource;
      ti81xx_mcasp_device.num_resources = ARRAY_SIZE(ti81xx_mcasp_resource);
   } else if (machine_is_dm385evm()) {
      ti81xx_mcasp_device.id = 1;
      ti81xx_mcasp_device.resource = dm385_mcasp_resource;
      ti81xx_mcasp_device.num_resources = ARRAY_SIZE(dm385_mcasp_resource);
   }

Also, in sound/soc/davinci/ti81xx-evm.c following condition is made to exclude use of MCASP1 in case of 814X.

#if defined(CONFIG_MACH_TI810XEVM) || defined(CONFIG_MACH_TI810XDVR)|| defined (CONFIG_MACH_UD8107_DVR)
      .cpu_dai_name= "davinci-mcasp.1",
#else
           .cpu_dai_name= "davinci-mcasp.2",
#endif

 ==========================


Regards,

Dharati Shah