blob: e20051f1be4d7b0efcdc3a88eeb004ae7a963dfd [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
Uwe Zeisbergerf30c2262006-10-03 23:01:26 +02002 * sound/oss/opl3sa2.c
Linus Torvalds1da177e2005-04-16 15:20:36 -07003 *
4 * A low level driver for Yamaha OPL3-SA2 and SA3 cards.
5 * NOTE: All traces of the name OPL3-SAx have now (December 2000) been
6 * removed from the driver code, as an email exchange with Yamaha
7 * provided the information that the YMF-719 is indeed just a
8 * re-badged 715.
9 *
10 * Copyright 1998-2001 Scott Murray <scott@spiteful.org>
11 *
12 * Originally based on the CS4232 driver (in cs4232.c) by Hannu Savolainen
13 * and others. Now incorporates code/ideas from pss.c, also by Hannu
14 * Savolainen. Both of those files are distributed with the following
15 * license:
16 *
17 * "Copyright (C) by Hannu Savolainen 1993-1997
18 *
19 * OSS/Free for Linux is distributed under the GNU GENERAL PUBLIC LICENSE (GPL)
20 * Version 2 (June 1991). See the "COPYING" file distributed with this software
21 * for more info."
22 *
23 * As such, in accordance with the above license, this file, opl3sa2.c, is
24 * distributed under the GNU GENERAL PUBLIC LICENSE (GPL) Version 2 (June 1991).
25 * See the "COPYING" file distributed with this software for more information.
26 *
27 * Change History
28 * --------------
29 * Scott Murray Original driver (Jun 14, 1998)
30 * Paul J.Y. Lahaie Changed probing / attach code order
31 * Scott Murray Added mixer support (Dec 03, 1998)
32 * Scott Murray Changed detection code to be more forgiving,
33 * added force option as last resort,
34 * fixed ioctl return values. (Dec 30, 1998)
35 * Scott Murray Simpler detection code should work all the time now
36 * (with thanks to Ben Hutchings for the heuristic),
37 * removed now unnecessary force option. (Jan 5, 1999)
38 * Christoph Hellwig Adapted to module_init/module_exit (Mar 4, 2000)
39 * Scott Murray Reworked SA2 versus SA3 mixer code, updated chipset
40 * version detection code (again!). (Dec 5, 2000)
41 * Scott Murray Adjusted master volume mixer scaling. (Dec 6, 2000)
42 * Scott Murray Based on a patch by Joel Yliluoma (aka Bisqwit),
43 * integrated wide mixer and adjusted mic, bass, treble
44 * scaling. (Dec 6, 2000)
45 * Scott Murray Based on a patch by Peter Englmaier, integrated
46 * ymode and loopback options. (Dec 6, 2000)
47 * Scott Murray Inspired by a patch by Peter Englmaier, and based on
48 * what ALSA does, added initialization code for the
49 * default DMA and IRQ settings. (Dec 6, 2000)
50 * Scott Murray Added some more checks to the card detection code,
51 * based on what ALSA does. (Dec 12, 2000)
52 * Scott Murray Inspired by similar patches from John Fremlin,
53 * Jim Radford, Mike Rolig, and Ingmar Steen, added 2.4
54 * ISA PnP API support, mainly based on bits from
55 * sb_card.c and awe_wave.c. (Dec 12, 2000)
56 * Scott Murray Some small cleanups to the init code output.
57 * (Jan 7, 2001)
58 * Zwane Mwaikambo Added PM support. (Dec 4 2001)
59 *
60 * Adam Belay Converted driver to new PnP Layer (Oct 12, 2002)
61 * Zwane Mwaikambo Code, data structure cleanups. (Feb 15 2002)
62 * Zwane Mwaikambo Free resources during auxiliary device probe
63 * failures (Apr 29 2002)
64 *
65 */
66
Linus Torvalds1da177e2005-04-16 15:20:36 -070067#include <linux/pnp.h>
68#include <linux/init.h>
69#include <linux/module.h>
70#include <linux/delay.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070071#include "sound_config.h"
72
73#include "ad1848.h"
74#include "mpu401.h"
75
76#define OPL3SA2_MODULE_NAME "opl3sa2"
77#define PFX OPL3SA2_MODULE_NAME ": "
78
79/* Useful control port indexes: */
80#define OPL3SA2_PM 0x01
81#define OPL3SA2_SYS_CTRL 0x02
82#define OPL3SA2_IRQ_CONFIG 0x03
83#define OPL3SA2_DMA_CONFIG 0x06
84#define OPL3SA2_MASTER_LEFT 0x07
85#define OPL3SA2_MASTER_RIGHT 0x08
86#define OPL3SA2_MIC 0x09
87#define OPL3SA2_MISC 0x0A
88
89#define OPL3SA3_WIDE 0x14
90#define OPL3SA3_BASS 0x15
91#define OPL3SA3_TREBLE 0x16
92
93/* Useful constants: */
94#define DEFAULT_VOLUME 50
95#define DEFAULT_MIC 50
96#define DEFAULT_TIMBRE 0
97
98/* Power saving modes */
99#define OPL3SA2_PM_MODE0 0x00
100#define OPL3SA2_PM_MODE1 0x04 /* PSV */
101#define OPL3SA2_PM_MODE2 0x05 /* PSV | PDX */
102#define OPL3SA2_PM_MODE3 0x27 /* ADOWN | PSV | PDN | PDX */
103
104
105/* For checking against what the card returns: */
106#define VERSION_UNKNOWN 0
107#define VERSION_YMF711 1
108#define VERSION_YMF715 2
109#define VERSION_YMF715B 3
110#define VERSION_YMF715E 4
111/* also assuming that anything > 4 but <= 7 is a 715E */
112
113/* Chipset type constants for use below */
114#define CHIPSET_UNKNOWN -1
115#define CHIPSET_OPL3SA2 0
116#define CHIPSET_OPL3SA3 1
117static const char *CHIPSET_TABLE[] = {"OPL3-SA2", "OPL3-SA3"};
118
119#ifdef CONFIG_PNP
120#define OPL3SA2_CARDS_MAX 4
121#else
122#define OPL3SA2_CARDS_MAX 1
123#endif
124
125/* This should be pretty obvious */
126static int opl3sa2_cards_num;
127
128typedef struct {
129 /* device resources */
130 unsigned short cfg_port;
131 struct address_info cfg;
132 struct address_info cfg_mss;
133 struct address_info cfg_mpu;
134#ifdef CONFIG_PNP
135 /* PnP Stuff */
136 struct pnp_dev* pdev;
137 int activated; /* Whether said devices have been activated */
138#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -0700139 unsigned int card;
140 int chipset; /* What's my version(s)? */
141 char *chipset_name;
142
143 /* mixer data */
144 int mixer;
145 unsigned int volume_l;
146 unsigned int volume_r;
147 unsigned int mic;
148 unsigned int bass_l;
149 unsigned int bass_r;
150 unsigned int treble_l;
151 unsigned int treble_r;
152 unsigned int wide_l;
153 unsigned int wide_r;
154} opl3sa2_state_t;
155static opl3sa2_state_t opl3sa2_state[OPL3SA2_CARDS_MAX];
156
157
158
159/* Our parameters */
160static int __initdata io = -1;
161static int __initdata mss_io = -1;
162static int __initdata mpu_io = -1;
163static int __initdata irq = -1;
164static int __initdata dma = -1;
165static int __initdata dma2 = -1;
166static int __initdata ymode = -1;
167static int __initdata loopback = -1;
168
169#ifdef CONFIG_PNP
170/* PnP specific parameters */
171static int __initdata isapnp = 1;
172static int __initdata multiple = 1;
173
174/* Whether said devices have been activated */
175static int opl3sa2_activated[OPL3SA2_CARDS_MAX];
176#else
177static int __initdata isapnp; /* = 0 */
178static int __initdata multiple; /* = 0 */
179#endif
180
181MODULE_DESCRIPTION("Module for OPL3-SA2 and SA3 sound cards (uses AD1848 MSS driver).");
182MODULE_AUTHOR("Scott Murray <scott@spiteful.org>");
183MODULE_LICENSE("GPL");
184
185
186module_param(io, int, 0);
187MODULE_PARM_DESC(io, "Set I/O base of OPL3-SA2 or SA3 card (usually 0x370. Address must be even and must be from 0x100 to 0xFFE)");
188
189module_param(mss_io, int, 0);
190MODULE_PARM_DESC(mss_io, "Set MSS (audio) I/O base (0x530, 0xE80, or other. Address must end in 0 or 4 and must be from 0x530 to 0xF48)");
191
192module_param(mpu_io, int, 0);
193MODULE_PARM_DESC(mpu_io, "Set MIDI I/O base (0x330 or other. Address must be even and must be from 0x300 to 0x334)");
194
195module_param(irq, int, 0);
Magnus Dammd3904932005-04-16 15:25:55 -0700196MODULE_PARM_DESC(irq, "Set MSS (audio) IRQ (5, 7, 9, 10, 11, 12)");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700197
198module_param(dma, int, 0);
199MODULE_PARM_DESC(dma, "Set MSS (audio) first DMA channel (0, 1, 3)");
200
201module_param(dma2, int, 0);
202MODULE_PARM_DESC(dma2, "Set MSS (audio) second DMA channel (0, 1, 3)");
203
204module_param(ymode, int, 0);
205MODULE_PARM_DESC(ymode, "Set Yamaha 3D enhancement mode (0 = Desktop/Normal, 1 = Notebook PC (1), 2 = Notebook PC (2), 3 = Hi-Fi)");
206
207module_param(loopback, int, 0);
208MODULE_PARM_DESC(loopback, "Set A/D input source. Useful for echo cancellation (0 = Mic Rch (default), 1 = Mono output loopback)");
209
210#ifdef CONFIG_PNP
211module_param(isapnp, bool, 0);
212MODULE_PARM_DESC(isapnp, "When set to 0, ISA PnP support will be disabled");
213
214module_param(multiple, bool, 0);
215MODULE_PARM_DESC(multiple, "When set to 0, will not search for multiple cards");
216#endif
217
218
219/*
220 * Standard read and write functions
221*/
222
223static inline void opl3sa2_write(unsigned short port,
224 unsigned char index,
225 unsigned char data)
226{
227 outb_p(index, port);
228 outb(data, port + 1);
229}
230
231
232static inline void opl3sa2_read(unsigned short port,
233 unsigned char index,
234 unsigned char* data)
235{
236 outb_p(index, port);
237 *data = inb(port + 1);
238}
239
240
241/*
242 * All of the mixer functions...
243 */
244
245static void opl3sa2_set_volume(opl3sa2_state_t* devc, int left, int right)
246{
247 static unsigned char scale[101] = {
248 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0e, 0x0e, 0x0e,
249 0x0e, 0x0e, 0x0e, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0d, 0x0c,
250 0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0c, 0x0b, 0x0b, 0x0b, 0x0b,
251 0x0b, 0x0b, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x0a, 0x09, 0x09,
252 0x09, 0x09, 0x09, 0x09, 0x09, 0x08, 0x08, 0x08, 0x08, 0x08,
253 0x08, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x06, 0x06, 0x06,
254 0x06, 0x06, 0x06, 0x06, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05,
255 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x03, 0x03, 0x03, 0x03,
256 0x03, 0x03, 0x03, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x01,
257 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
258 0x00
259 };
260 unsigned char vol;
261
262 vol = scale[left];
263
264 /* If level is zero, turn on mute */
265 if(!left)
266 vol |= 0x80;
267
268 opl3sa2_write(devc->cfg_port, OPL3SA2_MASTER_LEFT, vol);
269
270 vol = scale[right];
271
272 /* If level is zero, turn on mute */
273 if(!right)
274 vol |= 0x80;
275
276 opl3sa2_write(devc->cfg_port, OPL3SA2_MASTER_RIGHT, vol);
277}
278
279
280static void opl3sa2_set_mic(opl3sa2_state_t* devc, int level)
281{
282 unsigned char vol = 0x1F;
283
284 if((level >= 0) && (level <= 100))
285 vol = 0x1F - (unsigned char) (32 * level / 101);
286
287 /* If level is zero, turn on mute */
288 if(!level)
289 vol |= 0x80;
290
291 opl3sa2_write(devc->cfg_port, OPL3SA2_MIC, vol);
292}
293
294
295static void opl3sa3_set_bass(opl3sa2_state_t* devc, int left, int right)
296{
297 unsigned char bass;
298
299 bass = left ? ((unsigned char) (8 * left / 101)) : 0;
300 bass |= (right ? ((unsigned char) (8 * right / 101)) : 0) << 4;
301
302 opl3sa2_write(devc->cfg_port, OPL3SA3_BASS, bass);
303}
304
305
306static void opl3sa3_set_treble(opl3sa2_state_t* devc, int left, int right)
307{
308 unsigned char treble;
309
310 treble = left ? ((unsigned char) (8 * left / 101)) : 0;
311 treble |= (right ? ((unsigned char) (8 * right / 101)) : 0) << 4;
312
313 opl3sa2_write(devc->cfg_port, OPL3SA3_TREBLE, treble);
314}
315
316
317
318
319static void opl3sa2_mixer_reset(opl3sa2_state_t* devc)
320{
321 if (devc) {
322 opl3sa2_set_volume(devc, DEFAULT_VOLUME, DEFAULT_VOLUME);
323 devc->volume_l = devc->volume_r = DEFAULT_VOLUME;
324
325 opl3sa2_set_mic(devc, DEFAULT_MIC);
326 devc->mic = DEFAULT_MIC;
327
328 if (devc->chipset == CHIPSET_OPL3SA3) {
329 opl3sa3_set_bass(devc, DEFAULT_TIMBRE, DEFAULT_TIMBRE);
330 devc->bass_l = devc->bass_r = DEFAULT_TIMBRE;
331 opl3sa3_set_treble(devc, DEFAULT_TIMBRE, DEFAULT_TIMBRE);
332 devc->treble_l = devc->treble_r = DEFAULT_TIMBRE;
333 }
334 }
335}
336
Linus Torvalds1da177e2005-04-16 15:20:36 -0700337static inline void arg_to_vol_mono(unsigned int vol, int* value)
338{
339 int left;
340
341 left = vol & 0x00ff;
342 if (left > 100)
343 left = 100;
344 *value = left;
345}
346
347
348static inline void arg_to_vol_stereo(unsigned int vol, int* aleft, int* aright)
349{
350 arg_to_vol_mono(vol, aleft);
351 arg_to_vol_mono(vol >> 8, aright);
352}
353
354
355static inline int ret_vol_mono(int vol)
356{
357 return ((vol << 8) | vol);
358}
359
360
361static inline int ret_vol_stereo(int left, int right)
362{
363 return ((right << 8) | left);
364}
365
366
367static int opl3sa2_mixer_ioctl(int dev, unsigned int cmd, void __user *arg)
368{
369 int retval, value, cmdf = cmd & 0xff;
370 int __user *p = (int __user *)arg;
371
372 opl3sa2_state_t* devc = &opl3sa2_state[dev];
373
374 switch (cmdf) {
375 case SOUND_MIXER_VOLUME:
376 case SOUND_MIXER_MIC:
377 case SOUND_MIXER_DEVMASK:
378 case SOUND_MIXER_STEREODEVS:
379 case SOUND_MIXER_RECMASK:
380 case SOUND_MIXER_RECSRC:
381 case SOUND_MIXER_CAPS:
382 break;
383
384 default:
385 return -EINVAL;
386 }
387
388 if (((cmd >> 8) & 0xff) != 'M')
389 return -EINVAL;
390
391 retval = 0;
392 if (_SIOC_DIR (cmd) & _SIOC_WRITE) {
393 switch (cmdf) {
394 case SOUND_MIXER_VOLUME:
395 retval = get_user(value, (unsigned __user *) arg);
396 if (retval)
397 break;
398 arg_to_vol_stereo(value, &devc->volume_l, &devc->volume_r);
399 opl3sa2_set_volume(devc, devc->volume_l, devc->volume_r);
400 value = ret_vol_stereo(devc->volume_l, devc->volume_r);
401 retval = put_user(value, p);
402 break;
403
404 case SOUND_MIXER_MIC:
405 retval = get_user(value, (unsigned __user *) arg);
406 if (retval)
407 break;
408 arg_to_vol_mono(value, &devc->mic);
409 opl3sa2_set_mic(devc, devc->mic);
410 value = ret_vol_mono(devc->mic);
411 retval = put_user(value, p);
412 break;
413
414 default:
415 retval = -EINVAL;
416 }
417 }
418 else {
419 /*
420 * Return parameters
421 */
422 switch (cmdf) {
423 case SOUND_MIXER_DEVMASK:
424 retval = put_user(SOUND_MASK_VOLUME | SOUND_MASK_MIC, p);
425 break;
426
427 case SOUND_MIXER_STEREODEVS:
428 retval = put_user(SOUND_MASK_VOLUME, p);
429 break;
430
431 case SOUND_MIXER_RECMASK:
432 /* No recording devices */
433 retval = put_user(0, p);
434 break;
435
436 case SOUND_MIXER_CAPS:
437 retval = put_user(SOUND_CAP_EXCL_INPUT, p);
438 break;
439
440 case SOUND_MIXER_RECSRC:
441 /* No recording source */
442 retval = put_user(0, p);
443 break;
444
445 case SOUND_MIXER_VOLUME:
446 value = ret_vol_stereo(devc->volume_l, devc->volume_r);
447 retval = put_user(value, p);
448 break;
449
450 case SOUND_MIXER_MIC:
451 value = ret_vol_mono(devc->mic);
452 put_user(value, p);
453 break;
454
455 default:
456 retval = -EINVAL;
457 }
458 }
459 return retval;
460}
461/* opl3sa2_mixer_ioctl end */
462
463
464static int opl3sa3_mixer_ioctl(int dev, unsigned int cmd, void __user * arg)
465{
466 int value, retval, cmdf = cmd & 0xff;
467
468 opl3sa2_state_t* devc = &opl3sa2_state[dev];
469
470 switch (cmdf) {
471 case SOUND_MIXER_BASS:
472 value = ret_vol_stereo(devc->bass_l, devc->bass_r);
473 retval = put_user(value, (int __user *) arg);
474 break;
475
476 case SOUND_MIXER_TREBLE:
477 value = ret_vol_stereo(devc->treble_l, devc->treble_r);
478 retval = put_user(value, (int __user *) arg);
479 break;
480
481 case SOUND_MIXER_DIGITAL1:
482 value = ret_vol_stereo(devc->wide_l, devc->wide_r);
483 retval = put_user(value, (int __user *) arg);
484 break;
485
486 default:
487 retval = -EINVAL;
488 }
489 return retval;
490}
491/* opl3sa3_mixer_ioctl end */
492
493
494static struct mixer_operations opl3sa2_mixer_operations =
495{
496 .owner = THIS_MODULE,
497 .id = "OPL3-SA2",
498 .name = "Yamaha OPL3-SA2",
499 .ioctl = opl3sa2_mixer_ioctl
500};
501
502static struct mixer_operations opl3sa3_mixer_operations =
503{
504 .owner = THIS_MODULE,
505 .id = "OPL3-SA3",
506 .name = "Yamaha OPL3-SA3",
507 .ioctl = opl3sa3_mixer_ioctl
508};
509
510/* End of mixer-related stuff */
511
512
513/*
514 * Component probe, attach, unload functions
515 */
516
517static inline void __exit unload_opl3sa2_mpu(struct address_info *hw_config)
518{
519 unload_mpu401(hw_config);
520}
521
522
523static void __init attach_opl3sa2_mss(struct address_info* hw_config, struct resource *ports)
524{
525 int initial_mixers;
526
527 initial_mixers = num_mixers;
528 attach_ms_sound(hw_config, ports, THIS_MODULE); /* Slot 0 */
529 if (hw_config->slots[0] != -1) {
530 /* Did the MSS driver install? */
531 if(num_mixers == (initial_mixers + 1)) {
Adrian Bunk575c9682006-01-15 02:00:17 +0100532 /* The MSS mixer is installed, reroute mixers appropriately */
Linus Torvalds1da177e2005-04-16 15:20:36 -0700533 AD1848_REROUTE(SOUND_MIXER_LINE1, SOUND_MIXER_CD);
534 AD1848_REROUTE(SOUND_MIXER_LINE2, SOUND_MIXER_SYNTH);
535 AD1848_REROUTE(SOUND_MIXER_LINE3, SOUND_MIXER_LINE);
536 }
537 else {
538 printk(KERN_ERR PFX "MSS mixer not installed?\n");
539 }
540 }
541}
542
543
544static inline void __exit unload_opl3sa2_mss(struct address_info* hw_config)
545{
546 unload_ms_sound(hw_config);
547}
548
549
550static int __init probe_opl3sa2(struct address_info* hw_config, int card)
551{
552 unsigned char misc;
553 unsigned char tmp;
554 unsigned char version;
555
556 /*
557 * Try and allocate our I/O port range.
558 */
559 if (!request_region(hw_config->io_base, 2, OPL3SA2_MODULE_NAME)) {
560 printk(KERN_ERR PFX "Control I/O port %#x not free\n",
561 hw_config->io_base);
562 goto out_nodev;
563 }
564
565 /*
566 * Check if writing to the read-only version bits of the miscellaneous
567 * register succeeds or not (it should not).
568 */
569 opl3sa2_read(hw_config->io_base, OPL3SA2_MISC, &misc);
570 opl3sa2_write(hw_config->io_base, OPL3SA2_MISC, misc ^ 0x07);
571 opl3sa2_read(hw_config->io_base, OPL3SA2_MISC, &tmp);
572 if(tmp != misc) {
573 printk(KERN_ERR PFX "Control I/O port %#x is not a YMF7xx chipset!\n",
574 hw_config->io_base);
575 goto out_region;
576 }
577
578 /*
579 * Check if the MIC register is accessible.
580 */
581 opl3sa2_read(hw_config->io_base, OPL3SA2_MIC, &tmp);
582 opl3sa2_write(hw_config->io_base, OPL3SA2_MIC, 0x8a);
583 opl3sa2_read(hw_config->io_base, OPL3SA2_MIC, &tmp);
584 if((tmp & 0x9f) != 0x8a) {
585 printk(KERN_ERR
586 PFX "Control I/O port %#x is not a YMF7xx chipset!\n",
587 hw_config->io_base);
588 goto out_region;
589 }
590 opl3sa2_write(hw_config->io_base, OPL3SA2_MIC, tmp);
591
592 /*
593 * Determine chipset type (SA2 or SA3)
594 *
595 * This is done by looking at the chipset version in the lower 3 bits
596 * of the miscellaneous register.
597 */
598 version = misc & 0x07;
599 printk(KERN_DEBUG PFX "Chipset version = %#x\n", version);
600 switch (version) {
601 case 0:
602 opl3sa2_state[card].chipset = CHIPSET_UNKNOWN;
603 printk(KERN_ERR
604 PFX "Unknown Yamaha audio controller version\n");
605 break;
606
607 case VERSION_YMF711:
608 opl3sa2_state[card].chipset = CHIPSET_OPL3SA2;
609 printk(KERN_INFO PFX "Found OPL3-SA2 (YMF711)\n");
610 break;
611
612 case VERSION_YMF715:
613 opl3sa2_state[card].chipset = CHIPSET_OPL3SA3;
614 printk(KERN_INFO
615 PFX "Found OPL3-SA3 (YMF715 or YMF719)\n");
616 break;
617
618 case VERSION_YMF715B:
619 opl3sa2_state[card].chipset = CHIPSET_OPL3SA3;
620 printk(KERN_INFO
621 PFX "Found OPL3-SA3 (YMF715B or YMF719B)\n");
622 break;
623
624 case VERSION_YMF715E:
625 default:
626 opl3sa2_state[card].chipset = CHIPSET_OPL3SA3;
627 printk(KERN_INFO
628 PFX "Found OPL3-SA3 (YMF715E or YMF719E)\n");
629 break;
630 }
631
632 if (opl3sa2_state[card].chipset != CHIPSET_UNKNOWN) {
633 /* Generate a pretty name */
634 opl3sa2_state[card].chipset_name = (char *)CHIPSET_TABLE[opl3sa2_state[card].chipset];
635 return 0;
636 }
637
638out_region:
639 release_region(hw_config->io_base, 2);
640out_nodev:
641 return -ENODEV;
642}
643
644
645static void __init attach_opl3sa2(struct address_info* hw_config, int card)
646{
647 /* Initialize IRQ configuration to IRQ-B: -, IRQ-A: WSS+MPU+OPL3 */
648 opl3sa2_write(hw_config->io_base, OPL3SA2_IRQ_CONFIG, 0x0d);
649
650 /* Initialize DMA configuration */
651 if(hw_config->dma2 == hw_config->dma) {
652 /* Want DMA configuration DMA-B: -, DMA-A: WSS-P+WSS-R */
653 opl3sa2_write(hw_config->io_base, OPL3SA2_DMA_CONFIG, 0x03);
654 }
655 else {
656 /* Want DMA configuration DMA-B: WSS-R, DMA-A: WSS-P */
657 opl3sa2_write(hw_config->io_base, OPL3SA2_DMA_CONFIG, 0x21);
658 }
659}
660
661
662static void __init attach_opl3sa2_mixer(struct address_info *hw_config, int card)
663{
664 struct mixer_operations* mixer_operations;
665 opl3sa2_state_t* devc = &opl3sa2_state[card];
666
667 /* Install master mixer */
668 if (devc->chipset == CHIPSET_OPL3SA3) {
669 mixer_operations = &opl3sa3_mixer_operations;
670 }
671 else {
672 mixer_operations = &opl3sa2_mixer_operations;
673 }
674
675 devc->cfg_port = hw_config->io_base;
676 devc->mixer = sound_install_mixer(MIXER_DRIVER_VERSION,
677 mixer_operations->name,
678 mixer_operations,
679 sizeof(struct mixer_operations),
680 devc);
681 if(devc->mixer < 0) {
682 printk(KERN_ERR PFX "Could not install %s master mixer\n",
683 mixer_operations->name);
684 }
685 else {
686 opl3sa2_mixer_reset(devc);
687
688 }
689}
690
691
692static void opl3sa2_clear_slots(struct address_info* hw_config)
693{
694 int i;
695
696 for(i = 0; i < 6; i++) {
697 hw_config->slots[i] = -1;
698 }
699}
700
701
702static void __init opl3sa2_set_ymode(struct address_info* hw_config, int ymode)
703{
704 /*
705 * Set the Yamaha 3D enhancement mode (aka Ymersion) if asked to and
706 * it's supported.
707 *
708 * 0: Desktop (aka normal) 5-12 cm speakers
709 * 1: Notebook PC mode 1 3 cm speakers
710 * 2: Notebook PC mode 2 1.5 cm speakers
711 * 3: Hi-fi 16-38 cm speakers
712 */
713 if(ymode >= 0 && ymode <= 3) {
714 unsigned char sys_ctrl;
715
716 opl3sa2_read(hw_config->io_base, OPL3SA2_SYS_CTRL, &sys_ctrl);
717 sys_ctrl = (sys_ctrl & 0xcf) | ((ymode & 3) << 4);
718 opl3sa2_write(hw_config->io_base, OPL3SA2_SYS_CTRL, sys_ctrl);
719 }
720 else {
721 printk(KERN_ERR PFX "not setting ymode, it must be one of 0,1,2,3\n");
722 }
723}
724
725
726static void __init opl3sa2_set_loopback(struct address_info* hw_config, int loopback)
727{
728 if(loopback >= 0 && loopback <= 1) {
729 unsigned char misc;
730
731 opl3sa2_read(hw_config->io_base, OPL3SA2_MISC, &misc);
732 misc = (misc & 0xef) | ((loopback & 1) << 4);
733 opl3sa2_write(hw_config->io_base, OPL3SA2_MISC, misc);
734 }
735 else {
736 printk(KERN_ERR PFX "not setting loopback, it must be either 0 or 1\n");
737 }
738}
739
740
741static void __exit unload_opl3sa2(struct address_info* hw_config, int card)
742{
743 /* Release control ports */
744 release_region(hw_config->io_base, 2);
745
746 /* Unload mixer */
747 if(opl3sa2_state[card].mixer >= 0)
748 sound_unload_mixerdev(opl3sa2_state[card].mixer);
749
750}
751
752#ifdef CONFIG_PNP
753static struct pnp_device_id pnp_opl3sa2_list[] = {
754 {.id = "YMH0021", .driver_data = 0},
755 {.id = ""}
756};
757
758MODULE_DEVICE_TABLE(pnp, pnp_opl3sa2_list);
759
760static int opl3sa2_pnp_probe(struct pnp_dev *dev, const struct pnp_device_id *dev_id)
761{
762 int card = opl3sa2_cards_num;
763
764 /* we don't actually want to return an error as the user may have specified
765 * no multiple card search
766 */
767
768 if (opl3sa2_cards_num == OPL3SA2_CARDS_MAX)
769 return 0;
770 opl3sa2_activated[card] = 1;
771
772 /* Our own config: */
773 opl3sa2_state[card].cfg.io_base = pnp_port_start(dev, 4);
774 opl3sa2_state[card].cfg.irq = pnp_irq(dev, 0);
775 opl3sa2_state[card].cfg.dma = pnp_dma(dev, 0);
776 opl3sa2_state[card].cfg.dma2 = pnp_dma(dev, 1);
777
778 /* The MSS config: */
779 opl3sa2_state[card].cfg_mss.io_base = pnp_port_start(dev, 1);
780 opl3sa2_state[card].cfg_mss.irq = pnp_irq(dev, 0);
781 opl3sa2_state[card].cfg_mss.dma = pnp_dma(dev, 0);
782 opl3sa2_state[card].cfg_mss.dma2 = pnp_dma(dev, 1);
783 opl3sa2_state[card].cfg_mss.card_subtype = 1; /* No IRQ or DMA setup */
784
785 opl3sa2_state[card].cfg_mpu.io_base = pnp_port_start(dev, 3);
786 opl3sa2_state[card].cfg_mpu.irq = pnp_irq(dev, 0);
787 opl3sa2_state[card].cfg_mpu.dma = -1;
788 opl3sa2_state[card].cfg_mpu.dma2 = -1;
789 opl3sa2_state[card].cfg_mpu.always_detect = 1; /* It's there, so use shared IRQs */
790
791 /* Call me paranoid: */
792 opl3sa2_clear_slots(&opl3sa2_state[card].cfg);
793 opl3sa2_clear_slots(&opl3sa2_state[card].cfg_mss);
794 opl3sa2_clear_slots(&opl3sa2_state[card].cfg_mpu);
795
796 opl3sa2_state[card].pdev = dev;
797 opl3sa2_cards_num++;
798
799 return 0;
800}
801
802static struct pnp_driver opl3sa2_driver = {
803 .name = "opl3sa2",
804 .id_table = pnp_opl3sa2_list,
805 .probe = opl3sa2_pnp_probe,
806};
807
808#endif /* CONFIG_PNP */
809
810/* End of component functions */
811
Linus Torvalds1da177e2005-04-16 15:20:36 -0700812/*
813 * Install OPL3-SA2 based card(s).
814 *
815 * Need to have ad1848 and mpu401 loaded ready.
816 */
817static int __init init_opl3sa2(void)
818{
819 int card, max;
820
821 /* Sanitize isapnp and multiple settings */
822 isapnp = isapnp != 0 ? 1 : 0;
823 multiple = multiple != 0 ? 1 : 0;
824
825 max = (multiple && isapnp) ? OPL3SA2_CARDS_MAX : 1;
826
827#ifdef CONFIG_PNP
828 if (isapnp){
829 pnp_register_driver(&opl3sa2_driver);
830 if(!opl3sa2_cards_num){
831 printk(KERN_INFO PFX "No PnP cards found\n");
832 isapnp = 0;
833 }
834 max = opl3sa2_cards_num;
835 }
836#endif
837
838 for (card = 0; card < max; card++) {
839 /* If a user wants an I/O then assume they meant it */
840 struct resource *ports;
841 int base;
842
843 if (!isapnp) {
844 if (io == -1 || irq == -1 || dma == -1 ||
845 dma2 == -1 || mss_io == -1) {
846 printk(KERN_ERR
847 PFX "io, mss_io, irq, dma, and dma2 must be set\n");
848 return -EINVAL;
849 }
850 opl3sa2_cards_num++;
851
852 /*
853 * Our own config:
854 * (NOTE: IRQ and DMA aren't used, so they're set to
855 * give pretty output from conf_printf. :)
856 */
857 opl3sa2_state[card].cfg.io_base = io;
858 opl3sa2_state[card].cfg.irq = irq;
859 opl3sa2_state[card].cfg.dma = dma;
860 opl3sa2_state[card].cfg.dma2 = dma2;
861
862 /* The MSS config: */
863 opl3sa2_state[card].cfg_mss.io_base = mss_io;
864 opl3sa2_state[card].cfg_mss.irq = irq;
865 opl3sa2_state[card].cfg_mss.dma = dma;
866 opl3sa2_state[card].cfg_mss.dma2 = dma2;
867 opl3sa2_state[card].cfg_mss.card_subtype = 1; /* No IRQ or DMA setup */
868
869 opl3sa2_state[card].cfg_mpu.io_base = mpu_io;
870 opl3sa2_state[card].cfg_mpu.irq = irq;
871 opl3sa2_state[card].cfg_mpu.dma = -1;
872 opl3sa2_state[card].cfg_mpu.always_detect = 1; /* Use shared IRQs */
873
874 /* Call me paranoid: */
875 opl3sa2_clear_slots(&opl3sa2_state[card].cfg);
876 opl3sa2_clear_slots(&opl3sa2_state[card].cfg_mss);
877 opl3sa2_clear_slots(&opl3sa2_state[card].cfg_mpu);
878 }
879
880 /* FIXME: leak */
881 if (probe_opl3sa2(&opl3sa2_state[card].cfg, card))
882 return -ENODEV;
883
884 base = opl3sa2_state[card].cfg_mss.io_base;
885
886 if (!request_region(base, 4, "WSS config"))
887 goto failed;
888
889 ports = request_region(base + 4, 4, "ad1848");
890 if (!ports)
891 goto failed2;
892
893 if (!probe_ms_sound(&opl3sa2_state[card].cfg_mss, ports)) {
894 /*
895 * If one or more cards are already registered, don't
896 * return an error but print a warning. Note, this
897 * should never really happen unless the hardware or
898 * ISA PnP screwed up.
899 */
900 release_region(base + 4, 4);
901 failed2:
902 release_region(base, 4);
903 failed:
904 release_region(opl3sa2_state[card].cfg.io_base, 2);
905
906 if (opl3sa2_cards_num) {
907 printk(KERN_WARNING
908 PFX "There was a problem probing one "
909 " of the ISA PNP cards, continuing\n");
910 opl3sa2_cards_num--;
911 continue;
912 } else
913 return -ENODEV;
914 }
915
916 attach_opl3sa2(&opl3sa2_state[card].cfg, card);
917 conf_printf(opl3sa2_state[card].chipset_name, &opl3sa2_state[card].cfg);
918 attach_opl3sa2_mixer(&opl3sa2_state[card].cfg, card);
919 attach_opl3sa2_mss(&opl3sa2_state[card].cfg_mss, ports);
920
921 /* ewww =) */
922 opl3sa2_state[card].card = card;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700923
924 /*
925 * Set the Yamaha 3D enhancement mode (aka Ymersion) if asked to and
926 * it's supported.
927 */
928 if (ymode != -1) {
929 if (opl3sa2_state[card].chipset == CHIPSET_OPL3SA2) {
930 printk(KERN_ERR
931 PFX "ymode not supported on OPL3-SA2\n");
932 }
933 else {
934 opl3sa2_set_ymode(&opl3sa2_state[card].cfg, ymode);
935 }
936 }
937
938
939 /* Set A/D input to Mono loopback if asked to. */
940 if (loopback != -1) {
941 opl3sa2_set_loopback(&opl3sa2_state[card].cfg, loopback);
942 }
943
944 /* Attach MPU if we've been asked to do so, failure isn't fatal */
945 if (opl3sa2_state[card].cfg_mpu.io_base != -1) {
946 int base = opl3sa2_state[card].cfg_mpu.io_base;
947 struct resource *ports;
948 ports = request_region(base, 2, "mpu401");
949 if (!ports)
950 goto out;
951 if (!probe_mpu401(&opl3sa2_state[card].cfg_mpu, ports)) {
952 release_region(base, 2);
953 goto out;
954 }
955 if (attach_mpu401(&opl3sa2_state[card].cfg_mpu, THIS_MODULE)) {
956 printk(KERN_ERR PFX "failed to attach MPU401\n");
957 opl3sa2_state[card].cfg_mpu.slots[1] = -1;
958 }
959 }
960 }
961
962out:
963 if (isapnp) {
964 printk(KERN_NOTICE PFX "%d PnP card(s) found.\n", opl3sa2_cards_num);
965 }
966
967 return 0;
968}
969
970
971/*
972 * Uninstall OPL3-SA2 based card(s).
973 */
974static void __exit cleanup_opl3sa2(void)
975{
976 int card;
977
978 for(card = 0; card < opl3sa2_cards_num; card++) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700979 if (opl3sa2_state[card].cfg_mpu.slots[1] != -1) {
980 unload_opl3sa2_mpu(&opl3sa2_state[card].cfg_mpu);
981 }
982 unload_opl3sa2_mss(&opl3sa2_state[card].cfg_mss);
983 unload_opl3sa2(&opl3sa2_state[card].cfg, card);
984#ifdef CONFIG_PNP
985 pnp_unregister_driver(&opl3sa2_driver);
986#endif
987 }
988}
989
990module_init(init_opl3sa2);
991module_exit(cleanup_opl3sa2);
992
993#ifndef MODULE
994static int __init setup_opl3sa2(char *str)
995{
996 /* io, irq, dma, dma2,... */
997#ifdef CONFIG_PNP
998 int ints[11];
999#else
1000 int ints[9];
1001#endif
1002 str = get_options(str, ARRAY_SIZE(ints), ints);
1003
1004 io = ints[1];
1005 irq = ints[2];
1006 dma = ints[3];
1007 dma2 = ints[4];
1008 mss_io = ints[5];
1009 mpu_io = ints[6];
1010 ymode = ints[7];
1011 loopback = ints[8];
1012#ifdef CONFIG_PNP
1013 isapnp = ints[9];
1014 multiple = ints[10];
1015#endif
1016 return 1;
1017}
1018
1019__setup("opl3sa2=", setup_opl3sa2);
1020#endif