#include <sound/driver.h>
#include <linux/slab.h>
#include <linux/vmalloc.h>
+#include <linux/delay.h>
#include <sound/core.h>
#include <sound/asoundef.h>
#include <sound/pcm.h>
#include <sound/vx_core.h>
#include "vx_cmd.h"
-#define chip_t vx_core_t
-
/*
* we use a vmalloc'ed (sg-)buffer
*/
static int vx_toggle_pipe(vx_core_t *chip, vx_pipe_t *pipe, int state)
{
- int err, i, cur_state, delay;
+ int err, i, cur_state;
/* Check the pipe is not already in the requested state */
if (vx_get_pipe_state(chip, pipe, &cur_state) < 0)
* enough sound buffer for this pipe)
*/
if (state) {
- int delay = CAN_START_DELAY;
for (i = 0 ; i < MAX_WAIT_FOR_DSP; i++) {
- snd_vx_delay(chip, delay);
err = vx_pipe_can_start(chip, pipe);
if (err > 0)
break;
/* Wait for a few, before asking again
* to avoid flooding the DSP with our requests
*/
- if ((i % 4 ) == 0)
- delay <<= 1;
+ mdelay(1);
}
}
* reaching the expected state before returning
* Check one pipe only (since they are synchronous)
*/
- delay = WAIT_STATE_DELAY;
for (i = 0; i < MAX_WAIT_FOR_DSP; i++) {
- snd_vx_delay(chip, delay);
err = vx_get_pipe_state(chip, pipe, &cur_state);
if (err < 0 || cur_state == state)
break;
err = -EIO;
- if ((i % 4 ) == 0)
- delay <<= 1;
+ mdelay(1);
}
return err < 0 ? -EIO : 0;
}
struct vx_rmh rmh;
int data_mode;
- *pipep = 0;
+ *pipep = NULL;
vx_init_rmh(&rmh, CMD_RES_PIPE);
vx_set_pipe_cmd_params(&rmh, capture, audioid, num_audio);
#if 0 // NYI
return err;
/* initialize the pipe record */
- pipe = snd_magic_kcalloc(vx_pipe_t, 0, GFP_KERNEL);
+ pipe = kcalloc(1, sizeof(*pipe), GFP_KERNEL);
if (! pipe) {
/* release the pipe */
vx_init_rmh(&rmh, CMD_FREE_PIPE);
vx_set_pipe_cmd_params(&rmh, pipe->is_capture, pipe->number, 0);
vx_send_msg(chip, &rmh);
- snd_magic_kfree(pipe);
+ kfree(pipe);
return 0;
}
static snd_pcm_hardware_t vx_pcm_playback_hw = {
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
- SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_MMAP_VALID),
+ SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_MMAP_VALID |
+ SNDRV_PCM_INFO_RESUME),
.formats = /*SNDRV_PCM_FMTBIT_U8 |*/ SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S24_3LE,
.rates = SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_8000_48000,
.rate_min = 5000,
{
snd_pcm_runtime_t *runtime = subs->runtime;
vx_core_t *chip = snd_pcm_substream_chip(subs);
- vx_pipe_t *pipe = 0;
+ vx_pipe_t *pipe = NULL;
unsigned int audio;
int err;
if (! subs->runtime->private_data)
return -EINVAL;
- pipe = snd_magic_cast(vx_pipe_t, subs->runtime->private_data, return -EINVAL);
+ pipe = subs->runtime->private_data;
if (--pipe->references == 0) {
- chip->playback_pipes[pipe->number] = 0;
+ chip->playback_pipes[pipe->number] = NULL;
vx_free_pipe(chip, pipe);
}
static void vx_pcm_delayed_start(unsigned long arg)
{
snd_pcm_substream_t *subs = (snd_pcm_substream_t *)arg;
- vx_core_t *chip = snd_magic_cast(vx_core_t, subs->pcm->private_data, return);
- vx_pipe_t *pipe = snd_magic_cast(vx_pipe_t, subs->runtime->private_data, return);
+ vx_core_t *chip = subs->pcm->private_data;
+ vx_pipe_t *pipe = subs->runtime->private_data;
int err;
/* printk( KERN_DEBUG "DDDD tasklet delayed start jiffies = %ld\n", jiffies);*/
static int vx_pcm_trigger(snd_pcm_substream_t *subs, int cmd)
{
vx_core_t *chip = snd_pcm_substream_chip(subs);
- vx_pipe_t *pipe = snd_magic_cast(vx_pipe_t, subs->runtime->private_data, return -EINVAL);
+ vx_pipe_t *pipe = subs->runtime->private_data;
int err;
if (chip->chip_status & VX_STAT_IS_STALE)
switch (cmd) {
case SNDRV_PCM_TRIGGER_START:
+ case SNDRV_PCM_TRIGGER_RESUME:
if (! pipe->is_capture)
vx_pcm_playback_transfer(chip, subs, pipe, 2);
/* FIXME:
pipe->running = 1;
break;
case SNDRV_PCM_TRIGGER_STOP:
+ case SNDRV_PCM_TRIGGER_SUSPEND:
vx_toggle_pipe(chip, pipe, 0);
vx_stop_pipe(chip, pipe);
vx_stop_stream(chip, pipe);
static snd_pcm_uframes_t vx_pcm_playback_pointer(snd_pcm_substream_t *subs)
{
snd_pcm_runtime_t *runtime = subs->runtime;
- vx_pipe_t *pipe = snd_magic_cast(vx_pipe_t, runtime->private_data, return -EINVAL);
+ vx_pipe_t *pipe = runtime->private_data;
return pipe->position;
}
{
vx_core_t *chip = snd_pcm_substream_chip(subs);
snd_pcm_runtime_t *runtime = subs->runtime;
- vx_pipe_t *pipe = snd_magic_cast(vx_pipe_t, runtime->private_data, return -EINVAL);
+ vx_pipe_t *pipe = runtime->private_data;
int err, data_mode;
// int max_size, nchunks;
static snd_pcm_hardware_t vx_pcm_capture_hw = {
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
- SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_MMAP_VALID),
+ SNDRV_PCM_INFO_PAUSE | SNDRV_PCM_INFO_MMAP_VALID |
+ SNDRV_PCM_INFO_RESUME),
.formats = /*SNDRV_PCM_FMTBIT_U8 |*/ SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S24_3LE,
.rates = SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_8000_48000,
.rate_min = 5000,
if (! subs->runtime->private_data)
return -EINVAL;
- pipe = snd_magic_cast(vx_pipe_t, subs->runtime->private_data, return -EINVAL);
- chip->capture_pipes[pipe->number] = 0;
+ pipe = subs->runtime->private_data;
+ chip->capture_pipes[pipe->number] = NULL;
pipe_out_monitoring = pipe->monitoring_pipe;
if (pipe_out_monitoring) {
if (--pipe_out_monitoring->references == 0) {
vx_free_pipe(chip, pipe_out_monitoring);
- chip->playback_pipes[pipe->number] = 0;
- pipe->monitoring_pipe = 0;
+ chip->playback_pipes[pipe->number] = NULL;
+ pipe->monitoring_pipe = NULL;
}
}
static snd_pcm_uframes_t vx_pcm_capture_pointer(snd_pcm_substream_t *subs)
{
snd_pcm_runtime_t *runtime = subs->runtime;
- vx_pipe_t *pipe = snd_magic_cast(vx_pipe_t, runtime->private_data, return -EINVAL);
+ vx_pipe_t *pipe = runtime->private_data;
return bytes_to_frames(runtime, pipe->hw_ptr);
}
*/
static void snd_vx_pcm_free(snd_pcm_t *pcm)
{
- vx_core_t *chip = snd_magic_cast(vx_core_t, pcm->private_data, return);
+ vx_core_t *chip = pcm->private_data;
chip->pcm[pcm->device] = NULL;
if (chip->playback_pipes) {
kfree(chip->playback_pipes);
- chip->playback_pipes = 0;
+ chip->playback_pipes = NULL;
}
if (chip->capture_pipes) {
kfree(chip->capture_pipes);
- chip->capture_pipes = 0;
+ chip->capture_pipes = NULL;
}
}