* Copyright (c) by Jaroslav Kysela <perex@suse.cz>
*/
-#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/slab.h>
static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-MAX */
static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* ID for this card */
static int enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP; /* Enable this card */
-static int boot_devs;
-module_param_array(index, int, boot_devs, 0444);
+module_param_array(index, int, NULL, 0444);
MODULE_PARM_DESC(index, "Index value for Sun CS4231 soundcard.");
-module_param_array(id, charp, boot_devs, 0444);
+module_param_array(id, charp, NULL, 0444);
MODULE_PARM_DESC(id, "ID string for Sun CS4231 soundcard.");
-module_param_array(enable, bool, boot_devs, 0444);
+module_param_array(enable, bool, NULL, 0444);
MODULE_PARM_DESC(enable, "Enable Sun CS4231 soundcard.");
MODULE_AUTHOR("Jaroslav Kysela, Derrick J. Brashear and David S. Miller");
MODULE_DESCRIPTION("Sun CS4231");
MODULE_LICENSE("GPL");
MODULE_SUPPORTED_DEVICE("{{Sun,CS4231}}");
-typedef struct snd_cs4231 {
- spinlock_t lock;
- void __iomem *port;
+#ifdef SBUS_SUPPORT
+struct sbus_dma_info {
+ spinlock_t lock;
+ int dir;
+ void __iomem *regs;
+};
+#endif
+
+struct snd_cs4231;
+struct cs4231_dma_control {
+ void (*prepare)(struct cs4231_dma_control *dma_cont, int dir);
+ void (*enable)(struct cs4231_dma_control *dma_cont, int on);
+ int (*request)(struct cs4231_dma_control *dma_cont, dma_addr_t bus_addr, size_t len);
+ unsigned int (*address)(struct cs4231_dma_control *dma_cont);
+ void (*reset)(struct snd_cs4231 *chip);
+ void (*preallocate)(struct snd_cs4231 *chip, struct snd_pcm *pcm);
#ifdef EBUS_SUPPORT
- struct ebus_dma_info eb2c;
- struct ebus_dma_info eb2p;
+ struct ebus_dma_info ebus_info;
+#endif
+#ifdef SBUS_SUPPORT
+ struct sbus_dma_info sbus_info;
#endif
+};
+
+struct snd_cs4231 {
+ spinlock_t lock;
+ void __iomem *port;
+
+ struct cs4231_dma_control p_dma;
+ struct cs4231_dma_control c_dma;
u32 flags;
#define CS4231_FLAG_EBUS 0x00000001
#define CS4231_FLAG_PLAYBACK 0x00000002
#define CS4231_FLAG_CAPTURE 0x00000004
- snd_card_t *card;
- snd_pcm_t *pcm;
- snd_pcm_substream_t *playback_substream;
+ struct snd_card *card;
+ struct snd_pcm *pcm;
+ struct snd_pcm_substream *playback_substream;
unsigned int p_periods_sent;
- snd_pcm_substream_t *capture_substream;
+ struct snd_pcm_substream *capture_substream;
unsigned int c_periods_sent;
- snd_timer_t *timer;
+ struct snd_timer *timer;
unsigned short mode;
#define CS4231_MODE_NONE 0x0000
unsigned char image[32]; /* registers image */
int mce_bit;
int calibrate_mute;
- struct semaphore mce_mutex;
- struct semaphore open_mutex;
+ struct mutex mce_mutex;
+ struct mutex open_mutex;
union {
#ifdef SBUS_SUPPORT
unsigned int irq[2];
unsigned int regs_size;
struct snd_cs4231 *next;
-} cs4231_t;
+};
-static cs4231_t *cs4231_list;
+static struct snd_cs4231 *cs4231_list;
/* Eventually we can use sound/isa/cs423x/cs4231_lib.c directly, but for
* now.... -DaveM
#define CS4231_GLOBALIRQ 0x01 /* IRQ is active */
-/* definitions for codec irq status */
+/* definitions for codec irq status - CS4231_IRQ_STATUS */
#define CS4231_PLAYBACK_IRQ 0x10
#define CS4231_RECORD_IRQ 0x20
#define APCPNVA 0x38UL /* APC Play DMA Next Address */
#define APCPNC 0x3cUL /* APC Play Next Count */
+/* Defines for SBUS DMA-routines */
+
+#define APCVA 0x0UL /* APC DMA Address */
+#define APCC 0x4UL /* APC Count */
+#define APCNVA 0x8UL /* APC DMA Next Address */
+#define APCNC 0xcUL /* APC Next Count */
+#define APC_PLAY 0x30UL /* Play registers start at 0x30 */
+#define APC_RECORD 0x20UL /* Record registers start at 0x20 */
+
/* APCCSR bits */
#define APC_INT_PENDING 0x800000 /* Interrupt Pending */
27042, 32000, 33075, 37800, 44100, 48000
};
-static snd_pcm_hw_constraint_list_t hw_constraints_rates = {
+static struct snd_pcm_hw_constraint_list hw_constraints_rates = {
.count = 14,
.list = rates,
};
-static int snd_cs4231_xrate(snd_pcm_runtime_t *runtime)
+static int snd_cs4231_xrate(struct snd_pcm_runtime *runtime)
{
return snd_pcm_hw_constraint_list(runtime, 0,
SNDRV_PCM_HW_PARAM_RATE,
0x00, /* 1f/31 - cbrl */
};
-static u8 __cs4231_readb(cs4231_t *cp, void __iomem *reg_addr)
+static u8 __cs4231_readb(struct snd_cs4231 *cp, void __iomem *reg_addr)
{
#ifdef EBUS_SUPPORT
if (cp->flags & CS4231_FLAG_EBUS) {
#endif
}
-static void __cs4231_writeb(cs4231_t *cp, u8 val, void __iomem *reg_addr)
+static void __cs4231_writeb(struct snd_cs4231 *cp, u8 val, void __iomem *reg_addr)
{
#ifdef EBUS_SUPPORT
if (cp->flags & CS4231_FLAG_EBUS) {
* Basic I/O functions
*/
-void snd_cs4231_outm(cs4231_t *chip, unsigned char reg,
+static void snd_cs4231_outm(struct snd_cs4231 *chip, unsigned char reg,
unsigned char mask, unsigned char value)
{
int timeout;
udelay(100);
#ifdef CONFIG_SND_DEBUG
if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
- snd_printk("outm: auto calibration time out - reg = 0x%x, value = 0x%x\n", reg, value);
+ snd_printdd("outm: auto calibration time out - reg = 0x%x, value = 0x%x\n", reg, value);
#endif
if (chip->calibrate_mute) {
chip->image[reg] &= mask;
}
}
-static void snd_cs4231_dout(cs4231_t *chip, unsigned char reg, unsigned char value)
+static void snd_cs4231_dout(struct snd_cs4231 *chip, unsigned char reg, unsigned char value)
{
int timeout;
timeout > 0 && (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT);
timeout--)
udelay(100);
+#ifdef CONFIG_SND_DEBUG
+ if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
+ snd_printdd("out: auto calibration time out - reg = 0x%x, value = 0x%x\n", reg, value);
+#endif
__cs4231_writeb(chip, chip->mce_bit | reg, CS4231P(chip, REGSEL));
__cs4231_writeb(chip, value, CS4231P(chip, REG));
mb();
}
-static void snd_cs4231_out(cs4231_t *chip, unsigned char reg, unsigned char value)
+static void snd_cs4231_out(struct snd_cs4231 *chip, unsigned char reg, unsigned char value)
{
int timeout;
udelay(100);
#ifdef CONFIG_SND_DEBUG
if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
- snd_printk("out: auto calibration time out - reg = 0x%x, value = 0x%x\n", reg, value);
+ snd_printdd("out: auto calibration time out - reg = 0x%x, value = 0x%x\n", reg, value);
#endif
__cs4231_writeb(chip, chip->mce_bit | reg, CS4231P(chip, REGSEL));
__cs4231_writeb(chip, value, CS4231P(chip, REG));
chip->image[reg] = value;
mb();
-#if 0
- printk("codec out - reg 0x%x = 0x%x\n", chip->mce_bit | reg, value);
-#endif
}
-static unsigned char snd_cs4231_in(cs4231_t *chip, unsigned char reg)
+static unsigned char snd_cs4231_in(struct snd_cs4231 *chip, unsigned char reg)
{
int timeout;
unsigned char ret;
udelay(100);
#ifdef CONFIG_SND_DEBUG
if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
- snd_printk("in: auto calibration time out - reg = 0x%x\n", reg);
+ snd_printdd("in: auto calibration time out - reg = 0x%x\n", reg);
#endif
__cs4231_writeb(chip, chip->mce_bit | reg, CS4231P(chip, REGSEL));
mb();
ret = __cs4231_readb(chip, CS4231P(chip, REG));
-#if 0
- printk("codec in - reg 0x%x = 0x%x\n", chip->mce_bit | reg, ret);
-#endif
return ret;
}
-#ifdef CONFIG_SND_DEBUG
-
-void snd_cs4231_debug(cs4231_t *chip)
-{
- printk("CS4231 REGS: INDEX = 0x%02x ",
- __cs4231_readb(chip, CS4231P(chip, REGSEL)));
- printk(" STATUS = 0x%02x\n",
- __cs4231_readb(chip, CS4231P(chip, STATUS)));
- printk(" 0x00: left input = 0x%02x ", snd_cs4231_in(chip, 0x00));
- printk(" 0x10: alt 1 (CFIG 2) = 0x%02x\n", snd_cs4231_in(chip, 0x10));
- printk(" 0x01: right input = 0x%02x ", snd_cs4231_in(chip, 0x01));
- printk(" 0x11: alt 2 (CFIG 3) = 0x%02x\n", snd_cs4231_in(chip, 0x11));
- printk(" 0x02: GF1 left input = 0x%02x ", snd_cs4231_in(chip, 0x02));
- printk(" 0x12: left line in = 0x%02x\n", snd_cs4231_in(chip, 0x12));
- printk(" 0x03: GF1 right input = 0x%02x ", snd_cs4231_in(chip, 0x03));
- printk(" 0x13: right line in = 0x%02x\n", snd_cs4231_in(chip, 0x13));
- printk(" 0x04: CD left input = 0x%02x ", snd_cs4231_in(chip, 0x04));
- printk(" 0x14: timer low = 0x%02x\n", snd_cs4231_in(chip, 0x14));
- printk(" 0x05: CD right input = 0x%02x ", snd_cs4231_in(chip, 0x05));
- printk(" 0x15: timer high = 0x%02x\n", snd_cs4231_in(chip, 0x15));
- printk(" 0x06: left output = 0x%02x ", snd_cs4231_in(chip, 0x06));
- printk(" 0x16: left MIC (PnP) = 0x%02x\n", snd_cs4231_in(chip, 0x16));
- printk(" 0x07: right output = 0x%02x ", snd_cs4231_in(chip, 0x07));
- printk(" 0x17: right MIC (PnP) = 0x%02x\n", snd_cs4231_in(chip, 0x17));
- printk(" 0x08: playback format = 0x%02x ", snd_cs4231_in(chip, 0x08));
- printk(" 0x18: IRQ status = 0x%02x\n", snd_cs4231_in(chip, 0x18));
- printk(" 0x09: iface (CFIG 1) = 0x%02x ", snd_cs4231_in(chip, 0x09));
- printk(" 0x19: left line out = 0x%02x\n", snd_cs4231_in(chip, 0x19));
- printk(" 0x0a: pin control = 0x%02x ", snd_cs4231_in(chip, 0x0a));
- printk(" 0x1a: mono control = 0x%02x\n", snd_cs4231_in(chip, 0x1a));
- printk(" 0x0b: init & status = 0x%02x ", snd_cs4231_in(chip, 0x0b));
- printk(" 0x1b: right line out = 0x%02x\n", snd_cs4231_in(chip, 0x1b));
- printk(" 0x0c: revision & mode = 0x%02x ", snd_cs4231_in(chip, 0x0c));
- printk(" 0x1c: record format = 0x%02x\n", snd_cs4231_in(chip, 0x1c));
- printk(" 0x0d: loopback = 0x%02x ", snd_cs4231_in(chip, 0x0d));
- printk(" 0x1d: var freq (PnP) = 0x%02x\n", snd_cs4231_in(chip, 0x1d));
- printk(" 0x0e: ply upr count = 0x%02x ", snd_cs4231_in(chip, 0x0e));
- printk(" 0x1e: rec upr count = 0x%02x\n", snd_cs4231_in(chip, 0x1e));
- printk(" 0x0f: ply lwr count = 0x%02x ", snd_cs4231_in(chip, 0x0f));
- printk(" 0x1f: rec lwr count = 0x%02x\n", snd_cs4231_in(chip, 0x1f));
-}
-
-#endif
-
/*
* CS4231 detection / MCE routines
*/
-static void snd_cs4231_busy_wait(cs4231_t *chip)
+static void snd_cs4231_busy_wait(struct snd_cs4231 *chip)
{
int timeout;
/* huh.. looks like this sequence is proper for CS4231A chip (GUS MAX) */
for (timeout = 5; timeout > 0; timeout--)
__cs4231_readb(chip, CS4231P(chip, REGSEL));
+
/* end of cleanup sequence */
- for (timeout = 250;
+ for (timeout = 500;
timeout > 0 && (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT);
timeout--)
- udelay(100);
+ udelay(1000);
}
-static void snd_cs4231_mce_up(cs4231_t *chip)
+static void snd_cs4231_mce_up(struct snd_cs4231 *chip)
{
unsigned long flags;
int timeout;
udelay(100);
#ifdef CONFIG_SND_DEBUG
if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
- snd_printk("mce_up - auto calibration time out (0)\n");
+ snd_printdd("mce_up - auto calibration time out (0)\n");
#endif
chip->mce_bit |= CS4231_MCE;
timeout = __cs4231_readb(chip, CS4231P(chip, REGSEL));
if (timeout == 0x80)
- snd_printk("mce_up [%p]: serious init problem - codec still busy\n", chip->port);
+ snd_printdd("mce_up [%p]: serious init problem - codec still busy\n", chip->port);
if (!(timeout & CS4231_MCE))
__cs4231_writeb(chip, chip->mce_bit | (timeout & 0x1f), CS4231P(chip, REGSEL));
spin_unlock_irqrestore(&chip->lock, flags);
}
-static void snd_cs4231_mce_down(cs4231_t *chip)
+static void snd_cs4231_mce_down(struct snd_cs4231 *chip)
{
unsigned long flags;
int timeout;
- signed long time;
spin_lock_irqsave(&chip->lock, flags);
snd_cs4231_busy_wait(chip);
-#if 0
- printk("(1) timeout = %i\n", timeout);
-#endif
#ifdef CONFIG_SND_DEBUG
if (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT)
- snd_printk("mce_down [0x%lx] - auto calibration time out (0)\n", CS4231P(chip, REGSEL));
+ snd_printdd("mce_down [%p] - auto calibration time out (0)\n", CS4231P(chip, REGSEL));
#endif
chip->mce_bit &= ~CS4231_MCE;
timeout = __cs4231_readb(chip, CS4231P(chip, REGSEL));
__cs4231_writeb(chip, chip->mce_bit | (timeout & 0x1f), CS4231P(chip, REGSEL));
if (timeout == 0x80)
- snd_printk("mce_down [%p]: serious init problem - codec still busy\n", chip->port);
+ snd_printdd("mce_down [%p]: serious init problem - codec still busy\n", chip->port);
if ((timeout & CS4231_MCE) == 0) {
spin_unlock_irqrestore(&chip->lock, flags);
return;
spin_unlock_irqrestore(&chip->lock, flags);
return;
}
-#if 0
- printk("(2) timeout = %i, jiffies = %li\n", timeout, jiffies);
-#endif
- time = HZ / 4;
+
+ /* in 10ms increments, check condition, up to 250ms */
+ timeout = 25;
while (snd_cs4231_in(chip, CS4231_TEST_INIT) & CS4231_CALIB_IN_PROGRESS) {
spin_unlock_irqrestore(&chip->lock, flags);
- if (time <= 0) {
+ if (--timeout < 0) {
snd_printk("mce_down - auto calibration time out (2)\n");
return;
}
- set_current_state(TASK_INTERRUPTIBLE);
- time = schedule_timeout(time);
+ msleep(10);
spin_lock_irqsave(&chip->lock, flags);
}
-#if 0
- printk("(3) jiffies = %li\n", jiffies);
-#endif
- time = HZ / 10;
+
+ /* in 10ms increments, check condition, up to 100ms */
+ timeout = 10;
while (__cs4231_readb(chip, CS4231P(chip, REGSEL)) & CS4231_INIT) {
spin_unlock_irqrestore(&chip->lock, flags);
- if (time <= 0) {
+ if (--timeout < 0) {
snd_printk("mce_down - auto calibration time out (3)\n");
return;
}
- set_current_state(TASK_INTERRUPTIBLE);
- time = schedule_timeout(time);
+ msleep(10);
spin_lock_irqsave(&chip->lock, flags);
}
spin_unlock_irqrestore(&chip->lock, flags);
-#if 0
- printk("(4) jiffies = %li\n", jiffies);
- snd_printk("mce_down - exit = 0x%x\n", __cs4231_readb(chip, CS4231P(chip, REGSEL)));
-#endif
}
-#if 0 /* Unused for now... */
-static unsigned int snd_cs4231_get_count(unsigned char format, unsigned int size)
-{
- switch (format & 0xe0) {
- case CS4231_LINEAR_16:
- case CS4231_LINEAR_16_BIG:
- size >>= 1;
- break;
- case CS4231_ADPCM_16:
- return size >> 2;
- }
- if (format & CS4231_STEREO)
- size >>= 1;
- return size;
-}
-#endif
-
-#ifdef EBUS_SUPPORT
-static void snd_cs4231_ebus_advance_dma(struct ebus_dma_info *p, snd_pcm_substream_t *substream, unsigned int *periods_sent)
+static void snd_cs4231_advance_dma(struct cs4231_dma_control *dma_cont,
+ struct snd_pcm_substream *substream,
+ unsigned int *periods_sent)
{
- snd_pcm_runtime_t *runtime = substream->runtime;
+ struct snd_pcm_runtime *runtime = substream->runtime;
while (1) {
- unsigned int dma_size = snd_pcm_lib_period_bytes(substream);
- unsigned int offset = dma_size * (*periods_sent);
+ unsigned int period_size = snd_pcm_lib_period_bytes(substream);
+ unsigned int offset = period_size * (*periods_sent);
- if (dma_size >= (1 << 24))
- BUG();
+ BUG_ON(period_size >= (1 << 24));
- if (ebus_dma_request(p, runtime->dma_addr + offset, dma_size))
+ if (dma_cont->request(dma_cont, runtime->dma_addr + offset, period_size))
return;
-#if 0
- printk("ebus_advance: Sent period %u (size[%x] offset[%x])\n",
- (*periods_sent), dma_size, offset);
-#endif
(*periods_sent) = ((*periods_sent) + 1) % runtime->periods;
}
}
-#endif
-static void cs4231_dma_trigger(cs4231_t *chip, unsigned int what, int on)
+static void cs4231_dma_trigger(struct snd_pcm_substream *substream,
+ unsigned int what, int on)
{
-#ifdef EBUS_SUPPORT
- if (chip->flags & CS4231_FLAG_EBUS) {
- if (what & CS4231_PLAYBACK_ENABLE) {
- if (on) {
- ebus_dma_prepare(&chip->eb2p, 0);
- ebus_dma_enable(&chip->eb2p, 1);
- snd_cs4231_ebus_advance_dma(&chip->eb2p,
- chip->playback_substream,
- &chip->p_periods_sent);
- } else {
- ebus_dma_enable(&chip->eb2p, 0);
- }
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct cs4231_dma_control *dma_cont;
+
+ if (what & CS4231_PLAYBACK_ENABLE) {
+ dma_cont = &chip->p_dma;
+ if (on) {
+ dma_cont->prepare(dma_cont, 0);
+ dma_cont->enable(dma_cont, 1);
+ snd_cs4231_advance_dma(dma_cont,
+ chip->playback_substream,
+ &chip->p_periods_sent);
+ } else {
+ dma_cont->enable(dma_cont, 0);
}
- if (what & CS4231_RECORD_ENABLE) {
- if (on) {
- ebus_dma_prepare(&chip->eb2c, 1);
- ebus_dma_enable(&chip->eb2c, 1);
- snd_cs4231_ebus_advance_dma(&chip->eb2c,
- chip->capture_substream,
- &chip->c_periods_sent);
- } else {
- ebus_dma_enable(&chip->eb2c, 0);
- }
+ }
+ if (what & CS4231_RECORD_ENABLE) {
+ dma_cont = &chip->c_dma;
+ if (on) {
+ dma_cont->prepare(dma_cont, 1);
+ dma_cont->enable(dma_cont, 1);
+ snd_cs4231_advance_dma(dma_cont,
+ chip->capture_substream,
+ &chip->c_periods_sent);
+ } else {
+ dma_cont->enable(dma_cont, 0);
}
- } else {
-#endif
-#ifdef SBUS_SUPPORT
-#endif
-#ifdef EBUS_SUPPORT
}
-#endif
}
-static int snd_cs4231_trigger(snd_pcm_substream_t *substream, int cmd)
+static int snd_cs4231_trigger(struct snd_pcm_substream *substream, int cmd)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
int result = 0;
switch (cmd) {
case SNDRV_PCM_TRIGGER_STOP:
{
unsigned int what = 0;
- snd_pcm_substream_t *s;
+ struct snd_pcm_substream *s;
struct list_head *pos;
unsigned long flags;
}
}
-#if 0
- printk("TRIGGER: what[%x] on(%d)\n",
- what, (cmd == SNDRV_PCM_TRIGGER_START));
-#endif
-
spin_lock_irqsave(&chip->lock, flags);
if (cmd == SNDRV_PCM_TRIGGER_START) {
- cs4231_dma_trigger(chip, what, 1);
+ cs4231_dma_trigger(substream, what, 1);
chip->image[CS4231_IFACE_CTRL] |= what;
- if (what & CS4231_PLAYBACK_ENABLE) {
- snd_cs4231_out(chip, CS4231_PLY_LWR_CNT, 0xff);
- snd_cs4231_out(chip, CS4231_PLY_UPR_CNT, 0xff);
- }
- if (what & CS4231_RECORD_ENABLE) {
- snd_cs4231_out(chip, CS4231_REC_LWR_CNT, 0xff);
- snd_cs4231_out(chip, CS4231_REC_UPR_CNT, 0xff);
- }
} else {
- cs4231_dma_trigger(chip, what, 0);
+ cs4231_dma_trigger(substream, what, 0);
chip->image[CS4231_IFACE_CTRL] &= ~what;
}
snd_cs4231_out(chip, CS4231_IFACE_CTRL,
result = -EINVAL;
break;
}
-#if 0
- snd_cs4231_debug(chip);
-#endif
+
return result;
}
return freq_bits[13];
}
-static unsigned char snd_cs4231_get_format(cs4231_t *chip, int format, int channels)
+static unsigned char snd_cs4231_get_format(struct snd_cs4231 *chip, int format, int channels)
{
unsigned char rformat;
}
if (channels > 1)
rformat |= CS4231_STEREO;
-#if 0
- snd_printk("get_format: 0x%x (mode=0x%x)\n", format, mode);
-#endif
return rformat;
}
-static void snd_cs4231_calibrate_mute(cs4231_t *chip, int mute)
+static void snd_cs4231_calibrate_mute(struct snd_cs4231 *chip, int mute)
{
unsigned long flags;
spin_unlock_irqrestore(&chip->lock, flags);
}
-static void snd_cs4231_playback_format(cs4231_t *chip, snd_pcm_hw_params_t *params,
+static void snd_cs4231_playback_format(struct snd_cs4231 *chip, struct snd_pcm_hw_params *params,
unsigned char pdfr)
{
unsigned long flags;
- down(&chip->mce_mutex);
+ mutex_lock(&chip->mce_mutex);
snd_cs4231_calibrate_mute(chip, 1);
snd_cs4231_mce_up(chip);
snd_cs4231_mce_down(chip);
snd_cs4231_calibrate_mute(chip, 0);
- up(&chip->mce_mutex);
+ mutex_unlock(&chip->mce_mutex);
}
-static void snd_cs4231_capture_format(cs4231_t *chip, snd_pcm_hw_params_t *params,
+static void snd_cs4231_capture_format(struct snd_cs4231 *chip, struct snd_pcm_hw_params *params,
unsigned char cdfr)
{
unsigned long flags;
- down(&chip->mce_mutex);
+ mutex_lock(&chip->mce_mutex);
snd_cs4231_calibrate_mute(chip, 1);
snd_cs4231_mce_up(chip);
snd_cs4231_mce_down(chip);
snd_cs4231_calibrate_mute(chip, 0);
- up(&chip->mce_mutex);
+ mutex_unlock(&chip->mce_mutex);
}
/*
* Timer interface
*/
-static unsigned long snd_cs4231_timer_resolution(snd_timer_t *timer)
+static unsigned long snd_cs4231_timer_resolution(struct snd_timer *timer)
{
- cs4231_t *chip = snd_timer_chip(timer);
+ struct snd_cs4231 *chip = snd_timer_chip(timer);
return chip->image[CS4231_PLAYBK_FORMAT] & 1 ? 9969 : 9920;
}
-static int snd_cs4231_timer_start(snd_timer_t *timer)
+static int snd_cs4231_timer_start(struct snd_timer *timer)
{
unsigned long flags;
unsigned int ticks;
- cs4231_t *chip = snd_timer_chip(timer);
+ struct snd_cs4231 *chip = snd_timer_chip(timer);
spin_lock_irqsave(&chip->lock, flags);
ticks = timer->sticks;
return 0;
}
-static int snd_cs4231_timer_stop(snd_timer_t *timer)
+static int snd_cs4231_timer_stop(struct snd_timer *timer)
{
unsigned long flags;
- cs4231_t *chip = snd_timer_chip(timer);
+ struct snd_cs4231 *chip = snd_timer_chip(timer);
spin_lock_irqsave(&chip->lock, flags);
snd_cs4231_out(chip, CS4231_ALT_FEATURE_1,
return 0;
}
-static void snd_cs4231_init(cs4231_t *chip)
+static void __init snd_cs4231_init(struct snd_cs4231 *chip)
{
unsigned long flags;
snd_cs4231_mce_down(chip);
#ifdef SNDRV_DEBUG_MCE
- snd_printk("init: (1)\n");
+ snd_printdd("init: (1)\n");
#endif
snd_cs4231_mce_up(chip);
spin_lock_irqsave(&chip->lock, flags);
snd_cs4231_mce_down(chip);
#ifdef SNDRV_DEBUG_MCE
- snd_printk("init: (2)\n");
+ snd_printdd("init: (2)\n");
#endif
snd_cs4231_mce_up(chip);
snd_cs4231_mce_down(chip);
#ifdef SNDRV_DEBUG_MCE
- snd_printk("init: (3) - afei = 0x%x\n", chip->image[CS4231_ALT_FEATURE_1]);
+ snd_printdd("init: (3) - afei = 0x%x\n", chip->image[CS4231_ALT_FEATURE_1]);
#endif
spin_lock_irqsave(&chip->lock, flags);
snd_cs4231_mce_down(chip);
#ifdef SNDRV_DEBUG_MCE
- snd_printk("init: (4)\n");
+ snd_printdd("init: (4)\n");
#endif
snd_cs4231_mce_up(chip);
snd_cs4231_mce_down(chip);
#ifdef SNDRV_DEBUG_MCE
- snd_printk("init: (5)\n");
+ snd_printdd("init: (5)\n");
#endif
}
-static int snd_cs4231_open(cs4231_t *chip, unsigned int mode)
+static int snd_cs4231_open(struct snd_cs4231 *chip, unsigned int mode)
{
unsigned long flags;
- down(&chip->open_mutex);
+ mutex_lock(&chip->open_mutex);
if ((chip->mode & mode)) {
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return -EAGAIN;
}
if (chip->mode & CS4231_MODE_OPEN) {
chip->mode |= mode;
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return 0;
}
/* ok. now enable and ack CODEC IRQ */
CS4231_RECORD_IRQ |
CS4231_TIMER_IRQ);
snd_cs4231_out(chip, CS4231_IRQ_STATUS, 0);
+
spin_unlock_irqrestore(&chip->lock, flags);
chip->mode = mode;
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return 0;
}
-static void snd_cs4231_close(cs4231_t *chip, unsigned int mode)
+static void snd_cs4231_close(struct snd_cs4231 *chip, unsigned int mode)
{
unsigned long flags;
- down(&chip->open_mutex);
+ mutex_lock(&chip->open_mutex);
chip->mode &= ~mode;
if (chip->mode & CS4231_MODE_OPEN) {
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
return;
}
snd_cs4231_calibrate_mute(chip, 1);
snd_cs4231_calibrate_mute(chip, 0);
chip->mode = 0;
- up(&chip->open_mutex);
+ mutex_unlock(&chip->open_mutex);
}
/*
* timer open/close
*/
-static int snd_cs4231_timer_open(snd_timer_t *timer)
+static int snd_cs4231_timer_open(struct snd_timer *timer)
{
- cs4231_t *chip = snd_timer_chip(timer);
+ struct snd_cs4231 *chip = snd_timer_chip(timer);
snd_cs4231_open(chip, CS4231_MODE_TIMER);
return 0;
}
-static int snd_cs4231_timer_close(snd_timer_t * timer)
+static int snd_cs4231_timer_close(struct snd_timer * timer)
{
- cs4231_t *chip = snd_timer_chip(timer);
+ struct snd_cs4231 *chip = snd_timer_chip(timer);
snd_cs4231_close(chip, CS4231_MODE_TIMER);
return 0;
}
-static struct _snd_timer_hardware snd_cs4231_timer_table =
+static struct snd_timer_hardware snd_cs4231_timer_table =
{
.flags = SNDRV_TIMER_HW_AUTO,
.resolution = 9945,
* ok.. exported functions..
*/
-static int snd_cs4231_playback_hw_params(snd_pcm_substream_t *substream,
- snd_pcm_hw_params_t *hw_params)
+static int snd_cs4231_playback_hw_params(struct snd_pcm_substream *substream,
+ struct snd_pcm_hw_params *hw_params)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
unsigned char new_pdfr;
int err;
return 0;
}
-static int snd_cs4231_playback_hw_free(snd_pcm_substream_t *substream)
+static int snd_cs4231_playback_hw_free(struct snd_pcm_substream *substream)
{
return snd_pcm_lib_free_pages(substream);
}
-static int snd_cs4231_playback_prepare(snd_pcm_substream_t *substream)
+static int snd_cs4231_playback_prepare(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct snd_pcm_runtime *runtime = substream->runtime;
unsigned long flags;
spin_lock_irqsave(&chip->lock, flags);
+
chip->image[CS4231_IFACE_CTRL] &= ~(CS4231_PLAYBACK_ENABLE |
CS4231_PLAYBACK_PIO);
+
+ BUG_ON(runtime->period_size > 0xffff + 1);
+
+ chip->p_periods_sent = 0;
spin_unlock_irqrestore(&chip->lock, flags);
return 0;
}
-static int snd_cs4231_capture_hw_params(snd_pcm_substream_t *substream,
- snd_pcm_hw_params_t *hw_params)
+static int snd_cs4231_capture_hw_params(struct snd_pcm_substream *substream,
+ struct snd_pcm_hw_params *hw_params)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
unsigned char new_cdfr;
int err;
return 0;
}
-static int snd_cs4231_capture_hw_free(snd_pcm_substream_t *substream)
+static int snd_cs4231_capture_hw_free(struct snd_pcm_substream *substream)
{
return snd_pcm_lib_free_pages(substream);
}
-static int snd_cs4231_capture_prepare(snd_pcm_substream_t *substream)
+static int snd_cs4231_capture_prepare(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
unsigned long flags;
spin_lock_irqsave(&chip->lock, flags);
chip->image[CS4231_IFACE_CTRL] &= ~(CS4231_RECORD_ENABLE |
CS4231_RECORD_PIO);
+
+ chip->c_periods_sent = 0;
spin_unlock_irqrestore(&chip->lock, flags);
return 0;
}
-static void snd_cs4231_overrange(cs4231_t *chip)
+static void snd_cs4231_overrange(struct snd_cs4231 *chip)
{
unsigned long flags;
unsigned char res;
chip->capture_substream->runtime->overrange++;
}
-static void snd_cs4231_generic_interrupt(cs4231_t *chip)
-{
- unsigned long flags;
- unsigned char status;
-
- status = snd_cs4231_in(chip, CS4231_IRQ_STATUS);
- if (!status)
- return;
-
- if (status & CS4231_TIMER_IRQ) {
- if (chip->timer)
- snd_timer_interrupt(chip->timer, chip->timer->sticks);
- }
- if (status & CS4231_PLAYBACK_IRQ)
- snd_pcm_period_elapsed(chip->playback_substream);
- if (status & CS4231_RECORD_IRQ) {
- snd_cs4231_overrange(chip);
- snd_pcm_period_elapsed(chip->capture_substream);
- }
-
- /* ACK the CS4231 interrupt. */
- spin_lock_irqsave(&chip->lock, flags);
- snd_cs4231_outm(chip, CS4231_IRQ_STATUS, ~CS4231_ALL_IRQS | ~status, 0);
- spin_unlock_irqrestore(&chip->lock, flags);
-}
-
-#ifdef SBUS_SUPPORT
-static irqreturn_t snd_cs4231_sbus_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+static void snd_cs4231_play_callback(struct snd_cs4231 *chip)
{
- cs4231_t *chip = dev_id;
- u32 csr;
-
- csr = sbus_readl(chip->port + APCCSR);
- if (!(csr & (APC_INT_PENDING |
- APC_PLAY_INT |
- APC_CAPT_INT |
- APC_GENL_INT |
- APC_XINT_PEMP |
- APC_XINT_CEMP)))
- return IRQ_NONE;
-
- /* ACK the APC interrupt. */
- sbus_writel(csr, chip->port + APCCSR);
-
- snd_cs4231_generic_interrupt(chip);
-
- return IRQ_HANDLED;
-}
-#endif
-
-#ifdef EBUS_SUPPORT
-static void snd_cs4231_ebus_play_callback(struct ebus_dma_info *p, int event, void *cookie)
-{
- cs4231_t *chip = cookie;
-
if (chip->image[CS4231_IFACE_CTRL] & CS4231_PLAYBACK_ENABLE) {
snd_pcm_period_elapsed(chip->playback_substream);
- snd_cs4231_ebus_advance_dma(p, chip->playback_substream,
+ snd_cs4231_advance_dma(&chip->p_dma, chip->playback_substream,
&chip->p_periods_sent);
}
}
-static void snd_cs4231_ebus_capture_callback(struct ebus_dma_info *p, int event, void *cookie)
+static void snd_cs4231_capture_callback(struct snd_cs4231 *chip)
{
- cs4231_t *chip = cookie;
-
if (chip->image[CS4231_IFACE_CTRL] & CS4231_RECORD_ENABLE) {
snd_pcm_period_elapsed(chip->capture_substream);
- snd_cs4231_ebus_advance_dma(p, chip->capture_substream,
+ snd_cs4231_advance_dma(&chip->c_dma, chip->capture_substream,
&chip->c_periods_sent);
}
}
-#endif
-static snd_pcm_uframes_t snd_cs4231_playback_pointer(snd_pcm_substream_t *substream)
+static snd_pcm_uframes_t snd_cs4231_playback_pointer(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
- size_t ptr, residue, period_bytes;
-
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct cs4231_dma_control *dma_cont = &chip->p_dma;
+ size_t ptr;
+
if (!(chip->image[CS4231_IFACE_CTRL] & CS4231_PLAYBACK_ENABLE))
return 0;
- period_bytes = snd_pcm_lib_period_bytes(substream);
- ptr = period_bytes * chip->p_periods_sent;
-#ifdef EBUS_SUPPORT
- if (chip->flags & CS4231_FLAG_EBUS) {
- residue = ebus_dma_residue(&chip->eb2p);
- } else {
-#endif
-#ifdef SBUS_SUPPORT
- residue = sbus_readl(chip->port + APCPC);
-#endif
-#ifdef EBUS_SUPPORT
- }
-#endif
- ptr += (period_bytes - residue);
+ ptr = dma_cont->address(dma_cont);
+ if (ptr != 0)
+ ptr -= substream->runtime->dma_addr;
+
return bytes_to_frames(substream->runtime, ptr);
}
-static snd_pcm_uframes_t snd_cs4231_capture_pointer(snd_pcm_substream_t * substream)
+static snd_pcm_uframes_t snd_cs4231_capture_pointer(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
- size_t ptr, residue, period_bytes;
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct cs4231_dma_control *dma_cont = &chip->c_dma;
+ size_t ptr;
if (!(chip->image[CS4231_IFACE_CTRL] & CS4231_RECORD_ENABLE))
return 0;
- period_bytes = snd_pcm_lib_period_bytes(substream);
- ptr = period_bytes * chip->c_periods_sent;
-#ifdef EBUS_SUPPORT
- if (chip->flags & CS4231_FLAG_EBUS) {
- residue = ebus_dma_residue(&chip->eb2c);
- } else {
-#endif
-#ifdef SBUS_SUPPORT
- residue = sbus_readl(chip->port + APCCC);
-#endif
-#ifdef EBUS_SUPPORT
- }
-#endif
- ptr += (period_bytes - residue);
+ ptr = dma_cont->address(dma_cont);
+ if (ptr != 0)
+ ptr -= substream->runtime->dma_addr;
+
return bytes_to_frames(substream->runtime, ptr);
}
*/
-static int snd_cs4231_probe(cs4231_t *chip)
+static int __init snd_cs4231_probe(struct snd_cs4231 *chip)
{
unsigned long flags;
int i, id, vers;
unsigned char *ptr;
-#if 0
- snd_cs4231_debug(chip);
-#endif
id = vers = 0;
for (i = 0; i < 50; i++) {
mb();
break; /* this is valid value */
}
}
- snd_printdd("cs4231: port = 0x%lx, id = 0x%x\n", chip->port, id);
+ snd_printdd("cs4231: port = %p, id = 0x%x\n", chip->port, id);
if (id != 0x0a)
return -ENODEV; /* no valid device found */
spin_lock_irqsave(&chip->lock, flags);
- /* Reset DMA engine. */
-#ifdef EBUS_SUPPORT
- if (chip->flags & CS4231_FLAG_EBUS) {
- /* Done by ebus_dma_register */
- } else {
-#endif
-#ifdef SBUS_SUPPORT
- sbus_writel(APC_CHIP_RESET, chip->port + APCCSR);
- sbus_writel(0x00, chip->port + APCCSR);
- sbus_writel(sbus_readl(chip->port + APCCSR) | APC_CDC_RESET,
- chip->port + APCCSR);
-
- udelay(20);
-
- sbus_writel(sbus_readl(chip->port + APCCSR) & ~APC_CDC_RESET,
- chip->port + APCCSR);
- sbus_writel(sbus_readl(chip->port + APCCSR) | (APC_XINT_ENA |
- APC_XINT_PENA |
- APC_XINT_CENA),
- chip->port + APCCSR);
-#endif
-#ifdef EBUS_SUPPORT
- }
-#endif
+ /* Reset DMA engine (sbus only). */
+ chip->p_dma.reset(chip);
__cs4231_readb(chip, CS4231P(chip, STATUS)); /* clear any pendings IRQ */
__cs4231_writeb(chip, 0, CS4231P(chip, STATUS));
return 0; /* all things are ok.. */
}
-static snd_pcm_hardware_t snd_cs4231_playback =
+static struct snd_pcm_hardware snd_cs4231_playback =
{
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
SNDRV_PCM_INFO_MMAP_VALID | SNDRV_PCM_INFO_SYNC_START),
.channels_min = 1,
.channels_max = 2,
.buffer_bytes_max = (32*1024),
- .period_bytes_min = 4096,
+ .period_bytes_min = 64,
.period_bytes_max = (32*1024),
.periods_min = 1,
.periods_max = 1024,
};
-static snd_pcm_hardware_t snd_cs4231_capture =
+static struct snd_pcm_hardware snd_cs4231_capture =
{
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
SNDRV_PCM_INFO_MMAP_VALID | SNDRV_PCM_INFO_SYNC_START),
.channels_min = 1,
.channels_max = 2,
.buffer_bytes_max = (32*1024),
- .period_bytes_min = 4096,
+ .period_bytes_min = 64,
.period_bytes_max = (32*1024),
.periods_min = 1,
.periods_max = 1024,
};
-static int snd_cs4231_playback_open(snd_pcm_substream_t *substream)
+static int snd_cs4231_playback_open(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
- snd_pcm_runtime_t *runtime = substream->runtime;
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct snd_pcm_runtime *runtime = substream->runtime;
int err;
runtime->hw = snd_cs4231_playback;
return 0;
}
-static int snd_cs4231_capture_open(snd_pcm_substream_t *substream)
+static int snd_cs4231_capture_open(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
- snd_pcm_runtime_t *runtime = substream->runtime;
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
+ struct snd_pcm_runtime *runtime = substream->runtime;
int err;
runtime->hw = snd_cs4231_capture;
return 0;
}
-static int snd_cs4231_playback_close(snd_pcm_substream_t *substream)
+static int snd_cs4231_playback_close(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
- chip->playback_substream = NULL;
snd_cs4231_close(chip, CS4231_MODE_PLAY);
+ chip->playback_substream = NULL;
return 0;
}
-static int snd_cs4231_capture_close(snd_pcm_substream_t *substream)
+static int snd_cs4231_capture_close(struct snd_pcm_substream *substream)
{
- cs4231_t *chip = snd_pcm_substream_chip(substream);
+ struct snd_cs4231 *chip = snd_pcm_substream_chip(substream);
- chip->capture_substream = NULL;
snd_cs4231_close(chip, CS4231_MODE_RECORD);
+ chip->capture_substream = NULL;
return 0;
}
* XXX the audio AUXIO register...
*/
-static snd_pcm_ops_t snd_cs4231_playback_ops = {
+static struct snd_pcm_ops snd_cs4231_playback_ops = {
.open = snd_cs4231_playback_open,
.close = snd_cs4231_playback_close,
.ioctl = snd_pcm_lib_ioctl,
.pointer = snd_cs4231_playback_pointer,
};
-static snd_pcm_ops_t snd_cs4231_capture_ops = {
+static struct snd_pcm_ops snd_cs4231_capture_ops = {
.open = snd_cs4231_capture_open,
.close = snd_cs4231_capture_close,
.ioctl = snd_pcm_lib_ioctl,
.pointer = snd_cs4231_capture_pointer,
};
-static void snd_cs4231_pcm_free(snd_pcm_t *pcm)
-{
- cs4231_t *chip = pcm->private_data;
- chip->pcm = NULL;
- snd_pcm_lib_preallocate_free_for_all(pcm);
-}
-
-int snd_cs4231_pcm(cs4231_t *chip)
+static int __init snd_cs4231_pcm(struct snd_cs4231 *chip)
{
- snd_pcm_t *pcm;
+ struct snd_pcm *pcm;
int err;
if ((err = snd_pcm_new(chip->card, "CS4231", 0, 1, 1, &pcm)) < 0)
/* global setup */
pcm->private_data = chip;
- pcm->private_free = snd_cs4231_pcm_free;
pcm->info_flags = SNDRV_PCM_INFO_JOINT_DUPLEX;
strcpy(pcm->name, "CS4231");
-#ifdef EBUS_SUPPORT
- if (chip->flags & CS4231_FLAG_EBUS) {
- snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV,
- snd_dma_pci_data(chip->dev_u.pdev),
- 64*1024, 128*1024);
- } else {
-#endif
-#ifdef SBUS_SUPPORT
- snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_SBUS,
- snd_dma_sbus_data(chip->dev_u.sdev),
- 64*1024, 128*1024);
-#endif
-#ifdef EBUS_SUPPORT
- }
-#endif
+ chip->p_dma.preallocate(chip, pcm);
chip->pcm = pcm;
return 0;
}
-static void snd_cs4231_timer_free(snd_timer_t *timer)
-{
- cs4231_t *chip = timer->private_data;
- chip->timer = NULL;
-}
-
-int snd_cs4231_timer(cs4231_t *chip)
+static int __init snd_cs4231_timer(struct snd_cs4231 *chip)
{
- snd_timer_t *timer;
- snd_timer_id_t tid;
+ struct snd_timer *timer;
+ struct snd_timer_id tid;
int err;
/* Timer initialization */
return err;
strcpy(timer->name, "CS4231");
timer->private_data = chip;
- timer->private_free = snd_cs4231_timer_free;
timer->hw = snd_cs4231_timer_table;
chip->timer = timer;
* MIXER part
*/
-static int snd_cs4231_info_mux(snd_kcontrol_t *kcontrol, snd_ctl_elem_info_t *uinfo)
+static int snd_cs4231_info_mux(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_info *uinfo)
{
static char *texts[4] = {
"Line", "CD", "Mic", "Mix"
};
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
snd_assert(chip->card != NULL, return -EINVAL);
uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
return 0;
}
-static int snd_cs4231_get_mux(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_get_mux(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
spin_lock_irqsave(&chip->lock, flags);
return 0;
}
-static int snd_cs4231_put_mux(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_put_mux(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
unsigned short left, right;
int change;
return change;
}
-int snd_cs4231_info_single(snd_kcontrol_t *kcontrol, snd_ctl_elem_info_t *uinfo)
+static int snd_cs4231_info_single(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_info *uinfo)
{
int mask = (kcontrol->private_value >> 16) & 0xff;
return 0;
}
-int snd_cs4231_get_single(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_get_single(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
int reg = kcontrol->private_value & 0xff;
int shift = (kcontrol->private_value >> 8) & 0xff;
return 0;
}
-int snd_cs4231_put_single(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_put_single(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
int reg = kcontrol->private_value & 0xff;
int shift = (kcontrol->private_value >> 8) & 0xff;
return change;
}
-int snd_cs4231_info_double(snd_kcontrol_t *kcontrol, snd_ctl_elem_info_t *uinfo)
+static int snd_cs4231_info_double(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_info *uinfo)
{
int mask = (kcontrol->private_value >> 24) & 0xff;
return 0;
}
-int snd_cs4231_get_double(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_get_double(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
int left_reg = kcontrol->private_value & 0xff;
int right_reg = (kcontrol->private_value >> 8) & 0xff;
return 0;
}
-int snd_cs4231_put_double(snd_kcontrol_t *kcontrol, snd_ctl_elem_value_t *ucontrol)
+static int snd_cs4231_put_double(struct snd_kcontrol *kcontrol,
+ struct snd_ctl_elem_value *ucontrol)
{
- cs4231_t *chip = snd_kcontrol_chip(kcontrol);
+ struct snd_cs4231 *chip = snd_kcontrol_chip(kcontrol);
unsigned long flags;
int left_reg = kcontrol->private_value & 0xff;
int right_reg = (kcontrol->private_value >> 8) & 0xff;
.get = snd_cs4231_get_double, .put = snd_cs4231_put_double, \
.private_value = left_reg | (right_reg << 8) | (shift_left << 16) | (shift_right << 19) | (mask << 24) | (invert << 22) }
-static snd_kcontrol_new_t snd_cs4231_controls[] = {
+static struct snd_kcontrol_new snd_cs4231_controls[] __initdata = {
CS4231_DOUBLE("PCM Playback Switch", 0, CS4231_LEFT_OUTPUT, CS4231_RIGHT_OUTPUT, 7, 7, 1, 1),
CS4231_DOUBLE("PCM Playback Volume", 0, CS4231_LEFT_OUTPUT, CS4231_RIGHT_OUTPUT, 0, 0, 63, 1),
CS4231_DOUBLE("Line Playback Switch", 0, CS4231_LEFT_LINE_IN, CS4231_RIGHT_LINE_IN, 7, 7, 1, 1),
CS4231_SINGLE("Headphone Out Switch", 0, CS4231_PIN_CTRL, 7, 1, 1)
};
-int snd_cs4231_mixer(cs4231_t *chip)
+static int __init snd_cs4231_mixer(struct snd_cs4231 *chip)
{
- snd_card_t *card;
+ struct snd_card *card;
int err, idx;
snd_assert(chip != NULL && chip->pcm != NULL, return -EINVAL);
static int dev;
-static int cs4231_attach_begin(snd_card_t **rcard)
+static int __init cs4231_attach_begin(struct snd_card **rcard)
{
- snd_card_t *card;
+ struct snd_card *card;
*rcard = NULL;
return 0;
}
-static int cs4231_attach_finish(snd_card_t *card, cs4231_t *chip)
+static int __init cs4231_attach_finish(struct snd_card *card, struct snd_cs4231 *chip)
{
int err;
}
#ifdef SBUS_SUPPORT
-static int snd_cs4231_sbus_free(cs4231_t *chip)
+
+static irqreturn_t snd_cs4231_sbus_interrupt(int irq, void *dev_id)
+{
+ unsigned long flags;
+ unsigned char status;
+ u32 csr;
+ struct snd_cs4231 *chip = dev_id;
+
+ /*This is IRQ is not raised by the cs4231*/
+ if (!(__cs4231_readb(chip, CS4231P(chip, STATUS)) & CS4231_GLOBALIRQ))
+ return IRQ_NONE;
+
+ /* ACK the APC interrupt. */
+ csr = sbus_readl(chip->port + APCCSR);
+
+ sbus_writel(csr, chip->port + APCCSR);
+
+ if ((csr & APC_PDMA_READY) &&
+ (csr & APC_PLAY_INT) &&
+ (csr & APC_XINT_PNVA) &&
+ !(csr & APC_XINT_EMPT))
+ snd_cs4231_play_callback(chip);
+
+ if ((csr & APC_CDMA_READY) &&
+ (csr & APC_CAPT_INT) &&
+ (csr & APC_XINT_CNVA) &&
+ !(csr & APC_XINT_EMPT))
+ snd_cs4231_capture_callback(chip);
+
+ status = snd_cs4231_in(chip, CS4231_IRQ_STATUS);
+
+ if (status & CS4231_TIMER_IRQ) {
+ if (chip->timer)
+ snd_timer_interrupt(chip->timer, chip->timer->sticks);
+ }
+
+ if ((status & CS4231_RECORD_IRQ) && (csr & APC_CDMA_READY))
+ snd_cs4231_overrange(chip);
+
+ /* ACK the CS4231 interrupt. */
+ spin_lock_irqsave(&chip->lock, flags);
+ snd_cs4231_outm(chip, CS4231_IRQ_STATUS, ~CS4231_ALL_IRQS | ~status, 0);
+ spin_unlock_irqrestore(&chip->lock, flags);
+
+ return IRQ_HANDLED;
+}
+
+/*
+ * SBUS DMA routines
+ */
+
+static int sbus_dma_request(struct cs4231_dma_control *dma_cont, dma_addr_t bus_addr, size_t len)
+{
+ unsigned long flags;
+ u32 test, csr;
+ int err;
+ struct sbus_dma_info *base = &dma_cont->sbus_info;
+
+ if (len >= (1 << 24))
+ return -EINVAL;
+ spin_lock_irqsave(&base->lock, flags);
+ csr = sbus_readl(base->regs + APCCSR);
+ err = -EINVAL;
+ test = APC_CDMA_READY;
+ if ( base->dir == APC_PLAY )
+ test = APC_PDMA_READY;
+ if (!(csr & test))
+ goto out;
+ err = -EBUSY;
+ test = APC_XINT_CNVA;
+ if ( base->dir == APC_PLAY )
+ test = APC_XINT_PNVA;
+ if (!(csr & test))
+ goto out;
+ err = 0;
+ sbus_writel(bus_addr, base->regs + base->dir + APCNVA);
+ sbus_writel(len, base->regs + base->dir + APCNC);
+out:
+ spin_unlock_irqrestore(&base->lock, flags);
+ return err;
+}
+
+static void sbus_dma_prepare(struct cs4231_dma_control *dma_cont, int d)
+{
+ unsigned long flags;
+ u32 csr, test;
+ struct sbus_dma_info *base = &dma_cont->sbus_info;
+
+ spin_lock_irqsave(&base->lock, flags);
+ csr = sbus_readl(base->regs + APCCSR);
+ test = APC_GENL_INT | APC_PLAY_INT | APC_XINT_ENA |
+ APC_XINT_PLAY | APC_XINT_PEMP | APC_XINT_GENL |
+ APC_XINT_PENA;
+ if ( base->dir == APC_RECORD )
+ test = APC_GENL_INT | APC_CAPT_INT | APC_XINT_ENA |
+ APC_XINT_CAPT | APC_XINT_CEMP | APC_XINT_GENL;
+ csr |= test;
+ sbus_writel(csr, base->regs + APCCSR);
+ spin_unlock_irqrestore(&base->lock, flags);
+}
+
+static void sbus_dma_enable(struct cs4231_dma_control *dma_cont, int on)
+{
+ unsigned long flags;
+ u32 csr, shift;
+ struct sbus_dma_info *base = &dma_cont->sbus_info;
+
+ spin_lock_irqsave(&base->lock, flags);
+ if (!on) {
+ sbus_writel(0, base->regs + base->dir + APCNC);
+ sbus_writel(0, base->regs + base->dir + APCNVA);
+ sbus_writel(0, base->regs + base->dir + APCC);
+ sbus_writel(0, base->regs + base->dir + APCVA);
+
+ /* ACK any APC interrupts. */
+ csr = sbus_readl(base->regs + APCCSR);
+ sbus_writel(csr, base->regs + APCCSR);
+ }
+ udelay(1000);
+ csr = sbus_readl(base->regs + APCCSR);
+ shift = 0;
+ if ( base->dir == APC_PLAY )
+ shift = 1;
+ if (on)
+ csr &= ~(APC_CPAUSE << shift);
+ else
+ csr |= (APC_CPAUSE << shift);
+ sbus_writel(csr, base->regs + APCCSR);
+ if (on)
+ csr |= (APC_CDMA_READY << shift);
+ else
+ csr &= ~(APC_CDMA_READY << shift);
+ sbus_writel(csr, base->regs + APCCSR);
+
+ spin_unlock_irqrestore(&base->lock, flags);
+}
+
+static unsigned int sbus_dma_addr(struct cs4231_dma_control *dma_cont)
+{
+ struct sbus_dma_info *base = &dma_cont->sbus_info;
+
+ return sbus_readl(base->regs + base->dir + APCVA);
+}
+
+static void sbus_dma_reset(struct snd_cs4231 *chip)
+{
+ sbus_writel(APC_CHIP_RESET, chip->port + APCCSR);
+ sbus_writel(0x00, chip->port + APCCSR);
+ sbus_writel(sbus_readl(chip->port + APCCSR) | APC_CDC_RESET,
+ chip->port + APCCSR);
+
+ udelay(20);
+
+ sbus_writel(sbus_readl(chip->port + APCCSR) & ~APC_CDC_RESET,
+ chip->port + APCCSR);
+ sbus_writel(sbus_readl(chip->port + APCCSR) | (APC_XINT_ENA |
+ APC_XINT_PENA |
+ APC_XINT_CENA),
+ chip->port + APCCSR);
+}
+
+static void sbus_dma_preallocate(struct snd_cs4231 *chip, struct snd_pcm *pcm)
+{
+ snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_SBUS,
+ snd_dma_sbus_data(chip->dev_u.sdev),
+ 64*1024, 128*1024);
+}
+
+/*
+ * Init and exit routines
+ */
+
+static int snd_cs4231_sbus_free(struct snd_cs4231 *chip)
{
if (chip->irq[0])
free_irq(chip->irq[0], chip);
if (chip->port)
sbus_iounmap(chip->port, chip->regs_size);
- if (chip->timer)
- snd_device_free(chip->card, chip->timer);
-
kfree(chip);
return 0;
}
-static int snd_cs4231_sbus_dev_free(snd_device_t *device)
+static int snd_cs4231_sbus_dev_free(struct snd_device *device)
{
- cs4231_t *cp = device->device_data;
+ struct snd_cs4231 *cp = device->device_data;
return snd_cs4231_sbus_free(cp);
}
-static snd_device_ops_t snd_cs4231_sbus_dev_ops = {
+static struct snd_device_ops snd_cs4231_sbus_dev_ops = {
.dev_free = snd_cs4231_sbus_dev_free,
};
-static int __init snd_cs4231_sbus_create(snd_card_t *card,
+static int __init snd_cs4231_sbus_create(struct snd_card *card,
struct sbus_dev *sdev,
int dev,
- cs4231_t **rchip)
+ struct snd_cs4231 **rchip)
{
- cs4231_t *chip;
+ struct snd_cs4231 *chip;
int err;
*rchip = NULL;
- chip = kcalloc(1, sizeof(*chip), GFP_KERNEL);
+ chip = kzalloc(sizeof(*chip), GFP_KERNEL);
if (chip == NULL)
return -ENOMEM;
spin_lock_init(&chip->lock);
- init_MUTEX(&chip->mce_mutex);
- init_MUTEX(&chip->open_mutex);
+ spin_lock_init(&chip->c_dma.sbus_info.lock);
+ spin_lock_init(&chip->p_dma.sbus_info.lock);
+ mutex_init(&chip->mce_mutex);
+ mutex_init(&chip->open_mutex);
chip->card = card;
chip->dev_u.sdev = sdev;
chip->regs_size = sdev->reg_addrs[0].reg_size;
chip->port = sbus_ioremap(&sdev->resource[0], 0,
chip->regs_size, "cs4231");
if (!chip->port) {
- snd_printk("cs4231-%d: Unable to map chip registers.\n", dev);
+ snd_printdd("cs4231-%d: Unable to map chip registers.\n", dev);
return -EIO;
}
+ chip->c_dma.sbus_info.regs = chip->port;
+ chip->p_dma.sbus_info.regs = chip->port;
+ chip->c_dma.sbus_info.dir = APC_RECORD;
+ chip->p_dma.sbus_info.dir = APC_PLAY;
+
+ chip->p_dma.prepare = sbus_dma_prepare;
+ chip->p_dma.enable = sbus_dma_enable;
+ chip->p_dma.request = sbus_dma_request;
+ chip->p_dma.address = sbus_dma_addr;
+ chip->p_dma.reset = sbus_dma_reset;
+ chip->p_dma.preallocate = sbus_dma_preallocate;
+
+ chip->c_dma.prepare = sbus_dma_prepare;
+ chip->c_dma.enable = sbus_dma_enable;
+ chip->c_dma.request = sbus_dma_request;
+ chip->c_dma.address = sbus_dma_addr;
+ chip->c_dma.reset = sbus_dma_reset;
+ chip->c_dma.preallocate = sbus_dma_preallocate;
+
if (request_irq(sdev->irqs[0], snd_cs4231_sbus_interrupt,
- SA_SHIRQ, "cs4231", chip)) {
- snd_printk("cs4231-%d: Unable to grab SBUS IRQ %s\n",
- dev,
- __irq_itoa(sdev->irqs[0]));
+ IRQF_SHARED, "cs4231", chip)) {
+ snd_printdd("cs4231-%d: Unable to grab SBUS IRQ %d\n",
+ dev, sdev->irqs[0]);
snd_cs4231_sbus_free(chip);
return -EBUSY;
}
return 0;
}
-static int cs4231_sbus_attach(struct sbus_dev *sdev)
+static int __init cs4231_sbus_attach(struct sbus_dev *sdev)
{
struct resource *rp = &sdev->resource[0];
- cs4231_t *cp;
- snd_card_t *card;
+ struct snd_cs4231 *cp;
+ struct snd_card *card;
int err;
err = cs4231_attach_begin(&card);
if (err)
return err;
- sprintf(card->longname, "%s at 0x%02lx:0x%08lx, irq %s",
+ sprintf(card->longname, "%s at 0x%02lx:0x%016Lx, irq %d",
card->shortname,
rp->flags & 0xffL,
- rp->start,
- __irq_itoa(sdev->irqs[0]));
+ (unsigned long long)rp->start,
+ sdev->irqs[0]);
if ((err = snd_cs4231_sbus_create(card, sdev, dev, &cp)) < 0) {
snd_card_free(card);
#endif
#ifdef EBUS_SUPPORT
-static int snd_cs4231_ebus_free(cs4231_t *chip)
+
+static void snd_cs4231_ebus_play_callback(struct ebus_dma_info *p, int event, void *cookie)
+{
+ struct snd_cs4231 *chip = cookie;
+
+ snd_cs4231_play_callback(chip);
+}
+
+static void snd_cs4231_ebus_capture_callback(struct ebus_dma_info *p, int event, void *cookie)
+{
+ struct snd_cs4231 *chip = cookie;
+
+ snd_cs4231_capture_callback(chip);
+}
+
+/*
+ * EBUS DMA wrappers
+ */
+
+static int _ebus_dma_request(struct cs4231_dma_control *dma_cont, dma_addr_t bus_addr, size_t len)
+{
+ return ebus_dma_request(&dma_cont->ebus_info, bus_addr, len);
+}
+
+static void _ebus_dma_enable(struct cs4231_dma_control *dma_cont, int on)
+{
+ ebus_dma_enable(&dma_cont->ebus_info, on);
+}
+
+static void _ebus_dma_prepare(struct cs4231_dma_control *dma_cont, int dir)
+{
+ ebus_dma_prepare(&dma_cont->ebus_info, dir);
+}
+
+static unsigned int _ebus_dma_addr(struct cs4231_dma_control *dma_cont)
+{
+ return ebus_dma_addr(&dma_cont->ebus_info);
+}
+
+static void _ebus_dma_reset(struct snd_cs4231 *chip)
+{
+ return;
+}
+
+static void _ebus_dma_preallocate(struct snd_cs4231 *chip, struct snd_pcm *pcm)
+{
+ snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV,
+ snd_dma_pci_data(chip->dev_u.pdev),
+ 64*1024, 128*1024);
+}
+
+/*
+ * Init and exit routines
+ */
+
+static int snd_cs4231_ebus_free(struct snd_cs4231 *chip)
{
- if (chip->eb2c.regs) {
- ebus_dma_unregister(&chip->eb2c);
- iounmap(chip->eb2c.regs);
+ if (chip->c_dma.ebus_info.regs) {
+ ebus_dma_unregister(&chip->c_dma.ebus_info);
+ iounmap(chip->c_dma.ebus_info.regs);
}
- if (chip->eb2p.regs) {
- ebus_dma_unregister(&chip->eb2p);
- iounmap(chip->eb2p.regs);
+ if (chip->p_dma.ebus_info.regs) {
+ ebus_dma_unregister(&chip->p_dma.ebus_info);
+ iounmap(chip->p_dma.ebus_info.regs);
}
if (chip->port)
iounmap(chip->port);
- if (chip->timer)
- snd_device_free(chip->card, chip->timer);
kfree(chip);
return 0;
}
-static int snd_cs4231_ebus_dev_free(snd_device_t *device)
+static int snd_cs4231_ebus_dev_free(struct snd_device *device)
{
- cs4231_t *cp = device->device_data;
+ struct snd_cs4231 *cp = device->device_data;
return snd_cs4231_ebus_free(cp);
}
-static snd_device_ops_t snd_cs4231_ebus_dev_ops = {
+static struct snd_device_ops snd_cs4231_ebus_dev_ops = {
.dev_free = snd_cs4231_ebus_dev_free,
};
-static int __init snd_cs4231_ebus_create(snd_card_t *card,
+static int __init snd_cs4231_ebus_create(struct snd_card *card,
struct linux_ebus_device *edev,
int dev,
- cs4231_t **rchip)
+ struct snd_cs4231 **rchip)
{
- cs4231_t *chip;
+ struct snd_cs4231 *chip;
int err;
*rchip = NULL;
- chip = kcalloc(1, sizeof(*chip), GFP_KERNEL);
+ chip = kzalloc(sizeof(*chip), GFP_KERNEL);
if (chip == NULL)
return -ENOMEM;
spin_lock_init(&chip->lock);
- spin_lock_init(&chip->eb2c.lock);
- spin_lock_init(&chip->eb2p.lock);
- init_MUTEX(&chip->mce_mutex);
- init_MUTEX(&chip->open_mutex);
+ spin_lock_init(&chip->c_dma.ebus_info.lock);
+ spin_lock_init(&chip->p_dma.ebus_info.lock);
+ mutex_init(&chip->mce_mutex);
+ mutex_init(&chip->open_mutex);
chip->flags |= CS4231_FLAG_EBUS;
chip->card = card;
chip->dev_u.pdev = edev->bus->self;
memcpy(&chip->image, &snd_cs4231_original_image,
sizeof(snd_cs4231_original_image));
- strcpy(chip->eb2c.name, "cs4231(capture)");
- chip->eb2c.flags = EBUS_DMA_FLAG_USE_EBDMA_HANDLER;
- chip->eb2c.callback = snd_cs4231_ebus_capture_callback;
- chip->eb2c.client_cookie = chip;
- chip->eb2c.irq = edev->irqs[0];
- strcpy(chip->eb2p.name, "cs4231(play)");
- chip->eb2p.flags = EBUS_DMA_FLAG_USE_EBDMA_HANDLER;
- chip->eb2p.callback = snd_cs4231_ebus_play_callback;
- chip->eb2p.client_cookie = chip;
- chip->eb2p.irq = edev->irqs[1];
+ strcpy(chip->c_dma.ebus_info.name, "cs4231(capture)");
+ chip->c_dma.ebus_info.flags = EBUS_DMA_FLAG_USE_EBDMA_HANDLER;
+ chip->c_dma.ebus_info.callback = snd_cs4231_ebus_capture_callback;
+ chip->c_dma.ebus_info.client_cookie = chip;
+ chip->c_dma.ebus_info.irq = edev->irqs[0];
+ strcpy(chip->p_dma.ebus_info.name, "cs4231(play)");
+ chip->p_dma.ebus_info.flags = EBUS_DMA_FLAG_USE_EBDMA_HANDLER;
+ chip->p_dma.ebus_info.callback = snd_cs4231_ebus_play_callback;
+ chip->p_dma.ebus_info.client_cookie = chip;
+ chip->p_dma.ebus_info.irq = edev->irqs[1];
+
+ chip->p_dma.prepare = _ebus_dma_prepare;
+ chip->p_dma.enable = _ebus_dma_enable;
+ chip->p_dma.request = _ebus_dma_request;
+ chip->p_dma.address = _ebus_dma_addr;
+ chip->p_dma.reset = _ebus_dma_reset;
+ chip->p_dma.preallocate = _ebus_dma_preallocate;
+
+ chip->c_dma.prepare = _ebus_dma_prepare;
+ chip->c_dma.enable = _ebus_dma_enable;
+ chip->c_dma.request = _ebus_dma_request;
+ chip->c_dma.address = _ebus_dma_addr;
+ chip->c_dma.reset = _ebus_dma_reset;
+ chip->c_dma.preallocate = _ebus_dma_preallocate;
chip->port = ioremap(edev->resource[0].start, 0x10);
- chip->eb2p.regs = ioremap(edev->resource[1].start, 0x10);
- chip->eb2c.regs = ioremap(edev->resource[2].start, 0x10);
- if (!chip->port || !chip->eb2p.regs || !chip->eb2c.regs) {
+ chip->p_dma.ebus_info.regs = ioremap(edev->resource[1].start, 0x10);
+ chip->c_dma.ebus_info.regs = ioremap(edev->resource[2].start, 0x10);
+ if (!chip->port || !chip->p_dma.ebus_info.regs || !chip->c_dma.ebus_info.regs) {
snd_cs4231_ebus_free(chip);
- snd_printk("cs4231-%d: Unable to map chip registers.\n", dev);
+ snd_printdd("cs4231-%d: Unable to map chip registers.\n", dev);
return -EIO;
}
- if (ebus_dma_register(&chip->eb2c)) {
+ if (ebus_dma_register(&chip->c_dma.ebus_info)) {
snd_cs4231_ebus_free(chip);
- snd_printk("cs4231-%d: Unable to register EBUS capture DMA\n", dev);
+ snd_printdd("cs4231-%d: Unable to register EBUS capture DMA\n", dev);
return -EBUSY;
}
- if (ebus_dma_irq_enable(&chip->eb2c, 1)) {
+ if (ebus_dma_irq_enable(&chip->c_dma.ebus_info, 1)) {
snd_cs4231_ebus_free(chip);
- snd_printk("cs4231-%d: Unable to enable EBUS capture IRQ\n", dev);
+ snd_printdd("cs4231-%d: Unable to enable EBUS capture IRQ\n", dev);
return -EBUSY;
}
- if (ebus_dma_register(&chip->eb2p)) {
+ if (ebus_dma_register(&chip->p_dma.ebus_info)) {
snd_cs4231_ebus_free(chip);
- snd_printk("cs4231-%d: Unable to register EBUS play DMA\n", dev);
+ snd_printdd("cs4231-%d: Unable to register EBUS play DMA\n", dev);
return -EBUSY;
}
- if (ebus_dma_irq_enable(&chip->eb2p, 1)) {
+ if (ebus_dma_irq_enable(&chip->p_dma.ebus_info, 1)) {
snd_cs4231_ebus_free(chip);
- snd_printk("cs4231-%d: Unable to enable EBUS play IRQ\n", dev);
+ snd_printdd("cs4231-%d: Unable to enable EBUS play IRQ\n", dev);
return -EBUSY;
}
return 0;
}
-static int cs4231_ebus_attach(struct linux_ebus_device *edev)
+static int __init cs4231_ebus_attach(struct linux_ebus_device *edev)
{
- snd_card_t *card;
- cs4231_t *chip;
+ struct snd_card *card;
+ struct snd_cs4231 *chip;
int err;
err = cs4231_attach_begin(&card);
if (err)
return err;
- sprintf(card->longname, "%s at 0x%lx, irq %s",
+ sprintf(card->longname, "%s at 0x%lx, irq %d",
card->shortname,
edev->resource[0].start,
- __irq_itoa(edev->irqs[0]));
+ edev->irqs[0]);
if ((err = snd_cs4231_ebus_create(card, edev, dev, &chip)) < 0) {
snd_card_free(card);
for_each_ebusdev(edev, ebus) {
int match = 0;
- if (!strcmp(edev->prom_name, "SUNW,CS4231")) {
+ if (!strcmp(edev->prom_node->name, "SUNW,CS4231")) {
match = 1;
- } else if (!strcmp(edev->prom_name, "audio")) {
- char compat[16];
+ } else if (!strcmp(edev->prom_node->name, "audio")) {
+ char *compat;
- prom_getstring(edev->prom_node, "compatible",
- compat, sizeof(compat));
- compat[15] = '\0';
- if (!strcmp(compat, "SUNW,CS4231"))
+ compat = of_get_property(edev->prom_node,
+ "compatible", NULL);
+ if (compat && !strcmp(compat, "SUNW,CS4231"))
match = 1;
}
static void __exit cs4231_exit(void)
{
- cs4231_t *p = cs4231_list;
+ struct snd_cs4231 *p = cs4231_list;
while (p != NULL) {
- cs4231_t *next = p->next;
+ struct snd_cs4231 *next = p->next;
snd_card_free(p->card);