linux/sound/isa/sb/sb16_main.c
<<
>>
Prefs
   1/*
   2 *  Copyright (c) by Jaroslav Kysela <perex@perex.cz>
   3 *  Routines for control of 16-bit SoundBlaster cards and clones
   4 *  Note: This is very ugly hardware which uses one 8-bit DMA channel and
   5 *        second 16-bit DMA channel. Unfortunately 8-bit DMA channel can't
   6 *        transfer 16-bit samples and 16-bit DMA channels can't transfer
   7 *        8-bit samples. This make full duplex more complicated than
   8 *        can be... People, don't buy these soundcards for full 16-bit
   9 *        duplex!!!
  10 *  Note: 16-bit wide is assigned to first direction which made request.
  11 *        With full duplex - playback is preferred with abstract layer.
  12 *
  13 *  Note: Some chip revisions have hardware bug. Changing capture
  14 *        channel from full-duplex 8bit DMA to 16bit DMA will block
  15 *        16bit DMA transfers from DSP chip (capture) until 8bit transfer
  16 *        to DSP chip (playback) starts. This bug can be avoided with
  17 *        "16bit DMA Allocation" setting set to Playback or Capture.
  18 *
  19 *
  20 *   This program is free software; you can redistribute it and/or modify
  21 *   it under the terms of the GNU General Public License as published by
  22 *   the Free Software Foundation; either version 2 of the License, or
  23 *   (at your option) any later version.
  24 *
  25 *   This program is distributed in the hope that it will be useful,
  26 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
  27 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  28 *   GNU General Public License for more details.
  29 *
  30 *   You should have received a copy of the GNU General Public License
  31 *   along with this program; if not, write to the Free Software
  32 *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  33 *
  34 */
  35
  36#include <asm/io.h>
  37#include <asm/dma.h>
  38#include <linux/init.h>
  39#include <linux/time.h>
  40#include <sound/core.h>
  41#include <sound/sb.h>
  42#include <sound/sb16_csp.h>
  43#include <sound/mpu401.h>
  44#include <sound/control.h>
  45#include <sound/info.h>
  46
  47MODULE_AUTHOR("Jaroslav Kysela <perex@perex.cz>");
  48MODULE_DESCRIPTION("Routines for control of 16-bit SoundBlaster cards and clones");
  49MODULE_LICENSE("GPL");
  50
  51#ifdef CONFIG_SND_SB16_CSP
  52static void snd_sb16_csp_playback_prepare(struct snd_sb *chip, struct snd_pcm_runtime *runtime)
  53{
  54        if (chip->hardware == SB_HW_16CSP) {
  55                struct snd_sb_csp *csp = chip->csp;
  56
  57                if (csp->running & SNDRV_SB_CSP_ST_LOADED) {
  58                        /* manually loaded codec */
  59                        if ((csp->mode & SNDRV_SB_CSP_MODE_DSP_WRITE) &&
  60                            ((1U << runtime->format) == csp->acc_format)) {
  61                                /* Supported runtime PCM format for playback */
  62                                if (csp->ops.csp_use(csp) == 0) {
  63                                        /* If CSP was successfully acquired */
  64                                        goto __start_CSP;
  65                                }
  66                        } else if ((csp->mode & SNDRV_SB_CSP_MODE_QSOUND) && (csp->q_enabled)) {
  67                                /* QSound decoder is loaded and enabled */
  68                                if ((1 << runtime->format) & (SNDRV_PCM_FMTBIT_S8 | SNDRV_PCM_FMTBIT_U8 |
  69                                                              SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_U16_LE)) {
  70                                        /* Only for simple PCM formats */
  71                                        if (csp->ops.csp_use(csp) == 0) {
  72                                                /* If CSP was successfully acquired */
  73                                                goto __start_CSP;
  74                                        }
  75                                }
  76                        }
  77                } else if (csp->ops.csp_use(csp) == 0) {
  78                        /* Acquire CSP and try to autoload hardware codec */
  79                        if (csp->ops.csp_autoload(csp, runtime->format, SNDRV_SB_CSP_MODE_DSP_WRITE)) {
  80                                /* Unsupported format, release CSP */
  81                                csp->ops.csp_unuse(csp);
  82                        } else {
  83                      __start_CSP:
  84                                /* Try to start CSP */
  85                                if (csp->ops.csp_start(csp, (chip->mode & SB_MODE_PLAYBACK_16) ?
  86                                                       SNDRV_SB_CSP_SAMPLE_16BIT : SNDRV_SB_CSP_SAMPLE_8BIT,
  87                                                       (runtime->channels > 1) ?
  88                                                       SNDRV_SB_CSP_STEREO : SNDRV_SB_CSP_MONO)) {
  89                                        /* Failed, release CSP */
  90                                        csp->ops.csp_unuse(csp);
  91                                } else {
  92                                        /* Success, CSP acquired and running */
  93                                        chip->open = SNDRV_SB_CSP_MODE_DSP_WRITE;
  94                                }
  95                        }
  96                }
  97        }
  98}
  99
 100static void snd_sb16_csp_capture_prepare(struct snd_sb *chip, struct snd_pcm_runtime *runtime)
 101{
 102        if (chip->hardware == SB_HW_16CSP) {
 103                struct snd_sb_csp *csp = chip->csp;
 104
 105                if (csp->running & SNDRV_SB_CSP_ST_LOADED) {
 106                        /* manually loaded codec */
 107                        if ((csp->mode & SNDRV_SB_CSP_MODE_DSP_READ) &&
 108                            ((1U << runtime->format) == csp->acc_format)) {
 109                                /* Supported runtime PCM format for capture */
 110                                if (csp->ops.csp_use(csp) == 0) {
 111                                        /* If CSP was successfully acquired */
 112                                        goto __start_CSP;
 113                                }
 114                        }
 115                } else if (csp->ops.csp_use(csp) == 0) {
 116                        /* Acquire CSP and try to autoload hardware codec */
 117                        if (csp->ops.csp_autoload(csp, runtime->format, SNDRV_SB_CSP_MODE_DSP_READ)) {
 118                                /* Unsupported format, release CSP */
 119                                csp->ops.csp_unuse(csp);
 120                        } else {
 121                      __start_CSP:
 122                                /* Try to start CSP */
 123                                if (csp->ops.csp_start(csp, (chip->mode & SB_MODE_CAPTURE_16) ?
 124                                                       SNDRV_SB_CSP_SAMPLE_16BIT : SNDRV_SB_CSP_SAMPLE_8BIT,
 125                                                       (runtime->channels > 1) ?
 126                                                       SNDRV_SB_CSP_STEREO : SNDRV_SB_CSP_MONO)) {
 127                                        /* Failed, release CSP */
 128                                        csp->ops.csp_unuse(csp);
 129                                } else {
 130                                        /* Success, CSP acquired and running */
 131                                        chip->open = SNDRV_SB_CSP_MODE_DSP_READ;
 132                                }
 133                        }
 134                }
 135        }
 136}
 137
 138static void snd_sb16_csp_update(struct snd_sb *chip)
 139{
 140        if (chip->hardware == SB_HW_16CSP) {
 141                struct snd_sb_csp *csp = chip->csp;
 142
 143                if (csp->qpos_changed) {
 144                        spin_lock(&chip->reg_lock);
 145                        csp->ops.csp_qsound_transfer (csp);
 146                        spin_unlock(&chip->reg_lock);
 147                }
 148        }
 149}
 150
 151static void snd_sb16_csp_playback_open(struct snd_sb *chip, struct snd_pcm_runtime *runtime)
 152{
 153        /* CSP decoders (QSound excluded) support only 16bit transfers */
 154        if (chip->hardware == SB_HW_16CSP) {
 155                struct snd_sb_csp *csp = chip->csp;
 156
 157                if (csp->running & SNDRV_SB_CSP_ST_LOADED) {
 158                        /* manually loaded codec */
 159                        if (csp->mode & SNDRV_SB_CSP_MODE_DSP_WRITE) {
 160                                runtime->hw.formats |= csp->acc_format;
 161                        }
 162                } else {
 163                        /* autoloaded codecs */
 164                        runtime->hw.formats |= SNDRV_PCM_FMTBIT_MU_LAW | SNDRV_PCM_FMTBIT_A_LAW |
 165                                               SNDRV_PCM_FMTBIT_IMA_ADPCM;
 166                }
 167        }
 168}
 169
 170static void snd_sb16_csp_playback_close(struct snd_sb *chip)
 171{
 172        if ((chip->hardware == SB_HW_16CSP) && (chip->open == SNDRV_SB_CSP_MODE_DSP_WRITE)) {
 173                struct snd_sb_csp *csp = chip->csp;
 174
 175                if (csp->ops.csp_stop(csp) == 0) {
 176                        csp->ops.csp_unuse(csp);
 177                        chip->open = 0;
 178                }
 179        }
 180}
 181
 182static void snd_sb16_csp_capture_open(struct snd_sb *chip, struct snd_pcm_runtime *runtime)
 183{
 184        /* CSP coders support only 16bit transfers */
 185        if (chip->hardware == SB_HW_16CSP) {
 186                struct snd_sb_csp *csp = chip->csp;
 187
 188                if (csp->running & SNDRV_SB_CSP_ST_LOADED) {
 189                        /* manually loaded codec */
 190                        if (csp->mode & SNDRV_SB_CSP_MODE_DSP_READ) {
 191                                runtime->hw.formats |= csp->acc_format;
 192                        }
 193                } else {
 194                        /* autoloaded codecs */
 195                        runtime->hw.formats |= SNDRV_PCM_FMTBIT_MU_LAW | SNDRV_PCM_FMTBIT_A_LAW |
 196                                               SNDRV_PCM_FMTBIT_IMA_ADPCM;
 197                }
 198        }
 199}
 200
 201static void snd_sb16_csp_capture_close(struct snd_sb *chip)
 202{
 203        if ((chip->hardware == SB_HW_16CSP) && (chip->open == SNDRV_SB_CSP_MODE_DSP_READ)) {
 204                struct snd_sb_csp *csp = chip->csp;
 205
 206                if (csp->ops.csp_stop(csp) == 0) {
 207                        csp->ops.csp_unuse(csp);
 208                        chip->open = 0;
 209                }
 210        }
 211}
 212#else
 213#define snd_sb16_csp_playback_prepare(chip, runtime)    /*nop*/
 214#define snd_sb16_csp_capture_prepare(chip, runtime)     /*nop*/
 215#define snd_sb16_csp_update(chip)                       /*nop*/
 216#define snd_sb16_csp_playback_open(chip, runtime)       /*nop*/
 217#define snd_sb16_csp_playback_close(chip)               /*nop*/
 218#define snd_sb16_csp_capture_open(chip, runtime)        /*nop*/
 219#define snd_sb16_csp_capture_close(chip)                /*nop*/
 220#endif
 221
 222
 223static void snd_sb16_setup_rate(struct snd_sb *chip,
 224                                unsigned short rate,
 225                                int channel)
 226{
 227        unsigned long flags;
 228
 229        spin_lock_irqsave(&chip->reg_lock, flags);
 230        if (chip->mode & (channel == SNDRV_PCM_STREAM_PLAYBACK ? SB_MODE_PLAYBACK_16 : SB_MODE_CAPTURE_16))
 231                snd_sb_ack_16bit(chip);
 232        else
 233                snd_sb_ack_8bit(chip);
 234        if (!(chip->mode & SB_RATE_LOCK)) {
 235                chip->locked_rate = rate;
 236                snd_sbdsp_command(chip, SB_DSP_SAMPLE_RATE_IN);
 237                snd_sbdsp_command(chip, rate >> 8);
 238                snd_sbdsp_command(chip, rate & 0xff);
 239                snd_sbdsp_command(chip, SB_DSP_SAMPLE_RATE_OUT);
 240                snd_sbdsp_command(chip, rate >> 8);
 241                snd_sbdsp_command(chip, rate & 0xff);
 242        }
 243        spin_unlock_irqrestore(&chip->reg_lock, flags);
 244}
 245
 246static int snd_sb16_hw_params(struct snd_pcm_substream *substream,
 247                              struct snd_pcm_hw_params *hw_params)
 248{
 249        return snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(hw_params));
 250}
 251
 252static int snd_sb16_hw_free(struct snd_pcm_substream *substream)
 253{
 254        snd_pcm_lib_free_pages(substream);
 255        return 0;
 256}
 257
 258static int snd_sb16_playback_prepare(struct snd_pcm_substream *substream)
 259{
 260        unsigned long flags;
 261        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 262        struct snd_pcm_runtime *runtime = substream->runtime;
 263        unsigned char format;
 264        unsigned int size, count, dma;
 265
 266        snd_sb16_csp_playback_prepare(chip, runtime);
 267        if (snd_pcm_format_unsigned(runtime->format) > 0) {
 268                format = runtime->channels > 1 ? SB_DSP4_MODE_UNS_STEREO : SB_DSP4_MODE_UNS_MONO;
 269        } else {
 270                format = runtime->channels > 1 ? SB_DSP4_MODE_SIGN_STEREO : SB_DSP4_MODE_SIGN_MONO;
 271        }
 272
 273        snd_sb16_setup_rate(chip, runtime->rate, SNDRV_PCM_STREAM_PLAYBACK);
 274        size = chip->p_dma_size = snd_pcm_lib_buffer_bytes(substream);
 275        dma = (chip->mode & SB_MODE_PLAYBACK_8) ? chip->dma8 : chip->dma16;
 276        snd_dma_program(dma, runtime->dma_addr, size, DMA_MODE_WRITE | DMA_AUTOINIT);
 277
 278        count = snd_pcm_lib_period_bytes(substream);
 279        spin_lock_irqsave(&chip->reg_lock, flags);
 280        if (chip->mode & SB_MODE_PLAYBACK_16) {
 281                count >>= 1;
 282                count--;
 283                snd_sbdsp_command(chip, SB_DSP4_OUT16_AI);
 284                snd_sbdsp_command(chip, format);
 285                snd_sbdsp_command(chip, count & 0xff);
 286                snd_sbdsp_command(chip, count >> 8);
 287                snd_sbdsp_command(chip, SB_DSP_DMA16_OFF);
 288        } else {
 289                count--;
 290                snd_sbdsp_command(chip, SB_DSP4_OUT8_AI);
 291                snd_sbdsp_command(chip, format);
 292                snd_sbdsp_command(chip, count & 0xff);
 293                snd_sbdsp_command(chip, count >> 8);
 294                snd_sbdsp_command(chip, SB_DSP_DMA8_OFF);
 295        }
 296        spin_unlock_irqrestore(&chip->reg_lock, flags);
 297        return 0;
 298}
 299
 300static int snd_sb16_playback_trigger(struct snd_pcm_substream *substream,
 301                                     int cmd)
 302{
 303        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 304        int result = 0;
 305
 306        spin_lock(&chip->reg_lock);
 307        switch (cmd) {
 308        case SNDRV_PCM_TRIGGER_START:
 309        case SNDRV_PCM_TRIGGER_RESUME:
 310                chip->mode |= SB_RATE_LOCK_PLAYBACK;
 311                snd_sbdsp_command(chip, chip->mode & SB_MODE_PLAYBACK_16 ? SB_DSP_DMA16_ON : SB_DSP_DMA8_ON);
 312                break;
 313        case SNDRV_PCM_TRIGGER_STOP:
 314        case SNDRV_PCM_TRIGGER_SUSPEND:
 315                snd_sbdsp_command(chip, chip->mode & SB_MODE_PLAYBACK_16 ? SB_DSP_DMA16_OFF : SB_DSP_DMA8_OFF);
 316                /* next two lines are needed for some types of DSP4 (SB AWE 32 - 4.13) */
 317                if (chip->mode & SB_RATE_LOCK_CAPTURE)
 318                        snd_sbdsp_command(chip, chip->mode & SB_MODE_CAPTURE_16 ? SB_DSP_DMA16_ON : SB_DSP_DMA8_ON);
 319                chip->mode &= ~SB_RATE_LOCK_PLAYBACK;
 320                break;
 321        default:
 322                result = -EINVAL;
 323        }
 324        spin_unlock(&chip->reg_lock);
 325        return result;
 326}
 327
 328static int snd_sb16_capture_prepare(struct snd_pcm_substream *substream)
 329{
 330        unsigned long flags;
 331        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 332        struct snd_pcm_runtime *runtime = substream->runtime;
 333        unsigned char format;
 334        unsigned int size, count, dma;
 335
 336        snd_sb16_csp_capture_prepare(chip, runtime);
 337        if (snd_pcm_format_unsigned(runtime->format) > 0) {
 338                format = runtime->channels > 1 ? SB_DSP4_MODE_UNS_STEREO : SB_DSP4_MODE_UNS_MONO;
 339        } else {
 340                format = runtime->channels > 1 ? SB_DSP4_MODE_SIGN_STEREO : SB_DSP4_MODE_SIGN_MONO;
 341        }
 342        snd_sb16_setup_rate(chip, runtime->rate, SNDRV_PCM_STREAM_CAPTURE);
 343        size = chip->c_dma_size = snd_pcm_lib_buffer_bytes(substream);
 344        dma = (chip->mode & SB_MODE_CAPTURE_8) ? chip->dma8 : chip->dma16;
 345        snd_dma_program(dma, runtime->dma_addr, size, DMA_MODE_READ | DMA_AUTOINIT);
 346
 347        count = snd_pcm_lib_period_bytes(substream);
 348        spin_lock_irqsave(&chip->reg_lock, flags);
 349        if (chip->mode & SB_MODE_CAPTURE_16) {
 350                count >>= 1;
 351                count--;
 352                snd_sbdsp_command(chip, SB_DSP4_IN16_AI);
 353                snd_sbdsp_command(chip, format);
 354                snd_sbdsp_command(chip, count & 0xff);
 355                snd_sbdsp_command(chip, count >> 8);
 356                snd_sbdsp_command(chip, SB_DSP_DMA16_OFF);
 357        } else {
 358                count--;
 359                snd_sbdsp_command(chip, SB_DSP4_IN8_AI);
 360                snd_sbdsp_command(chip, format);
 361                snd_sbdsp_command(chip, count & 0xff);
 362                snd_sbdsp_command(chip, count >> 8);
 363                snd_sbdsp_command(chip, SB_DSP_DMA8_OFF);
 364        }
 365        spin_unlock_irqrestore(&chip->reg_lock, flags);
 366        return 0;
 367}
 368
 369static int snd_sb16_capture_trigger(struct snd_pcm_substream *substream,
 370                                    int cmd)
 371{
 372        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 373        int result = 0;
 374
 375        spin_lock(&chip->reg_lock);
 376        switch (cmd) {
 377        case SNDRV_PCM_TRIGGER_START:
 378        case SNDRV_PCM_TRIGGER_RESUME:
 379                chip->mode |= SB_RATE_LOCK_CAPTURE;
 380                snd_sbdsp_command(chip, chip->mode & SB_MODE_CAPTURE_16 ? SB_DSP_DMA16_ON : SB_DSP_DMA8_ON);
 381                break;
 382        case SNDRV_PCM_TRIGGER_STOP:
 383        case SNDRV_PCM_TRIGGER_SUSPEND:
 384                snd_sbdsp_command(chip, chip->mode & SB_MODE_CAPTURE_16 ? SB_DSP_DMA16_OFF : SB_DSP_DMA8_OFF);
 385                /* next two lines are needed for some types of DSP4 (SB AWE 32 - 4.13) */
 386                if (chip->mode & SB_RATE_LOCK_PLAYBACK)
 387                        snd_sbdsp_command(chip, chip->mode & SB_MODE_PLAYBACK_16 ? SB_DSP_DMA16_ON : SB_DSP_DMA8_ON);
 388                chip->mode &= ~SB_RATE_LOCK_CAPTURE;
 389                break;
 390        default:
 391                result = -EINVAL;
 392        }
 393        spin_unlock(&chip->reg_lock);
 394        return result;
 395}
 396
 397irqreturn_t snd_sb16dsp_interrupt(int irq, void *dev_id)
 398{
 399        struct snd_sb *chip = dev_id;
 400        unsigned char status;
 401        int ok;
 402
 403        spin_lock(&chip->mixer_lock);
 404        status = snd_sbmixer_read(chip, SB_DSP4_IRQSTATUS);
 405        spin_unlock(&chip->mixer_lock);
 406        if ((status & SB_IRQTYPE_MPUIN) && chip->rmidi_callback)
 407                chip->rmidi_callback(irq, chip->rmidi->private_data);
 408        if (status & SB_IRQTYPE_8BIT) {
 409                ok = 0;
 410                if (chip->mode & SB_MODE_PLAYBACK_8) {
 411                        snd_pcm_period_elapsed(chip->playback_substream);
 412                        snd_sb16_csp_update(chip);
 413                        ok++;
 414                }
 415                if (chip->mode & SB_MODE_CAPTURE_8) {
 416                        snd_pcm_period_elapsed(chip->capture_substream);
 417                        ok++;
 418                }
 419                spin_lock(&chip->reg_lock);
 420                if (!ok)
 421                        snd_sbdsp_command(chip, SB_DSP_DMA8_OFF);
 422                snd_sb_ack_8bit(chip);
 423                spin_unlock(&chip->reg_lock);
 424        }
 425        if (status & SB_IRQTYPE_16BIT) {
 426                ok = 0;
 427                if (chip->mode & SB_MODE_PLAYBACK_16) {
 428                        snd_pcm_period_elapsed(chip->playback_substream);
 429                        snd_sb16_csp_update(chip);
 430                        ok++;
 431                }
 432                if (chip->mode & SB_MODE_CAPTURE_16) {
 433                        snd_pcm_period_elapsed(chip->capture_substream);
 434                        ok++;
 435                }
 436                spin_lock(&chip->reg_lock);
 437                if (!ok)
 438                        snd_sbdsp_command(chip, SB_DSP_DMA16_OFF);
 439                snd_sb_ack_16bit(chip);
 440                spin_unlock(&chip->reg_lock);
 441        }
 442        return IRQ_HANDLED;
 443}
 444
 445/*
 446
 447 */
 448
 449static snd_pcm_uframes_t snd_sb16_playback_pointer(struct snd_pcm_substream *substream)
 450{
 451        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 452        unsigned int dma;
 453        size_t ptr;
 454
 455        dma = (chip->mode & SB_MODE_PLAYBACK_8) ? chip->dma8 : chip->dma16;
 456        ptr = snd_dma_pointer(dma, chip->p_dma_size);
 457        return bytes_to_frames(substream->runtime, ptr);
 458}
 459
 460static snd_pcm_uframes_t snd_sb16_capture_pointer(struct snd_pcm_substream *substream)
 461{
 462        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 463        unsigned int dma;
 464        size_t ptr;
 465
 466        dma = (chip->mode & SB_MODE_CAPTURE_8) ? chip->dma8 : chip->dma16;
 467        ptr = snd_dma_pointer(dma, chip->c_dma_size);
 468        return bytes_to_frames(substream->runtime, ptr);
 469}
 470
 471/*
 472
 473 */
 474
 475static struct snd_pcm_hardware snd_sb16_playback =
 476{
 477        .info =                 (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
 478                                 SNDRV_PCM_INFO_MMAP_VALID),
 479        .formats =              0,
 480        .rates =                SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_8000_44100,
 481        .rate_min =             4000,
 482        .rate_max =             44100,
 483        .channels_min =         1,
 484        .channels_max =         2,
 485        .buffer_bytes_max =     (128*1024),
 486        .period_bytes_min =     64,
 487        .period_bytes_max =     (128*1024),
 488        .periods_min =          1,
 489        .periods_max =          1024,
 490        .fifo_size =            0,
 491};
 492
 493static struct snd_pcm_hardware snd_sb16_capture =
 494{
 495        .info =                 (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
 496                                 SNDRV_PCM_INFO_MMAP_VALID),
 497        .formats =              0,
 498        .rates =                SNDRV_PCM_RATE_CONTINUOUS | SNDRV_PCM_RATE_8000_44100,
 499        .rate_min =             4000,
 500        .rate_max =             44100,
 501        .channels_min =         1,
 502        .channels_max =         2,
 503        .buffer_bytes_max =     (128*1024),
 504        .period_bytes_min =     64,
 505        .period_bytes_max =     (128*1024),
 506        .periods_min =          1,
 507        .periods_max =          1024,
 508        .fifo_size =            0,
 509};
 510
 511/*
 512 *  open/close
 513 */
 514
 515static int snd_sb16_playback_open(struct snd_pcm_substream *substream)
 516{
 517        unsigned long flags;
 518        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 519        struct snd_pcm_runtime *runtime = substream->runtime;
 520
 521        spin_lock_irqsave(&chip->open_lock, flags);
 522        if (chip->mode & SB_MODE_PLAYBACK) {
 523                spin_unlock_irqrestore(&chip->open_lock, flags);
 524                return -EAGAIN;
 525        }
 526        runtime->hw = snd_sb16_playback;
 527
 528        /* skip if 16 bit DMA was reserved for capture */
 529        if (chip->force_mode16 & SB_MODE_CAPTURE_16)
 530                goto __skip_16bit;
 531
 532        if (chip->dma16 >= 0 && !(chip->mode & SB_MODE_CAPTURE_16)) {
 533                chip->mode |= SB_MODE_PLAYBACK_16;
 534                runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_U16_LE;
 535                /* Vibra16X hack */
 536                if (chip->dma16 <= 3) {
 537                        runtime->hw.buffer_bytes_max =
 538                        runtime->hw.period_bytes_max = 64 * 1024;
 539                } else {
 540                        snd_sb16_csp_playback_open(chip, runtime);
 541                }
 542                goto __open_ok;
 543        }
 544
 545      __skip_16bit:
 546        if (chip->dma8 >= 0 && !(chip->mode & SB_MODE_CAPTURE_8)) {
 547                chip->mode |= SB_MODE_PLAYBACK_8;
 548                /* DSP v 4.xx can transfer 16bit data through 8bit DMA channel, SBHWPG 2-7 */
 549                if (chip->dma16 < 0) {
 550                        runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_U16_LE;
 551                        chip->mode |= SB_MODE_PLAYBACK_16;
 552                } else {
 553                        runtime->hw.formats = SNDRV_PCM_FMTBIT_U8 | SNDRV_PCM_FMTBIT_S8;
 554                }
 555                runtime->hw.buffer_bytes_max =
 556                runtime->hw.period_bytes_max = 64 * 1024;
 557                goto __open_ok;
 558        }
 559        spin_unlock_irqrestore(&chip->open_lock, flags);
 560        return -EAGAIN;
 561
 562      __open_ok:
 563        if (chip->hardware == SB_HW_ALS100)
 564                runtime->hw.rate_max = 48000;
 565        if (chip->hardware == SB_HW_CS5530) {
 566                runtime->hw.buffer_bytes_max = 32 * 1024;
 567                runtime->hw.periods_min = 2;
 568                runtime->hw.rate_min = 44100;
 569        }
 570        if (chip->mode & SB_RATE_LOCK)
 571                runtime->hw.rate_min = runtime->hw.rate_max = chip->locked_rate;
 572        chip->playback_substream = substream;
 573        spin_unlock_irqrestore(&chip->open_lock, flags);
 574        return 0;
 575}
 576
 577static int snd_sb16_playback_close(struct snd_pcm_substream *substream)
 578{
 579        unsigned long flags;
 580        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 581
 582        snd_sb16_csp_playback_close(chip);
 583        spin_lock_irqsave(&chip->open_lock, flags);
 584        chip->playback_substream = NULL;
 585        chip->mode &= ~SB_MODE_PLAYBACK;
 586        spin_unlock_irqrestore(&chip->open_lock, flags);
 587        return 0;
 588}
 589
 590static int snd_sb16_capture_open(struct snd_pcm_substream *substream)
 591{
 592        unsigned long flags;
 593        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 594        struct snd_pcm_runtime *runtime = substream->runtime;
 595
 596        spin_lock_irqsave(&chip->open_lock, flags);
 597        if (chip->mode & SB_MODE_CAPTURE) {
 598                spin_unlock_irqrestore(&chip->open_lock, flags);
 599                return -EAGAIN;
 600        }
 601        runtime->hw = snd_sb16_capture;
 602
 603        /* skip if 16 bit DMA was reserved for playback */
 604        if (chip->force_mode16 & SB_MODE_PLAYBACK_16)
 605                goto __skip_16bit;
 606
 607        if (chip->dma16 >= 0 && !(chip->mode & SB_MODE_PLAYBACK_16)) {
 608                chip->mode |= SB_MODE_CAPTURE_16;
 609                runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_U16_LE;
 610                /* Vibra16X hack */
 611                if (chip->dma16 <= 3) {
 612                        runtime->hw.buffer_bytes_max =
 613                        runtime->hw.period_bytes_max = 64 * 1024;
 614                } else {
 615                        snd_sb16_csp_capture_open(chip, runtime);
 616                }
 617                goto __open_ok;
 618        }
 619
 620      __skip_16bit:
 621        if (chip->dma8 >= 0 && !(chip->mode & SB_MODE_PLAYBACK_8)) {
 622                chip->mode |= SB_MODE_CAPTURE_8;
 623                /* DSP v 4.xx can transfer 16bit data through 8bit DMA channel, SBHWPG 2-7 */
 624                if (chip->dma16 < 0) {
 625                        runtime->hw.formats = SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_U16_LE;
 626                        chip->mode |= SB_MODE_CAPTURE_16;
 627                } else {
 628                        runtime->hw.formats = SNDRV_PCM_FMTBIT_U8 | SNDRV_PCM_FMTBIT_S8;
 629                }
 630                runtime->hw.buffer_bytes_max =
 631                runtime->hw.period_bytes_max = 64 * 1024;
 632                goto __open_ok;
 633        }
 634        spin_unlock_irqrestore(&chip->open_lock, flags);
 635        return -EAGAIN;
 636
 637      __open_ok:
 638        if (chip->hardware == SB_HW_ALS100)
 639                runtime->hw.rate_max = 48000;
 640        if (chip->hardware == SB_HW_CS5530) {
 641                runtime->hw.buffer_bytes_max = 32 * 1024;
 642                runtime->hw.periods_min = 2;
 643                runtime->hw.rate_min = 44100;
 644        }
 645        if (chip->mode & SB_RATE_LOCK)
 646                runtime->hw.rate_min = runtime->hw.rate_max = chip->locked_rate;
 647        chip->capture_substream = substream;
 648        spin_unlock_irqrestore(&chip->open_lock, flags);
 649        return 0;
 650}
 651
 652static int snd_sb16_capture_close(struct snd_pcm_substream *substream)
 653{
 654        unsigned long flags;
 655        struct snd_sb *chip = snd_pcm_substream_chip(substream);
 656
 657        snd_sb16_csp_capture_close(chip);
 658        spin_lock_irqsave(&chip->open_lock, flags);
 659        chip->capture_substream = NULL;
 660        chip->mode &= ~SB_MODE_CAPTURE;
 661        spin_unlock_irqrestore(&chip->open_lock, flags);
 662        return 0;
 663}
 664
 665/*
 666 *  DMA control interface
 667 */
 668
 669static int snd_sb16_set_dma_mode(struct snd_sb *chip, int what)
 670{
 671        if (chip->dma8 < 0 || chip->dma16 < 0) {
 672                if (snd_BUG_ON(what))
 673                        return -EINVAL;
 674                return 0;
 675        }
 676        if (what == 0) {
 677                chip->force_mode16 = 0;
 678        } else if (what == 1) {
 679                chip->force_mode16 = SB_MODE_PLAYBACK_16;
 680        } else if (what == 2) {
 681                chip->force_mode16 = SB_MODE_CAPTURE_16;
 682        } else {
 683                return -EINVAL;
 684        }
 685        return 0;
 686}
 687
 688static int snd_sb16_get_dma_mode(struct snd_sb *chip)
 689{
 690        if (chip->dma8 < 0 || chip->dma16 < 0)
 691                return 0;
 692        switch (chip->force_mode16) {
 693        case SB_MODE_PLAYBACK_16:
 694                return 1;
 695        case SB_MODE_CAPTURE_16:
 696                return 2;
 697        default:
 698                return 0;
 699        }
 700}
 701
 702static int snd_sb16_dma_control_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
 703{
 704        static char *texts[3] = {
 705                "Auto", "Playback", "Capture"
 706        };
 707
 708        uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
 709        uinfo->count = 1;
 710        uinfo->value.enumerated.items = 3;
 711        if (uinfo->value.enumerated.item > 2)
 712                uinfo->value.enumerated.item = 2;
 713        strcpy(uinfo->value.enumerated.name, texts[uinfo->value.enumerated.item]);
 714        return 0;
 715}
 716
 717static int snd_sb16_dma_control_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
 718{
 719        struct snd_sb *chip = snd_kcontrol_chip(kcontrol);
 720        unsigned long flags;
 721        
 722        spin_lock_irqsave(&chip->reg_lock, flags);
 723        ucontrol->value.enumerated.item[0] = snd_sb16_get_dma_mode(chip);
 724        spin_unlock_irqrestore(&chip->reg_lock, flags);
 725        return 0;
 726}
 727
 728static int snd_sb16_dma_control_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
 729{
 730        struct snd_sb *chip = snd_kcontrol_chip(kcontrol);
 731        unsigned long flags;
 732        unsigned char nval, oval;
 733        int change;
 734        
 735        if ((nval = ucontrol->value.enumerated.item[0]) > 2)
 736                return -EINVAL;
 737        spin_lock_irqsave(&chip->reg_lock, flags);
 738        oval = snd_sb16_get_dma_mode(chip);
 739        change = nval != oval;
 740        snd_sb16_set_dma_mode(chip, nval);
 741        spin_unlock_irqrestore(&chip->reg_lock, flags);
 742        return change;
 743}
 744
 745static struct snd_kcontrol_new snd_sb16_dma_control = {
 746        .iface = SNDRV_CTL_ELEM_IFACE_CARD,
 747        .name = "16-bit DMA Allocation",
 748        .info = snd_sb16_dma_control_info,
 749        .get = snd_sb16_dma_control_get,
 750        .put = snd_sb16_dma_control_put
 751};
 752
 753/*
 754 *  Initialization part
 755 */
 756 
 757int snd_sb16dsp_configure(struct snd_sb * chip)
 758{
 759        unsigned long flags;
 760        unsigned char irqreg = 0, dmareg = 0, mpureg;
 761        unsigned char realirq, realdma, realmpureg;
 762        /* note: mpu register should be present only on SB16 Vibra soundcards */
 763
 764        // printk(KERN_DEBUG "codec->irq=%i, codec->dma8=%i, codec->dma16=%i\n", chip->irq, chip->dma8, chip->dma16);
 765        spin_lock_irqsave(&chip->mixer_lock, flags);
 766        mpureg = snd_sbmixer_read(chip, SB_DSP4_MPUSETUP) & ~0x06;
 767        spin_unlock_irqrestore(&chip->mixer_lock, flags);
 768        switch (chip->irq) {
 769        case 2:
 770        case 9:
 771                irqreg |= SB_IRQSETUP_IRQ9;
 772                break;
 773        case 5:
 774                irqreg |= SB_IRQSETUP_IRQ5;
 775                break;
 776        case 7:
 777                irqreg |= SB_IRQSETUP_IRQ7;
 778                break;
 779        case 10:
 780                irqreg |= SB_IRQSETUP_IRQ10;
 781                break;
 782        default:
 783                return -EINVAL;
 784        }
 785        if (chip->dma8 >= 0) {
 786                switch (chip->dma8) {
 787                case 0:
 788                        dmareg |= SB_DMASETUP_DMA0;
 789                        break;
 790                case 1:
 791                        dmareg |= SB_DMASETUP_DMA1;
 792                        break;
 793                case 3:
 794                        dmareg |= SB_DMASETUP_DMA3;
 795                        break;
 796                default:
 797                        return -EINVAL;
 798                }
 799        }
 800        if (chip->dma16 >= 0 && chip->dma16 != chip->dma8) {
 801                switch (chip->dma16) {
 802                case 5:
 803                        dmareg |= SB_DMASETUP_DMA5;
 804                        break;
 805                case 6:
 806                        dmareg |= SB_DMASETUP_DMA6;
 807                        break;
 808                case 7:
 809                        dmareg |= SB_DMASETUP_DMA7;
 810                        break;
 811                default:
 812                        return -EINVAL;
 813                }
 814        }
 815        switch (chip->mpu_port) {
 816        case 0x300:
 817                mpureg |= 0x04;
 818                break;
 819        case 0x330:
 820                mpureg |= 0x00;
 821                break;
 822        default:
 823                mpureg |= 0x02; /* disable MPU */
 824        }
 825        spin_lock_irqsave(&chip->mixer_lock, flags);
 826
 827        snd_sbmixer_write(chip, SB_DSP4_IRQSETUP, irqreg);
 828        realirq = snd_sbmixer_read(chip, SB_DSP4_IRQSETUP);
 829
 830        snd_sbmixer_write(chip, SB_DSP4_DMASETUP, dmareg);
 831        realdma = snd_sbmixer_read(chip, SB_DSP4_DMASETUP);
 832
 833        snd_sbmixer_write(chip, SB_DSP4_MPUSETUP, mpureg);
 834        realmpureg = snd_sbmixer_read(chip, SB_DSP4_MPUSETUP);
 835
 836        spin_unlock_irqrestore(&chip->mixer_lock, flags);
 837        if ((~realirq) & irqreg || (~realdma) & dmareg) {
 838                snd_printk(KERN_ERR "SB16 [0x%lx]: unable to set DMA & IRQ (PnP device?)\n", chip->port);
 839                snd_printk(KERN_ERR "SB16 [0x%lx]: wanted: irqreg=0x%x, dmareg=0x%x, mpureg = 0x%x\n", chip->port, realirq, realdma, realmpureg);
 840                snd_printk(KERN_ERR "SB16 [0x%lx]:    got: irqreg=0x%x, dmareg=0x%x, mpureg = 0x%x\n", chip->port, irqreg, dmareg, mpureg);
 841                return -ENODEV;
 842        }
 843        return 0;
 844}
 845
 846static struct snd_pcm_ops snd_sb16_playback_ops = {
 847        .open =         snd_sb16_playback_open,
 848        .close =        snd_sb16_playback_close,
 849        .ioctl =        snd_pcm_lib_ioctl,
 850        .hw_params =    snd_sb16_hw_params,
 851        .hw_free =      snd_sb16_hw_free,
 852        .prepare =      snd_sb16_playback_prepare,
 853        .trigger =      snd_sb16_playback_trigger,
 854        .pointer =      snd_sb16_playback_pointer,
 855};
 856
 857static struct snd_pcm_ops snd_sb16_capture_ops = {
 858        .open =         snd_sb16_capture_open,
 859        .close =        snd_sb16_capture_close,
 860        .ioctl =        snd_pcm_lib_ioctl,
 861        .hw_params =    snd_sb16_hw_params,
 862        .hw_free =      snd_sb16_hw_free,
 863        .prepare =      snd_sb16_capture_prepare,
 864        .trigger =      snd_sb16_capture_trigger,
 865        .pointer =      snd_sb16_capture_pointer,
 866};
 867
 868int snd_sb16dsp_pcm(struct snd_sb * chip, int device, struct snd_pcm ** rpcm)
 869{
 870        struct snd_card *card = chip->card;
 871        struct snd_pcm *pcm;
 872        int err;
 873
 874        if (rpcm)
 875                *rpcm = NULL;
 876        if ((err = snd_pcm_new(card, "SB16 DSP", device, 1, 1, &pcm)) < 0)
 877                return err;
 878        sprintf(pcm->name, "DSP v%i.%i", chip->version >> 8, chip->version & 0xff);
 879        pcm->info_flags = SNDRV_PCM_INFO_JOINT_DUPLEX;
 880        pcm->private_data = chip;
 881
 882        snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_sb16_playback_ops);
 883        snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_sb16_capture_ops);
 884
 885        if (chip->dma16 >= 0 && chip->dma8 != chip->dma16)
 886                snd_ctl_add(card, snd_ctl_new1(&snd_sb16_dma_control, chip));
 887        else
 888                pcm->info_flags = SNDRV_PCM_INFO_HALF_DUPLEX;
 889
 890        snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV,
 891                                              snd_dma_isa_data(),
 892                                              64*1024, 128*1024);
 893
 894        if (rpcm)
 895                *rpcm = pcm;
 896        return 0;
 897}
 898
 899const struct snd_pcm_ops *snd_sb16dsp_get_pcm_ops(int direction)
 900{
 901        return direction == SNDRV_PCM_STREAM_PLAYBACK ?
 902                &snd_sb16_playback_ops : &snd_sb16_capture_ops;
 903}
 904
 905EXPORT_SYMBOL(snd_sb16dsp_pcm);
 906EXPORT_SYMBOL(snd_sb16dsp_get_pcm_ops);
 907EXPORT_SYMBOL(snd_sb16dsp_configure);
 908EXPORT_SYMBOL(snd_sb16dsp_interrupt);
 909
 910/*
 911 *  INIT part
 912 */
 913
 914static int __init alsa_sb16_init(void)
 915{
 916        return 0;
 917}
 918
 919static void __exit alsa_sb16_exit(void)
 920{
 921}
 922
 923module_init(alsa_sb16_init)
 924module_exit(alsa_sb16_exit)
 925