summaryrefslogtreecommitdiff
path: root/sound
diff options
context:
space:
mode:
authorVinod G <vinodg@nvidia.com>2011-02-28 19:03:06 -0800
committerDan Willemsen <dwillemsen@nvidia.com>2011-04-26 15:52:25 -0700
commitd482cadcf3b3fe4588b9f4617150915086ffc794 (patch)
treef3ba681f081622e521007f3fd5c2952d8e70152c /sound
parent9fe928c73d1f2c7a12d1ec62f933250f4b429298 (diff)
arm: tegra: Cleanup the pcm dma code
Integrate the changes from main branch and latest code from alsa. Original-Change-Id: Ifcfd19bfaa3897a0faed28b0b5357792b0b21a9f Reviewed-on: http://git-master/r/21192 Reviewed-by: Vinod Gopalakrishnakurup <vinodg@nvidia.com> Tested-by: Vinod Gopalakrishnakurup <vinodg@nvidia.com> Reviewed-by: Scott Peterson <speterson@nvidia.com> Change-Id: Ibc1bb27032e92da651ec356d6391d0ee0204c881
Diffstat (limited to 'sound')
-rw-r--r--sound/soc/tegra/tegra_i2s.c28
-rw-r--r--sound/soc/tegra/tegra_pcm.c71
-rw-r--r--sound/soc/tegra/tegra_soc.h27
3 files changed, 73 insertions, 53 deletions
diff --git a/sound/soc/tegra/tegra_i2s.c b/sound/soc/tegra/tegra_i2s.c
index 48115d8cbeb4..f96cfe6e0abf 100644
--- a/sound/soc/tegra/tegra_i2s.c
+++ b/sound/soc/tegra/tegra_i2s.c
@@ -1,20 +1,22 @@
/*
* tegra_i2s.c -- ALSA Soc Audio Layer
*
- * (c) 2010-2011 Nvidia Graphics Pvt. Ltd.
- * http://www.nvidia.com
+ * Copyright (c) 2009-2011, NVIDIA Corporation.
*
- * (c) 2006 Wolfson Microelectronics PLC.
- * Graeme Gregory graeme.gregory@wolfsonmicro.com or linux@wolfsonmicro.com
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * version 2 as published by the Free Software Foundation.
*
- * (c) 2004-2005 Simtec Electronics
- * http://armlinux.simtec.co.uk/
- * Ben Dooks <ben@simtec.co.uk>
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2 of the License, or (at your
- * option) any later version.
*/
#include "tegra_soc.h"
@@ -111,7 +113,6 @@ static inline void stop_i2s_capture(struct snd_soc_dai *cpu_dai)
i2s_fifo_enable(cpu_dai->id, I2S_FIFO_RX, 0);
while (i2s_get_status(cpu_dai->id) & I2S_I2S_FIFO_RX_BUSY);
}
-#endif
static int tegra_i2s_hw_params(struct snd_pcm_substream *substream,
@@ -203,6 +204,7 @@ static int tegra_i2s_set_dai_fmt(struct snd_soc_dai *cpu_dai,
i2s_set_master(i2s_id, val1);
info->i2s_master = val1;
+
val2 = AUDIO_LRCK_LEFT_LOW;
switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) {
@@ -359,7 +361,7 @@ static void tegra_i2s_shutdown(struct snd_pcm_substream *substream,
}
static int tegra_i2s_probe(struct platform_device *pdev,
- struct snd_soc_dai *dai)
+ struct snd_soc_dai *cpu_dai)
{
return 0;
}
diff --git a/sound/soc/tegra/tegra_pcm.c b/sound/soc/tegra/tegra_pcm.c
index abb2e1115812..f42e981f4ca7 100644
--- a/sound/soc/tegra/tegra_pcm.c
+++ b/sound/soc/tegra/tegra_pcm.c
@@ -1,24 +1,25 @@
/*
* tegra_pcm.c -- ALSA Soc Audio Layer
*
- * (c) 2010-2011 Nvidia Corporation.
- * http://www.nvidia.com
+ * Copyright (c) 2009-2011, NVIDIA Corporation.
*
- * (c) 2006 Wolfson Microelectronics PLC.
- * Graeme Gregory graeme.gregory@wolfsonmicro.com or linux@wolfsonmicro.com
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * version 2 as published by the Free Software Foundation.
*
- * (c) 2004-2005 Simtec Electronics
- * http://armlinux.simtec.co.uk/
- * Ben Dooks <ben@simtec.co.uk>
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2 of the License, or (at your
- * option) any later version.
*/
#include "tegra_soc.h"
-#include <mach/tegra_das.h>
#define PLAYBACK_STARTED true
#define PLAYBACK_STOPPED false
@@ -28,6 +29,7 @@ static void tegra_pcm_play(struct tegra_runtime_data *prtd)
struct snd_pcm_substream *substream = prtd->substream;
struct snd_pcm_runtime *runtime = substream->runtime;
struct snd_dma_buffer *buf = &substream->dma_buffer;
+ struct tegra_dma_req *dma_req;
if (runtime->dma_addr) {
prtd->size = frames_to_bytes(runtime, runtime->period_size);
@@ -156,10 +158,11 @@ static int tegra_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
tegra_pcm_capture(prtd); /* dma enqueue req */
}
break;
+
case SNDRV_PCM_TRIGGER_STOP:
case SNDRV_PCM_TRIGGER_SUSPEND:
case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
- prtd->state = STATE_ABORT;
+
prtd->dma_state = STATE_ABORT;
tegra_dma_cancel(prtd->dma_chan);
if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
@@ -180,6 +183,7 @@ static int tegra_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
}
}
break;
+
default:
ret = -EINVAL;
break;
@@ -228,11 +232,11 @@ static int tegra_pcm_open(struct snd_pcm_substream *substream)
goto fail;
}
+ /*
prtd = kzalloc(sizeof(struct tegra_runtime_data), GFP_KERNEL);
if (prtd == NULL)
return -ENOMEM;
- memset(prtd, 0, sizeof(*prtd));
runtime->private_data = prtd;
prtd->substream = substream;
@@ -258,10 +262,10 @@ static int tegra_pcm_open(struct snd_pcm_substream *substream)
}
prtd->dma_chan = tegra_dma_allocate_channel(TEGRA_DMA_MODE_CONTINUOUS_DOUBLE);
- if (IS_ERR(prtd->dma_chan)) {
- pr_err("%s: could not allocate DMA channel for I2S: %ld\n",
- __func__, PTR_ERR(prtd->dma_chan));
- ret = PTR_ERR(prtd->dma_chan);
+ if (prtd->dma_chan == NULL) {
+ pr_err("%s: could not allocate DMA channel for PCM:\n",
+ __func__);
+ ret = -ENOMEM;
goto fail;
}
@@ -296,8 +300,6 @@ static int tegra_pcm_close(struct snd_pcm_substream *substream)
return 0;
}
- prtd->state = STATE_EXIT;
-
if (prtd->dma_chan) {
prtd->dma_state = STATE_EXIT;
for (i = 0; i < DMA_REQ_QCOUNT; i++)
@@ -342,12 +344,17 @@ static int tegra_pcm_preallocate_dma_buffer(struct snd_pcm *pcm, int stream)
struct snd_dma_buffer *buf = &substream->dma_buffer;
size_t size = tegra_pcm_hardware.buffer_bytes_max;
+ buf->area = dma_alloc_writecombine(pcm->card->dev, size,
+ &buf->addr, GFP_KERNEL);
+
+ if (!buf->area)
+ return -ENOMEM;
+
buf->dev.type = SNDRV_DMA_TYPE_DEV;
buf->dev.dev = pcm->card->dev;
buf->private_data = NULL;
- buf->area = dma_alloc_writecombine(pcm->card->dev, size,
- &buf->addr, GFP_KERNEL);
buf->bytes = size;
+
return 0;
}
@@ -371,7 +378,7 @@ static void tegra_pcm_deallocate_dma_buffer(struct snd_pcm *pcm, int stream)
}
}
-static void tegra_pcm_free_dma_buffers(struct snd_pcm *pcm)
+static void tegra_pcm_free(struct snd_pcm *pcm)
{
struct snd_pcm_substream *substream;
struct snd_dma_buffer *buf;
@@ -386,7 +393,6 @@ static void tegra_pcm_free_dma_buffers(struct snd_pcm *pcm)
}
tegra_pcm_deallocate_dma_buffer(pcm ,stream);
}
-
}
static u64 tegra_dma_mask = DMA_BIT_MASK(32);
@@ -405,24 +411,29 @@ static int tegra_pcm_new(struct snd_card *card,
ret = tegra_pcm_preallocate_dma_buffer(pcm,
SNDRV_PCM_STREAM_PLAYBACK);
if (ret)
- goto out;
+ goto err;
}
if (dai->capture.channels_min) {
ret = tegra_pcm_preallocate_dma_buffer(pcm,
SNDRV_PCM_STREAM_CAPTURE);
if (ret)
- goto out;
+ goto err_free_play;
}
-out:
+
+ return 0;
+
+err_free_play:
+ tegra_pcm_deallocate_dma_buffer(pcm, SNDRV_PCM_STREAM_PLAYBACK);
+err:
return ret;
}
struct snd_soc_platform tegra_soc_platform = {
- .name = "tegra-audio",
+ .name = "tegra-pcm-audio",
.pcm_ops = &tegra_pcm_ops,
.pcm_new = tegra_pcm_new,
- .pcm_free = tegra_pcm_free_dma_buffers,
+ .pcm_free = tegra_pcm_free,
};
EXPORT_SYMBOL_GPL(tegra_soc_platform);
@@ -438,5 +449,5 @@ static void __exit tegra_soc_platform_exit(void)
}
module_exit(tegra_soc_platform_exit);
-MODULE_DESCRIPTION("Tegra PCM DMA module");
+MODULE_DESCRIPTION("Tegra PCM ASoC module");
MODULE_LICENSE("GPL");
diff --git a/sound/soc/tegra/tegra_soc.h b/sound/soc/tegra/tegra_soc.h
index 7554ecec90d7..cf878f6a77aa 100644
--- a/sound/soc/tegra/tegra_soc.h
+++ b/sound/soc/tegra/tegra_soc.h
@@ -1,19 +1,22 @@
/*
* tegra_soc.h -- SoC audio for tegra
*
- * (c) 2010-2011 Nvidia Graphics Pvt. Ltd.
- * http://www.nvidia.com
+* Copyright (c) 2009-2011, NVIDIA Corporation.
*
- * Copyright 2007 Wolfson Microelectronics PLC.
- * Author: Graeme Gregory
- * graeme.gregory@wolfsonmicro.com or linux@wolfsonmicro.com
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * version 2 as published by the Free Software Foundation.
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License as published by the
- * Free Software Foundation; either version 2 of the License, or (at your
- * option) any later version.
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
*
- */
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
+ * 02110-1301 USA
+ * */
#ifndef __TEGRA_AUDIO__
#define __TEGRA_AUDIO__
@@ -138,6 +141,10 @@ int tegra_controls_init(struct snd_soc_codec *codec);
int tegra_jack_init(struct snd_soc_codec *codec);
void tegra_jack_exit(void);
void tegra_jack_resume(void);
+void setup_dma_request(struct snd_pcm_substream *substream,
+ struct tegra_dma_req *req,
+ void (*dma_callback)(struct tegra_dma_req *req),
+ void *dma_data);
void tegra_switch_set_state(int state);