root/drivers/sound/sscape.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. sscape_read
  2. sscape_write
  3. host_open
  4. host_close
  5. host_write
  6. host_read
  7. host_command1
  8. host_command2
  9. host_command3
  10. set_mt32
  11. set_control
  12. get_board_type
  13. sscapeintr
  14. do_dma
  15. verify_mpu
  16. sscape_coproc_open
  17. sscape_coproc_close
  18. sscape_coproc_reset
  19. sscape_download_boot
  20. download_boot_block
  21. sscape_coproc_ioctl
  22. sscape_audio_open
  23. sscape_audio_close
  24. set_speed
  25. set_channels
  26. set_format
  27. sscape_audio_ioctl
  28. sscape_audio_output_block
  29. sscape_audio_start_input
  30. sscape_audio_prepare_for_input
  31. sscape_audio_prepare_for_output
  32. sscape_audio_halt
  33. sscape_audio_reset
  34. attach_sscape
  35. probe_sscape
  36. probe_ss_ms_sound
  37. attach_ss_ms_sound
  38. unload_sscape
  39. unload_ss_ms_sound

   1 /*
   2  * sound/sscape.c
   3  *
   4  * Low level driver for Ensoniq Soundscape
   5  */
   6 /*
   7  * Copyright by Hannu Savolainen 1993-1996
   8  *
   9  * Redistribution and use in source and binary forms, with or without
  10  * modification, are permitted provided that the following conditions are
  11  * met: 1. Redistributions of source code must retain the above copyright
  12  * notice, this list of conditions and the following disclaimer. 2.
  13  * Redistributions in binary form must reproduce the above copyright notice,
  14  * this list of conditions and the following disclaimer in the documentation
  15  * and/or other materials provided with the distribution.
  16  *
  17  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY
  18  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  19  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  20  * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR
  21  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  22  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
  23  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  24  * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  25  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  26  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  27  * SUCH DAMAGE.
  28  */
  29 #include <linux/config.h>
  30 
  31 
  32 #include "sound_config.h"
  33 
  34 #if defined(CONFIG_SSCAPE)
  35 
  36 #include "coproc.h"
  37 
  38 /*
  39  *    I/O ports
  40  */
  41 #define MIDI_DATA        0
  42 #define MIDI_CTRL        1
  43 #define HOST_CTRL        2
  44 #define TX_READY                0x02
  45 #define RX_READY                0x01
  46 #define HOST_DATA        3
  47 #define ODIE_ADDR        4
  48 #define ODIE_DATA        5
  49 
  50 /*
  51  *    Indirect registers
  52  */
  53 #define GA_INTSTAT_REG   0
  54 #define GA_INTENA_REG    1
  55 #define GA_DMAA_REG      2
  56 #define GA_DMAB_REG      3
  57 #define GA_INTCFG_REG    4
  58 #define GA_DMACFG_REG    5
  59 #define GA_CDCFG_REG     6
  60 #define GA_SMCFGA_REG    7
  61 #define GA_SMCFGB_REG    8
  62 #define GA_HMCTL_REG     9
  63 
  64 /*
  65  * DMA channel identifiers (A and B)
  66  */
  67 #define SSCAPE_DMA_A            0
  68 #define SSCAPE_DMA_B            1
  69 
  70 #define PORT(name)      (devc->base+name)
  71 
  72 /*
  73  * Host commands recognized by the OBP microcode
  74  */
  75 #define CMD_GEN_HOST_ACK        0x80
  76 #define CMD_GEN_MPU_ACK         0x81
  77 #define CMD_GET_BOARD_TYPE      0x82
  78 #define CMD_SET_CONTROL         0x88
  79 #define CMD_GET_CONTROL         0x89
  80 #define         CTL_MASTER_VOL          0
  81 #define         CTL_MIC_MODE            2
  82 #define         CTL_SYNTH_VOL           4
  83 #define         CTL_WAVE_VOL            7
  84 #define CMD_SET_MT32            0x96
  85 #define CMD_GET_MT32            0x97
  86 #define CMD_SET_EXTMIDI         0x9b
  87 #define CMD_GET_EXTMIDI         0x9c
  88 
  89 #define CMD_ACK                 0x80
  90 
  91 typedef struct sscape_info
  92   {
  93     int             base, irq, dma;
  94     int             ok;         /* Properly detected */
  95     int             failed;
  96     int             dma_allocated;
  97     int             my_audiodev;
  98     int             opened;
  99     int            *osp;
 100   }
 101 
 102 sscape_info;
 103 static struct sscape_info dev_info =
 104 {0};
 105 static struct sscape_info *devc = &dev_info;
 106 
 107 static wait_handle *sscape_sleeper = NULL;
 108 static volatile struct snd_wait sscape_sleep_flag =
 109 {0};
 110 
 111 /* Some older cards have assigned interrupt bits differently than new ones */
 112 static char     valid_interrupts_old[] =
 113 {9, 7, 5, 15};
 114 
 115 static char     valid_interrupts_new[] =
 116 {9, 5, 7, 10};
 117 
 118 static char    *valid_interrupts = valid_interrupts_new;
 119 
 120 #ifdef REVEAL_SPEA
 121 static char     old_hardware = 1;
 122 
 123 #else
 124 static char     old_hardware = 0;
 125 
 126 #endif
 127 
 128 static unsigned char
 129 sscape_read (struct sscape_info *devc, int reg)
     /* [previous][next][first][last][top][bottom][index][help] */
 130 {
 131   unsigned long   flags;
 132   unsigned char   val;
 133 
 134   save_flags (flags);
 135   cli ();
 136   outb (reg, PORT (ODIE_ADDR));
 137   val = inb (PORT (ODIE_DATA));
 138   restore_flags (flags);
 139   return val;
 140 }
 141 
 142 static void
 143 sscape_write (struct sscape_info *devc, int reg, int data)
     /* [previous][next][first][last][top][bottom][index][help] */
 144 {
 145   unsigned long   flags;
 146 
 147   save_flags (flags);
 148   cli ();
 149   outb (reg, PORT (ODIE_ADDR));
 150   outb (data, PORT (ODIE_DATA));
 151   restore_flags (flags);
 152 }
 153 
 154 static void
 155 host_open (struct sscape_info *devc)
     /* [previous][next][first][last][top][bottom][index][help] */
 156 {
 157   outb (0x00, PORT (HOST_CTRL));        /* Put the board to the host mode */
 158 }
 159 
 160 static void
 161 host_close (struct sscape_info *devc)
     /* [previous][next][first][last][top][bottom][index][help] */
 162 {
 163   outb (0x03, PORT (HOST_CTRL));        /* Put the board to the MIDI mode */
 164 }
 165 
 166 static int
 167 host_write (struct sscape_info *devc, unsigned char *data, int count)
     /* [previous][next][first][last][top][bottom][index][help] */
 168 {
 169   unsigned long   flags;
 170   int             i, timeout_val;
 171 
 172   save_flags (flags);
 173   cli ();
 174 
 175   /*
 176      * Send the command and data bytes
 177    */
 178 
 179   for (i = 0; i < count; i++)
 180     {
 181       for (timeout_val = 10000; timeout_val > 0; timeout_val--)
 182         if (inb (PORT (HOST_CTRL)) & TX_READY)
 183           break;
 184 
 185       if (timeout_val <= 0)
 186         {
 187           restore_flags (flags);
 188           return 0;
 189         }
 190 
 191       outb (data[i], PORT (HOST_DATA));
 192     }
 193 
 194 
 195   restore_flags (flags);
 196 
 197   return 1;
 198 }
 199 
 200 static int
 201 host_read (struct sscape_info *devc)
     /* [previous][next][first][last][top][bottom][index][help] */
 202 {
 203   unsigned long   flags;
 204   int             timeout_val;
 205   unsigned char   data;
 206 
 207   save_flags (flags);
 208   cli ();
 209 
 210   /*
 211      * Read a byte
 212    */
 213 
 214   for (timeout_val = 10000; timeout_val > 0; timeout_val--)
 215     if (inb (PORT (HOST_CTRL)) & RX_READY)
 216       break;
 217 
 218   if (timeout_val <= 0)
 219     {
 220       restore_flags (flags);
 221       return -1;
 222     }
 223 
 224   data = inb (PORT (HOST_DATA));
 225 
 226   restore_flags (flags);
 227 
 228   return data;
 229 }
 230 
 231 static int
 232 host_command1 (struct sscape_info *devc, int cmd)
     /* [previous][next][first][last][top][bottom][index][help] */
 233 {
 234   unsigned char   buf[10];
 235 
 236   buf[0] = (unsigned char) (cmd & 0xff);
 237 
 238   return host_write (devc, buf, 1);
 239 }
 240 
 241 static int
 242 host_command2 (struct sscape_info *devc, int cmd, int parm1)
     /* [previous][next][first][last][top][bottom][index][help] */
 243 {
 244   unsigned char   buf[10];
 245 
 246   buf[0] = (unsigned char) (cmd & 0xff);
 247   buf[1] = (unsigned char) (parm1 & 0xff);
 248 
 249   return host_write (devc, buf, 2);
 250 }
 251 
 252 static int
 253 host_command3 (struct sscape_info *devc, int cmd, int parm1, int parm2)
     /* [previous][next][first][last][top][bottom][index][help] */
 254 {
 255   unsigned char   buf[10];
 256 
 257   buf[0] = (unsigned char) (cmd & 0xff);
 258   buf[1] = (unsigned char) (parm1 & 0xff);
 259   buf[2] = (unsigned char) (parm2 & 0xff);
 260 
 261   return host_write (devc, buf, 3);
 262 }
 263 
 264 static void
 265 set_mt32 (struct sscape_info *devc, int value)
     /* [previous][next][first][last][top][bottom][index][help] */
 266 {
 267   host_open (devc);
 268   host_command2 (devc, CMD_SET_MT32,
 269                  value ? 1 : 0);
 270   if (host_read (devc) != CMD_ACK)
 271     {
 272       /* printk ("SNDSCAPE: Setting MT32 mode failed\n"); */
 273     }
 274   host_close (devc);
 275 }
 276 
 277 static void
 278 set_control (struct sscape_info *devc, int ctrl, int value)
     /* [previous][next][first][last][top][bottom][index][help] */
 279 {
 280   host_open (devc);
 281   host_command3 (devc, CMD_SET_CONTROL, ctrl, value);
 282   if (host_read (devc) != CMD_ACK)
 283     {
 284       printk ("SNDSCAPE: Setting control (%d) failed\n", ctrl);
 285     }
 286   host_close (devc);
 287 }
 288 
 289 static int
 290 get_board_type (struct sscape_info *devc)
     /* [previous][next][first][last][top][bottom][index][help] */
 291 {
 292   int             tmp;
 293 
 294   host_open (devc);
 295   if (!host_command1 (devc, CMD_GET_BOARD_TYPE))
 296     tmp = -1;
 297   else
 298     tmp = host_read (devc);
 299   host_close (devc);
 300   return tmp;
 301 }
 302 
 303 void
 304 sscapeintr (int irq, void *dev_id, struct pt_regs *dummy)
     /* [previous][next][first][last][top][bottom][index][help] */
 305 {
 306   unsigned char   bits, tmp;
 307   static int      debug = 0;
 308 
 309   bits = sscape_read (devc, GA_INTSTAT_REG);
 310   if ((sscape_sleep_flag.mode & WK_SLEEP))
 311     {
 312       {
 313         sscape_sleep_flag.mode = WK_WAKEUP;
 314         module_wake_up (&sscape_sleeper);
 315       };
 316     }
 317 
 318   if (bits & 0x02)              /* Host interface interrupt */
 319     {
 320       printk ("SSCAPE: Host interrupt, data=%02x\n", host_read (devc));
 321     }
 322 
 323 #if (defined(CONFIG_MPU401) || defined(CONFIG_MPU_EMU)) && defined(CONFIG_MIDI)
 324   if (bits & 0x01)
 325     {
 326       mpuintr (irq, NULL, NULL);
 327       if (debug++ > 10)         /* Temporary debugging hack */
 328         {
 329           sscape_write (devc, GA_INTENA_REG, 0x00);     /* Disable all interrupts */
 330         }
 331     }
 332 #endif
 333 
 334   /*
 335      * Acknowledge interrupts (toggle the interrupt bits)
 336    */
 337 
 338   tmp = sscape_read (devc, GA_INTENA_REG);
 339   sscape_write (devc, GA_INTENA_REG, (~bits & 0x0e) | (tmp & 0xf1));
 340 
 341 }
 342 
 343 
 344 static void
 345 do_dma (struct sscape_info *devc, int dma_chan, unsigned long buf, int blk_size, int mode)
     /* [previous][next][first][last][top][bottom][index][help] */
 346 {
 347   unsigned char   temp;
 348 
 349   if (dma_chan != SSCAPE_DMA_A)
 350     {
 351       printk ("SSCAPE: Tried to use DMA channel  != A. Why?\n");
 352       return;
 353     }
 354 
 355   DMAbuf_start_dma (devc->my_audiodev,
 356                     buf,
 357                     blk_size, mode);
 358 
 359   temp = devc->dma << 4;        /* Setup DMA channel select bits */
 360   if (devc->dma <= 3)
 361     temp |= 0x80;               /* 8 bit DMA channel */
 362 
 363   temp |= 1;                    /* Trigger DMA */
 364   sscape_write (devc, GA_DMAA_REG, temp);
 365   temp &= 0xfe;                 /* Clear DMA trigger */
 366   sscape_write (devc, GA_DMAA_REG, temp);
 367 }
 368 
 369 static int
 370 verify_mpu (struct sscape_info *devc)
     /* [previous][next][first][last][top][bottom][index][help] */
 371 {
 372   /*
 373      * The SoundScape board could be in three modes (MPU, 8250 and host).
 374      * If the card is not in the MPU mode, enabling the MPU driver will
 375      * cause infinite loop (the driver believes that there is always some
 376      * received data in the buffer.
 377      *
 378      * Detect this by looking if there are more than 10 received MIDI bytes
 379      * (0x00) in the buffer.
 380    */
 381 
 382   int             i;
 383 
 384   for (i = 0; i < 10; i++)
 385     {
 386       if (inb (devc->base + HOST_CTRL) & 0x80)
 387         return 1;
 388 
 389       if (inb (devc->base) != 0x00)
 390         return 1;
 391     }
 392 
 393   printk ("SoundScape: The device is not in the MPU-401 mode\n");
 394   return 0;
 395 }
 396 
 397 static int
 398 sscape_coproc_open (void *dev_info, int sub_device)
     /* [previous][next][first][last][top][bottom][index][help] */
 399 {
 400   if (sub_device == COPR_MIDI)
 401     {
 402       set_mt32 (devc, 0);
 403       if (!verify_mpu (devc))
 404         return -EIO;
 405     }
 406 
 407   sscape_sleep_flag.mode = WK_NONE;
 408   return 0;
 409 }
 410 
 411 static void
 412 sscape_coproc_close (void *dev_info, int sub_device)
     /* [previous][next][first][last][top][bottom][index][help] */
 413 {
 414   struct sscape_info *devc = dev_info;
 415   unsigned long   flags;
 416 
 417   save_flags (flags);
 418   cli ();
 419   if (devc->dma_allocated)
 420     {
 421       sscape_write (devc, GA_DMAA_REG, 0x20);   /* DMA channel disabled */
 422 #ifdef CONFIG_NATIVE_PCM
 423 #endif
 424       devc->dma_allocated = 0;
 425     }
 426   sscape_sleep_flag.mode = WK_NONE;
 427   restore_flags (flags);
 428 
 429   return;
 430 }
 431 
 432 static void
 433 sscape_coproc_reset (void *dev_info)
     /* [previous][next][first][last][top][bottom][index][help] */
 434 {
 435 }
 436 
 437 static int
 438 sscape_download_boot (struct sscape_info *devc, unsigned char *block, int size, int flag)
     /* [previous][next][first][last][top][bottom][index][help] */
 439 {
 440   unsigned long   flags;
 441   unsigned char   temp;
 442   int             done, timeout_val;
 443   static int      already_done = 0;
 444 
 445   if (flag & CPF_FIRST)
 446     {
 447       /*
 448          * First block. Have to allocate DMA and to reset the board
 449          * before continuing.
 450        */
 451 
 452       if (already_done)
 453         {
 454           printk ("Can't run 'ssinit' twice\n");
 455           return 0;
 456         }
 457       already_done = 1;
 458 
 459       save_flags (flags);
 460       cli ();
 461       if (devc->dma_allocated == 0)
 462         {
 463 #ifdef CONFIG_NATIVE_PCM
 464 #endif
 465 
 466           devc->dma_allocated = 1;
 467         }
 468       restore_flags (flags);
 469 
 470       sscape_write (devc, GA_HMCTL_REG,
 471                     (temp = sscape_read (devc, GA_HMCTL_REG)) & 0x3f);  /*Reset */
 472 
 473       for (timeout_val = 10000; timeout_val > 0; timeout_val--)
 474         sscape_read (devc, GA_HMCTL_REG);       /* Delay */
 475 
 476       /* Take board out of reset */
 477       sscape_write (devc, GA_HMCTL_REG,
 478                     (temp = sscape_read (devc, GA_HMCTL_REG)) | 0x80);
 479     }
 480 
 481   /*
 482      * Transfer one code block using DMA
 483    */
 484   memcpy (audio_devs[devc->my_audiodev]->dmap_out->raw_buf, block, size);
 485 
 486   save_flags (flags);
 487   cli ();
 488 /******** INTERRUPTS DISABLED NOW ********/
 489   do_dma (devc, SSCAPE_DMA_A,
 490           audio_devs[devc->my_audiodev]->dmap_out->raw_buf_phys,
 491           size, DMA_MODE_WRITE);
 492 
 493   /*
 494    * Wait until transfer completes.
 495    */
 496   sscape_sleep_flag.mode = WK_NONE;
 497   done = 0;
 498   timeout_val = 100;
 499   while (!done && timeout_val-- > 0)
 500     {
 501       int             resid;
 502 
 503 
 504       {
 505         unsigned long   tl;
 506 
 507         if (1)
 508           current_set_timeout (tl = jiffies + (1));
 509         else
 510           tl = (unsigned long) -1;
 511         sscape_sleep_flag.mode = WK_SLEEP;
 512         module_interruptible_sleep_on (&sscape_sleeper);
 513         if (!(sscape_sleep_flag.mode & WK_WAKEUP))
 514           {
 515             if (jiffies >= tl)
 516               sscape_sleep_flag.mode |= WK_TIMEOUT;
 517           }
 518         sscape_sleep_flag.mode &= ~WK_SLEEP;
 519       };
 520       clear_dma_ff (devc->dma);
 521       if ((resid = get_dma_residue (devc->dma)) == 0)
 522         done = 1;
 523     }
 524 
 525   restore_flags (flags);
 526   if (!done)
 527     return 0;
 528 
 529   if (flag & CPF_LAST)
 530     {
 531       /*
 532          * Take the board out of reset
 533        */
 534       outb (0x00, PORT (HOST_CTRL));
 535       outb (0x00, PORT (MIDI_CTRL));
 536 
 537       temp = sscape_read (devc, GA_HMCTL_REG);
 538       temp |= 0x40;
 539       sscape_write (devc, GA_HMCTL_REG, temp);  /* Kickstart the board */
 540 
 541       /*
 542          * Wait until the ODB wakes up
 543        */
 544 
 545       save_flags (flags);
 546       cli ();
 547       done = 0;
 548       timeout_val = 5 * HZ;
 549       while (!done && timeout_val-- > 0)
 550         {
 551 
 552           {
 553             unsigned long   tl;
 554 
 555             if (1)
 556               current_set_timeout (tl = jiffies + (1));
 557             else
 558               tl = (unsigned long) -1;
 559             sscape_sleep_flag.mode = WK_SLEEP;
 560             module_interruptible_sleep_on (&sscape_sleeper);
 561             if (!(sscape_sleep_flag.mode & WK_WAKEUP))
 562               {
 563                 if (jiffies >= tl)
 564                   sscape_sleep_flag.mode |= WK_TIMEOUT;
 565               }
 566             sscape_sleep_flag.mode &= ~WK_SLEEP;
 567           };
 568           if (inb (PORT (HOST_DATA)) == 0xff)   /* OBP startup acknowledge */
 569             done = 1;
 570         }
 571       restore_flags (flags);
 572       if (!done)
 573         {
 574           printk ("SoundScape: The OBP didn't respond after code download\n");
 575           return 0;
 576         }
 577 
 578       save_flags (flags);
 579       cli ();
 580       done = 0;
 581       timeout_val = 5 * HZ;
 582       while (!done && timeout_val-- > 0)
 583         {
 584 
 585           {
 586             unsigned long   tl;
 587 
 588             if (1)
 589               current_set_timeout (tl = jiffies + (1));
 590             else
 591               tl = (unsigned long) -1;
 592             sscape_sleep_flag.mode = WK_SLEEP;
 593             module_interruptible_sleep_on (&sscape_sleeper);
 594             if (!(sscape_sleep_flag.mode & WK_WAKEUP))
 595               {
 596                 if (jiffies >= tl)
 597                   sscape_sleep_flag.mode |= WK_TIMEOUT;
 598               }
 599             sscape_sleep_flag.mode &= ~WK_SLEEP;
 600           };
 601           if (inb (PORT (HOST_DATA)) == 0xfe)   /* Host startup acknowledge */
 602             done = 1;
 603         }
 604       restore_flags (flags);
 605       if (!done)
 606         {
 607           printk ("SoundScape: OBP Initialization failed.\n");
 608           return 0;
 609         }
 610 
 611       printk ("SoundScape board of type %d initialized OK\n",
 612               get_board_type (devc));
 613 
 614       set_control (devc, CTL_MASTER_VOL, 100);
 615       set_control (devc, CTL_SYNTH_VOL, 100);
 616 
 617 #ifdef SSCAPE_DEBUG3
 618       /*
 619          * Temporary debugging aid. Print contents of the registers after
 620          * downloading the code.
 621        */
 622       {
 623         int             i;
 624 
 625         for (i = 0; i < 13; i++)
 626           printk ("I%d = %02x (new value)\n", i, sscape_read (devc, i));
 627       }
 628 #endif
 629 
 630     }
 631 
 632   return 1;
 633 }
 634 
 635 static int
 636 download_boot_block (void *dev_info, copr_buffer * buf)
     /* [previous][next][first][last][top][bottom][index][help] */
 637 {
 638   if (buf->len <= 0 || buf->len > sizeof (buf->data))
 639     return -EINVAL;
 640 
 641   if (!sscape_download_boot (devc, buf->data, buf->len, buf->flags))
 642     {
 643       printk ("SSCAPE: Unable to load microcode block to the OBP.\n");
 644       return -EIO;
 645     }
 646 
 647   return 0;
 648 }
 649 
 650 static int
 651 sscape_coproc_ioctl (void *dev_info, unsigned int cmd, caddr_t arg, int local)
     /* [previous][next][first][last][top][bottom][index][help] */
 652 {
 653 
 654   switch (cmd)
 655     {
 656     case SNDCTL_COPR_RESET:
 657       sscape_coproc_reset (dev_info);
 658       return 0;
 659       break;
 660 
 661     case SNDCTL_COPR_LOAD:
 662       {
 663         copr_buffer    *buf;
 664         int             err;
 665 
 666         buf = (copr_buffer *) kmalloc (sizeof (copr_buffer), GFP_KERNEL);
 667         if (buf == NULL)
 668           return -ENOSPC;
 669         memcpy_fromfs ((char *) buf, &(((char *) arg)[0]), sizeof (*buf));
 670         err = download_boot_block (dev_info, buf);
 671         kfree (buf);
 672         return err;
 673       }
 674       break;
 675 
 676     default:
 677       return -EINVAL;
 678     }
 679 
 680 }
 681 
 682 static coproc_operations sscape_coproc_operations =
 683 {
 684   "SoundScape M68K",
 685   sscape_coproc_open,
 686   sscape_coproc_close,
 687   sscape_coproc_ioctl,
 688   sscape_coproc_reset,
 689   &dev_info
 690 };
 691 
 692 static int
 693 sscape_audio_open (int dev, int mode)
     /* [previous][next][first][last][top][bottom][index][help] */
 694 {
 695   unsigned long   flags;
 696   sscape_info    *devc = (sscape_info *) audio_devs[dev]->devc;
 697 
 698   save_flags (flags);
 699   cli ();
 700   if (devc->opened)
 701     {
 702       restore_flags (flags);
 703       return -EBUSY;
 704     }
 705   devc->opened = 1;
 706   restore_flags (flags);
 707 #ifdef SSCAPE_DEBUG4
 708   /*
 709      * Temporary debugging aid. Print contents of the registers
 710      * when the device is opened.
 711    */
 712   {
 713     int             i;
 714 
 715     for (i = 0; i < 13; i++)
 716       printk ("I%d = %02x\n", i, sscape_read (devc, i));
 717   }
 718 #endif
 719 
 720   return 0;
 721 }
 722 
 723 static void
 724 sscape_audio_close (int dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 725 {
 726   unsigned long   flags;
 727   sscape_info    *devc = (sscape_info *) audio_devs[dev]->devc;
 728 
 729   DEB (printk ("sscape_audio_close(void)\n"));
 730 
 731   save_flags (flags);
 732   cli ();
 733 
 734   devc->opened = 0;
 735 
 736   restore_flags (flags);
 737 }
 738 
 739 static int
 740 set_speed (sscape_info * devc, int arg)
     /* [previous][next][first][last][top][bottom][index][help] */
 741 {
 742   return 8000;
 743 }
 744 
 745 static int
 746 set_channels (sscape_info * devc, int arg)
     /* [previous][next][first][last][top][bottom][index][help] */
 747 {
 748   return 1;
 749 }
 750 
 751 static int
 752 set_format (sscape_info * devc, int arg)
     /* [previous][next][first][last][top][bottom][index][help] */
 753 {
 754   return AFMT_U8;
 755 }
 756 
 757 static int
 758 sscape_audio_ioctl (int dev, unsigned int cmd, caddr_t arg, int local)
     /* [previous][next][first][last][top][bottom][index][help] */
 759 {
 760   sscape_info    *devc = (sscape_info *) audio_devs[dev]->devc;
 761 
 762   switch (cmd)
 763     {
 764     case SOUND_PCM_WRITE_RATE:
 765       if (local)
 766         return set_speed (devc, (int) arg);
 767       return snd_ioctl_return ((int *) arg, set_speed (devc, get_fs_long ((long *) arg)));
 768 
 769     case SOUND_PCM_READ_RATE:
 770       if (local)
 771         return 8000;
 772       return snd_ioctl_return ((int *) arg, 8000);
 773 
 774     case SNDCTL_DSP_STEREO:
 775       if (local)
 776         return set_channels (devc, (int) arg + 1) - 1;
 777       return snd_ioctl_return ((int *) arg, set_channels (devc, get_fs_long ((long *) arg) + 1) - 1);
 778 
 779     case SOUND_PCM_WRITE_CHANNELS:
 780       if (local)
 781         return set_channels (devc, (int) arg);
 782       return snd_ioctl_return ((int *) arg, set_channels (devc, get_fs_long ((long *) arg)));
 783 
 784     case SOUND_PCM_READ_CHANNELS:
 785       if (local)
 786         return 1;
 787       return snd_ioctl_return ((int *) arg, 1);
 788 
 789     case SNDCTL_DSP_SAMPLESIZE:
 790       if (local)
 791         return set_format (devc, (int) arg);
 792       return snd_ioctl_return ((int *) arg, set_format (devc, get_fs_long ((long *) arg)));
 793 
 794     case SOUND_PCM_READ_BITS:
 795       if (local)
 796         return 8;
 797       return snd_ioctl_return ((int *) arg, 8);
 798 
 799     default:;
 800     }
 801   return -EINVAL;
 802 }
 803 
 804 static void
 805 sscape_audio_output_block (int dev, unsigned long buf, int count, int intrflag, int dma_restart)
     /* [previous][next][first][last][top][bottom][index][help] */
 806 {
 807 }
 808 
 809 static void
 810 sscape_audio_start_input (int dev, unsigned long buf, int count, int intrflag, int dma_restart)
     /* [previous][next][first][last][top][bottom][index][help] */
 811 {
 812 }
 813 
 814 static int
 815 sscape_audio_prepare_for_input (int dev, int bsize, int bcount)
     /* [previous][next][first][last][top][bottom][index][help] */
 816 {
 817   return 0;
 818 }
 819 
 820 static int
 821 sscape_audio_prepare_for_output (int dev, int bsize, int bcount)
     /* [previous][next][first][last][top][bottom][index][help] */
 822 {
 823   return 0;
 824 }
 825 
 826 static void
 827 sscape_audio_halt (int dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 828 {
 829 }
 830 
 831 static void
 832 sscape_audio_reset (int dev)
     /* [previous][next][first][last][top][bottom][index][help] */
 833 {
 834   sscape_audio_halt (dev);
 835 }
 836 
 837 static struct audio_operations sscape_audio_operations =
 838 {
 839   "Not functional",
 840   0,
 841   AFMT_U8 | AFMT_S16_LE,
 842   NULL,
 843   sscape_audio_open,
 844   sscape_audio_close,
 845   sscape_audio_output_block,
 846   sscape_audio_start_input,
 847   sscape_audio_ioctl,
 848   sscape_audio_prepare_for_input,
 849   sscape_audio_prepare_for_output,
 850   sscape_audio_reset,
 851   sscape_audio_halt,
 852   NULL,
 853   NULL
 854 };
 855 
 856 static int      sscape_detected = 0;
 857 
 858 long
 859 attach_sscape (long mem_start, struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
 860 {
 861   int             my_dev;
 862 
 863 #ifndef SSCAPE_REGS
 864   /*
 865      * Config register values for Spea/V7 Media FX and Ensoniq S-2000.
 866      * These values are card
 867      * dependent. If you have another SoundScape based card, you have to
 868      * find the correct values. Do the following:
 869      *  - Compile this driver with SSCAPE_DEBUG1 defined.
 870      *  - Shut down and power off your machine.
 871      *  - Boot with DOS so that the SSINIT.EXE program is run.
 872      *  - Warm boot to {Linux|SYSV|BSD} and write down the lines displayed
 873      *    when detecting the SoundScape.
 874      *  - Modify the following list to use the values printed during boot.
 875      *    Undefine the SSCAPE_DEBUG1
 876    */
 877 #define SSCAPE_REGS { \
 878 /* I0 */        0x00, \
 879                 0xf0, /* Note! Ignored. Set always to 0xf0 */ \
 880                 0x20, /* Note! Ignored. Set always to 0x20 */ \
 881                 0x20, /* Note! Ignored. Set always to 0x20 */ \
 882                 0xf5, /* Ignored */ \
 883                 0x10, \
 884                 0x00, \
 885                 0x2e, /* I7 MEM config A. Likely to vary between models */ \
 886                 0x00, /* I8 MEM config B. Likely to vary between models */ \
 887 /* I9 */        0x40 /* Ignored */ \
 888         }
 889 #endif
 890 
 891   unsigned long   flags;
 892   static unsigned char regs[10] = SSCAPE_REGS;
 893 
 894   int             i, irq_bits = 0xff;
 895 
 896   if (sscape_detected != hw_config->io_base)
 897     return mem_start;
 898 
 899   if (old_hardware)
 900     {
 901       valid_interrupts = valid_interrupts_old;
 902       conf_printf ("Ensoniq Soundscape (old)", hw_config);
 903     }
 904   else
 905     conf_printf ("Ensoniq Soundscape", hw_config);
 906 
 907   for (i = 0; i < sizeof (valid_interrupts); i++)
 908     if (hw_config->irq == valid_interrupts[i])
 909       {
 910         irq_bits = i;
 911         break;
 912       }
 913 
 914   if (hw_config->irq > 15 || (regs[4] = irq_bits == 0xff))
 915     {
 916       printk ("Invalid IRQ%d\n", hw_config->irq);
 917       return mem_start;
 918     }
 919 
 920   save_flags (flags);
 921   cli ();
 922 
 923   for (i = 1; i < 10; i++)
 924     switch (i)
 925       {
 926       case 1:                   /* Host interrupt enable */
 927         sscape_write (devc, i, 0xf0);   /* All interrupts enabled */
 928         break;
 929 
 930       case 2:                   /* DMA A status/trigger register */
 931       case 3:                   /* DMA B status/trigger register */
 932         sscape_write (devc, i, 0x20);   /* DMA channel disabled */
 933         break;
 934 
 935       case 4:                   /* Host interrupt config reg */
 936         sscape_write (devc, i, 0xf0 | (irq_bits << 2) | irq_bits);
 937         break;
 938 
 939       case 5:                   /* Don't destroy CD-ROM DMA config bits (0xc0) */
 940         sscape_write (devc, i, (regs[i] & 0x3f) |
 941                       (sscape_read (devc, i) & 0xc0));
 942         break;
 943 
 944       case 6:                   /* CD-ROM config. Don't touch. */
 945         break;
 946 
 947       case 9:                   /* Master control reg. Don't modify CR-ROM bits. Disable SB emul */
 948         sscape_write (devc, i,
 949                       (sscape_read (devc, i) & 0xf0) | 0x08);
 950         break;
 951 
 952       default:
 953         sscape_write (devc, i, regs[i]);
 954       }
 955 
 956   restore_flags (flags);
 957 
 958 #ifdef SSCAPE_DEBUG2
 959   /*
 960      * Temporary debugging aid. Print contents of the registers after
 961      * changing them.
 962    */
 963   {
 964     int             i;
 965 
 966     for (i = 0; i < 13; i++)
 967       printk ("I%d = %02x (new value)\n", i, sscape_read (devc, i));
 968   }
 969 #endif
 970 
 971 #if defined(CONFIG_MIDI) && defined(CONFIG_MPU_EMU)
 972   if (probe_mpu401 (hw_config))
 973     hw_config->always_detect = 1;
 974   {
 975     int             prev_devs;
 976 
 977     prev_devs = num_midis;
 978     mem_start = attach_mpu401 (mem_start, hw_config);
 979 
 980     if (num_midis == (prev_devs + 1))   /* The MPU driver installed itself */
 981       midi_devs[prev_devs]->coproc = &sscape_coproc_operations;
 982   }
 983 #endif
 984 
 985 #ifndef EXCLUDE_NATIVE_PCM
 986   /* Not supported yet */
 987 
 988 #ifdef CONFIG_AUDIO
 989   if (num_audiodevs < MAX_AUDIO_DEV)
 990     {
 991       audio_devs[my_dev = num_audiodevs++] = &sscape_audio_operations;
 992       audio_devs[my_dev]->dmachan1 = hw_config->dma;
 993       audio_devs[my_dev]->buffsize = DSP_BUFFSIZE;
 994       audio_devs[my_dev]->devc = devc;
 995       devc->my_audiodev = my_dev;
 996       devc->opened = 0;
 997       audio_devs[my_dev]->coproc = &sscape_coproc_operations;
 998       if (snd_set_irq_handler (hw_config->irq, sscapeintr, "SoundScape", devc->osp) < 0)
 999         printk ("Error: Can't allocate IRQ for SoundScape\n");
1000 
1001       sscape_write (devc, GA_INTENA_REG, 0x80);         /* Master IRQ enable */
1002     }
1003   else
1004     printk ("SoundScape: More than enough audio devices detected\n");
1005 #endif
1006 #endif
1007   devc->ok = 1;
1008   devc->failed = 0;
1009   return mem_start;
1010 }
1011 
1012 int
1013 probe_sscape (struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
1014 {
1015   unsigned char   save;
1016 
1017   devc->failed = 1;
1018   devc->base = hw_config->io_base;
1019   devc->irq = hw_config->irq;
1020   devc->dma = hw_config->dma;
1021   devc->osp = hw_config->osp;
1022 
1023   if (sscape_detected != 0 && sscape_detected != hw_config->io_base)
1024     return 0;
1025 
1026   /*
1027      * First check that the address register of "ODIE" is
1028      * there and that it has exactly 4 writeable bits.
1029      * First 4 bits
1030    */
1031   if ((save = inb (PORT (ODIE_ADDR))) & 0xf0)
1032     return 0;
1033 
1034   outb (0x00, PORT (ODIE_ADDR));
1035   if (inb (PORT (ODIE_ADDR)) != 0x00)
1036     return 0;
1037 
1038   outb (0xff, PORT (ODIE_ADDR));
1039   if (inb (PORT (ODIE_ADDR)) != 0x0f)
1040     return 0;
1041 
1042   outb (save, PORT (ODIE_ADDR));
1043 
1044   /*
1045      * Now verify that some indirect registers return zero on some bits.
1046      * This may break the driver with some future revisions of "ODIE" but...
1047    */
1048 
1049   if (sscape_read (devc, 0) & 0x0c)
1050     return 0;
1051 
1052   if (sscape_read (devc, 1) & 0x0f)
1053     return 0;
1054 
1055   if (sscape_read (devc, 5) & 0x0f)
1056     return 0;
1057 
1058 #ifdef SSCAPE_DEBUG1
1059   /*
1060      * Temporary debugging aid. Print contents of the registers before
1061      * changing them.
1062    */
1063   {
1064     int             i;
1065 
1066     for (i = 0; i < 13; i++)
1067       printk ("I%d = %02x (old value)\n", i, sscape_read (devc, i));
1068   }
1069 #endif
1070 
1071   if (old_hardware)             /* Check that it's really an old Spea/Reveal card. */
1072     {
1073       unsigned char   tmp;
1074       int             cc;
1075 
1076       if (!((tmp = sscape_read (devc, GA_HMCTL_REG)) & 0xc0))
1077         {
1078           sscape_write (devc, GA_HMCTL_REG, tmp | 0x80);
1079           for (cc = 0; cc < 200000; ++cc)
1080             inb (devc->base + ODIE_ADDR);
1081         }
1082       else
1083         old_hardware = 0;
1084     }
1085 
1086   if (sound_alloc_dma (hw_config->dma, "soundscape"))
1087     {
1088       printk ("sscape.c: Can't allocate DMA channel\n");
1089       return 0;
1090     }
1091 
1092   sscape_detected = hw_config->io_base;
1093 
1094   return 1;
1095 }
1096 
1097 int
1098 probe_ss_ms_sound (struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
1099 {
1100   int             i, irq_bits = 0xff;
1101 
1102   if (devc->failed)
1103     return 0;
1104 
1105   if (devc->ok == 0)
1106     {
1107       printk ("SoundScape: Invalid initialization order.\n");
1108       return 0;
1109     }
1110 
1111   for (i = 0; i < sizeof (valid_interrupts); i++)
1112     if (hw_config->irq == valid_interrupts[i])
1113       {
1114         irq_bits = i;
1115         break;
1116       }
1117   if (hw_config->irq > 15 || irq_bits == 0xff)
1118     {
1119       printk ("SoundScape: Invalid MSS IRQ%d\n", hw_config->irq);
1120       return 0;
1121     }
1122 
1123   return ad1848_detect (hw_config->io_base, NULL, hw_config->osp);
1124 }
1125 
1126 long
1127 attach_ss_ms_sound (long mem_start, struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
1128 {
1129   /*
1130      * This routine configures the SoundScape card for use with the
1131      * Win Sound System driver. The AD1848 codec interface uses the CD-ROM
1132      * config registers of the "ODIE".
1133    */
1134 
1135   int             i, irq_bits = 0xff;
1136 
1137 #ifndef CONFIG_NATIVE_PCM
1138   int             prev_devs = num_audiodevs;
1139 
1140 #endif
1141 
1142   /*
1143      * Setup the DMA polarity.
1144    */
1145   sscape_write (devc, GA_DMACFG_REG, 0x50);
1146 
1147   /*
1148      * Take the gate-array off of the DMA channel.
1149    */
1150   sscape_write (devc, GA_DMAB_REG, 0x20);
1151 
1152   /*
1153      * Init the AD1848 (CD-ROM) config reg.
1154    */
1155 
1156   for (i = 0; i < sizeof (valid_interrupts); i++)
1157     if (hw_config->irq == valid_interrupts[i])
1158       {
1159         irq_bits = i;
1160         break;
1161       }
1162 
1163   sscape_write (devc, GA_CDCFG_REG, 0x89 | (hw_config->dma << 4) |
1164                 (irq_bits << 1));
1165 
1166   if (hw_config->irq == devc->irq)
1167     printk ("SoundScape: Warning! The WSS mode can't share IRQ with MIDI\n");
1168 
1169   ad1848_init ("SoundScape", hw_config->io_base,
1170                hw_config->irq,
1171                hw_config->dma,
1172                hw_config->dma,
1173                0,
1174                devc->osp);
1175 
1176 #ifndef CONFIG_NATIVE_PCM
1177   if (num_audiodevs == (prev_devs + 1))         /* The AD1848 driver installed itself */
1178     audio_devs[prev_devs]->coproc = &sscape_coproc_operations;
1179 #endif
1180 #ifdef SSCAPE_DEBUG5
1181   /*
1182      * Temporary debugging aid. Print contents of the registers
1183      * after the AD1848 device has been initialized.
1184    */
1185   {
1186     int             i;
1187 
1188     for (i = 0; i < 13; i++)
1189       printk ("I%d = %02x\n", i, sscape_read (devc, i));
1190   }
1191 #endif
1192 
1193   return mem_start;
1194 }
1195 
1196 void
1197 unload_sscape (struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
1198 {
1199 #if (defined(CONFIG_MPU401) || defined(CONFIG_MPU_EMU)) && defined(CONFIG_MIDI)
1200   unload_mpu401 (hw_config);
1201 #endif
1202   snd_release_irq (hw_config->irq);
1203   sound_free_dma (hw_config->dma);
1204 }
1205 
1206 void
1207 unload_ss_ms_sound (struct address_info *hw_config)
     /* [previous][next][first][last][top][bottom][index][help] */
1208 {
1209   ad1848_unload (hw_config->io_base,
1210                  hw_config->irq,
1211                  hw_config->dma,
1212                  hw_config->dma,
1213                  0);
1214 }
1215 
1216 #endif

/* [previous][next][first][last][top][bottom][index][help] */