Commit 78df617acf83745908ae71f322e084284054ea66

Authored by Andreas Mohr
Committed by Takashi Iwai
1 parent dfbf951115

ALSA: azt3328: fix previous breakage, improve suspend, cleanups

- fix my previous codec activity breakage (_non-warned_ variable assignment
  issue)
- convert suspend/resume to 32bit I/O access (I/O is painful; to improve
  suspend/resume performance)
- change DEBUG_PLAY_REC to DEBUG_CODEC for consistency
- printk cleanup
- some logging improvements
- minor cleanup/improvements

The variable assignment issue above was a conditional assignment to the
call_function variable (this ended with the non-preinitialized variable
not getting assigned in some cases, thus a dangling stack value, yet gcc 4.3.3
unbelievably did _NOT_ warn about it in this case!!),
needed to change this into _always_ assigning the check result.
Practical result of this bug was that when shutting down
_either_ playback or capture, _both_ streams dropped dead :P

Tested, working (plus resume) and checkpatch.pl:ed on 2.6.30-rc5,
applies cleanly to 2.6.30 proper with my previous (committed)
patches applied.

Signed-off-by: Andreas Mohr <andi@lisas.de>
Signed-off-by: Takashi Iwai <tiwai@suse.de>

Showing 2 changed files with 135 additions and 81 deletions Inline Diff

1 /* 1 /*
2 * azt3328.c - driver for Aztech AZF3328 based soundcards (e.g. PCI168). 2 * azt3328.c - driver for Aztech AZF3328 based soundcards (e.g. PCI168).
3 * Copyright (C) 2002, 2005 - 2009 by Andreas Mohr <andi AT lisas.de> 3 * Copyright (C) 2002, 2005 - 2009 by Andreas Mohr <andi AT lisas.de>
4 * 4 *
5 * Framework borrowed from Bart Hartgers's als4000.c. 5 * Framework borrowed from Bart Hartgers's als4000.c.
6 * Driver developed on PCI168 AP(W) version (PCI rev. 10, subsystem ID 1801), 6 * Driver developed on PCI168 AP(W) version (PCI rev. 10, subsystem ID 1801),
7 * found in a Fujitsu-Siemens PC ("Cordant", aluminum case). 7 * found in a Fujitsu-Siemens PC ("Cordant", aluminum case).
8 * Other versions are: 8 * Other versions are:
9 * PCI168 A(W), sub ID 1800 9 * PCI168 A(W), sub ID 1800
10 * PCI168 A/AP, sub ID 8000 10 * PCI168 A/AP, sub ID 8000
11 * Please give me feedback in case you try my driver with one of these!! 11 * Please give me feedback in case you try my driver with one of these!!
12 * 12 *
13 * Keywords: Windows XP Vista 168nt4-125.zip 168win95-125.zip PCI 168 download 13 * Keywords: Windows XP Vista 168nt4-125.zip 168win95-125.zip PCI 168 download
14 * (XP/Vista do not support this card at all but every Linux distribution 14 * (XP/Vista do not support this card at all but every Linux distribution
15 * has very good support out of the box; 15 * has very good support out of the box;
16 * just to make sure that the right people hit this and get to know that, 16 * just to make sure that the right people hit this and get to know that,
17 * despite the high level of Internet ignorance - as usual :-P - 17 * despite the high level of Internet ignorance - as usual :-P -
18 * about Linux support for this card) 18 * about very good support for this card - on Linux!)
19 * 19 *
20 * GPL LICENSE 20 * GPL LICENSE
21 * This program is free software; you can redistribute it and/or modify 21 * This program is free software; you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by 22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation; either version 2 of the License, or 23 * the Free Software Foundation; either version 2 of the License, or
24 * (at your option) any later version. 24 * (at your option) any later version.
25 * 25 *
26 * This program is distributed in the hope that it will be useful, 26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of 27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
29 * GNU General Public License for more details. 29 * GNU General Public License for more details.
30 30
31 * You should have received a copy of the GNU General Public License 31 * You should have received a copy of the GNU General Public License
32 * along with this program; if not, write to the Free Software 32 * along with this program; if not, write to the Free Software
33 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 33 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
34 * 34 *
35 * NOTES 35 * NOTES
36 * Since Aztech does not provide any chipset documentation, 36 * Since Aztech does not provide any chipset documentation,
37 * even on repeated request to various addresses, 37 * even on repeated request to various addresses,
38 * and the answer that was finally given was negative 38 * and the answer that was finally given was negative
39 * (and I was stupid enough to manage to get hold of a PCI168 soundcard 39 * (and I was stupid enough to manage to get hold of a PCI168 soundcard
40 * in the first place >:-P}), 40 * in the first place >:-P}),
41 * I was forced to base this driver on reverse engineering 41 * I was forced to base this driver on reverse engineering
42 * (3 weeks' worth of evenings filled with driver work). 42 * (3 weeks' worth of evenings filled with driver work).
43 * (and no, I did NOT go the easy way: to pick up a SB PCI128 for 9 Euros) 43 * (and no, I did NOT go the easy way: to pick up a SB PCI128 for 9 Euros)
44 * 44 *
45 * It is quite likely that the AZF3328 chip is the PCI cousin of the 45 * It is quite likely that the AZF3328 chip is the PCI cousin of the
46 * AZF3318 ("azt1020 pnp", "MM Pro 16") ISA chip, given very similar specs. 46 * AZF3318 ("azt1020 pnp", "MM Pro 16") ISA chip, given very similar specs.
47 * 47 *
48 * The AZF3328 chip (note: AZF3328, *not* AZT3328, that's just the driver name 48 * The AZF3328 chip (note: AZF3328, *not* AZT3328, that's just the driver name
49 * for compatibility reasons) from Azfin (joint-venture of Aztech and Fincitec, 49 * for compatibility reasons) from Azfin (joint-venture of Aztech and Fincitec,
50 * Fincitec acquired by National Semiconductor in 2002, together with the 50 * Fincitec acquired by National Semiconductor in 2002, together with the
51 * Fincitec-related company ARSmikro) has the following features: 51 * Fincitec-related company ARSmikro) has the following features:
52 * 52 *
53 * - compatibility & compliance: 53 * - compatibility & compliance:
54 * - Microsoft PC 97 ("PC 97 Hardware Design Guide", 54 * - Microsoft PC 97 ("PC 97 Hardware Design Guide",
55 * http://www.microsoft.com/whdc/archive/pcguides.mspx) 55 * http://www.microsoft.com/whdc/archive/pcguides.mspx)
56 * - Microsoft PC 98 Baseline Audio 56 * - Microsoft PC 98 Baseline Audio
57 * - MPU401 UART 57 * - MPU401 UART
58 * - Sound Blaster Emulation (DOS Box) 58 * - Sound Blaster Emulation (DOS Box)
59 * - builtin AC97 conformant codec (SNR over 80dB) 59 * - builtin AC97 conformant codec (SNR over 80dB)
60 * Note that "conformant" != "compliant"!! this chip's mixer register layout 60 * Note that "conformant" != "compliant"!! this chip's mixer register layout
61 * *differs* from the standard AC97 layout: 61 * *differs* from the standard AC97 layout:
62 * they chose to not implement the headphone register (which is not a 62 * they chose to not implement the headphone register (which is not a
63 * problem since it's merely optional), yet when doing this, they committed 63 * problem since it's merely optional), yet when doing this, they committed
64 * the grave sin of letting other registers follow immediately instead of 64 * the grave sin of letting other registers follow immediately instead of
65 * keeping a headphone dummy register, thereby shifting the mixer register 65 * keeping a headphone dummy register, thereby shifting the mixer register
66 * addresses illegally. So far unfortunately it looks like the very flexible 66 * addresses illegally. So far unfortunately it looks like the very flexible
67 * ALSA AC97 support is still not enough to easily compensate for such a 67 * ALSA AC97 support is still not enough to easily compensate for such a
68 * grave layout violation despite all tweaks and quirks mechanisms it offers. 68 * grave layout violation despite all tweaks and quirks mechanisms it offers.
69 * - builtin genuine OPL3 - verified to work fine, 20080506 69 * - builtin genuine OPL3 - verified to work fine, 20080506
70 * - full duplex 16bit playback/record at independent sampling rate 70 * - full duplex 16bit playback/record at independent sampling rate
71 * - MPU401 (+ legacy address support, claimed by one official spec sheet) 71 * - MPU401 (+ legacy address support, claimed by one official spec sheet)
72 * FIXME: how to enable legacy addr?? 72 * FIXME: how to enable legacy addr??
73 * - game port (legacy address support) 73 * - game port (legacy address support)
74 * - builtin DirectInput support, helps reduce CPU overhead (interrupt-driven 74 * - builtin DirectInput support, helps reduce CPU overhead (interrupt-driven
75 * features supported). - See common term "Digital Enhanced Game Port"... 75 * features supported). - See common term "Digital Enhanced Game Port"...
76 * (probably DirectInput 3.0 spec - confirm) 76 * (probably DirectInput 3.0 spec - confirm)
77 * - builtin 3D enhancement (said to be YAMAHA Ymersion) 77 * - builtin 3D enhancement (said to be YAMAHA Ymersion)
78 * - built-in General DirectX timer having a 20 bits counter 78 * - built-in General DirectX timer having a 20 bits counter
79 * with 1us resolution (see below!) 79 * with 1us resolution (see below!)
80 * - I2S serial output port for external DAC 80 * - I2S serial output port for external DAC
81 * [FIXME: 3.3V or 5V level? maximum rate is 66.2kHz right?] 81 * [FIXME: 3.3V or 5V level? maximum rate is 66.2kHz right?]
82 * - supports 33MHz PCI spec 2.1, PCI power management 1.0, compliant with ACPI 82 * - supports 33MHz PCI spec 2.1, PCI power management 1.0, compliant with ACPI
83 * - supports hardware volume control 83 * - supports hardware volume control
84 * - single chip low cost solution (128 pin QFP) 84 * - single chip low cost solution (128 pin QFP)
85 * - supports programmable Sub-vendor and Sub-system ID [24C02 SEEPROM chip] 85 * - supports programmable Sub-vendor and Sub-system ID [24C02 SEEPROM chip]
86 * required for Microsoft's logo compliance (FIXME: where?) 86 * required for Microsoft's logo compliance (FIXME: where?)
87 * At least the Trident 4D Wave DX has one bit somewhere 87 * At least the Trident 4D Wave DX has one bit somewhere
88 * to enable writes to PCI subsystem VID registers, that should be it. 88 * to enable writes to PCI subsystem VID registers, that should be it.
89 * This might easily be in extended PCI reg space, since PCI168 also has 89 * This might easily be in extended PCI reg space, since PCI168 also has
90 * some custom data starting at 0x80. What kind of config settings 90 * some custom data starting at 0x80. What kind of config settings
91 * are located in our extended PCI space anyway?? 91 * are located in our extended PCI space anyway??
92 * - PCI168 AP(W) card: power amplifier with 4 Watts/channel at 4 Ohms 92 * - PCI168 AP(W) card: power amplifier with 4 Watts/channel at 4 Ohms
93 * [TDA1517P chip] 93 * [TDA1517P chip]
94 * 94 *
95 * Note that this driver now is actually *better* than the Windows driver, 95 * Note that this driver now is actually *better* than the Windows driver,
96 * since it additionally supports the card's 1MHz DirectX timer - just try 96 * since it additionally supports the card's 1MHz DirectX timer - just try
97 * the following snd-seq module parameters etc.: 97 * the following snd-seq module parameters etc.:
98 * - options snd-seq seq_default_timer_class=2 seq_default_timer_sclass=0 98 * - options snd-seq seq_default_timer_class=2 seq_default_timer_sclass=0
99 * seq_default_timer_card=0 seq_client_load=1 seq_default_timer_device=0 99 * seq_default_timer_card=0 seq_client_load=1 seq_default_timer_device=0
100 * seq_default_timer_subdevice=0 seq_default_timer_resolution=1000000 100 * seq_default_timer_subdevice=0 seq_default_timer_resolution=1000000
101 * - "timidity -iAv -B2,8 -Os -EFreverb=0" 101 * - "timidity -iAv -B2,8 -Os -EFreverb=0"
102 * - "pmidi -p 128:0 jazz.mid" 102 * - "pmidi -p 128:0 jazz.mid"
103 * 103 *
104 * OPL3 hardware playback testing, try something like: 104 * OPL3 hardware playback testing, try something like:
105 * cat /proc/asound/hwdep 105 * cat /proc/asound/hwdep
106 * and 106 * and
107 * aconnect -o 107 * aconnect -o
108 * Then use 108 * Then use
109 * sbiload -Dhw:x,y --opl3 /usr/share/sounds/opl3/std.o3 ......./drums.o3 109 * sbiload -Dhw:x,y --opl3 /usr/share/sounds/opl3/std.o3 ......./drums.o3
110 * where x,y is the xx-yy number as given in hwdep. 110 * where x,y is the xx-yy number as given in hwdep.
111 * Then try 111 * Then try
112 * pmidi -p a:b jazz.mid 112 * pmidi -p a:b jazz.mid
113 * where a:b is the client number plus 0 usually, as given by aconnect above. 113 * where a:b is the client number plus 0 usually, as given by aconnect above.
114 * Oh, and make sure to unmute the FM mixer control (doh!) 114 * Oh, and make sure to unmute the FM mixer control (doh!)
115 * NOTE: power use during OPL3 playback is _VERY_ high (70W --> 90W!) 115 * NOTE: power use during OPL3 playback is _VERY_ high (70W --> 90W!)
116 * despite no CPU activity, possibly due to hindering ACPI idling somehow. 116 * despite no CPU activity, possibly due to hindering ACPI idling somehow.
117 * Shouldn't be a problem of the AZF3328 chip itself, I'd hope. 117 * Shouldn't be a problem of the AZF3328 chip itself, I'd hope.
118 * Higher PCM / FM mixer levels seem to conflict (causes crackling), 118 * Higher PCM / FM mixer levels seem to conflict (causes crackling),
119 * at least sometimes. Maybe even use with hardware sequencer timer above :) 119 * at least sometimes. Maybe even use with hardware sequencer timer above :)
120 * adplay/adplug-utils might soon offer hardware-based OPL3 playback, too. 120 * adplay/adplug-utils might soon offer hardware-based OPL3 playback, too.
121 * 121 *
122 * Certain PCI versions of this card are susceptible to DMA traffic underruns 122 * Certain PCI versions of this card are susceptible to DMA traffic underruns
123 * in some systems (resulting in sound crackling/clicking/popping), 123 * in some systems (resulting in sound crackling/clicking/popping),
124 * probably because they don't have a DMA FIFO buffer or so. 124 * probably because they don't have a DMA FIFO buffer or so.
125 * Overview (PCI ID/PCI subID/PCI rev.): 125 * Overview (PCI ID/PCI subID/PCI rev.):
126 * - no DMA crackling on SiS735: 0x50DC/0x1801/16 126 * - no DMA crackling on SiS735: 0x50DC/0x1801/16
127 * - unknown performance: 0x50DC/0x1801/10 127 * - unknown performance: 0x50DC/0x1801/10
128 * (well, it's not bad on an Athlon 1800 with now very optimized IRQ handler) 128 * (well, it's not bad on an Athlon 1800 with now very optimized IRQ handler)
129 * 129 *
130 * Crackling happens with VIA chipsets or, in my case, an SiS735, which is 130 * Crackling happens with VIA chipsets or, in my case, an SiS735, which is
131 * supposed to be very fast and supposed to get rid of crackling much 131 * supposed to be very fast and supposed to get rid of crackling much
132 * better than a VIA, yet ironically I still get crackling, like many other 132 * better than a VIA, yet ironically I still get crackling, like many other
133 * people with the same chipset. 133 * people with the same chipset.
134 * Possible remedies: 134 * Possible remedies:
135 * - use speaker (amplifier) output instead of headphone output 135 * - use speaker (amplifier) output instead of headphone output
136 * (in case crackling is due to overloaded output clipping) 136 * (in case crackling is due to overloaded output clipping)
137 * - plug card into a different PCI slot, preferrably one that isn't shared 137 * - plug card into a different PCI slot, preferrably one that isn't shared
138 * too much (this helps a lot, but not completely!) 138 * too much (this helps a lot, but not completely!)
139 * - get rid of PCI VGA card, use AGP instead 139 * - get rid of PCI VGA card, use AGP instead
140 * - upgrade or downgrade BIOS 140 * - upgrade or downgrade BIOS
141 * - fiddle with PCI latency settings (setpci -v -s BUSID latency_timer=XX) 141 * - fiddle with PCI latency settings (setpci -v -s BUSID latency_timer=XX)
142 * Not too helpful. 142 * Not too helpful.
143 * - Disable ACPI/power management/"Auto Detect RAM/PCI Clk" in BIOS 143 * - Disable ACPI/power management/"Auto Detect RAM/PCI Clk" in BIOS
144 * 144 *
145 * BUGS 145 * BUGS
146 * - full-duplex might *still* be problematic, however a recent test was fine 146 * - full-duplex might *still* be problematic, however a recent test was fine
147 * - (non-bug) "Bass/Treble or 3D settings don't work" - they do get evaluated 147 * - (non-bug) "Bass/Treble or 3D settings don't work" - they do get evaluated
148 * if you set PCM output switch to "pre 3D" instead of "post 3D". 148 * if you set PCM output switch to "pre 3D" instead of "post 3D".
149 * If this can't be set, then get a mixer application that Isn't Stupid (tm) 149 * If this can't be set, then get a mixer application that Isn't Stupid (tm)
150 * (e.g. kmix, gamix) - unfortunately several are!! 150 * (e.g. kmix, gamix) - unfortunately several are!!
151 * - locking is not entirely clean, especially the audio stream activity 151 * - locking is not entirely clean, especially the audio stream activity
152 * ints --> may be racy 152 * ints --> may be racy
153 * - an _unconnected_ secondary joystick at the gameport will be reported 153 * - an _unconnected_ secondary joystick at the gameport will be reported
154 * to be "active" (floating values, not precisely -1) due to the way we need 154 * to be "active" (floating values, not precisely -1) due to the way we need
155 * to read the Digital Enhanced Game Port. Not sure whether it is fixable. 155 * to read the Digital Enhanced Game Port. Not sure whether it is fixable.
156 * 156 *
157 * TODO 157 * TODO
158 * - use PCI_VDEVICE 158 * - use PCI_VDEVICE
159 * - verify driver status on x86_64 159 * - verify driver status on x86_64
160 * - test multi-card driver operation 160 * - test multi-card driver operation
161 * - (ab)use 1MHz DirectX timer as kernel clocksource 161 * - (ab)use 1MHz DirectX timer as kernel clocksource
162 * - test MPU401 MIDI playback etc. 162 * - test MPU401 MIDI playback etc.
163 * - add more power micro-management (disable various units of the card 163 * - add more power micro-management (disable various units of the card
164 * as long as they're unused, to improve audio quality and save power). 164 * as long as they're unused, to improve audio quality and save power).
165 * However this requires more I/O ports which I haven't figured out yet 165 * However this requires more I/O ports which I haven't figured out yet
166 * and which thus might not even exist... 166 * and which thus might not even exist...
167 * The standard suspend/resume functionality could probably make use of 167 * The standard suspend/resume functionality could probably make use of
168 * some improvement, too... 168 * some improvement, too...
169 * - figure out what all unknown port bits are responsible for 169 * - figure out what all unknown port bits are responsible for
170 * - figure out some cleverly evil scheme to possibly make ALSA AC97 code 170 * - figure out some cleverly evil scheme to possibly make ALSA AC97 code
171 * fully accept our quite incompatible ""AC97"" mixer and thus save some 171 * fully accept our quite incompatible ""AC97"" mixer and thus save some
172 * code (but I'm not too optimistic that doing this is possible at all) 172 * code (but I'm not too optimistic that doing this is possible at all)
173 * - use MMIO (memory-mapped I/O)? Slightly faster access, e.g. for gameport. 173 * - use MMIO (memory-mapped I/O)? Slightly faster access, e.g. for gameport.
174 */ 174 */
175 175
176 #include <asm/io.h> 176 #include <asm/io.h>
177 #include <linux/init.h> 177 #include <linux/init.h>
178 #include <linux/pci.h> 178 #include <linux/pci.h>
179 #include <linux/delay.h> 179 #include <linux/delay.h>
180 #include <linux/slab.h> 180 #include <linux/slab.h>
181 #include <linux/gameport.h> 181 #include <linux/gameport.h>
182 #include <linux/moduleparam.h> 182 #include <linux/moduleparam.h>
183 #include <linux/dma-mapping.h> 183 #include <linux/dma-mapping.h>
184 #include <sound/core.h> 184 #include <sound/core.h>
185 #include <sound/control.h> 185 #include <sound/control.h>
186 #include <sound/pcm.h> 186 #include <sound/pcm.h>
187 #include <sound/rawmidi.h> 187 #include <sound/rawmidi.h>
188 #include <sound/mpu401.h> 188 #include <sound/mpu401.h>
189 #include <sound/opl3.h> 189 #include <sound/opl3.h>
190 #include <sound/initval.h> 190 #include <sound/initval.h>
191 #include "azt3328.h" 191 #include "azt3328.h"
192 192
193 MODULE_AUTHOR("Andreas Mohr <andi AT lisas.de>"); 193 MODULE_AUTHOR("Andreas Mohr <andi AT lisas.de>");
194 MODULE_DESCRIPTION("Aztech AZF3328 (PCI168)"); 194 MODULE_DESCRIPTION("Aztech AZF3328 (PCI168)");
195 MODULE_LICENSE("GPL"); 195 MODULE_LICENSE("GPL");
196 MODULE_SUPPORTED_DEVICE("{{Aztech,AZF3328}}"); 196 MODULE_SUPPORTED_DEVICE("{{Aztech,AZF3328}}");
197 197
198 #if defined(CONFIG_GAMEPORT) || (defined(MODULE) && defined(CONFIG_GAMEPORT_MODULE)) 198 #if defined(CONFIG_GAMEPORT) || (defined(MODULE) && defined(CONFIG_GAMEPORT_MODULE))
199 #define SUPPORT_GAMEPORT 1 199 #define SUPPORT_GAMEPORT 1
200 #endif 200 #endif
201 201
202 /* === Debug settings === 202 /* === Debug settings ===
203 Further diagnostic functionality than the settings below 203 Further diagnostic functionality than the settings below
204 does not need to be provided, since one can easily write a bash script 204 does not need to be provided, since one can easily write a bash script
205 to dump the card's I/O ports (those listed in lspci -v -v): 205 to dump the card's I/O ports (those listed in lspci -v -v):
206 function dump() 206 function dump()
207 { 207 {
208 local descr=$1; local addr=$2; local count=$3 208 local descr=$1; local addr=$2; local count=$3
209 209
210 echo "${descr}: ${count} @ ${addr}:" 210 echo "${descr}: ${count} @ ${addr}:"
211 dd if=/dev/port skip=$[${addr}] count=${count} bs=1 2>/dev/null| hexdump -C 211 dd if=/dev/port skip=$[${addr}] count=${count} bs=1 2>/dev/null| hexdump -C
212 } 212 }
213 and then use something like 213 and then use something like
214 "dump joy200 0x200 8", "dump mpu388 0x388 4", "dump joy 0xb400 8", 214 "dump joy200 0x200 8", "dump mpu388 0x388 4", "dump joy 0xb400 8",
215 "dump codec00 0xa800 32", "dump mixer 0xb800 64", "dump synth 0xbc00 8", 215 "dump codec00 0xa800 32", "dump mixer 0xb800 64", "dump synth 0xbc00 8",
216 possibly within a "while true; do ... sleep 1; done" loop. 216 possibly within a "while true; do ... sleep 1; done" loop.
217 Tweaking ports could be done using 217 Tweaking ports could be done using
218 VALSTRING="`printf "%02x" $value`" 218 VALSTRING="`printf "%02x" $value`"
219 printf "\x""$VALSTRING"|dd of=/dev/port seek=$[${addr}] bs=1 2>/dev/null 219 printf "\x""$VALSTRING"|dd of=/dev/port seek=$[${addr}] bs=1 2>/dev/null
220 */ 220 */
221 221
222 #define DEBUG_MISC 0 222 #define DEBUG_MISC 0
223 #define DEBUG_CALLS 0 223 #define DEBUG_CALLS 0
224 #define DEBUG_MIXER 0 224 #define DEBUG_MIXER 0
225 #define DEBUG_PLAY_REC 0 225 #define DEBUG_CODEC 0
226 #define DEBUG_IO 0 226 #define DEBUG_IO 0
227 #define DEBUG_TIMER 0 227 #define DEBUG_TIMER 0
228 #define DEBUG_GAME 0 228 #define DEBUG_GAME 0
229 #define DEBUG_PM 0
229 #define MIXER_TESTING 0 230 #define MIXER_TESTING 0
230 231
231 #if DEBUG_MISC 232 #if DEBUG_MISC
232 #define snd_azf3328_dbgmisc(format, args...) printk(KERN_ERR format, ##args) 233 #define snd_azf3328_dbgmisc(format, args...) printk(KERN_DEBUG format, ##args)
233 #else 234 #else
234 #define snd_azf3328_dbgmisc(format, args...) 235 #define snd_azf3328_dbgmisc(format, args...)
235 #endif 236 #endif
236 237
237 #if DEBUG_CALLS 238 #if DEBUG_CALLS
238 #define snd_azf3328_dbgcalls(format, args...) printk(format, ##args) 239 #define snd_azf3328_dbgcalls(format, args...) printk(format, ##args)
239 #define snd_azf3328_dbgcallenter() printk(KERN_ERR "--> %s\n", __func__) 240 #define snd_azf3328_dbgcallenter() printk(KERN_DEBUG "--> %s\n", __func__)
240 #define snd_azf3328_dbgcallleave() printk(KERN_ERR "<-- %s\n", __func__) 241 #define snd_azf3328_dbgcallleave() printk(KERN_DEBUG "<-- %s\n", __func__)
241 #else 242 #else
242 #define snd_azf3328_dbgcalls(format, args...) 243 #define snd_azf3328_dbgcalls(format, args...)
243 #define snd_azf3328_dbgcallenter() 244 #define snd_azf3328_dbgcallenter()
244 #define snd_azf3328_dbgcallleave() 245 #define snd_azf3328_dbgcallleave()
245 #endif 246 #endif
246 247
247 #if DEBUG_MIXER 248 #if DEBUG_MIXER
248 #define snd_azf3328_dbgmixer(format, args...) printk(KERN_DEBUG format, ##args) 249 #define snd_azf3328_dbgmixer(format, args...) printk(KERN_DEBUG format, ##args)
249 #else 250 #else
250 #define snd_azf3328_dbgmixer(format, args...) 251 #define snd_azf3328_dbgmixer(format, args...)
251 #endif 252 #endif
252 253
253 #if DEBUG_PLAY_REC 254 #if DEBUG_CODEC
254 #define snd_azf3328_dbgplay(format, args...) printk(KERN_DEBUG format, ##args) 255 #define snd_azf3328_dbgcodec(format, args...) printk(KERN_DEBUG format, ##args)
255 #else 256 #else
256 #define snd_azf3328_dbgplay(format, args...) 257 #define snd_azf3328_dbgcodec(format, args...)
257 #endif 258 #endif
258 259
259 #if DEBUG_MISC 260 #if DEBUG_MISC
260 #define snd_azf3328_dbgtimer(format, args...) printk(KERN_DEBUG format, ##args) 261 #define snd_azf3328_dbgtimer(format, args...) printk(KERN_DEBUG format, ##args)
261 #else 262 #else
262 #define snd_azf3328_dbgtimer(format, args...) 263 #define snd_azf3328_dbgtimer(format, args...)
263 #endif 264 #endif
264 265
265 #if DEBUG_GAME 266 #if DEBUG_GAME
266 #define snd_azf3328_dbggame(format, args...) printk(KERN_DEBUG format, ##args) 267 #define snd_azf3328_dbggame(format, args...) printk(KERN_DEBUG format, ##args)
267 #else 268 #else
268 #define snd_azf3328_dbggame(format, args...) 269 #define snd_azf3328_dbggame(format, args...)
269 #endif 270 #endif
270 271
272 #if DEBUG_PM
273 #define snd_azf3328_dbgpm(format, args...) printk(KERN_DEBUG format, ##args)
274 #else
275 #define snd_azf3328_dbgpm(format, args...)
276 #endif
277
271 static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-MAX */ 278 static int index[SNDRV_CARDS] = SNDRV_DEFAULT_IDX; /* Index 0-MAX */
272 module_param_array(index, int, NULL, 0444); 279 module_param_array(index, int, NULL, 0444);
273 MODULE_PARM_DESC(index, "Index value for AZF3328 soundcard."); 280 MODULE_PARM_DESC(index, "Index value for AZF3328 soundcard.");
274 281
275 static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* ID for this card */ 282 static char *id[SNDRV_CARDS] = SNDRV_DEFAULT_STR; /* ID for this card */
276 module_param_array(id, charp, NULL, 0444); 283 module_param_array(id, charp, NULL, 0444);
277 MODULE_PARM_DESC(id, "ID string for AZF3328 soundcard."); 284 MODULE_PARM_DESC(id, "ID string for AZF3328 soundcard.");
278 285
279 static int enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP; /* Enable this card */ 286 static int enable[SNDRV_CARDS] = SNDRV_DEFAULT_ENABLE_PNP; /* Enable this card */
280 module_param_array(enable, bool, NULL, 0444); 287 module_param_array(enable, bool, NULL, 0444);
281 MODULE_PARM_DESC(enable, "Enable AZF3328 soundcard."); 288 MODULE_PARM_DESC(enable, "Enable AZF3328 soundcard.");
282 289
283 static int seqtimer_scaling = 128; 290 static int seqtimer_scaling = 128;
284 module_param(seqtimer_scaling, int, 0444); 291 module_param(seqtimer_scaling, int, 0444);
285 MODULE_PARM_DESC(seqtimer_scaling, "Set 1024000Hz sequencer timer scale factor (lockup danger!). Default 128."); 292 MODULE_PARM_DESC(seqtimer_scaling, "Set 1024000Hz sequencer timer scale factor (lockup danger!). Default 128.");
286 293
287 struct snd_azf3328_codec_data { 294 struct snd_azf3328_codec_data {
288 unsigned long io_base; 295 unsigned long io_base;
289 struct snd_pcm_substream *substream; 296 struct snd_pcm_substream *substream;
290 bool running; 297 bool running;
291 const char *name; 298 const char *name;
292 }; 299 };
293 300
294 enum snd_azf3328_codec_type { 301 enum snd_azf3328_codec_type {
295 AZF_CODEC_PLAYBACK = 0, 302 AZF_CODEC_PLAYBACK = 0,
296 AZF_CODEC_CAPTURE = 1, 303 AZF_CODEC_CAPTURE = 1,
297 AZF_CODEC_I2S_OUT = 2, 304 AZF_CODEC_I2S_OUT = 2,
298 }; 305 };
299 306
300 struct snd_azf3328 { 307 struct snd_azf3328 {
301 /* often-used fields towards beginning, then grouped */ 308 /* often-used fields towards beginning, then grouped */
302 309
303 unsigned long ctrl_io; /* usually 0xb000, size 128 */ 310 unsigned long ctrl_io; /* usually 0xb000, size 128 */
304 unsigned long game_io; /* usually 0xb400, size 8 */ 311 unsigned long game_io; /* usually 0xb400, size 8 */
305 unsigned long mpu_io; /* usually 0xb800, size 4 */ 312 unsigned long mpu_io; /* usually 0xb800, size 4 */
306 unsigned long opl3_io; /* usually 0xbc00, size 8 */ 313 unsigned long opl3_io; /* usually 0xbc00, size 8 */
307 unsigned long mixer_io; /* usually 0xc000, size 64 */ 314 unsigned long mixer_io; /* usually 0xc000, size 64 */
308 315
309 spinlock_t reg_lock; 316 spinlock_t reg_lock;
310 317
311 struct snd_timer *timer; 318 struct snd_timer *timer;
312 319
313 struct snd_pcm *pcm[3]; 320 struct snd_pcm *pcm[3];
314 321
315 /* playback, recording and I2S out codecs */ 322 /* playback, recording and I2S out codecs */
316 struct snd_azf3328_codec_data codecs[3]; 323 struct snd_azf3328_codec_data codecs[3];
317 324
318 struct snd_card *card; 325 struct snd_card *card;
319 struct snd_rawmidi *rmidi; 326 struct snd_rawmidi *rmidi;
320 327
321 #ifdef SUPPORT_GAMEPORT 328 #ifdef SUPPORT_GAMEPORT
322 struct gameport *gameport; 329 struct gameport *gameport;
323 u16 axes[4]; 330 u16 axes[4];
324 #endif 331 #endif
325 332
326 struct pci_dev *pci; 333 struct pci_dev *pci;
327 int irq; 334 int irq;
328 335
329 /* register 0x6a is write-only, thus need to remember setting. 336 /* register 0x6a is write-only, thus need to remember setting.
330 * If we need to add more registers here, then we might try to fold this 337 * If we need to add more registers here, then we might try to fold this
331 * into some transparent combined shadow register handling with 338 * into some transparent combined shadow register handling with
332 * CONFIG_PM register storage below, but that's slightly difficult. */ 339 * CONFIG_PM register storage below, but that's slightly difficult. */
333 u16 shadow_reg_ctrl_6AH; 340 u16 shadow_reg_ctrl_6AH;
334 341
335 #ifdef CONFIG_PM 342 #ifdef CONFIG_PM
336 /* register value containers for power management 343 /* register value containers for power management
337 * Note: not always full I/O range preserved (just like Win driver!) */ 344 * Note: not always full I/O range preserved (similar to Win driver!) */
338 u16 saved_regs_ctrl[AZF_IO_SIZE_CTRL_PM / 2]; 345 u32 saved_regs_ctrl[AZF_ALIGN(AZF_IO_SIZE_CTRL_PM) / 4];
339 u16 saved_regs_game [AZF_IO_SIZE_GAME_PM / 2]; 346 u32 saved_regs_game[AZF_ALIGN(AZF_IO_SIZE_GAME_PM) / 4];
340 u16 saved_regs_mpu [AZF_IO_SIZE_MPU_PM / 2]; 347 u32 saved_regs_mpu[AZF_ALIGN(AZF_IO_SIZE_MPU_PM) / 4];
341 u16 saved_regs_opl3 [AZF_IO_SIZE_OPL3_PM / 2]; 348 u32 saved_regs_opl3[AZF_ALIGN(AZF_IO_SIZE_OPL3_PM) / 4];
342 u16 saved_regs_mixer[AZF_IO_SIZE_MIXER_PM / 2]; 349 u32 saved_regs_mixer[AZF_ALIGN(AZF_IO_SIZE_MIXER_PM) / 4];
343 #endif 350 #endif
344 }; 351 };
345 352
346 static const struct pci_device_id snd_azf3328_ids[] = { 353 static const struct pci_device_id snd_azf3328_ids[] = {
347 { 0x122D, 0x50DC, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, /* PCI168/3328 */ 354 { 0x122D, 0x50DC, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, /* PCI168/3328 */
348 { 0x122D, 0x80DA, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, /* 3328 */ 355 { 0x122D, 0x80DA, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 }, /* 3328 */
349 { 0, } 356 { 0, }
350 }; 357 };
351 358
352 MODULE_DEVICE_TABLE(pci, snd_azf3328_ids); 359 MODULE_DEVICE_TABLE(pci, snd_azf3328_ids);
353 360
354 361
355 static int 362 static int
356 snd_azf3328_io_reg_setb(unsigned reg, u8 mask, bool do_set) 363 snd_azf3328_io_reg_setb(unsigned reg, u8 mask, bool do_set)
357 { 364 {
358 u8 prev = inb(reg), new; 365 u8 prev = inb(reg), new;
359 366
360 new = (do_set) ? (prev|mask) : (prev & ~mask); 367 new = (do_set) ? (prev|mask) : (prev & ~mask);
361 /* we need to always write the new value no matter whether it differs 368 /* we need to always write the new value no matter whether it differs
362 * or not, since some register bits don't indicate their setting */ 369 * or not, since some register bits don't indicate their setting */
363 outb(new, reg); 370 outb(new, reg);
364 if (new != prev) 371 if (new != prev)
365 return 1; 372 return 1;
366 373
367 return 0; 374 return 0;
368 } 375 }
369 376
370 static inline void 377 static inline void
371 snd_azf3328_codec_outb(const struct snd_azf3328_codec_data *codec, 378 snd_azf3328_codec_outb(const struct snd_azf3328_codec_data *codec,
372 unsigned reg, 379 unsigned reg,
373 u8 value 380 u8 value
374 ) 381 )
375 { 382 {
376 outb(value, codec->io_base + reg); 383 outb(value, codec->io_base + reg);
377 } 384 }
378 385
379 static inline u8 386 static inline u8
380 snd_azf3328_codec_inb(const struct snd_azf3328_codec_data *codec, unsigned reg) 387 snd_azf3328_codec_inb(const struct snd_azf3328_codec_data *codec, unsigned reg)
381 { 388 {
382 return inb(codec->io_base + reg); 389 return inb(codec->io_base + reg);
383 } 390 }
384 391
385 static inline void 392 static inline void
386 snd_azf3328_codec_outw(const struct snd_azf3328_codec_data *codec, 393 snd_azf3328_codec_outw(const struct snd_azf3328_codec_data *codec,
387 unsigned reg, 394 unsigned reg,
388 u16 value 395 u16 value
389 ) 396 )
390 { 397 {
391 outw(value, codec->io_base + reg); 398 outw(value, codec->io_base + reg);
392 } 399 }
393 400
394 static inline u16 401 static inline u16
395 snd_azf3328_codec_inw(const struct snd_azf3328_codec_data *codec, unsigned reg) 402 snd_azf3328_codec_inw(const struct snd_azf3328_codec_data *codec, unsigned reg)
396 { 403 {
397 return inw(codec->io_base + reg); 404 return inw(codec->io_base + reg);
398 } 405 }
399 406
400 static inline void 407 static inline void
401 snd_azf3328_codec_outl(const struct snd_azf3328_codec_data *codec, 408 snd_azf3328_codec_outl(const struct snd_azf3328_codec_data *codec,
402 unsigned reg, 409 unsigned reg,
403 u32 value 410 u32 value
404 ) 411 )
405 { 412 {
406 outl(value, codec->io_base + reg); 413 outl(value, codec->io_base + reg);
407 } 414 }
408 415
409 static inline u32 416 static inline u32
410 snd_azf3328_codec_inl(const struct snd_azf3328_codec_data *codec, unsigned reg) 417 snd_azf3328_codec_inl(const struct snd_azf3328_codec_data *codec, unsigned reg)
411 { 418 {
412 return inl(codec->io_base + reg); 419 return inl(codec->io_base + reg);
413 } 420 }
414 421
415 static inline void 422 static inline void
416 snd_azf3328_ctrl_outb(const struct snd_azf3328 *chip, unsigned reg, u8 value) 423 snd_azf3328_ctrl_outb(const struct snd_azf3328 *chip, unsigned reg, u8 value)
417 { 424 {
418 outb(value, chip->ctrl_io + reg); 425 outb(value, chip->ctrl_io + reg);
419 } 426 }
420 427
421 static inline u8 428 static inline u8
422 snd_azf3328_ctrl_inb(const struct snd_azf3328 *chip, unsigned reg) 429 snd_azf3328_ctrl_inb(const struct snd_azf3328 *chip, unsigned reg)
423 { 430 {
424 return inb(chip->ctrl_io + reg); 431 return inb(chip->ctrl_io + reg);
425 } 432 }
426 433
427 static inline void 434 static inline void
428 snd_azf3328_ctrl_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value) 435 snd_azf3328_ctrl_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value)
429 { 436 {
430 outw(value, chip->ctrl_io + reg); 437 outw(value, chip->ctrl_io + reg);
431 } 438 }
432 439
433 static inline void 440 static inline void
434 snd_azf3328_ctrl_outl(const struct snd_azf3328 *chip, unsigned reg, u32 value) 441 snd_azf3328_ctrl_outl(const struct snd_azf3328 *chip, unsigned reg, u32 value)
435 { 442 {
436 outl(value, chip->ctrl_io + reg); 443 outl(value, chip->ctrl_io + reg);
437 } 444 }
438 445
439 static inline void 446 static inline void
440 snd_azf3328_game_outb(const struct snd_azf3328 *chip, unsigned reg, u8 value) 447 snd_azf3328_game_outb(const struct snd_azf3328 *chip, unsigned reg, u8 value)
441 { 448 {
442 outb(value, chip->game_io + reg); 449 outb(value, chip->game_io + reg);
443 } 450 }
444 451
445 static inline void 452 static inline void
446 snd_azf3328_game_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value) 453 snd_azf3328_game_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value)
447 { 454 {
448 outw(value, chip->game_io + reg); 455 outw(value, chip->game_io + reg);
449 } 456 }
450 457
451 static inline u8 458 static inline u8
452 snd_azf3328_game_inb(const struct snd_azf3328 *chip, unsigned reg) 459 snd_azf3328_game_inb(const struct snd_azf3328 *chip, unsigned reg)
453 { 460 {
454 return inb(chip->game_io + reg); 461 return inb(chip->game_io + reg);
455 } 462 }
456 463
457 static inline u16 464 static inline u16
458 snd_azf3328_game_inw(const struct snd_azf3328 *chip, unsigned reg) 465 snd_azf3328_game_inw(const struct snd_azf3328 *chip, unsigned reg)
459 { 466 {
460 return inw(chip->game_io + reg); 467 return inw(chip->game_io + reg);
461 } 468 }
462 469
463 static inline void 470 static inline void
464 snd_azf3328_mixer_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value) 471 snd_azf3328_mixer_outw(const struct snd_azf3328 *chip, unsigned reg, u16 value)
465 { 472 {
466 outw(value, chip->mixer_io + reg); 473 outw(value, chip->mixer_io + reg);
467 } 474 }
468 475
469 static inline u16 476 static inline u16
470 snd_azf3328_mixer_inw(const struct snd_azf3328 *chip, unsigned reg) 477 snd_azf3328_mixer_inw(const struct snd_azf3328 *chip, unsigned reg)
471 { 478 {
472 return inw(chip->mixer_io + reg); 479 return inw(chip->mixer_io + reg);
473 } 480 }
474 481
475 #define AZF_MUTE_BIT 0x80 482 #define AZF_MUTE_BIT 0x80
476 483
477 static bool 484 static bool
478 snd_azf3328_mixer_set_mute(const struct snd_azf3328 *chip, 485 snd_azf3328_mixer_set_mute(const struct snd_azf3328 *chip,
479 unsigned reg, bool do_mute 486 unsigned reg, bool do_mute
480 ) 487 )
481 { 488 {
482 unsigned long portbase = chip->mixer_io + reg + 1; 489 unsigned long portbase = chip->mixer_io + reg + 1;
483 bool updated; 490 bool updated;
484 491
485 /* the mute bit is on the *second* (i.e. right) register of a 492 /* the mute bit is on the *second* (i.e. right) register of a
486 * left/right channel setting */ 493 * left/right channel setting */
487 updated = snd_azf3328_io_reg_setb(portbase, AZF_MUTE_BIT, do_mute); 494 updated = snd_azf3328_io_reg_setb(portbase, AZF_MUTE_BIT, do_mute);
488 495
489 /* indicate whether it was muted before */ 496 /* indicate whether it was muted before */
490 return (do_mute) ? !updated : updated; 497 return (do_mute) ? !updated : updated;
491 } 498 }
492 499
493 static void 500 static void
494 snd_azf3328_mixer_write_volume_gradually(const struct snd_azf3328 *chip, 501 snd_azf3328_mixer_write_volume_gradually(const struct snd_azf3328 *chip,
495 unsigned reg, 502 unsigned reg,
496 unsigned char dst_vol_left, 503 unsigned char dst_vol_left,
497 unsigned char dst_vol_right, 504 unsigned char dst_vol_right,
498 int chan_sel, int delay 505 int chan_sel, int delay
499 ) 506 )
500 { 507 {
501 unsigned long portbase = chip->mixer_io + reg; 508 unsigned long portbase = chip->mixer_io + reg;
502 unsigned char curr_vol_left = 0, curr_vol_right = 0; 509 unsigned char curr_vol_left = 0, curr_vol_right = 0;
503 int left_change = 0, right_change = 0; 510 int left_change = 0, right_change = 0;
504 511
505 snd_azf3328_dbgcallenter(); 512 snd_azf3328_dbgcallenter();
506 513
507 if (chan_sel & SET_CHAN_LEFT) { 514 if (chan_sel & SET_CHAN_LEFT) {
508 curr_vol_left = inb(portbase + 1); 515 curr_vol_left = inb(portbase + 1);
509 516
510 /* take care of muting flag contained in left channel */ 517 /* take care of muting flag contained in left channel */
511 if (curr_vol_left & AZF_MUTE_BIT) 518 if (curr_vol_left & AZF_MUTE_BIT)
512 dst_vol_left |= AZF_MUTE_BIT; 519 dst_vol_left |= AZF_MUTE_BIT;
513 else 520 else
514 dst_vol_left &= ~AZF_MUTE_BIT; 521 dst_vol_left &= ~AZF_MUTE_BIT;
515 522
516 left_change = (curr_vol_left > dst_vol_left) ? -1 : 1; 523 left_change = (curr_vol_left > dst_vol_left) ? -1 : 1;
517 } 524 }
518 525
519 if (chan_sel & SET_CHAN_RIGHT) { 526 if (chan_sel & SET_CHAN_RIGHT) {
520 curr_vol_right = inb(portbase + 0); 527 curr_vol_right = inb(portbase + 0);
521 528
522 right_change = (curr_vol_right > dst_vol_right) ? -1 : 1; 529 right_change = (curr_vol_right > dst_vol_right) ? -1 : 1;
523 } 530 }
524 531
525 do { 532 do {
526 if (left_change) { 533 if (left_change) {
527 if (curr_vol_left != dst_vol_left) { 534 if (curr_vol_left != dst_vol_left) {
528 curr_vol_left += left_change; 535 curr_vol_left += left_change;
529 outb(curr_vol_left, portbase + 1); 536 outb(curr_vol_left, portbase + 1);
530 } else 537 } else
531 left_change = 0; 538 left_change = 0;
532 } 539 }
533 if (right_change) { 540 if (right_change) {
534 if (curr_vol_right != dst_vol_right) { 541 if (curr_vol_right != dst_vol_right) {
535 curr_vol_right += right_change; 542 curr_vol_right += right_change;
536 543
537 /* during volume change, the right channel is crackling 544 /* during volume change, the right channel is crackling
538 * somewhat more than the left channel, unfortunately. 545 * somewhat more than the left channel, unfortunately.
539 * This seems to be a hardware issue. */ 546 * This seems to be a hardware issue. */
540 outb(curr_vol_right, portbase + 0); 547 outb(curr_vol_right, portbase + 0);
541 } else 548 } else
542 right_change = 0; 549 right_change = 0;
543 } 550 }
544 if (delay) 551 if (delay)
545 mdelay(delay); 552 mdelay(delay);
546 } while ((left_change) || (right_change)); 553 } while ((left_change) || (right_change));
547 snd_azf3328_dbgcallleave(); 554 snd_azf3328_dbgcallleave();
548 } 555 }
549 556
550 /* 557 /*
551 * general mixer element 558 * general mixer element
552 */ 559 */
553 struct azf3328_mixer_reg { 560 struct azf3328_mixer_reg {
554 unsigned reg; 561 unsigned reg;
555 unsigned int lchan_shift, rchan_shift; 562 unsigned int lchan_shift, rchan_shift;
556 unsigned int mask; 563 unsigned int mask;
557 unsigned int invert: 1; 564 unsigned int invert: 1;
558 unsigned int stereo: 1; 565 unsigned int stereo: 1;
559 unsigned int enum_c: 4; 566 unsigned int enum_c: 4;
560 }; 567 };
561 568
562 #define COMPOSE_MIXER_REG(reg,lchan_shift,rchan_shift,mask,invert,stereo,enum_c) \ 569 #define COMPOSE_MIXER_REG(reg,lchan_shift,rchan_shift,mask,invert,stereo,enum_c) \
563 ((reg) | (lchan_shift << 8) | (rchan_shift << 12) | \ 570 ((reg) | (lchan_shift << 8) | (rchan_shift << 12) | \
564 (mask << 16) | \ 571 (mask << 16) | \
565 (invert << 24) | \ 572 (invert << 24) | \
566 (stereo << 25) | \ 573 (stereo << 25) | \
567 (enum_c << 26)) 574 (enum_c << 26))
568 575
569 static void snd_azf3328_mixer_reg_decode(struct azf3328_mixer_reg *r, unsigned long val) 576 static void snd_azf3328_mixer_reg_decode(struct azf3328_mixer_reg *r, unsigned long val)
570 { 577 {
571 r->reg = val & 0xff; 578 r->reg = val & 0xff;
572 r->lchan_shift = (val >> 8) & 0x0f; 579 r->lchan_shift = (val >> 8) & 0x0f;
573 r->rchan_shift = (val >> 12) & 0x0f; 580 r->rchan_shift = (val >> 12) & 0x0f;
574 r->mask = (val >> 16) & 0xff; 581 r->mask = (val >> 16) & 0xff;
575 r->invert = (val >> 24) & 1; 582 r->invert = (val >> 24) & 1;
576 r->stereo = (val >> 25) & 1; 583 r->stereo = (val >> 25) & 1;
577 r->enum_c = (val >> 26) & 0x0f; 584 r->enum_c = (val >> 26) & 0x0f;
578 } 585 }
579 586
580 /* 587 /*
581 * mixer switches/volumes 588 * mixer switches/volumes
582 */ 589 */
583 590
584 #define AZF3328_MIXER_SWITCH(xname, reg, shift, invert) \ 591 #define AZF3328_MIXER_SWITCH(xname, reg, shift, invert) \
585 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ 592 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
586 .info = snd_azf3328_info_mixer, \ 593 .info = snd_azf3328_info_mixer, \
587 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \ 594 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \
588 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, 0x1, invert, 0, 0), \ 595 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, 0x1, invert, 0, 0), \
589 } 596 }
590 597
591 #define AZF3328_MIXER_VOL_STEREO(xname, reg, mask, invert) \ 598 #define AZF3328_MIXER_VOL_STEREO(xname, reg, mask, invert) \
592 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ 599 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
593 .info = snd_azf3328_info_mixer, \ 600 .info = snd_azf3328_info_mixer, \
594 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \ 601 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \
595 .private_value = COMPOSE_MIXER_REG(reg, 8, 0, mask, invert, 1, 0), \ 602 .private_value = COMPOSE_MIXER_REG(reg, 8, 0, mask, invert, 1, 0), \
596 } 603 }
597 604
598 #define AZF3328_MIXER_VOL_MONO(xname, reg, mask, is_right_chan) \ 605 #define AZF3328_MIXER_VOL_MONO(xname, reg, mask, is_right_chan) \
599 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ 606 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
600 .info = snd_azf3328_info_mixer, \ 607 .info = snd_azf3328_info_mixer, \
601 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \ 608 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \
602 .private_value = COMPOSE_MIXER_REG(reg, is_right_chan ? 0 : 8, 0, mask, 1, 0, 0), \ 609 .private_value = COMPOSE_MIXER_REG(reg, is_right_chan ? 0 : 8, 0, mask, 1, 0, 0), \
603 } 610 }
604 611
605 #define AZF3328_MIXER_VOL_SPECIAL(xname, reg, mask, shift, invert) \ 612 #define AZF3328_MIXER_VOL_SPECIAL(xname, reg, mask, shift, invert) \
606 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ 613 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
607 .info = snd_azf3328_info_mixer, \ 614 .info = snd_azf3328_info_mixer, \
608 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \ 615 .get = snd_azf3328_get_mixer, .put = snd_azf3328_put_mixer, \
609 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, mask, invert, 0, 0), \ 616 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, mask, invert, 0, 0), \
610 } 617 }
611 618
612 #define AZF3328_MIXER_ENUM(xname, reg, enum_c, shift) \ 619 #define AZF3328_MIXER_ENUM(xname, reg, enum_c, shift) \
613 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \ 620 { .iface = SNDRV_CTL_ELEM_IFACE_MIXER, .name = xname, \
614 .info = snd_azf3328_info_mixer_enum, \ 621 .info = snd_azf3328_info_mixer_enum, \
615 .get = snd_azf3328_get_mixer_enum, .put = snd_azf3328_put_mixer_enum, \ 622 .get = snd_azf3328_get_mixer_enum, .put = snd_azf3328_put_mixer_enum, \
616 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, 0, 0, 0, enum_c), \ 623 .private_value = COMPOSE_MIXER_REG(reg, shift, 0, 0, 0, 0, enum_c), \
617 } 624 }
618 625
619 static int 626 static int
620 snd_azf3328_info_mixer(struct snd_kcontrol *kcontrol, 627 snd_azf3328_info_mixer(struct snd_kcontrol *kcontrol,
621 struct snd_ctl_elem_info *uinfo) 628 struct snd_ctl_elem_info *uinfo)
622 { 629 {
623 struct azf3328_mixer_reg reg; 630 struct azf3328_mixer_reg reg;
624 631
625 snd_azf3328_dbgcallenter(); 632 snd_azf3328_dbgcallenter();
626 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 633 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
627 uinfo->type = reg.mask == 1 ? 634 uinfo->type = reg.mask == 1 ?
628 SNDRV_CTL_ELEM_TYPE_BOOLEAN : SNDRV_CTL_ELEM_TYPE_INTEGER; 635 SNDRV_CTL_ELEM_TYPE_BOOLEAN : SNDRV_CTL_ELEM_TYPE_INTEGER;
629 uinfo->count = reg.stereo + 1; 636 uinfo->count = reg.stereo + 1;
630 uinfo->value.integer.min = 0; 637 uinfo->value.integer.min = 0;
631 uinfo->value.integer.max = reg.mask; 638 uinfo->value.integer.max = reg.mask;
632 snd_azf3328_dbgcallleave(); 639 snd_azf3328_dbgcallleave();
633 return 0; 640 return 0;
634 } 641 }
635 642
636 static int 643 static int
637 snd_azf3328_get_mixer(struct snd_kcontrol *kcontrol, 644 snd_azf3328_get_mixer(struct snd_kcontrol *kcontrol,
638 struct snd_ctl_elem_value *ucontrol) 645 struct snd_ctl_elem_value *ucontrol)
639 { 646 {
640 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol); 647 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol);
641 struct azf3328_mixer_reg reg; 648 struct azf3328_mixer_reg reg;
642 u16 oreg, val; 649 u16 oreg, val;
643 650
644 snd_azf3328_dbgcallenter(); 651 snd_azf3328_dbgcallenter();
645 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 652 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
646 653
647 oreg = snd_azf3328_mixer_inw(chip, reg.reg); 654 oreg = snd_azf3328_mixer_inw(chip, reg.reg);
648 val = (oreg >> reg.lchan_shift) & reg.mask; 655 val = (oreg >> reg.lchan_shift) & reg.mask;
649 if (reg.invert) 656 if (reg.invert)
650 val = reg.mask - val; 657 val = reg.mask - val;
651 ucontrol->value.integer.value[0] = val; 658 ucontrol->value.integer.value[0] = val;
652 if (reg.stereo) { 659 if (reg.stereo) {
653 val = (oreg >> reg.rchan_shift) & reg.mask; 660 val = (oreg >> reg.rchan_shift) & reg.mask;
654 if (reg.invert) 661 if (reg.invert)
655 val = reg.mask - val; 662 val = reg.mask - val;
656 ucontrol->value.integer.value[1] = val; 663 ucontrol->value.integer.value[1] = val;
657 } 664 }
658 snd_azf3328_dbgmixer("get: %02x is %04x -> vol %02lx|%02lx " 665 snd_azf3328_dbgmixer("get: %02x is %04x -> vol %02lx|%02lx "
659 "(shift %02d|%02d, mask %02x, inv. %d, stereo %d)\n", 666 "(shift %02d|%02d, mask %02x, inv. %d, stereo %d)\n",
660 reg.reg, oreg, 667 reg.reg, oreg,
661 ucontrol->value.integer.value[0], ucontrol->value.integer.value[1], 668 ucontrol->value.integer.value[0], ucontrol->value.integer.value[1],
662 reg.lchan_shift, reg.rchan_shift, reg.mask, reg.invert, reg.stereo); 669 reg.lchan_shift, reg.rchan_shift, reg.mask, reg.invert, reg.stereo);
663 snd_azf3328_dbgcallleave(); 670 snd_azf3328_dbgcallleave();
664 return 0; 671 return 0;
665 } 672 }
666 673
667 static int 674 static int
668 snd_azf3328_put_mixer(struct snd_kcontrol *kcontrol, 675 snd_azf3328_put_mixer(struct snd_kcontrol *kcontrol,
669 struct snd_ctl_elem_value *ucontrol) 676 struct snd_ctl_elem_value *ucontrol)
670 { 677 {
671 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol); 678 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol);
672 struct azf3328_mixer_reg reg; 679 struct azf3328_mixer_reg reg;
673 u16 oreg, nreg, val; 680 u16 oreg, nreg, val;
674 681
675 snd_azf3328_dbgcallenter(); 682 snd_azf3328_dbgcallenter();
676 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 683 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
677 oreg = snd_azf3328_mixer_inw(chip, reg.reg); 684 oreg = snd_azf3328_mixer_inw(chip, reg.reg);
678 val = ucontrol->value.integer.value[0] & reg.mask; 685 val = ucontrol->value.integer.value[0] & reg.mask;
679 if (reg.invert) 686 if (reg.invert)
680 val = reg.mask - val; 687 val = reg.mask - val;
681 nreg = oreg & ~(reg.mask << reg.lchan_shift); 688 nreg = oreg & ~(reg.mask << reg.lchan_shift);
682 nreg |= (val << reg.lchan_shift); 689 nreg |= (val << reg.lchan_shift);
683 if (reg.stereo) { 690 if (reg.stereo) {
684 val = ucontrol->value.integer.value[1] & reg.mask; 691 val = ucontrol->value.integer.value[1] & reg.mask;
685 if (reg.invert) 692 if (reg.invert)
686 val = reg.mask - val; 693 val = reg.mask - val;
687 nreg &= ~(reg.mask << reg.rchan_shift); 694 nreg &= ~(reg.mask << reg.rchan_shift);
688 nreg |= (val << reg.rchan_shift); 695 nreg |= (val << reg.rchan_shift);
689 } 696 }
690 if (reg.mask >= 0x07) /* it's a volume control, so better take care */ 697 if (reg.mask >= 0x07) /* it's a volume control, so better take care */
691 snd_azf3328_mixer_write_volume_gradually( 698 snd_azf3328_mixer_write_volume_gradually(
692 chip, reg.reg, nreg >> 8, nreg & 0xff, 699 chip, reg.reg, nreg >> 8, nreg & 0xff,
693 /* just set both channels, doesn't matter */ 700 /* just set both channels, doesn't matter */
694 SET_CHAN_LEFT|SET_CHAN_RIGHT, 701 SET_CHAN_LEFT|SET_CHAN_RIGHT,
695 0); 702 0);
696 else 703 else
697 snd_azf3328_mixer_outw(chip, reg.reg, nreg); 704 snd_azf3328_mixer_outw(chip, reg.reg, nreg);
698 705
699 snd_azf3328_dbgmixer("put: %02x to %02lx|%02lx, " 706 snd_azf3328_dbgmixer("put: %02x to %02lx|%02lx, "
700 "oreg %04x; shift %02d|%02d -> nreg %04x; after: %04x\n", 707 "oreg %04x; shift %02d|%02d -> nreg %04x; after: %04x\n",
701 reg.reg, ucontrol->value.integer.value[0], ucontrol->value.integer.value[1], 708 reg.reg, ucontrol->value.integer.value[0], ucontrol->value.integer.value[1],
702 oreg, reg.lchan_shift, reg.rchan_shift, 709 oreg, reg.lchan_shift, reg.rchan_shift,
703 nreg, snd_azf3328_mixer_inw(chip, reg.reg)); 710 nreg, snd_azf3328_mixer_inw(chip, reg.reg));
704 snd_azf3328_dbgcallleave(); 711 snd_azf3328_dbgcallleave();
705 return (nreg != oreg); 712 return (nreg != oreg);
706 } 713 }
707 714
708 static int 715 static int
709 snd_azf3328_info_mixer_enum(struct snd_kcontrol *kcontrol, 716 snd_azf3328_info_mixer_enum(struct snd_kcontrol *kcontrol,
710 struct snd_ctl_elem_info *uinfo) 717 struct snd_ctl_elem_info *uinfo)
711 { 718 {
712 static const char * const texts1[] = { 719 static const char * const texts1[] = {
713 "Mic1", "Mic2" 720 "Mic1", "Mic2"
714 }; 721 };
715 static const char * const texts2[] = { 722 static const char * const texts2[] = {
716 "Mix", "Mic" 723 "Mix", "Mic"
717 }; 724 };
718 static const char * const texts3[] = { 725 static const char * const texts3[] = {
719 "Mic", "CD", "Video", "Aux", 726 "Mic", "CD", "Video", "Aux",
720 "Line", "Mix", "Mix Mono", "Phone" 727 "Line", "Mix", "Mix Mono", "Phone"
721 }; 728 };
722 static const char * const texts4[] = { 729 static const char * const texts4[] = {
723 "pre 3D", "post 3D" 730 "pre 3D", "post 3D"
724 }; 731 };
725 struct azf3328_mixer_reg reg; 732 struct azf3328_mixer_reg reg;
726 const char * const *p = NULL; 733 const char * const *p = NULL;
727 734
728 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 735 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
729 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED; 736 uinfo->type = SNDRV_CTL_ELEM_TYPE_ENUMERATED;
730 uinfo->count = (reg.reg == IDX_MIXER_REC_SELECT) ? 2 : 1; 737 uinfo->count = (reg.reg == IDX_MIXER_REC_SELECT) ? 2 : 1;
731 uinfo->value.enumerated.items = reg.enum_c; 738 uinfo->value.enumerated.items = reg.enum_c;
732 if (uinfo->value.enumerated.item > reg.enum_c - 1U) 739 if (uinfo->value.enumerated.item > reg.enum_c - 1U)
733 uinfo->value.enumerated.item = reg.enum_c - 1U; 740 uinfo->value.enumerated.item = reg.enum_c - 1U;
734 if (reg.reg == IDX_MIXER_ADVCTL2) { 741 if (reg.reg == IDX_MIXER_ADVCTL2) {
735 switch(reg.lchan_shift) { 742 switch(reg.lchan_shift) {
736 case 8: /* modem out sel */ 743 case 8: /* modem out sel */
737 p = texts1; 744 p = texts1;
738 break; 745 break;
739 case 9: /* mono sel source */ 746 case 9: /* mono sel source */
740 p = texts2; 747 p = texts2;
741 break; 748 break;
742 case 15: /* PCM Out Path */ 749 case 15: /* PCM Out Path */
743 p = texts4; 750 p = texts4;
744 break; 751 break;
745 } 752 }
746 } else 753 } else
747 if (reg.reg == IDX_MIXER_REC_SELECT) 754 if (reg.reg == IDX_MIXER_REC_SELECT)
748 p = texts3; 755 p = texts3;
749 756
750 strcpy(uinfo->value.enumerated.name, p[uinfo->value.enumerated.item]); 757 strcpy(uinfo->value.enumerated.name, p[uinfo->value.enumerated.item]);
751 return 0; 758 return 0;
752 } 759 }
753 760
754 static int 761 static int
755 snd_azf3328_get_mixer_enum(struct snd_kcontrol *kcontrol, 762 snd_azf3328_get_mixer_enum(struct snd_kcontrol *kcontrol,
756 struct snd_ctl_elem_value *ucontrol) 763 struct snd_ctl_elem_value *ucontrol)
757 { 764 {
758 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol); 765 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol);
759 struct azf3328_mixer_reg reg; 766 struct azf3328_mixer_reg reg;
760 unsigned short val; 767 unsigned short val;
761 768
762 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 769 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
763 val = snd_azf3328_mixer_inw(chip, reg.reg); 770 val = snd_azf3328_mixer_inw(chip, reg.reg);
764 if (reg.reg == IDX_MIXER_REC_SELECT) { 771 if (reg.reg == IDX_MIXER_REC_SELECT) {
765 ucontrol->value.enumerated.item[0] = (val >> 8) & (reg.enum_c - 1); 772 ucontrol->value.enumerated.item[0] = (val >> 8) & (reg.enum_c - 1);
766 ucontrol->value.enumerated.item[1] = (val >> 0) & (reg.enum_c - 1); 773 ucontrol->value.enumerated.item[1] = (val >> 0) & (reg.enum_c - 1);
767 } else 774 } else
768 ucontrol->value.enumerated.item[0] = (val >> reg.lchan_shift) & (reg.enum_c - 1); 775 ucontrol->value.enumerated.item[0] = (val >> reg.lchan_shift) & (reg.enum_c - 1);
769 776
770 snd_azf3328_dbgmixer("get_enum: %02x is %04x -> %d|%d (shift %02d, enum_c %d)\n", 777 snd_azf3328_dbgmixer("get_enum: %02x is %04x -> %d|%d (shift %02d, enum_c %d)\n",
771 reg.reg, val, ucontrol->value.enumerated.item[0], ucontrol->value.enumerated.item[1], 778 reg.reg, val, ucontrol->value.enumerated.item[0], ucontrol->value.enumerated.item[1],
772 reg.lchan_shift, reg.enum_c); 779 reg.lchan_shift, reg.enum_c);
773 return 0; 780 return 0;
774 } 781 }
775 782
776 static int 783 static int
777 snd_azf3328_put_mixer_enum(struct snd_kcontrol *kcontrol, 784 snd_azf3328_put_mixer_enum(struct snd_kcontrol *kcontrol,
778 struct snd_ctl_elem_value *ucontrol) 785 struct snd_ctl_elem_value *ucontrol)
779 { 786 {
780 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol); 787 struct snd_azf3328 *chip = snd_kcontrol_chip(kcontrol);
781 struct azf3328_mixer_reg reg; 788 struct azf3328_mixer_reg reg;
782 u16 oreg, nreg, val; 789 u16 oreg, nreg, val;
783 790
784 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value); 791 snd_azf3328_mixer_reg_decode(&reg, kcontrol->private_value);
785 oreg = snd_azf3328_mixer_inw(chip, reg.reg); 792 oreg = snd_azf3328_mixer_inw(chip, reg.reg);
786 val = oreg; 793 val = oreg;
787 if (reg.reg == IDX_MIXER_REC_SELECT) { 794 if (reg.reg == IDX_MIXER_REC_SELECT) {
788 if (ucontrol->value.enumerated.item[0] > reg.enum_c - 1U || 795 if (ucontrol->value.enumerated.item[0] > reg.enum_c - 1U ||
789 ucontrol->value.enumerated.item[1] > reg.enum_c - 1U) 796 ucontrol->value.enumerated.item[1] > reg.enum_c - 1U)
790 return -EINVAL; 797 return -EINVAL;
791 val = (ucontrol->value.enumerated.item[0] << 8) | 798 val = (ucontrol->value.enumerated.item[0] << 8) |
792 (ucontrol->value.enumerated.item[1] << 0); 799 (ucontrol->value.enumerated.item[1] << 0);
793 } else { 800 } else {
794 if (ucontrol->value.enumerated.item[0] > reg.enum_c - 1U) 801 if (ucontrol->value.enumerated.item[0] > reg.enum_c - 1U)
795 return -EINVAL; 802 return -EINVAL;
796 val &= ~((reg.enum_c - 1) << reg.lchan_shift); 803 val &= ~((reg.enum_c - 1) << reg.lchan_shift);
797 val |= (ucontrol->value.enumerated.item[0] << reg.lchan_shift); 804 val |= (ucontrol->value.enumerated.item[0] << reg.lchan_shift);
798 } 805 }
799 snd_azf3328_mixer_outw(chip, reg.reg, val); 806 snd_azf3328_mixer_outw(chip, reg.reg, val);
800 nreg = val; 807 nreg = val;
801 808
802 snd_azf3328_dbgmixer("put_enum: %02x to %04x, oreg %04x\n", reg.reg, val, oreg); 809 snd_azf3328_dbgmixer("put_enum: %02x to %04x, oreg %04x\n", reg.reg, val, oreg);
803 return (nreg != oreg); 810 return (nreg != oreg);
804 } 811 }
805 812
806 static struct snd_kcontrol_new snd_azf3328_mixer_controls[] __devinitdata = { 813 static struct snd_kcontrol_new snd_azf3328_mixer_controls[] __devinitdata = {
807 AZF3328_MIXER_SWITCH("Master Playback Switch", IDX_MIXER_PLAY_MASTER, 15, 1), 814 AZF3328_MIXER_SWITCH("Master Playback Switch", IDX_MIXER_PLAY_MASTER, 15, 1),
808 AZF3328_MIXER_VOL_STEREO("Master Playback Volume", IDX_MIXER_PLAY_MASTER, 0x1f, 1), 815 AZF3328_MIXER_VOL_STEREO("Master Playback Volume", IDX_MIXER_PLAY_MASTER, 0x1f, 1),
809 AZF3328_MIXER_SWITCH("PCM Playback Switch", IDX_MIXER_WAVEOUT, 15, 1), 816 AZF3328_MIXER_SWITCH("PCM Playback Switch", IDX_MIXER_WAVEOUT, 15, 1),
810 AZF3328_MIXER_VOL_STEREO("PCM Playback Volume", 817 AZF3328_MIXER_VOL_STEREO("PCM Playback Volume",
811 IDX_MIXER_WAVEOUT, 0x1f, 1), 818 IDX_MIXER_WAVEOUT, 0x1f, 1),
812 AZF3328_MIXER_SWITCH("PCM 3D Bypass Playback Switch", 819 AZF3328_MIXER_SWITCH("PCM 3D Bypass Playback Switch",
813 IDX_MIXER_ADVCTL2, 7, 1), 820 IDX_MIXER_ADVCTL2, 7, 1),
814 AZF3328_MIXER_SWITCH("FM Playback Switch", IDX_MIXER_FMSYNTH, 15, 1), 821 AZF3328_MIXER_SWITCH("FM Playback Switch", IDX_MIXER_FMSYNTH, 15, 1),
815 AZF3328_MIXER_VOL_STEREO("FM Playback Volume", IDX_MIXER_FMSYNTH, 0x1f, 1), 822 AZF3328_MIXER_VOL_STEREO("FM Playback Volume", IDX_MIXER_FMSYNTH, 0x1f, 1),
816 AZF3328_MIXER_SWITCH("CD Playback Switch", IDX_MIXER_CDAUDIO, 15, 1), 823 AZF3328_MIXER_SWITCH("CD Playback Switch", IDX_MIXER_CDAUDIO, 15, 1),
817 AZF3328_MIXER_VOL_STEREO("CD Playback Volume", IDX_MIXER_CDAUDIO, 0x1f, 1), 824 AZF3328_MIXER_VOL_STEREO("CD Playback Volume", IDX_MIXER_CDAUDIO, 0x1f, 1),
818 AZF3328_MIXER_SWITCH("Capture Switch", IDX_MIXER_REC_VOLUME, 15, 1), 825 AZF3328_MIXER_SWITCH("Capture Switch", IDX_MIXER_REC_VOLUME, 15, 1),
819 AZF3328_MIXER_VOL_STEREO("Capture Volume", IDX_MIXER_REC_VOLUME, 0x0f, 0), 826 AZF3328_MIXER_VOL_STEREO("Capture Volume", IDX_MIXER_REC_VOLUME, 0x0f, 0),
820 AZF3328_MIXER_ENUM("Capture Source", IDX_MIXER_REC_SELECT, 8, 0), 827 AZF3328_MIXER_ENUM("Capture Source", IDX_MIXER_REC_SELECT, 8, 0),
821 AZF3328_MIXER_SWITCH("Mic Playback Switch", IDX_MIXER_MIC, 15, 1), 828 AZF3328_MIXER_SWITCH("Mic Playback Switch", IDX_MIXER_MIC, 15, 1),
822 AZF3328_MIXER_VOL_MONO("Mic Playback Volume", IDX_MIXER_MIC, 0x1f, 1), 829 AZF3328_MIXER_VOL_MONO("Mic Playback Volume", IDX_MIXER_MIC, 0x1f, 1),
823 AZF3328_MIXER_SWITCH("Mic Boost (+20dB)", IDX_MIXER_MIC, 6, 0), 830 AZF3328_MIXER_SWITCH("Mic Boost (+20dB)", IDX_MIXER_MIC, 6, 0),
824 AZF3328_MIXER_SWITCH("Line Playback Switch", IDX_MIXER_LINEIN, 15, 1), 831 AZF3328_MIXER_SWITCH("Line Playback Switch", IDX_MIXER_LINEIN, 15, 1),
825 AZF3328_MIXER_VOL_STEREO("Line Playback Volume", IDX_MIXER_LINEIN, 0x1f, 1), 832 AZF3328_MIXER_VOL_STEREO("Line Playback Volume", IDX_MIXER_LINEIN, 0x1f, 1),
826 AZF3328_MIXER_SWITCH("PC Speaker Playback Switch", IDX_MIXER_PCBEEP, 15, 1), 833 AZF3328_MIXER_SWITCH("PC Speaker Playback Switch", IDX_MIXER_PCBEEP, 15, 1),
827 AZF3328_MIXER_VOL_SPECIAL("PC Speaker Playback Volume", IDX_MIXER_PCBEEP, 0x0f, 1, 1), 834 AZF3328_MIXER_VOL_SPECIAL("PC Speaker Playback Volume", IDX_MIXER_PCBEEP, 0x0f, 1, 1),
828 AZF3328_MIXER_SWITCH("Video Playback Switch", IDX_MIXER_VIDEO, 15, 1), 835 AZF3328_MIXER_SWITCH("Video Playback Switch", IDX_MIXER_VIDEO, 15, 1),
829 AZF3328_MIXER_VOL_STEREO("Video Playback Volume", IDX_MIXER_VIDEO, 0x1f, 1), 836 AZF3328_MIXER_VOL_STEREO("Video Playback Volume", IDX_MIXER_VIDEO, 0x1f, 1),
830 AZF3328_MIXER_SWITCH("Aux Playback Switch", IDX_MIXER_AUX, 15, 1), 837 AZF3328_MIXER_SWITCH("Aux Playback Switch", IDX_MIXER_AUX, 15, 1),
831 AZF3328_MIXER_VOL_STEREO("Aux Playback Volume", IDX_MIXER_AUX, 0x1f, 1), 838 AZF3328_MIXER_VOL_STEREO("Aux Playback Volume", IDX_MIXER_AUX, 0x1f, 1),
832 AZF3328_MIXER_SWITCH("Modem Playback Switch", IDX_MIXER_MODEMOUT, 15, 1), 839 AZF3328_MIXER_SWITCH("Modem Playback Switch", IDX_MIXER_MODEMOUT, 15, 1),
833 AZF3328_MIXER_VOL_MONO("Modem Playback Volume", IDX_MIXER_MODEMOUT, 0x1f, 1), 840 AZF3328_MIXER_VOL_MONO("Modem Playback Volume", IDX_MIXER_MODEMOUT, 0x1f, 1),
834 AZF3328_MIXER_SWITCH("Modem Capture Switch", IDX_MIXER_MODEMIN, 15, 1), 841 AZF3328_MIXER_SWITCH("Modem Capture Switch", IDX_MIXER_MODEMIN, 15, 1),
835 AZF3328_MIXER_VOL_MONO("Modem Capture Volume", IDX_MIXER_MODEMIN, 0x1f, 1), 842 AZF3328_MIXER_VOL_MONO("Modem Capture Volume", IDX_MIXER_MODEMIN, 0x1f, 1),
836 AZF3328_MIXER_ENUM("Mic Select", IDX_MIXER_ADVCTL2, 2, 8), 843 AZF3328_MIXER_ENUM("Mic Select", IDX_MIXER_ADVCTL2, 2, 8),
837 AZF3328_MIXER_ENUM("Mono Output Select", IDX_MIXER_ADVCTL2, 2, 9), 844 AZF3328_MIXER_ENUM("Mono Output Select", IDX_MIXER_ADVCTL2, 2, 9),
838 AZF3328_MIXER_ENUM("PCM Output Route", IDX_MIXER_ADVCTL2, 2, 15), /* PCM Out Path, place in front since it controls *both* 3D and Bass/Treble! */ 845 AZF3328_MIXER_ENUM("PCM Output Route", IDX_MIXER_ADVCTL2, 2, 15), /* PCM Out Path, place in front since it controls *both* 3D and Bass/Treble! */
839 AZF3328_MIXER_VOL_SPECIAL("Tone Control - Treble", IDX_MIXER_BASSTREBLE, 0x07, 1, 0), 846 AZF3328_MIXER_VOL_SPECIAL("Tone Control - Treble", IDX_MIXER_BASSTREBLE, 0x07, 1, 0),
840 AZF3328_MIXER_VOL_SPECIAL("Tone Control - Bass", IDX_MIXER_BASSTREBLE, 0x07, 9, 0), 847 AZF3328_MIXER_VOL_SPECIAL("Tone Control - Bass", IDX_MIXER_BASSTREBLE, 0x07, 9, 0),
841 AZF3328_MIXER_SWITCH("3D Control - Switch", IDX_MIXER_ADVCTL2, 13, 0), 848 AZF3328_MIXER_SWITCH("3D Control - Switch", IDX_MIXER_ADVCTL2, 13, 0),
842 AZF3328_MIXER_VOL_SPECIAL("3D Control - Width", IDX_MIXER_ADVCTL1, 0x07, 1, 0), /* "3D Width" */ 849 AZF3328_MIXER_VOL_SPECIAL("3D Control - Width", IDX_MIXER_ADVCTL1, 0x07, 1, 0), /* "3D Width" */
843 AZF3328_MIXER_VOL_SPECIAL("3D Control - Depth", IDX_MIXER_ADVCTL1, 0x03, 8, 0), /* "Hifi 3D" */ 850 AZF3328_MIXER_VOL_SPECIAL("3D Control - Depth", IDX_MIXER_ADVCTL1, 0x03, 8, 0), /* "Hifi 3D" */
844 #if MIXER_TESTING 851 #if MIXER_TESTING
845 AZF3328_MIXER_SWITCH("0", IDX_MIXER_ADVCTL2, 0, 0), 852 AZF3328_MIXER_SWITCH("0", IDX_MIXER_ADVCTL2, 0, 0),
846 AZF3328_MIXER_SWITCH("1", IDX_MIXER_ADVCTL2, 1, 0), 853 AZF3328_MIXER_SWITCH("1", IDX_MIXER_ADVCTL2, 1, 0),
847 AZF3328_MIXER_SWITCH("2", IDX_MIXER_ADVCTL2, 2, 0), 854 AZF3328_MIXER_SWITCH("2", IDX_MIXER_ADVCTL2, 2, 0),
848 AZF3328_MIXER_SWITCH("3", IDX_MIXER_ADVCTL2, 3, 0), 855 AZF3328_MIXER_SWITCH("3", IDX_MIXER_ADVCTL2, 3, 0),
849 AZF3328_MIXER_SWITCH("4", IDX_MIXER_ADVCTL2, 4, 0), 856 AZF3328_MIXER_SWITCH("4", IDX_MIXER_ADVCTL2, 4, 0),
850 AZF3328_MIXER_SWITCH("5", IDX_MIXER_ADVCTL2, 5, 0), 857 AZF3328_MIXER_SWITCH("5", IDX_MIXER_ADVCTL2, 5, 0),
851 AZF3328_MIXER_SWITCH("6", IDX_MIXER_ADVCTL2, 6, 0), 858 AZF3328_MIXER_SWITCH("6", IDX_MIXER_ADVCTL2, 6, 0),
852 AZF3328_MIXER_SWITCH("7", IDX_MIXER_ADVCTL2, 7, 0), 859 AZF3328_MIXER_SWITCH("7", IDX_MIXER_ADVCTL2, 7, 0),
853 AZF3328_MIXER_SWITCH("8", IDX_MIXER_ADVCTL2, 8, 0), 860 AZF3328_MIXER_SWITCH("8", IDX_MIXER_ADVCTL2, 8, 0),
854 AZF3328_MIXER_SWITCH("9", IDX_MIXER_ADVCTL2, 9, 0), 861 AZF3328_MIXER_SWITCH("9", IDX_MIXER_ADVCTL2, 9, 0),
855 AZF3328_MIXER_SWITCH("10", IDX_MIXER_ADVCTL2, 10, 0), 862 AZF3328_MIXER_SWITCH("10", IDX_MIXER_ADVCTL2, 10, 0),
856 AZF3328_MIXER_SWITCH("11", IDX_MIXER_ADVCTL2, 11, 0), 863 AZF3328_MIXER_SWITCH("11", IDX_MIXER_ADVCTL2, 11, 0),
857 AZF3328_MIXER_SWITCH("12", IDX_MIXER_ADVCTL2, 12, 0), 864 AZF3328_MIXER_SWITCH("12", IDX_MIXER_ADVCTL2, 12, 0),
858 AZF3328_MIXER_SWITCH("13", IDX_MIXER_ADVCTL2, 13, 0), 865 AZF3328_MIXER_SWITCH("13", IDX_MIXER_ADVCTL2, 13, 0),
859 AZF3328_MIXER_SWITCH("14", IDX_MIXER_ADVCTL2, 14, 0), 866 AZF3328_MIXER_SWITCH("14", IDX_MIXER_ADVCTL2, 14, 0),
860 AZF3328_MIXER_SWITCH("15", IDX_MIXER_ADVCTL2, 15, 0), 867 AZF3328_MIXER_SWITCH("15", IDX_MIXER_ADVCTL2, 15, 0),
861 #endif 868 #endif
862 }; 869 };
863 870
864 static u16 __devinitdata snd_azf3328_init_values[][2] = { 871 static u16 __devinitdata snd_azf3328_init_values[][2] = {
865 { IDX_MIXER_PLAY_MASTER, MIXER_MUTE_MASK|0x1f1f }, 872 { IDX_MIXER_PLAY_MASTER, MIXER_MUTE_MASK|0x1f1f },
866 { IDX_MIXER_MODEMOUT, MIXER_MUTE_MASK|0x1f1f }, 873 { IDX_MIXER_MODEMOUT, MIXER_MUTE_MASK|0x1f1f },
867 { IDX_MIXER_BASSTREBLE, 0x0000 }, 874 { IDX_MIXER_BASSTREBLE, 0x0000 },
868 { IDX_MIXER_PCBEEP, MIXER_MUTE_MASK|0x1f1f }, 875 { IDX_MIXER_PCBEEP, MIXER_MUTE_MASK|0x1f1f },
869 { IDX_MIXER_MODEMIN, MIXER_MUTE_MASK|0x1f1f }, 876 { IDX_MIXER_MODEMIN, MIXER_MUTE_MASK|0x1f1f },
870 { IDX_MIXER_MIC, MIXER_MUTE_MASK|0x001f }, 877 { IDX_MIXER_MIC, MIXER_MUTE_MASK|0x001f },
871 { IDX_MIXER_LINEIN, MIXER_MUTE_MASK|0x1f1f }, 878 { IDX_MIXER_LINEIN, MIXER_MUTE_MASK|0x1f1f },
872 { IDX_MIXER_CDAUDIO, MIXER_MUTE_MASK|0x1f1f }, 879 { IDX_MIXER_CDAUDIO, MIXER_MUTE_MASK|0x1f1f },
873 { IDX_MIXER_VIDEO, MIXER_MUTE_MASK|0x1f1f }, 880 { IDX_MIXER_VIDEO, MIXER_MUTE_MASK|0x1f1f },
874 { IDX_MIXER_AUX, MIXER_MUTE_MASK|0x1f1f }, 881 { IDX_MIXER_AUX, MIXER_MUTE_MASK|0x1f1f },
875 { IDX_MIXER_WAVEOUT, MIXER_MUTE_MASK|0x1f1f }, 882 { IDX_MIXER_WAVEOUT, MIXER_MUTE_MASK|0x1f1f },
876 { IDX_MIXER_FMSYNTH, MIXER_MUTE_MASK|0x1f1f }, 883 { IDX_MIXER_FMSYNTH, MIXER_MUTE_MASK|0x1f1f },
877 { IDX_MIXER_REC_VOLUME, MIXER_MUTE_MASK|0x0707 }, 884 { IDX_MIXER_REC_VOLUME, MIXER_MUTE_MASK|0x0707 },
878 }; 885 };
879 886
880 static int __devinit 887 static int __devinit
881 snd_azf3328_mixer_new(struct snd_azf3328 *chip) 888 snd_azf3328_mixer_new(struct snd_azf3328 *chip)
882 { 889 {
883 struct snd_card *card; 890 struct snd_card *card;
884 const struct snd_kcontrol_new *sw; 891 const struct snd_kcontrol_new *sw;
885 unsigned int idx; 892 unsigned int idx;
886 int err; 893 int err;
887 894
888 snd_azf3328_dbgcallenter(); 895 snd_azf3328_dbgcallenter();
889 if (snd_BUG_ON(!chip || !chip->card)) 896 if (snd_BUG_ON(!chip || !chip->card))
890 return -EINVAL; 897 return -EINVAL;
891 898
892 card = chip->card; 899 card = chip->card;
893 900
894 /* mixer reset */ 901 /* mixer reset */
895 snd_azf3328_mixer_outw(chip, IDX_MIXER_RESET, 0x0000); 902 snd_azf3328_mixer_outw(chip, IDX_MIXER_RESET, 0x0000);
896 903
897 /* mute and zero volume channels */ 904 /* mute and zero volume channels */
898 for (idx = 0; idx < ARRAY_SIZE(snd_azf3328_init_values); ++idx) { 905 for (idx = 0; idx < ARRAY_SIZE(snd_azf3328_init_values); ++idx) {
899 snd_azf3328_mixer_outw(chip, 906 snd_azf3328_mixer_outw(chip,
900 snd_azf3328_init_values[idx][0], 907 snd_azf3328_init_values[idx][0],
901 snd_azf3328_init_values[idx][1]); 908 snd_azf3328_init_values[idx][1]);
902 } 909 }
903 910
904 /* add mixer controls */ 911 /* add mixer controls */
905 sw = snd_azf3328_mixer_controls; 912 sw = snd_azf3328_mixer_controls;
906 for (idx = 0; idx < ARRAY_SIZE(snd_azf3328_mixer_controls); 913 for (idx = 0; idx < ARRAY_SIZE(snd_azf3328_mixer_controls);
907 ++idx, ++sw) { 914 ++idx, ++sw) {
908 if ((err = snd_ctl_add(chip->card, snd_ctl_new1(sw, chip))) < 0) 915 if ((err = snd_ctl_add(chip->card, snd_ctl_new1(sw, chip))) < 0)
909 return err; 916 return err;
910 } 917 }
911 snd_component_add(card, "AZF3328 mixer"); 918 snd_component_add(card, "AZF3328 mixer");
912 strcpy(card->mixername, "AZF3328 mixer"); 919 strcpy(card->mixername, "AZF3328 mixer");
913 920
914 snd_azf3328_dbgcallleave(); 921 snd_azf3328_dbgcallleave();
915 return 0; 922 return 0;
916 } 923 }
917 924
918 static int 925 static int
919 snd_azf3328_hw_params(struct snd_pcm_substream *substream, 926 snd_azf3328_hw_params(struct snd_pcm_substream *substream,
920 struct snd_pcm_hw_params *hw_params) 927 struct snd_pcm_hw_params *hw_params)
921 { 928 {
922 int res; 929 int res;
923 snd_azf3328_dbgcallenter(); 930 snd_azf3328_dbgcallenter();
924 res = snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(hw_params)); 931 res = snd_pcm_lib_malloc_pages(substream, params_buffer_bytes(hw_params));
925 snd_azf3328_dbgcallleave(); 932 snd_azf3328_dbgcallleave();
926 return res; 933 return res;
927 } 934 }
928 935
929 static int 936 static int
930 snd_azf3328_hw_free(struct snd_pcm_substream *substream) 937 snd_azf3328_hw_free(struct snd_pcm_substream *substream)
931 { 938 {
932 snd_azf3328_dbgcallenter(); 939 snd_azf3328_dbgcallenter();
933 snd_pcm_lib_free_pages(substream); 940 snd_pcm_lib_free_pages(substream);
934 snd_azf3328_dbgcallleave(); 941 snd_azf3328_dbgcallleave();
935 return 0; 942 return 0;
936 } 943 }
937 944
938 static void 945 static void
939 snd_azf3328_codec_setfmt(struct snd_azf3328 *chip, 946 snd_azf3328_codec_setfmt(struct snd_azf3328 *chip,
940 enum snd_azf3328_codec_type codec_type, 947 enum snd_azf3328_codec_type codec_type,
941 enum azf_freq_t bitrate, 948 enum azf_freq_t bitrate,
942 unsigned int format_width, 949 unsigned int format_width,
943 unsigned int channels 950 unsigned int channels
944 ) 951 )
945 { 952 {
946 unsigned long flags; 953 unsigned long flags;
947 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type]; 954 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type];
948 u16 val = 0xff00; 955 u16 val = 0xff00;
949 956
950 snd_azf3328_dbgcallenter(); 957 snd_azf3328_dbgcallenter();
951 switch (bitrate) { 958 switch (bitrate) {
952 case AZF_FREQ_4000: val |= SOUNDFORMAT_FREQ_SUSPECTED_4000; break; 959 case AZF_FREQ_4000: val |= SOUNDFORMAT_FREQ_SUSPECTED_4000; break;
953 case AZF_FREQ_4800: val |= SOUNDFORMAT_FREQ_SUSPECTED_4800; break; 960 case AZF_FREQ_4800: val |= SOUNDFORMAT_FREQ_SUSPECTED_4800; break;
954 case AZF_FREQ_5512: 961 case AZF_FREQ_5512:
955 /* the AZF3328 names it "5510" for some strange reason */ 962 /* the AZF3328 names it "5510" for some strange reason */
956 val |= SOUNDFORMAT_FREQ_5510; break; 963 val |= SOUNDFORMAT_FREQ_5510; break;
957 case AZF_FREQ_6620: val |= SOUNDFORMAT_FREQ_6620; break; 964 case AZF_FREQ_6620: val |= SOUNDFORMAT_FREQ_6620; break;
958 case AZF_FREQ_8000: val |= SOUNDFORMAT_FREQ_8000; break; 965 case AZF_FREQ_8000: val |= SOUNDFORMAT_FREQ_8000; break;
959 case AZF_FREQ_9600: val |= SOUNDFORMAT_FREQ_9600; break; 966 case AZF_FREQ_9600: val |= SOUNDFORMAT_FREQ_9600; break;
960 case AZF_FREQ_11025: val |= SOUNDFORMAT_FREQ_11025; break; 967 case AZF_FREQ_11025: val |= SOUNDFORMAT_FREQ_11025; break;
961 case AZF_FREQ_13240: val |= SOUNDFORMAT_FREQ_SUSPECTED_13240; break; 968 case AZF_FREQ_13240: val |= SOUNDFORMAT_FREQ_SUSPECTED_13240; break;
962 case AZF_FREQ_16000: val |= SOUNDFORMAT_FREQ_16000; break; 969 case AZF_FREQ_16000: val |= SOUNDFORMAT_FREQ_16000; break;
963 case AZF_FREQ_22050: val |= SOUNDFORMAT_FREQ_22050; break; 970 case AZF_FREQ_22050: val |= SOUNDFORMAT_FREQ_22050; break;
964 case AZF_FREQ_32000: val |= SOUNDFORMAT_FREQ_32000; break; 971 case AZF_FREQ_32000: val |= SOUNDFORMAT_FREQ_32000; break;
965 default: 972 default:
966 snd_printk(KERN_WARNING "unknown bitrate %d, assuming 44.1kHz!\n", bitrate); 973 snd_printk(KERN_WARNING "unknown bitrate %d, assuming 44.1kHz!\n", bitrate);
967 /* fall-through */ 974 /* fall-through */
968 case AZF_FREQ_44100: val |= SOUNDFORMAT_FREQ_44100; break; 975 case AZF_FREQ_44100: val |= SOUNDFORMAT_FREQ_44100; break;
969 case AZF_FREQ_48000: val |= SOUNDFORMAT_FREQ_48000; break; 976 case AZF_FREQ_48000: val |= SOUNDFORMAT_FREQ_48000; break;
970 case AZF_FREQ_66200: val |= SOUNDFORMAT_FREQ_SUSPECTED_66200; break; 977 case AZF_FREQ_66200: val |= SOUNDFORMAT_FREQ_SUSPECTED_66200; break;
971 } 978 }
972 /* val = 0xff07; 3m27.993s (65301Hz; -> 64000Hz???) hmm, 66120, 65967, 66123 */ 979 /* val = 0xff07; 3m27.993s (65301Hz; -> 64000Hz???) hmm, 66120, 65967, 66123 */
973 /* val = 0xff09; 17m15.098s (13123,478Hz; -> 12000Hz???) hmm, 13237.2Hz? */ 980 /* val = 0xff09; 17m15.098s (13123,478Hz; -> 12000Hz???) hmm, 13237.2Hz? */
974 /* val = 0xff0a; 47m30.599s (4764,891Hz; -> 4800Hz???) yup, 4803Hz */ 981 /* val = 0xff0a; 47m30.599s (4764,891Hz; -> 4800Hz???) yup, 4803Hz */
975 /* val = 0xff0c; 57m0.510s (4010,263Hz; -> 4000Hz???) yup, 4003Hz */ 982 /* val = 0xff0c; 57m0.510s (4010,263Hz; -> 4000Hz???) yup, 4003Hz */
976 /* val = 0xff05; 5m11.556s (... -> 44100Hz) */ 983 /* val = 0xff05; 5m11.556s (... -> 44100Hz) */
977 /* val = 0xff03; 10m21.529s (21872,463Hz; -> 22050Hz???) */ 984 /* val = 0xff03; 10m21.529s (21872,463Hz; -> 22050Hz???) */
978 /* val = 0xff0f; 20m41.883s (10937,993Hz; -> 11025Hz???) */ 985 /* val = 0xff0f; 20m41.883s (10937,993Hz; -> 11025Hz???) */
979 /* val = 0xff0d; 41m23.135s (5523,600Hz; -> 5512Hz???) */ 986 /* val = 0xff0d; 41m23.135s (5523,600Hz; -> 5512Hz???) */
980 /* val = 0xff0e; 28m30.777s (8017Hz; -> 8000Hz???) */ 987 /* val = 0xff0e; 28m30.777s (8017Hz; -> 8000Hz???) */
981 988
982 if (channels == 2) 989 if (channels == 2)
983 val |= SOUNDFORMAT_FLAG_2CHANNELS; 990 val |= SOUNDFORMAT_FLAG_2CHANNELS;
984 991
985 if (format_width == 16) 992 if (format_width == 16)
986 val |= SOUNDFORMAT_FLAG_16BIT; 993 val |= SOUNDFORMAT_FLAG_16BIT;
987 994
988 spin_lock_irqsave(&chip->reg_lock, flags); 995 spin_lock_irqsave(&chip->reg_lock, flags);
989 996
990 /* set bitrate/format */ 997 /* set bitrate/format */
991 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_SOUNDFORMAT, val); 998 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_SOUNDFORMAT, val);
992 999
993 /* changing the bitrate/format settings switches off the 1000 /* changing the bitrate/format settings switches off the
994 * audio output with an annoying click in case of 8/16bit format change 1001 * audio output with an annoying click in case of 8/16bit format change
995 * (maybe shutting down DAC/ADC?), thus immediately 1002 * (maybe shutting down DAC/ADC?), thus immediately
996 * do some tweaking to reenable it and get rid of the clicking 1003 * do some tweaking to reenable it and get rid of the clicking
997 * (FIXME: yes, it works, but what exactly am I doing here?? :) 1004 * (FIXME: yes, it works, but what exactly am I doing here?? :)
998 * FIXME: does this have some side effects for full-duplex 1005 * FIXME: does this have some side effects for full-duplex
999 * or other dramatic side effects? */ 1006 * or other dramatic side effects? */
1000 if (codec_type == AZF_CODEC_PLAYBACK) /* only do it for playback */ 1007 if (codec_type == AZF_CODEC_PLAYBACK) /* only do it for playback */
1001 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1008 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1002 snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS) | 1009 snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS) |
1003 DMA_RUN_SOMETHING1 | 1010 DMA_RUN_SOMETHING1 |
1004 DMA_RUN_SOMETHING2 | 1011 DMA_RUN_SOMETHING2 |
1005 SOMETHING_ALMOST_ALWAYS_SET | 1012 SOMETHING_ALMOST_ALWAYS_SET |
1006 DMA_EPILOGUE_SOMETHING | 1013 DMA_EPILOGUE_SOMETHING |
1007 DMA_SOMETHING_ELSE 1014 DMA_SOMETHING_ELSE
1008 ); 1015 );
1009 1016
1010 spin_unlock_irqrestore(&chip->reg_lock, flags); 1017 spin_unlock_irqrestore(&chip->reg_lock, flags);
1011 snd_azf3328_dbgcallleave(); 1018 snd_azf3328_dbgcallleave();
1012 } 1019 }
1013 1020
1014 static inline void 1021 static inline void
1015 snd_azf3328_codec_setfmt_lowpower(struct snd_azf3328 *chip, 1022 snd_azf3328_codec_setfmt_lowpower(struct snd_azf3328 *chip,
1016 enum snd_azf3328_codec_type codec_type 1023 enum snd_azf3328_codec_type codec_type
1017 ) 1024 )
1018 { 1025 {
1019 /* choose lowest frequency for low power consumption. 1026 /* choose lowest frequency for low power consumption.
1020 * While this will cause louder noise due to rather coarse frequency, 1027 * While this will cause louder noise due to rather coarse frequency,
1021 * it should never matter since output should always 1028 * it should never matter since output should always
1022 * get disabled properly when idle anyway. */ 1029 * get disabled properly when idle anyway. */
1023 snd_azf3328_codec_setfmt(chip, codec_type, AZF_FREQ_4000, 8, 1); 1030 snd_azf3328_codec_setfmt(chip, codec_type, AZF_FREQ_4000, 8, 1);
1024 } 1031 }
1025 1032
1026 static void 1033 static void
1027 snd_azf3328_ctrl_reg_6AH_update(struct snd_azf3328 *chip, 1034 snd_azf3328_ctrl_reg_6AH_update(struct snd_azf3328 *chip,
1028 unsigned bitmask, 1035 unsigned bitmask,
1029 bool enable 1036 bool enable
1030 ) 1037 )
1031 { 1038 {
1032 if (enable) 1039 bool do_mask = !enable;
1033 chip->shadow_reg_ctrl_6AH &= ~bitmask; 1040 if (do_mask)
1034 else
1035 chip->shadow_reg_ctrl_6AH |= bitmask; 1041 chip->shadow_reg_ctrl_6AH |= bitmask;
1036 snd_azf3328_dbgplay("6AH_update mask 0x%04x enable %d: val 0x%04x\n", 1042 else
1037 bitmask, enable, chip->shadow_reg_ctrl_6AH); 1043 chip->shadow_reg_ctrl_6AH &= ~bitmask;
1044 snd_azf3328_dbgcodec("6AH_update mask 0x%04x do_mask %d: val 0x%04x\n",
1045 bitmask, do_mask, chip->shadow_reg_ctrl_6AH);
1038 snd_azf3328_ctrl_outw(chip, IDX_IO_6AH, chip->shadow_reg_ctrl_6AH); 1046 snd_azf3328_ctrl_outw(chip, IDX_IO_6AH, chip->shadow_reg_ctrl_6AH);
1039 } 1047 }
1040 1048
1041 static inline void 1049 static inline void
1042 snd_azf3328_ctrl_enable_codecs(struct snd_azf3328 *chip, bool enable) 1050 snd_azf3328_ctrl_enable_codecs(struct snd_azf3328 *chip, bool enable)
1043 { 1051 {
1044 snd_azf3328_dbgplay("codec_enable %d\n", enable); 1052 snd_azf3328_dbgcodec("codec_enable %d\n", enable);
1045 /* no idea what exactly is being done here, but I strongly assume it's 1053 /* no idea what exactly is being done here, but I strongly assume it's
1046 * PM related */ 1054 * PM related */
1047 snd_azf3328_ctrl_reg_6AH_update( 1055 snd_azf3328_ctrl_reg_6AH_update(
1048 chip, IO_6A_PAUSE_PLAYBACK_BIT8, enable 1056 chip, IO_6A_PAUSE_PLAYBACK_BIT8, enable
1049 ); 1057 );
1050 } 1058 }
1051 1059
1052 static void 1060 static void
1053 snd_azf3328_ctrl_codec_activity(struct snd_azf3328 *chip, 1061 snd_azf3328_ctrl_codec_activity(struct snd_azf3328 *chip,
1054 enum snd_azf3328_codec_type codec_type, 1062 enum snd_azf3328_codec_type codec_type,
1055 bool enable 1063 bool enable
1056 ) 1064 )
1057 { 1065 {
1058 struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type]; 1066 struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type];
1059 bool need_change = (codec->running != enable); 1067 bool need_change = (codec->running != enable);
1060 1068
1061 snd_azf3328_dbgplay( 1069 snd_azf3328_dbgcodec(
1062 "codec_activity: %s codec, enable %d, need_change %d\n", 1070 "codec_activity: %s codec, enable %d, need_change %d\n",
1063 codec->name, enable, need_change 1071 codec->name, enable, need_change
1064 ); 1072 );
1065 if (need_change) { 1073 if (need_change) {
1066 static const struct { 1074 static const struct {
1067 enum snd_azf3328_codec_type other1; 1075 enum snd_azf3328_codec_type other1;
1068 enum snd_azf3328_codec_type other2; 1076 enum snd_azf3328_codec_type other2;
1069 } peer_codecs[3] = 1077 } peer_codecs[3] =
1070 { { AZF_CODEC_CAPTURE, AZF_CODEC_I2S_OUT }, 1078 { { AZF_CODEC_CAPTURE, AZF_CODEC_I2S_OUT },
1071 { AZF_CODEC_PLAYBACK, AZF_CODEC_I2S_OUT }, 1079 { AZF_CODEC_PLAYBACK, AZF_CODEC_I2S_OUT },
1072 { AZF_CODEC_PLAYBACK, AZF_CODEC_CAPTURE } }; 1080 { AZF_CODEC_PLAYBACK, AZF_CODEC_CAPTURE } };
1073 bool call_function; 1081 bool call_function;
1074 1082
1075 if (enable) 1083 if (enable)
1076 /* if enable codec, call enable_codecs func 1084 /* if enable codec, call enable_codecs func
1077 to enable codec supply... */ 1085 to enable codec supply... */
1078 call_function = 1; 1086 call_function = 1;
1079 else { 1087 else {
1080 /* ...otherwise call enable_codecs func 1088 /* ...otherwise call enable_codecs func
1081 (which globally shuts down operation of codecs) 1089 (which globally shuts down operation of codecs)
1082 only in case the other codecs are currently 1090 only in case the other codecs are currently
1083 not active either! */ 1091 not active either! */
1084 if ((!chip->codecs[peer_codecs[codec_type].other1] 1092 call_function =
1085 .running) 1093 ((!chip->codecs[peer_codecs[codec_type].other1]
1086 && (!chip->codecs[peer_codecs[codec_type].other2] 1094 .running)
1087 .running)) 1095 && (!chip->codecs[peer_codecs[codec_type].other2]
1088 call_function = 1; 1096 .running));
1089 } 1097 }
1090 if (call_function) 1098 if (call_function)
1091 snd_azf3328_ctrl_enable_codecs(chip, enable); 1099 snd_azf3328_ctrl_enable_codecs(chip, enable);
1092 1100
1093 /* ...and adjust clock, too 1101 /* ...and adjust clock, too
1094 * (reduce noise and power consumption) */ 1102 * (reduce noise and power consumption) */
1095 if (!enable) 1103 if (!enable)
1096 snd_azf3328_codec_setfmt_lowpower( 1104 snd_azf3328_codec_setfmt_lowpower(
1097 chip, 1105 chip,
1098 codec_type 1106 codec_type
1099 ); 1107 );
1108 codec->running = enable;
1100 } 1109 }
1101 codec->running = enable;
1102 } 1110 }
1103 1111
1104 static void 1112 static void
1105 snd_azf3328_codec_setdmaa(struct snd_azf3328 *chip, 1113 snd_azf3328_codec_setdmaa(struct snd_azf3328 *chip,
1106 enum snd_azf3328_codec_type codec_type, 1114 enum snd_azf3328_codec_type codec_type,
1107 unsigned long addr, 1115 unsigned long addr,
1108 unsigned int count, 1116 unsigned int count,
1109 unsigned int size 1117 unsigned int size
1110 ) 1118 )
1111 { 1119 {
1112 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type]; 1120 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type];
1113 snd_azf3328_dbgcallenter(); 1121 snd_azf3328_dbgcallenter();
1114 if (!codec->running) { 1122 if (!codec->running) {
1115 /* AZF3328 uses a two buffer pointer DMA transfer approach */ 1123 /* AZF3328 uses a two buffer pointer DMA transfer approach */
1116 1124
1117 unsigned long flags; 1125 unsigned long flags, addr_area2;
1118 1126
1119 /* width 32bit (prevent overflow): */ 1127 /* width 32bit (prevent overflow): */
1120 u32 addr_area2, count_areas, lengths; 1128 u32 count_areas, lengths;
1121 1129
1122 count_areas = size/2; 1130 count_areas = size/2;
1123 addr_area2 = addr+count_areas; 1131 addr_area2 = addr+count_areas;
1124 count_areas--; /* max. index */ 1132 count_areas--; /* max. index */
1125 snd_azf3328_dbgplay("set DMA: buf1 %08lx[%lu], buf2 %08lx[%lu]\n", addr, count_areas, addr_area2, count_areas); 1133 snd_azf3328_dbgcodec("setdma: buffers %08lx[%u] / %08lx[%u]\n",
1134 addr, count_areas, addr_area2, count_areas);
1126 1135
1127 /* build combined I/O buffer length word */ 1136 /* build combined I/O buffer length word */
1128 lengths = (count_areas << 16) | (count_areas); 1137 lengths = (count_areas << 16) | (count_areas);
1129 spin_lock_irqsave(&chip->reg_lock, flags); 1138 spin_lock_irqsave(&chip->reg_lock, flags);
1130 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_START_1, addr); 1139 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_START_1, addr);
1131 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_START_2, 1140 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_START_2,
1132 addr_area2); 1141 addr_area2);
1133 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_LENGTHS, 1142 snd_azf3328_codec_outl(codec, IDX_IO_CODEC_DMA_LENGTHS,
1134 lengths); 1143 lengths);
1135 spin_unlock_irqrestore(&chip->reg_lock, flags); 1144 spin_unlock_irqrestore(&chip->reg_lock, flags);
1136 } 1145 }
1137 snd_azf3328_dbgcallleave(); 1146 snd_azf3328_dbgcallleave();
1138 } 1147 }
1139 1148
1140 static int 1149 static int
1141 snd_azf3328_codec_prepare(struct snd_pcm_substream *substream) 1150 snd_azf3328_codec_prepare(struct snd_pcm_substream *substream)
1142 { 1151 {
1143 #if 0 1152 #if 0
1144 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream); 1153 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream);
1145 struct snd_pcm_runtime *runtime = substream->runtime; 1154 struct snd_pcm_runtime *runtime = substream->runtime;
1146 unsigned int size = snd_pcm_lib_buffer_bytes(substream); 1155 unsigned int size = snd_pcm_lib_buffer_bytes(substream);
1147 unsigned int count = snd_pcm_lib_period_bytes(substream); 1156 unsigned int count = snd_pcm_lib_period_bytes(substream);
1148 #endif 1157 #endif
1149 1158
1150 snd_azf3328_dbgcallenter(); 1159 snd_azf3328_dbgcallenter();
1151 #if 0 1160 #if 0
1152 snd_azf3328_codec_setfmt(chip, AZF_CODEC_..., 1161 snd_azf3328_codec_setfmt(chip, AZF_CODEC_...,
1153 runtime->rate, 1162 runtime->rate,
1154 snd_pcm_format_width(runtime->format), 1163 snd_pcm_format_width(runtime->format),
1155 runtime->channels); 1164 runtime->channels);
1156 snd_azf3328_codec_setdmaa(chip, AZF_CODEC_..., 1165 snd_azf3328_codec_setdmaa(chip, AZF_CODEC_...,
1157 runtime->dma_addr, count, size); 1166 runtime->dma_addr, count, size);
1158 #endif 1167 #endif
1159 snd_azf3328_dbgcallleave(); 1168 snd_azf3328_dbgcallleave();
1160 return 0; 1169 return 0;
1161 } 1170 }
1162 1171
1163 static int 1172 static int
1164 snd_azf3328_codec_trigger(enum snd_azf3328_codec_type codec_type, 1173 snd_azf3328_codec_trigger(enum snd_azf3328_codec_type codec_type,
1165 struct snd_pcm_substream *substream, int cmd) 1174 struct snd_pcm_substream *substream, int cmd)
1166 { 1175 {
1167 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream); 1176 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream);
1168 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type]; 1177 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type];
1169 struct snd_pcm_runtime *runtime = substream->runtime; 1178 struct snd_pcm_runtime *runtime = substream->runtime;
1170 int result = 0; 1179 int result = 0;
1171 u16 flags1; 1180 u16 flags1;
1172 bool previously_muted = 0; 1181 bool previously_muted = 0;
1173 bool is_playback_codec = (AZF_CODEC_PLAYBACK == codec_type); 1182 bool is_playback_codec = (AZF_CODEC_PLAYBACK == codec_type);
1174 1183
1175 snd_azf3328_dbgcalls("snd_azf3328_codec_trigger cmd %d\n", cmd); 1184 snd_azf3328_dbgcalls("snd_azf3328_codec_trigger cmd %d\n", cmd);
1176 1185
1177 switch (cmd) { 1186 switch (cmd) {
1178 case SNDRV_PCM_TRIGGER_START: 1187 case SNDRV_PCM_TRIGGER_START:
1179 snd_azf3328_dbgplay("START %s\n", codec->name); 1188 snd_azf3328_dbgcodec("START %s\n", codec->name);
1180 1189
1181 if (is_playback_codec) { 1190 if (is_playback_codec) {
1182 /* mute WaveOut (avoid clicking during setup) */ 1191 /* mute WaveOut (avoid clicking during setup) */
1183 previously_muted = 1192 previously_muted =
1184 snd_azf3328_mixer_set_mute( 1193 snd_azf3328_mixer_set_mute(
1185 chip, IDX_MIXER_WAVEOUT, 1 1194 chip, IDX_MIXER_WAVEOUT, 1
1186 ); 1195 );
1187 } 1196 }
1188 1197
1189 snd_azf3328_codec_setfmt(chip, codec_type, 1198 snd_azf3328_codec_setfmt(chip, codec_type,
1190 runtime->rate, 1199 runtime->rate,
1191 snd_pcm_format_width(runtime->format), 1200 snd_pcm_format_width(runtime->format),
1192 runtime->channels); 1201 runtime->channels);
1193 1202
1194 spin_lock(&chip->reg_lock); 1203 spin_lock(&chip->reg_lock);
1195 /* first, remember current value: */ 1204 /* first, remember current value: */
1196 flags1 = snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS); 1205 flags1 = snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS);
1197 1206
1198 /* stop transfer */ 1207 /* stop transfer */
1199 flags1 &= ~DMA_RESUME; 1208 flags1 &= ~DMA_RESUME;
1200 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1209 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1201 1210
1202 /* FIXME: clear interrupts or what??? */ 1211 /* FIXME: clear interrupts or what??? */
1203 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_IRQTYPE, 0xffff); 1212 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_IRQTYPE, 0xffff);
1204 spin_unlock(&chip->reg_lock); 1213 spin_unlock(&chip->reg_lock);
1205 1214
1206 snd_azf3328_codec_setdmaa(chip, codec_type, runtime->dma_addr, 1215 snd_azf3328_codec_setdmaa(chip, codec_type, runtime->dma_addr,
1207 snd_pcm_lib_period_bytes(substream), 1216 snd_pcm_lib_period_bytes(substream),
1208 snd_pcm_lib_buffer_bytes(substream) 1217 snd_pcm_lib_buffer_bytes(substream)
1209 ); 1218 );
1210 1219
1211 spin_lock(&chip->reg_lock); 1220 spin_lock(&chip->reg_lock);
1212 #ifdef WIN9X 1221 #ifdef WIN9X
1213 /* FIXME: enable playback/recording??? */ 1222 /* FIXME: enable playback/recording??? */
1214 flags1 |= DMA_RUN_SOMETHING1 | DMA_RUN_SOMETHING2; 1223 flags1 |= DMA_RUN_SOMETHING1 | DMA_RUN_SOMETHING2;
1215 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1224 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1216 1225
1217 /* start transfer again */ 1226 /* start transfer again */
1218 /* FIXME: what is this value (0x0010)??? */ 1227 /* FIXME: what is this value (0x0010)??? */
1219 flags1 |= DMA_RESUME | DMA_EPILOGUE_SOMETHING; 1228 flags1 |= DMA_RESUME | DMA_EPILOGUE_SOMETHING;
1220 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1229 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1221 #else /* NT4 */ 1230 #else /* NT4 */
1222 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1231 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1223 0x0000); 1232 0x0000);
1224 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1233 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1225 DMA_RUN_SOMETHING1); 1234 DMA_RUN_SOMETHING1);
1226 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1235 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1227 DMA_RUN_SOMETHING1 | 1236 DMA_RUN_SOMETHING1 |
1228 DMA_RUN_SOMETHING2); 1237 DMA_RUN_SOMETHING2);
1229 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1238 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1230 DMA_RESUME | 1239 DMA_RESUME |
1231 SOMETHING_ALMOST_ALWAYS_SET | 1240 SOMETHING_ALMOST_ALWAYS_SET |
1232 DMA_EPILOGUE_SOMETHING | 1241 DMA_EPILOGUE_SOMETHING |
1233 DMA_SOMETHING_ELSE); 1242 DMA_SOMETHING_ELSE);
1234 #endif 1243 #endif
1235 spin_unlock(&chip->reg_lock); 1244 spin_unlock(&chip->reg_lock);
1236 snd_azf3328_ctrl_codec_activity(chip, codec_type, 1); 1245 snd_azf3328_ctrl_codec_activity(chip, codec_type, 1);
1237 1246
1238 if (is_playback_codec) { 1247 if (is_playback_codec) {
1239 /* now unmute WaveOut */ 1248 /* now unmute WaveOut */
1240 if (!previously_muted) 1249 if (!previously_muted)
1241 snd_azf3328_mixer_set_mute( 1250 snd_azf3328_mixer_set_mute(
1242 chip, IDX_MIXER_WAVEOUT, 0 1251 chip, IDX_MIXER_WAVEOUT, 0
1243 ); 1252 );
1244 } 1253 }
1245 1254
1246 snd_azf3328_dbgplay("STARTED %s\n", codec->name); 1255 snd_azf3328_dbgcodec("STARTED %s\n", codec->name);
1247 break; 1256 break;
1248 case SNDRV_PCM_TRIGGER_RESUME: 1257 case SNDRV_PCM_TRIGGER_RESUME:
1249 snd_azf3328_dbgplay("RESUME %s\n", codec->name); 1258 snd_azf3328_dbgcodec("RESUME %s\n", codec->name);
1250 /* resume codec if we were active */ 1259 /* resume codec if we were active */
1251 spin_lock(&chip->reg_lock); 1260 spin_lock(&chip->reg_lock);
1252 if (codec->running) 1261 if (codec->running)
1253 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1262 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1254 snd_azf3328_codec_inw( 1263 snd_azf3328_codec_inw(
1255 codec, IDX_IO_CODEC_DMA_FLAGS 1264 codec, IDX_IO_CODEC_DMA_FLAGS
1256 ) | DMA_RESUME 1265 ) | DMA_RESUME
1257 ); 1266 );
1258 spin_unlock(&chip->reg_lock); 1267 spin_unlock(&chip->reg_lock);
1259 break; 1268 break;
1260 case SNDRV_PCM_TRIGGER_STOP: 1269 case SNDRV_PCM_TRIGGER_STOP:
1261 snd_azf3328_dbgplay("STOP %s\n", codec->name); 1270 snd_azf3328_dbgcodec("STOP %s\n", codec->name);
1262 1271
1263 if (is_playback_codec) { 1272 if (is_playback_codec) {
1264 /* mute WaveOut (avoid clicking during setup) */ 1273 /* mute WaveOut (avoid clicking during setup) */
1265 previously_muted = 1274 previously_muted =
1266 snd_azf3328_mixer_set_mute( 1275 snd_azf3328_mixer_set_mute(
1267 chip, IDX_MIXER_WAVEOUT, 1 1276 chip, IDX_MIXER_WAVEOUT, 1
1268 ); 1277 );
1269 } 1278 }
1270 1279
1271 spin_lock(&chip->reg_lock); 1280 spin_lock(&chip->reg_lock);
1272 /* first, remember current value: */ 1281 /* first, remember current value: */
1273 flags1 = snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS); 1282 flags1 = snd_azf3328_codec_inw(codec, IDX_IO_CODEC_DMA_FLAGS);
1274 1283
1275 /* stop transfer */ 1284 /* stop transfer */
1276 flags1 &= ~DMA_RESUME; 1285 flags1 &= ~DMA_RESUME;
1277 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1286 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1278 1287
1279 /* hmm, is this really required? we're resetting the same bit 1288 /* hmm, is this really required? we're resetting the same bit
1280 * immediately thereafter... */ 1289 * immediately thereafter... */
1281 flags1 |= DMA_RUN_SOMETHING1; 1290 flags1 |= DMA_RUN_SOMETHING1;
1282 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1291 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1283 1292
1284 flags1 &= ~DMA_RUN_SOMETHING1; 1293 flags1 &= ~DMA_RUN_SOMETHING1;
1285 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1); 1294 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, flags1);
1286 spin_unlock(&chip->reg_lock); 1295 spin_unlock(&chip->reg_lock);
1287 snd_azf3328_ctrl_codec_activity(chip, codec_type, 0); 1296 snd_azf3328_ctrl_codec_activity(chip, codec_type, 0);
1288 1297
1289 if (is_playback_codec) { 1298 if (is_playback_codec) {
1290 /* now unmute WaveOut */ 1299 /* now unmute WaveOut */
1291 if (!previously_muted) 1300 if (!previously_muted)
1292 snd_azf3328_mixer_set_mute( 1301 snd_azf3328_mixer_set_mute(
1293 chip, IDX_MIXER_WAVEOUT, 0 1302 chip, IDX_MIXER_WAVEOUT, 0
1294 ); 1303 );
1295 } 1304 }
1296 1305
1297 snd_azf3328_dbgplay("STOPPED %s\n", codec->name); 1306 snd_azf3328_dbgcodec("STOPPED %s\n", codec->name);
1298 break; 1307 break;
1299 case SNDRV_PCM_TRIGGER_SUSPEND: 1308 case SNDRV_PCM_TRIGGER_SUSPEND:
1300 snd_azf3328_dbgplay("SUSPEND %s\n", codec->name); 1309 snd_azf3328_dbgcodec("SUSPEND %s\n", codec->name);
1301 /* make sure codec is stopped */ 1310 /* make sure codec is stopped */
1302 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS, 1311 snd_azf3328_codec_outw(codec, IDX_IO_CODEC_DMA_FLAGS,
1303 snd_azf3328_codec_inw( 1312 snd_azf3328_codec_inw(
1304 codec, IDX_IO_CODEC_DMA_FLAGS 1313 codec, IDX_IO_CODEC_DMA_FLAGS
1305 ) & ~DMA_RESUME 1314 ) & ~DMA_RESUME
1306 ); 1315 );
1307 break; 1316 break;
1308 case SNDRV_PCM_TRIGGER_PAUSE_PUSH: 1317 case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
1309 snd_printk(KERN_ERR "FIXME: SNDRV_PCM_TRIGGER_PAUSE_PUSH NIY!\n"); 1318 snd_printk(KERN_ERR "FIXME: SNDRV_PCM_TRIGGER_PAUSE_PUSH NIY!\n");
1310 break; 1319 break;
1311 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: 1320 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
1312 snd_printk(KERN_ERR "FIXME: SNDRV_PCM_TRIGGER_PAUSE_RELEASE NIY!\n"); 1321 snd_printk(KERN_ERR "FIXME: SNDRV_PCM_TRIGGER_PAUSE_RELEASE NIY!\n");
1313 break; 1322 break;
1314 default: 1323 default:
1315 printk(KERN_ERR "FIXME: unknown trigger mode!\n"); 1324 snd_printk(KERN_ERR "FIXME: unknown trigger mode!\n");
1316 return -EINVAL; 1325 return -EINVAL;
1317 } 1326 }
1318 1327
1319 snd_azf3328_dbgcallleave(); 1328 snd_azf3328_dbgcallleave();
1320 return result; 1329 return result;
1321 } 1330 }
1322 1331
1323 static int 1332 static int
1324 snd_azf3328_codec_playback_trigger(struct snd_pcm_substream *substream, int cmd) 1333 snd_azf3328_codec_playback_trigger(struct snd_pcm_substream *substream, int cmd)
1325 { 1334 {
1326 return snd_azf3328_codec_trigger(AZF_CODEC_PLAYBACK, substream, cmd); 1335 return snd_azf3328_codec_trigger(AZF_CODEC_PLAYBACK, substream, cmd);
1327 } 1336 }
1328 1337
1329 static int 1338 static int
1330 snd_azf3328_codec_capture_trigger(struct snd_pcm_substream *substream, int cmd) 1339 snd_azf3328_codec_capture_trigger(struct snd_pcm_substream *substream, int cmd)
1331 { 1340 {
1332 return snd_azf3328_codec_trigger(AZF_CODEC_CAPTURE, substream, cmd); 1341 return snd_azf3328_codec_trigger(AZF_CODEC_CAPTURE, substream, cmd);
1333 } 1342 }
1334 1343
1335 static int 1344 static int
1336 snd_azf3328_codec_i2s_out_trigger(struct snd_pcm_substream *substream, int cmd) 1345 snd_azf3328_codec_i2s_out_trigger(struct snd_pcm_substream *substream, int cmd)
1337 { 1346 {
1338 return snd_azf3328_codec_trigger(AZF_CODEC_I2S_OUT, substream, cmd); 1347 return snd_azf3328_codec_trigger(AZF_CODEC_I2S_OUT, substream, cmd);
1339 } 1348 }
1340 1349
1341 static snd_pcm_uframes_t 1350 static snd_pcm_uframes_t
1342 snd_azf3328_codec_pointer(struct snd_pcm_substream *substream, 1351 snd_azf3328_codec_pointer(struct snd_pcm_substream *substream,
1343 enum snd_azf3328_codec_type codec_type 1352 enum snd_azf3328_codec_type codec_type
1344 ) 1353 )
1345 { 1354 {
1346 const struct snd_azf3328 *chip = snd_pcm_substream_chip(substream); 1355 const struct snd_azf3328 *chip = snd_pcm_substream_chip(substream);
1347 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type]; 1356 const struct snd_azf3328_codec_data *codec = &chip->codecs[codec_type];
1348 unsigned long bufptr, result; 1357 unsigned long bufptr, result;
1349 snd_pcm_uframes_t frmres; 1358 snd_pcm_uframes_t frmres;
1350 1359
1351 #ifdef QUERY_HARDWARE 1360 #ifdef QUERY_HARDWARE
1352 bufptr = snd_azf3328_codec_inl(codec, IDX_IO_CODEC_DMA_START_1); 1361 bufptr = snd_azf3328_codec_inl(codec, IDX_IO_CODEC_DMA_START_1);
1353 #else 1362 #else
1354 bufptr = substream->runtime->dma_addr; 1363 bufptr = substream->runtime->dma_addr;
1355 #endif 1364 #endif
1356 result = snd_azf3328_codec_inl(codec, IDX_IO_CODEC_DMA_CURRPOS); 1365 result = snd_azf3328_codec_inl(codec, IDX_IO_CODEC_DMA_CURRPOS);
1357 1366
1358 /* calculate offset */ 1367 /* calculate offset */
1359 result -= bufptr; 1368 result -= bufptr;
1360 frmres = bytes_to_frames( substream->runtime, result); 1369 frmres = bytes_to_frames( substream->runtime, result);
1361 snd_azf3328_dbgplay("%s @ 0x%8lx, frames %8ld\n", 1370 snd_azf3328_dbgcodec("%s @ 0x%8lx, frames %8ld\n",
1362 codec->name, result, frmres); 1371 codec->name, result, frmres);
1363 return frmres; 1372 return frmres;
1364 } 1373 }
1365 1374
1366 static snd_pcm_uframes_t 1375 static snd_pcm_uframes_t
1367 snd_azf3328_codec_playback_pointer(struct snd_pcm_substream *substream) 1376 snd_azf3328_codec_playback_pointer(struct snd_pcm_substream *substream)
1368 { 1377 {
1369 return snd_azf3328_codec_pointer(substream, AZF_CODEC_PLAYBACK); 1378 return snd_azf3328_codec_pointer(substream, AZF_CODEC_PLAYBACK);
1370 } 1379 }
1371 1380
1372 static snd_pcm_uframes_t 1381 static snd_pcm_uframes_t
1373 snd_azf3328_codec_capture_pointer(struct snd_pcm_substream *substream) 1382 snd_azf3328_codec_capture_pointer(struct snd_pcm_substream *substream)
1374 { 1383 {
1375 return snd_azf3328_codec_pointer(substream, AZF_CODEC_CAPTURE); 1384 return snd_azf3328_codec_pointer(substream, AZF_CODEC_CAPTURE);
1376 } 1385 }
1377 1386
1378 static snd_pcm_uframes_t 1387 static snd_pcm_uframes_t
1379 snd_azf3328_codec_i2s_out_pointer(struct snd_pcm_substream *substream) 1388 snd_azf3328_codec_i2s_out_pointer(struct snd_pcm_substream *substream)
1380 { 1389 {
1381 return snd_azf3328_codec_pointer(substream, AZF_CODEC_I2S_OUT); 1390 return snd_azf3328_codec_pointer(substream, AZF_CODEC_I2S_OUT);
1382 } 1391 }
1383 1392
1384 /******************************************************************/ 1393 /******************************************************************/
1385 1394
1386 #ifdef SUPPORT_GAMEPORT 1395 #ifdef SUPPORT_GAMEPORT
1387 static inline void 1396 static inline void
1388 snd_azf3328_gameport_irq_enable(struct snd_azf3328 *chip, 1397 snd_azf3328_gameport_irq_enable(struct snd_azf3328 *chip,
1389 bool enable 1398 bool enable
1390 ) 1399 )
1391 { 1400 {
1392 snd_azf3328_io_reg_setb( 1401 snd_azf3328_io_reg_setb(
1393 chip->game_io+IDX_GAME_HWCONFIG, 1402 chip->game_io+IDX_GAME_HWCONFIG,
1394 GAME_HWCFG_IRQ_ENABLE, 1403 GAME_HWCFG_IRQ_ENABLE,
1395 enable 1404 enable
1396 ); 1405 );
1397 } 1406 }
1398 1407
1399 static inline void 1408 static inline void
1400 snd_azf3328_gameport_legacy_address_enable(struct snd_azf3328 *chip, 1409 snd_azf3328_gameport_legacy_address_enable(struct snd_azf3328 *chip,
1401 bool enable 1410 bool enable
1402 ) 1411 )
1403 { 1412 {
1404 snd_azf3328_io_reg_setb( 1413 snd_azf3328_io_reg_setb(
1405 chip->game_io+IDX_GAME_HWCONFIG, 1414 chip->game_io+IDX_GAME_HWCONFIG,
1406 GAME_HWCFG_LEGACY_ADDRESS_ENABLE, 1415 GAME_HWCFG_LEGACY_ADDRESS_ENABLE,
1407 enable 1416 enable
1408 ); 1417 );
1409 } 1418 }
1410 1419
1411 static void 1420 static void
1412 snd_azf3328_gameport_set_counter_frequency(struct snd_azf3328 *chip, 1421 snd_azf3328_gameport_set_counter_frequency(struct snd_azf3328 *chip,
1413 unsigned int freq_cfg 1422 unsigned int freq_cfg
1414 ) 1423 )
1415 { 1424 {
1416 snd_azf3328_io_reg_setb( 1425 snd_azf3328_io_reg_setb(
1417 chip->game_io+IDX_GAME_HWCONFIG, 1426 chip->game_io+IDX_GAME_HWCONFIG,
1418 0x02, 1427 0x02,
1419 (freq_cfg & 1) != 0 1428 (freq_cfg & 1) != 0
1420 ); 1429 );
1421 snd_azf3328_io_reg_setb( 1430 snd_azf3328_io_reg_setb(
1422 chip->game_io+IDX_GAME_HWCONFIG, 1431 chip->game_io+IDX_GAME_HWCONFIG,
1423 0x04, 1432 0x04,
1424 (freq_cfg & 2) != 0 1433 (freq_cfg & 2) != 0
1425 ); 1434 );
1426 } 1435 }
1427 1436
1428 static inline void 1437 static inline void
1429 snd_azf3328_gameport_axis_circuit_enable(struct snd_azf3328 *chip, bool enable) 1438 snd_azf3328_gameport_axis_circuit_enable(struct snd_azf3328 *chip, bool enable)
1430 { 1439 {
1431 snd_azf3328_ctrl_reg_6AH_update( 1440 snd_azf3328_ctrl_reg_6AH_update(
1432 chip, IO_6A_SOMETHING2_GAMEPORT, enable 1441 chip, IO_6A_SOMETHING2_GAMEPORT, enable
1433 ); 1442 );
1434 } 1443 }
1435 1444
1436 static inline void 1445 static inline void
1437 snd_azf3328_gameport_interrupt(struct snd_azf3328 *chip) 1446 snd_azf3328_gameport_interrupt(struct snd_azf3328 *chip)
1438 { 1447 {
1439 /* 1448 /*
1440 * skeleton handler only 1449 * skeleton handler only
1441 * (we do not want axis reading in interrupt handler - too much load!) 1450 * (we do not want axis reading in interrupt handler - too much load!)
1442 */ 1451 */
1443 snd_azf3328_dbggame("gameport irq\n"); 1452 snd_azf3328_dbggame("gameport irq\n");
1444 1453
1445 /* this should ACK the gameport IRQ properly, hopefully. */ 1454 /* this should ACK the gameport IRQ properly, hopefully. */
1446 snd_azf3328_game_inw(chip, IDX_GAME_AXIS_VALUE); 1455 snd_azf3328_game_inw(chip, IDX_GAME_AXIS_VALUE);
1447 } 1456 }
1448 1457
1449 static int 1458 static int
1450 snd_azf3328_gameport_open(struct gameport *gameport, int mode) 1459 snd_azf3328_gameport_open(struct gameport *gameport, int mode)
1451 { 1460 {
1452 struct snd_azf3328 *chip = gameport_get_port_data(gameport); 1461 struct snd_azf3328 *chip = gameport_get_port_data(gameport);
1453 int res; 1462 int res;
1454 1463
1455 snd_azf3328_dbggame("gameport_open, mode %d\n", mode); 1464 snd_azf3328_dbggame("gameport_open, mode %d\n", mode);
1456 switch (mode) { 1465 switch (mode) {
1457 case GAMEPORT_MODE_COOKED: 1466 case GAMEPORT_MODE_COOKED:
1458 case GAMEPORT_MODE_RAW: 1467 case GAMEPORT_MODE_RAW:
1459 res = 0; 1468 res = 0;
1460 break; 1469 break;
1461 default: 1470 default:
1462 res = -1; 1471 res = -1;
1463 break; 1472 break;
1464 } 1473 }
1465 1474
1466 snd_azf3328_gameport_set_counter_frequency(chip, 1475 snd_azf3328_gameport_set_counter_frequency(chip,
1467 GAME_HWCFG_ADC_COUNTER_FREQ_STD); 1476 GAME_HWCFG_ADC_COUNTER_FREQ_STD);
1468 snd_azf3328_gameport_axis_circuit_enable(chip, (res == 0)); 1477 snd_azf3328_gameport_axis_circuit_enable(chip, (res == 0));
1469 1478
1470 return res; 1479 return res;
1471 } 1480 }
1472 1481
1473 static void 1482 static void
1474 snd_azf3328_gameport_close(struct gameport *gameport) 1483 snd_azf3328_gameport_close(struct gameport *gameport)
1475 { 1484 {
1476 struct snd_azf3328 *chip = gameport_get_port_data(gameport); 1485 struct snd_azf3328 *chip = gameport_get_port_data(gameport);
1477 1486
1478 snd_azf3328_dbggame("gameport_close\n"); 1487 snd_azf3328_dbggame("gameport_close\n");
1479 snd_azf3328_gameport_set_counter_frequency(chip, 1488 snd_azf3328_gameport_set_counter_frequency(chip,
1480 GAME_HWCFG_ADC_COUNTER_FREQ_1_200); 1489 GAME_HWCFG_ADC_COUNTER_FREQ_1_200);
1481 snd_azf3328_gameport_axis_circuit_enable(chip, 0); 1490 snd_azf3328_gameport_axis_circuit_enable(chip, 0);
1482 } 1491 }
1483 1492
1484 static int 1493 static int
1485 snd_azf3328_gameport_cooked_read(struct gameport *gameport, 1494 snd_azf3328_gameport_cooked_read(struct gameport *gameport,
1486 int *axes, 1495 int *axes,
1487 int *buttons 1496 int *buttons
1488 ) 1497 )
1489 { 1498 {
1490 struct snd_azf3328 *chip = gameport_get_port_data(gameport); 1499 struct snd_azf3328 *chip = gameport_get_port_data(gameport);
1491 int i; 1500 int i;
1492 u8 val; 1501 u8 val;
1493 unsigned long flags; 1502 unsigned long flags;
1494 1503
1495 if (snd_BUG_ON(!chip)) 1504 if (snd_BUG_ON(!chip))
1496 return 0; 1505 return 0;
1497 1506
1498 spin_lock_irqsave(&chip->reg_lock, flags); 1507 spin_lock_irqsave(&chip->reg_lock, flags);
1499 val = snd_azf3328_game_inb(chip, IDX_GAME_LEGACY_COMPATIBLE); 1508 val = snd_azf3328_game_inb(chip, IDX_GAME_LEGACY_COMPATIBLE);
1500 *buttons = (~(val) >> 4) & 0xf; 1509 *buttons = (~(val) >> 4) & 0xf;
1501 1510
1502 /* ok, this one is a bit dirty: cooked_read is being polled by a timer, 1511 /* ok, this one is a bit dirty: cooked_read is being polled by a timer,
1503 * thus we're atomic and cannot actively wait in here 1512 * thus we're atomic and cannot actively wait in here
1504 * (which would be useful for us since it probably would be better 1513 * (which would be useful for us since it probably would be better
1505 * to trigger a measurement in here, then wait a short amount of 1514 * to trigger a measurement in here, then wait a short amount of
1506 * time until it's finished, then read values of _this_ measurement). 1515 * time until it's finished, then read values of _this_ measurement).
1507 * 1516 *
1508 * Thus we simply resort to reading values if they're available already 1517 * Thus we simply resort to reading values if they're available already
1509 * and trigger the next measurement. 1518 * and trigger the next measurement.
1510 */ 1519 */
1511 1520
1512 val = snd_azf3328_game_inb(chip, IDX_GAME_AXES_CONFIG); 1521 val = snd_azf3328_game_inb(chip, IDX_GAME_AXES_CONFIG);
1513 if (val & GAME_AXES_SAMPLING_READY) { 1522 if (val & GAME_AXES_SAMPLING_READY) {
1514 for (i = 0; i < ARRAY_SIZE(chip->axes); ++i) { 1523 for (i = 0; i < ARRAY_SIZE(chip->axes); ++i) {
1515 /* configure the axis to read */ 1524 /* configure the axis to read */
1516 val = (i << 4) | 0x0f; 1525 val = (i << 4) | 0x0f;
1517 snd_azf3328_game_outb(chip, IDX_GAME_AXES_CONFIG, val); 1526 snd_azf3328_game_outb(chip, IDX_GAME_AXES_CONFIG, val);
1518 1527
1519 chip->axes[i] = snd_azf3328_game_inw( 1528 chip->axes[i] = snd_azf3328_game_inw(
1520 chip, IDX_GAME_AXIS_VALUE 1529 chip, IDX_GAME_AXIS_VALUE
1521 ); 1530 );
1522 } 1531 }
1523 } 1532 }
1524 1533
1525 /* trigger next axes sampling, to be evaluated the next time we 1534 /* trigger next axes sampling, to be evaluated the next time we
1526 * enter this function */ 1535 * enter this function */
1527 1536
1528 /* for some very, very strange reason we cannot enable 1537 /* for some very, very strange reason we cannot enable
1529 * Measurement Ready monitoring for all axes here, 1538 * Measurement Ready monitoring for all axes here,
1530 * at least not when only one joystick connected */ 1539 * at least not when only one joystick connected */
1531 val = 0x03; /* we're able to monitor axes 1 and 2 only */ 1540 val = 0x03; /* we're able to monitor axes 1 and 2 only */
1532 snd_azf3328_game_outb(chip, IDX_GAME_AXES_CONFIG, val); 1541 snd_azf3328_game_outb(chip, IDX_GAME_AXES_CONFIG, val);
1533 1542
1534 snd_azf3328_game_outw(chip, IDX_GAME_AXIS_VALUE, 0xffff); 1543 snd_azf3328_game_outw(chip, IDX_GAME_AXIS_VALUE, 0xffff);
1535 spin_unlock_irqrestore(&chip->reg_lock, flags); 1544 spin_unlock_irqrestore(&chip->reg_lock, flags);
1536 1545
1537 for (i = 0; i < ARRAY_SIZE(chip->axes); i++) { 1546 for (i = 0; i < ARRAY_SIZE(chip->axes); i++) {
1538 axes[i] = chip->axes[i]; 1547 axes[i] = chip->axes[i];
1539 if (axes[i] == 0xffff) 1548 if (axes[i] == 0xffff)
1540 axes[i] = -1; 1549 axes[i] = -1;
1541 } 1550 }
1542 1551
1543 snd_azf3328_dbggame("cooked_read: axes %d %d %d %d buttons %d\n", 1552 snd_azf3328_dbggame("cooked_read: axes %d %d %d %d buttons %d\n",
1544 axes[0], axes[1], axes[2], axes[3], *buttons 1553 axes[0], axes[1], axes[2], axes[3], *buttons
1545 ); 1554 );
1546 1555
1547 return 0; 1556 return 0;
1548 } 1557 }
1549 1558
1550 static int __devinit 1559 static int __devinit
1551 snd_azf3328_gameport(struct snd_azf3328 *chip, int dev) 1560 snd_azf3328_gameport(struct snd_azf3328 *chip, int dev)
1552 { 1561 {
1553 struct gameport *gp; 1562 struct gameport *gp;
1554 1563
1555 chip->gameport = gp = gameport_allocate_port(); 1564 chip->gameport = gp = gameport_allocate_port();
1556 if (!gp) { 1565 if (!gp) {
1557 printk(KERN_ERR "azt3328: cannot alloc memory for gameport\n"); 1566 printk(KERN_ERR "azt3328: cannot alloc memory for gameport\n");
1558 return -ENOMEM; 1567 return -ENOMEM;
1559 } 1568 }
1560 1569
1561 gameport_set_name(gp, "AZF3328 Gameport"); 1570 gameport_set_name(gp, "AZF3328 Gameport");
1562 gameport_set_phys(gp, "pci%s/gameport0", pci_name(chip->pci)); 1571 gameport_set_phys(gp, "pci%s/gameport0", pci_name(chip->pci));
1563 gameport_set_dev_parent(gp, &chip->pci->dev); 1572 gameport_set_dev_parent(gp, &chip->pci->dev);
1564 gp->io = chip->game_io; 1573 gp->io = chip->game_io;
1565 gameport_set_port_data(gp, chip); 1574 gameport_set_port_data(gp, chip);
1566 1575
1567 gp->open = snd_azf3328_gameport_open; 1576 gp->open = snd_azf3328_gameport_open;
1568 gp->close = snd_azf3328_gameport_close; 1577 gp->close = snd_azf3328_gameport_close;
1569 gp->fuzz = 16; /* seems ok */ 1578 gp->fuzz = 16; /* seems ok */
1570 gp->cooked_read = snd_azf3328_gameport_cooked_read; 1579 gp->cooked_read = snd_azf3328_gameport_cooked_read;
1571 1580
1572 /* DISABLE legacy address: we don't need it! */ 1581 /* DISABLE legacy address: we don't need it! */
1573 snd_azf3328_gameport_legacy_address_enable(chip, 0); 1582 snd_azf3328_gameport_legacy_address_enable(chip, 0);
1574 1583
1575 snd_azf3328_gameport_set_counter_frequency(chip, 1584 snd_azf3328_gameport_set_counter_frequency(chip,
1576 GAME_HWCFG_ADC_COUNTER_FREQ_1_200); 1585 GAME_HWCFG_ADC_COUNTER_FREQ_1_200);
1577 snd_azf3328_gameport_axis_circuit_enable(chip, 0); 1586 snd_azf3328_gameport_axis_circuit_enable(chip, 0);
1578 1587
1579 gameport_register_port(chip->gameport); 1588 gameport_register_port(chip->gameport);
1580 1589
1581 return 0; 1590 return 0;
1582 } 1591 }
1583 1592
1584 static void 1593 static void
1585 snd_azf3328_gameport_free(struct snd_azf3328 *chip) 1594 snd_azf3328_gameport_free(struct snd_azf3328 *chip)
1586 { 1595 {
1587 if (chip->gameport) { 1596 if (chip->gameport) {
1588 gameport_unregister_port(chip->gameport); 1597 gameport_unregister_port(chip->gameport);
1589 chip->gameport = NULL; 1598 chip->gameport = NULL;
1590 } 1599 }
1591 snd_azf3328_gameport_irq_enable(chip, 0); 1600 snd_azf3328_gameport_irq_enable(chip, 0);
1592 } 1601 }
1593 #else 1602 #else
1594 static inline int 1603 static inline int
1595 snd_azf3328_gameport(struct snd_azf3328 *chip, int dev) { return -ENOSYS; } 1604 snd_azf3328_gameport(struct snd_azf3328 *chip, int dev) { return -ENOSYS; }
1596 static inline void 1605 static inline void
1597 snd_azf3328_gameport_free(struct snd_azf3328 *chip) { } 1606 snd_azf3328_gameport_free(struct snd_azf3328 *chip) { }
1598 static inline void 1607 static inline void
1599 snd_azf3328_gameport_interrupt(struct snd_azf3328 *chip) 1608 snd_azf3328_gameport_interrupt(struct snd_azf3328 *chip)
1600 { 1609 {
1601 printk(KERN_WARNING "huh, game port IRQ occurred!?\n"); 1610 printk(KERN_WARNING "huh, game port IRQ occurred!?\n");
1602 } 1611 }
1603 #endif /* SUPPORT_GAMEPORT */ 1612 #endif /* SUPPORT_GAMEPORT */
1604 1613
1605 /******************************************************************/ 1614 /******************************************************************/
1606 1615
1607 static inline void 1616 static inline void
1608 snd_azf3328_irq_log_unknown_type(u8 which) 1617 snd_azf3328_irq_log_unknown_type(u8 which)
1609 { 1618 {
1610 snd_azf3328_dbgplay( 1619 snd_azf3328_dbgcodec(
1611 "azt3328: unknown IRQ type (%x) occurred, please report!\n", 1620 "azt3328: unknown IRQ type (%x) occurred, please report!\n",
1612 which 1621 which
1613 ); 1622 );
1614 } 1623 }
1615 1624
1616 static inline void 1625 static inline void
1617 snd_azf3328_codec_interrupt(struct snd_azf3328 *chip, u8 status) 1626 snd_azf3328_codec_interrupt(struct snd_azf3328 *chip, u8 status)
1618 { 1627 {
1619 u8 which; 1628 u8 which;
1620 enum snd_azf3328_codec_type codec_type; 1629 enum snd_azf3328_codec_type codec_type;
1621 const struct snd_azf3328_codec_data *codec; 1630 const struct snd_azf3328_codec_data *codec;
1622 1631
1623 for (codec_type = AZF_CODEC_PLAYBACK; 1632 for (codec_type = AZF_CODEC_PLAYBACK;
1624 codec_type <= AZF_CODEC_I2S_OUT; 1633 codec_type <= AZF_CODEC_I2S_OUT;
1625 ++codec_type) { 1634 ++codec_type) {
1626 1635
1627 /* skip codec if there's no interrupt for it */ 1636 /* skip codec if there's no interrupt for it */
1628 if (!(status & (1 << codec_type))) 1637 if (!(status & (1 << codec_type)))
1629 continue; 1638 continue;
1630 1639
1631 codec = &chip->codecs[codec_type]; 1640 codec = &chip->codecs[codec_type];
1632 1641
1633 spin_lock(&chip->reg_lock); 1642 spin_lock(&chip->reg_lock);
1634 which = snd_azf3328_codec_inb(codec, IDX_IO_CODEC_IRQTYPE); 1643 which = snd_azf3328_codec_inb(codec, IDX_IO_CODEC_IRQTYPE);
1635 /* ack all IRQ types immediately */ 1644 /* ack all IRQ types immediately */
1636 snd_azf3328_codec_outb(codec, IDX_IO_CODEC_IRQTYPE, which); 1645 snd_azf3328_codec_outb(codec, IDX_IO_CODEC_IRQTYPE, which);
1637 spin_unlock(&chip->reg_lock); 1646 spin_unlock(&chip->reg_lock);
1638 1647
1639 if ((chip->pcm[codec_type]) 1648 if ((chip->pcm[codec_type]) && (codec->substream)) {
1640 && (chip->codecs[codec_type].substream)) { 1649 snd_pcm_period_elapsed(codec->substream);
1641 snd_pcm_period_elapsed( 1650 snd_azf3328_dbgcodec("%s period done (#%x), @ %x\n",
1642 chip->codecs[codec_type].substream
1643 );
1644 snd_azf3328_dbgplay("%s period done (#%x), @ %x\n",
1645 codec->name, 1651 codec->name,
1646 which, 1652 which,
1647 snd_azf3328_codec_inl( 1653 snd_azf3328_codec_inl(
1648 codec, IDX_IO_CODEC_DMA_CURRPOS 1654 codec, IDX_IO_CODEC_DMA_CURRPOS
1649 ) 1655 )
1650 ); 1656 );
1651 } else 1657 } else
1652 printk(KERN_WARNING "azt3328: irq handler problem!\n"); 1658 printk(KERN_WARNING "azt3328: irq handler problem!\n");
1653 if (which & IRQ_SOMETHING) 1659 if (which & IRQ_SOMETHING)
1654 snd_azf3328_irq_log_unknown_type(which); 1660 snd_azf3328_irq_log_unknown_type(which);
1655 } 1661 }
1656 } 1662 }
1657 1663
1658 static irqreturn_t 1664 static irqreturn_t
1659 snd_azf3328_interrupt(int irq, void *dev_id) 1665 snd_azf3328_interrupt(int irq, void *dev_id)
1660 { 1666 {
1661 struct snd_azf3328 *chip = dev_id; 1667 struct snd_azf3328 *chip = dev_id;
1662 u8 status; 1668 u8 status;
1663 #if DEBUG_PLAY_REC 1669 #if DEBUG_CODEC
1664 static unsigned long irq_count; 1670 static unsigned long irq_count;
1665 #endif 1671 #endif
1666 1672
1667 status = snd_azf3328_ctrl_inb(chip, IDX_IO_IRQSTATUS); 1673 status = snd_azf3328_ctrl_inb(chip, IDX_IO_IRQSTATUS);
1668 1674
1669 /* fast path out, to ease interrupt sharing */ 1675 /* fast path out, to ease interrupt sharing */
1670 if (!(status & 1676 if (!(status &
1671 (IRQ_PLAYBACK|IRQ_RECORDING|IRQ_I2S_OUT 1677 (IRQ_PLAYBACK|IRQ_RECORDING|IRQ_I2S_OUT
1672 |IRQ_GAMEPORT|IRQ_MPU401|IRQ_TIMER) 1678 |IRQ_GAMEPORT|IRQ_MPU401|IRQ_TIMER)
1673 )) 1679 ))
1674 return IRQ_NONE; /* must be interrupt for another device */ 1680 return IRQ_NONE; /* must be interrupt for another device */
1675 1681
1676 snd_azf3328_dbgplay( 1682 snd_azf3328_dbgcodec(
1677 "irq_count %ld! IDX_IO_IRQSTATUS %04x\n", 1683 "irq_count %ld! IDX_IO_IRQSTATUS %04x\n",
1678 irq_count++ /* debug-only */, 1684 irq_count++ /* debug-only */,
1679 status 1685 status
1680 ); 1686 );
1681 1687
1682 if (status & IRQ_TIMER) { 1688 if (status & IRQ_TIMER) {
1683 /* snd_azf3328_dbgplay("timer %ld\n", 1689 /* snd_azf3328_dbgcodec("timer %ld\n",
1684 snd_azf3328_codec_inl(chip, IDX_IO_TIMER_VALUE) 1690 snd_azf3328_codec_inl(chip, IDX_IO_TIMER_VALUE)
1685 & TIMER_VALUE_MASK 1691 & TIMER_VALUE_MASK
1686 ); */ 1692 ); */
1687 if (chip->timer) 1693 if (chip->timer)
1688 snd_timer_interrupt(chip->timer, chip->timer->sticks); 1694 snd_timer_interrupt(chip->timer, chip->timer->sticks);
1689 /* ACK timer */ 1695 /* ACK timer */
1690 spin_lock(&chip->reg_lock); 1696 spin_lock(&chip->reg_lock);
1691 snd_azf3328_ctrl_outb(chip, IDX_IO_TIMER_VALUE + 3, 0x07); 1697 snd_azf3328_ctrl_outb(chip, IDX_IO_TIMER_VALUE + 3, 0x07);
1692 spin_unlock(&chip->reg_lock); 1698 spin_unlock(&chip->reg_lock);
1693 snd_azf3328_dbgplay("azt3328: timer IRQ\n"); 1699 snd_azf3328_dbgcodec("azt3328: timer IRQ\n");
1694 } 1700 }
1695 1701
1696 if (status & (IRQ_PLAYBACK|IRQ_RECORDING|IRQ_I2S_OUT)) 1702 if (status & (IRQ_PLAYBACK|IRQ_RECORDING|IRQ_I2S_OUT))
1697 snd_azf3328_codec_interrupt(chip, status); 1703 snd_azf3328_codec_interrupt(chip, status);
1698 1704
1699 if (status & IRQ_GAMEPORT) 1705 if (status & IRQ_GAMEPORT)
1700 snd_azf3328_gameport_interrupt(chip); 1706 snd_azf3328_gameport_interrupt(chip);
1701 1707
1702 /* MPU401 has less critical IRQ requirements 1708 /* MPU401 has less critical IRQ requirements
1703 * than timer and playback/recording, right? */ 1709 * than timer and playback/recording, right? */
1704 if (status & IRQ_MPU401) { 1710 if (status & IRQ_MPU401) {
1705 snd_mpu401_uart_interrupt(irq, chip->rmidi->private_data); 1711 snd_mpu401_uart_interrupt(irq, chip->rmidi->private_data);
1706 1712
1707 /* hmm, do we have to ack the IRQ here somehow? 1713 /* hmm, do we have to ack the IRQ here somehow?
1708 * If so, then I don't know how yet... */ 1714 * If so, then I don't know how yet... */
1709 snd_azf3328_dbgplay("azt3328: MPU401 IRQ\n"); 1715 snd_azf3328_dbgcodec("azt3328: MPU401 IRQ\n");
1710 } 1716 }
1711 return IRQ_HANDLED; 1717 return IRQ_HANDLED;
1712 } 1718 }
1713 1719
1714 /*****************************************************************/ 1720 /*****************************************************************/
1715 1721
1716 /* as long as we think we have identical snd_pcm_hardware parameters 1722 /* as long as we think we have identical snd_pcm_hardware parameters
1717 for playback, capture and i2s out, we can use the same physical struct 1723 for playback, capture and i2s out, we can use the same physical struct
1718 since the struct is simply being copied into a member. 1724 since the struct is simply being copied into a member.
1719 */ 1725 */
1720 static const struct snd_pcm_hardware snd_azf3328_hardware = 1726 static const struct snd_pcm_hardware snd_azf3328_hardware =
1721 { 1727 {
1722 /* FIXME!! Correct? */ 1728 /* FIXME!! Correct? */
1723 .info = SNDRV_PCM_INFO_MMAP | 1729 .info = SNDRV_PCM_INFO_MMAP |
1724 SNDRV_PCM_INFO_INTERLEAVED | 1730 SNDRV_PCM_INFO_INTERLEAVED |
1725 SNDRV_PCM_INFO_MMAP_VALID, 1731 SNDRV_PCM_INFO_MMAP_VALID,
1726 .formats = SNDRV_PCM_FMTBIT_S8 | 1732 .formats = SNDRV_PCM_FMTBIT_S8 |
1727 SNDRV_PCM_FMTBIT_U8 | 1733 SNDRV_PCM_FMTBIT_U8 |
1728 SNDRV_PCM_FMTBIT_S16_LE | 1734 SNDRV_PCM_FMTBIT_S16_LE |
1729 SNDRV_PCM_FMTBIT_U16_LE, 1735 SNDRV_PCM_FMTBIT_U16_LE,
1730 .rates = SNDRV_PCM_RATE_5512 | 1736 .rates = SNDRV_PCM_RATE_5512 |
1731 SNDRV_PCM_RATE_8000_48000 | 1737 SNDRV_PCM_RATE_8000_48000 |
1732 SNDRV_PCM_RATE_KNOT, 1738 SNDRV_PCM_RATE_KNOT,
1733 .rate_min = AZF_FREQ_4000, 1739 .rate_min = AZF_FREQ_4000,
1734 .rate_max = AZF_FREQ_66200, 1740 .rate_max = AZF_FREQ_66200,
1735 .channels_min = 1, 1741 .channels_min = 1,
1736 .channels_max = 2, 1742 .channels_max = 2,
1737 .buffer_bytes_max = 65536, 1743 .buffer_bytes_max = 65536,
1738 .period_bytes_min = 64, 1744 .period_bytes_min = 64,
1739 .period_bytes_max = 65536, 1745 .period_bytes_max = 65536,
1740 .periods_min = 1, 1746 .periods_min = 1,
1741 .periods_max = 1024, 1747 .periods_max = 1024,
1742 /* FIXME: maybe that card actually has a FIFO? 1748 /* FIXME: maybe that card actually has a FIFO?
1743 * Hmm, it seems newer revisions do have one, but we still don't know 1749 * Hmm, it seems newer revisions do have one, but we still don't know
1744 * its size... */ 1750 * its size... */
1745 .fifo_size = 0, 1751 .fifo_size = 0,
1746 }; 1752 };
1747 1753
1748 1754
1749 static unsigned int snd_azf3328_fixed_rates[] = { 1755 static unsigned int snd_azf3328_fixed_rates[] = {
1750 AZF_FREQ_4000, 1756 AZF_FREQ_4000,
1751 AZF_FREQ_4800, 1757 AZF_FREQ_4800,
1752 AZF_FREQ_5512, 1758 AZF_FREQ_5512,
1753 AZF_FREQ_6620, 1759 AZF_FREQ_6620,
1754 AZF_FREQ_8000, 1760 AZF_FREQ_8000,
1755 AZF_FREQ_9600, 1761 AZF_FREQ_9600,
1756 AZF_FREQ_11025, 1762 AZF_FREQ_11025,
1757 AZF_FREQ_13240, 1763 AZF_FREQ_13240,
1758 AZF_FREQ_16000, 1764 AZF_FREQ_16000,
1759 AZF_FREQ_22050, 1765 AZF_FREQ_22050,
1760 AZF_FREQ_32000, 1766 AZF_FREQ_32000,
1761 AZF_FREQ_44100, 1767 AZF_FREQ_44100,
1762 AZF_FREQ_48000, 1768 AZF_FREQ_48000,
1763 AZF_FREQ_66200 1769 AZF_FREQ_66200
1764 }; 1770 };
1765 1771
1766 static struct snd_pcm_hw_constraint_list snd_azf3328_hw_constraints_rates = { 1772 static struct snd_pcm_hw_constraint_list snd_azf3328_hw_constraints_rates = {
1767 .count = ARRAY_SIZE(snd_azf3328_fixed_rates), 1773 .count = ARRAY_SIZE(snd_azf3328_fixed_rates),
1768 .list = snd_azf3328_fixed_rates, 1774 .list = snd_azf3328_fixed_rates,
1769 .mask = 0, 1775 .mask = 0,
1770 }; 1776 };
1771 1777
1772 /*****************************************************************/ 1778 /*****************************************************************/
1773 1779
1774 static int 1780 static int
1775 snd_azf3328_pcm_open(struct snd_pcm_substream *substream, 1781 snd_azf3328_pcm_open(struct snd_pcm_substream *substream,
1776 enum snd_azf3328_codec_type codec_type 1782 enum snd_azf3328_codec_type codec_type
1777 ) 1783 )
1778 { 1784 {
1779 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream); 1785 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream);
1780 struct snd_pcm_runtime *runtime = substream->runtime; 1786 struct snd_pcm_runtime *runtime = substream->runtime;
1781 1787
1782 snd_azf3328_dbgcallenter(); 1788 snd_azf3328_dbgcallenter();
1783 chip->codecs[codec_type].substream = substream; 1789 chip->codecs[codec_type].substream = substream;
1784 1790
1785 /* same parameters for all our codecs - at least we think so... */ 1791 /* same parameters for all our codecs - at least we think so... */
1786 runtime->hw = snd_azf3328_hardware; 1792 runtime->hw = snd_azf3328_hardware;
1787 1793
1788 snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE, 1794 snd_pcm_hw_constraint_list(runtime, 0, SNDRV_PCM_HW_PARAM_RATE,
1789 &snd_azf3328_hw_constraints_rates); 1795 &snd_azf3328_hw_constraints_rates);
1790 snd_azf3328_dbgcallleave(); 1796 snd_azf3328_dbgcallleave();
1791 return 0; 1797 return 0;
1792 } 1798 }
1793 1799
1794 static int 1800 static int
1795 snd_azf3328_playback_open(struct snd_pcm_substream *substream) 1801 snd_azf3328_playback_open(struct snd_pcm_substream *substream)
1796 { 1802 {
1797 return snd_azf3328_pcm_open(substream, AZF_CODEC_PLAYBACK); 1803 return snd_azf3328_pcm_open(substream, AZF_CODEC_PLAYBACK);
1798 } 1804 }
1799 1805
1800 static int 1806 static int
1801 snd_azf3328_capture_open(struct snd_pcm_substream *substream) 1807 snd_azf3328_capture_open(struct snd_pcm_substream *substream)
1802 { 1808 {
1803 return snd_azf3328_pcm_open(substream, AZF_CODEC_CAPTURE); 1809 return snd_azf3328_pcm_open(substream, AZF_CODEC_CAPTURE);
1804 } 1810 }
1805 1811
1806 static int 1812 static int
1807 snd_azf3328_i2s_out_open(struct snd_pcm_substream *substream) 1813 snd_azf3328_i2s_out_open(struct snd_pcm_substream *substream)
1808 { 1814 {
1809 return snd_azf3328_pcm_open(substream, AZF_CODEC_I2S_OUT); 1815 return snd_azf3328_pcm_open(substream, AZF_CODEC_I2S_OUT);
1810 } 1816 }
1811 1817
1812 static int 1818 static int
1813 snd_azf3328_pcm_close(struct snd_pcm_substream *substream, 1819 snd_azf3328_pcm_close(struct snd_pcm_substream *substream,
1814 enum snd_azf3328_codec_type codec_type 1820 enum snd_azf3328_codec_type codec_type
1815 ) 1821 )
1816 { 1822 {
1817 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream); 1823 struct snd_azf3328 *chip = snd_pcm_substream_chip(substream);
1818 1824
1819 snd_azf3328_dbgcallenter(); 1825 snd_azf3328_dbgcallenter();
1820 chip->codecs[codec_type].substream = NULL; 1826 chip->codecs[codec_type].substream = NULL;
1821 snd_azf3328_dbgcallleave(); 1827 snd_azf3328_dbgcallleave();
1822 return 0; 1828 return 0;
1823 } 1829 }
1824 1830
1825 static int 1831 static int
1826 snd_azf3328_playback_close(struct snd_pcm_substream *substream) 1832 snd_azf3328_playback_close(struct snd_pcm_substream *substream)
1827 { 1833 {
1828 return snd_azf3328_pcm_close(substream, AZF_CODEC_PLAYBACK); 1834 return snd_azf3328_pcm_close(substream, AZF_CODEC_PLAYBACK);
1829 } 1835 }
1830 1836
1831 static int 1837 static int
1832 snd_azf3328_capture_close(struct snd_pcm_substream *substream) 1838 snd_azf3328_capture_close(struct snd_pcm_substream *substream)
1833 { 1839 {
1834 return snd_azf3328_pcm_close(substream, AZF_CODEC_CAPTURE); 1840 return snd_azf3328_pcm_close(substream, AZF_CODEC_CAPTURE);
1835 } 1841 }
1836 1842
1837 static int 1843 static int
1838 snd_azf3328_i2s_out_close(struct snd_pcm_substream *substream) 1844 snd_azf3328_i2s_out_close(struct snd_pcm_substream *substream)
1839 { 1845 {
1840 return snd_azf3328_pcm_close(substream, AZF_CODEC_I2S_OUT); 1846 return snd_azf3328_pcm_close(substream, AZF_CODEC_I2S_OUT);
1841 } 1847 }
1842 1848
1843 /******************************************************************/ 1849 /******************************************************************/
1844 1850
1845 static struct snd_pcm_ops snd_azf3328_playback_ops = { 1851 static struct snd_pcm_ops snd_azf3328_playback_ops = {
1846 .open = snd_azf3328_playback_open, 1852 .open = snd_azf3328_playback_open,
1847 .close = snd_azf3328_playback_close, 1853 .close = snd_azf3328_playback_close,
1848 .ioctl = snd_pcm_lib_ioctl, 1854 .ioctl = snd_pcm_lib_ioctl,
1849 .hw_params = snd_azf3328_hw_params, 1855 .hw_params = snd_azf3328_hw_params,
1850 .hw_free = snd_azf3328_hw_free, 1856 .hw_free = snd_azf3328_hw_free,
1851 .prepare = snd_azf3328_codec_prepare, 1857 .prepare = snd_azf3328_codec_prepare,
1852 .trigger = snd_azf3328_codec_playback_trigger, 1858 .trigger = snd_azf3328_codec_playback_trigger,
1853 .pointer = snd_azf3328_codec_playback_pointer 1859 .pointer = snd_azf3328_codec_playback_pointer
1854 }; 1860 };
1855 1861
1856 static struct snd_pcm_ops snd_azf3328_capture_ops = { 1862 static struct snd_pcm_ops snd_azf3328_capture_ops = {
1857 .open = snd_azf3328_capture_open, 1863 .open = snd_azf3328_capture_open,
1858 .close = snd_azf3328_capture_close, 1864 .close = snd_azf3328_capture_close,
1859 .ioctl = snd_pcm_lib_ioctl, 1865 .ioctl = snd_pcm_lib_ioctl,
1860 .hw_params = snd_azf3328_hw_params, 1866 .hw_params = snd_azf3328_hw_params,
1861 .hw_free = snd_azf3328_hw_free, 1867 .hw_free = snd_azf3328_hw_free,
1862 .prepare = snd_azf3328_codec_prepare, 1868 .prepare = snd_azf3328_codec_prepare,
1863 .trigger = snd_azf3328_codec_capture_trigger, 1869 .trigger = snd_azf3328_codec_capture_trigger,
1864 .pointer = snd_azf3328_codec_capture_pointer 1870 .pointer = snd_azf3328_codec_capture_pointer
1865 }; 1871 };
1866 1872
1867 static struct snd_pcm_ops snd_azf3328_i2s_out_ops = { 1873 static struct snd_pcm_ops snd_azf3328_i2s_out_ops = {
1868 .open = snd_azf3328_i2s_out_open, 1874 .open = snd_azf3328_i2s_out_open,
1869 .close = snd_azf3328_i2s_out_close, 1875 .close = snd_azf3328_i2s_out_close,
1870 .ioctl = snd_pcm_lib_ioctl, 1876 .ioctl = snd_pcm_lib_ioctl,
1871 .hw_params = snd_azf3328_hw_params, 1877 .hw_params = snd_azf3328_hw_params,
1872 .hw_free = snd_azf3328_hw_free, 1878 .hw_free = snd_azf3328_hw_free,
1873 .prepare = snd_azf3328_codec_prepare, 1879 .prepare = snd_azf3328_codec_prepare,
1874 .trigger = snd_azf3328_codec_i2s_out_trigger, 1880 .trigger = snd_azf3328_codec_i2s_out_trigger,
1875 .pointer = snd_azf3328_codec_i2s_out_pointer 1881 .pointer = snd_azf3328_codec_i2s_out_pointer
1876 }; 1882 };
1877 1883
1878 static int __devinit 1884 static int __devinit
1879 snd_azf3328_pcm(struct snd_azf3328 *chip) 1885 snd_azf3328_pcm(struct snd_azf3328 *chip)
1880 { 1886 {
1881 enum { AZF_PCMDEV_STD, AZF_PCMDEV_I2S_OUT, NUM_AZF_PCMDEVS }; /* pcm devices */ 1887 enum { AZF_PCMDEV_STD, AZF_PCMDEV_I2S_OUT, NUM_AZF_PCMDEVS }; /* pcm devices */
1882 1888
1883 struct snd_pcm *pcm; 1889 struct snd_pcm *pcm;
1884 int err; 1890 int err;
1885 1891
1886 snd_azf3328_dbgcallenter(); 1892 snd_azf3328_dbgcallenter();
1887 1893
1888 err = snd_pcm_new(chip->card, "AZF3328 DSP", AZF_PCMDEV_STD, 1894 err = snd_pcm_new(chip->card, "AZF3328 DSP", AZF_PCMDEV_STD,
1889 1, 1, &pcm); 1895 1, 1, &pcm);
1890 if (err < 0) 1896 if (err < 0)
1891 return err; 1897 return err;
1892 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, 1898 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK,
1893 &snd_azf3328_playback_ops); 1899 &snd_azf3328_playback_ops);
1894 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, 1900 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE,
1895 &snd_azf3328_capture_ops); 1901 &snd_azf3328_capture_ops);
1896 1902
1897 pcm->private_data = chip; 1903 pcm->private_data = chip;
1898 pcm->info_flags = 0; 1904 pcm->info_flags = 0;
1899 strcpy(pcm->name, chip->card->shortname); 1905 strcpy(pcm->name, chip->card->shortname);
1900 /* same pcm object for playback/capture (see snd_pcm_new() above) */ 1906 /* same pcm object for playback/capture (see snd_pcm_new() above) */
1901 chip->pcm[AZF_CODEC_PLAYBACK] = pcm; 1907 chip->pcm[AZF_CODEC_PLAYBACK] = pcm;
1902 chip->pcm[AZF_CODEC_CAPTURE] = pcm; 1908 chip->pcm[AZF_CODEC_CAPTURE] = pcm;
1903 1909
1904 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV, 1910 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV,
1905 snd_dma_pci_data(chip->pci), 1911 snd_dma_pci_data(chip->pci),
1906 64*1024, 64*1024); 1912 64*1024, 64*1024);
1907 1913
1908 err = snd_pcm_new(chip->card, "AZF3328 I2S OUT", AZF_PCMDEV_I2S_OUT, 1914 err = snd_pcm_new(chip->card, "AZF3328 I2S OUT", AZF_PCMDEV_I2S_OUT,
1909 1, 0, &pcm); 1915 1, 0, &pcm);
1910 if (err < 0) 1916 if (err < 0)
1911 return err; 1917 return err;
1912 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, 1918 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK,
1913 &snd_azf3328_i2s_out_ops); 1919 &snd_azf3328_i2s_out_ops);
1914 1920
1915 pcm->private_data = chip; 1921 pcm->private_data = chip;
1916 pcm->info_flags = 0; 1922 pcm->info_flags = 0;
1917 strcpy(pcm->name, chip->card->shortname); 1923 strcpy(pcm->name, chip->card->shortname);
1918 chip->pcm[AZF_CODEC_I2S_OUT] = pcm; 1924 chip->pcm[AZF_CODEC_I2S_OUT] = pcm;
1919 1925
1920 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV, 1926 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_DEV,
1921 snd_dma_pci_data(chip->pci), 1927 snd_dma_pci_data(chip->pci),
1922 64*1024, 64*1024); 1928 64*1024, 64*1024);
1923 1929
1924 snd_azf3328_dbgcallleave(); 1930 snd_azf3328_dbgcallleave();
1925 return 0; 1931 return 0;
1926 } 1932 }
1927 1933
1928 /******************************************************************/ 1934 /******************************************************************/
1929 1935
1930 /*** NOTE: the physical timer resolution actually is 1024000 ticks per second 1936 /*** NOTE: the physical timer resolution actually is 1024000 ticks per second
1931 *** (probably derived from main crystal via a divider of 24), 1937 *** (probably derived from main crystal via a divider of 24),
1932 *** but announcing those attributes to user-space would make programs 1938 *** but announcing those attributes to user-space would make programs
1933 *** configure the timer to a 1 tick value, resulting in an absolutely fatal 1939 *** configure the timer to a 1 tick value, resulting in an absolutely fatal
1934 *** timer IRQ storm. 1940 *** timer IRQ storm.
1935 *** Thus I chose to announce a down-scaled virtual timer to the outside and 1941 *** Thus I chose to announce a down-scaled virtual timer to the outside and
1936 *** calculate real timer countdown values internally. 1942 *** calculate real timer countdown values internally.
1937 *** (the scale factor can be set via module parameter "seqtimer_scaling"). 1943 *** (the scale factor can be set via module parameter "seqtimer_scaling").
1938 ***/ 1944 ***/
1939 1945
1940 static int 1946 static int
1941 snd_azf3328_timer_start(struct snd_timer *timer) 1947 snd_azf3328_timer_start(struct snd_timer *timer)
1942 { 1948 {
1943 struct snd_azf3328 *chip; 1949 struct snd_azf3328 *chip;
1944 unsigned long flags; 1950 unsigned long flags;
1945 unsigned int delay; 1951 unsigned int delay;
1946 1952
1947 snd_azf3328_dbgcallenter(); 1953 snd_azf3328_dbgcallenter();
1948 chip = snd_timer_chip(timer); 1954 chip = snd_timer_chip(timer);
1949 delay = ((timer->sticks * seqtimer_scaling) - 1) & TIMER_VALUE_MASK; 1955 delay = ((timer->sticks * seqtimer_scaling) - 1) & TIMER_VALUE_MASK;
1950 if (delay < 49) { 1956 if (delay < 49) {
1951 /* uhoh, that's not good, since user-space won't know about 1957 /* uhoh, that's not good, since user-space won't know about
1952 * this timing tweak 1958 * this timing tweak
1953 * (we need to do it to avoid a lockup, though) */ 1959 * (we need to do it to avoid a lockup, though) */
1954 1960
1955 snd_azf3328_dbgtimer("delay was too low (%d)!\n", delay); 1961 snd_azf3328_dbgtimer("delay was too low (%d)!\n", delay);
1956 delay = 49; /* minimum time is 49 ticks */ 1962 delay = 49; /* minimum time is 49 ticks */
1957 } 1963 }
1958 snd_azf3328_dbgtimer("setting timer countdown value %d, add COUNTDOWN|IRQ\n", delay); 1964 snd_azf3328_dbgtimer("setting timer countdown value %d, add COUNTDOWN|IRQ\n", delay);
1959 delay |= TIMER_COUNTDOWN_ENABLE | TIMER_IRQ_ENABLE; 1965 delay |= TIMER_COUNTDOWN_ENABLE | TIMER_IRQ_ENABLE;
1960 spin_lock_irqsave(&chip->reg_lock, flags); 1966 spin_lock_irqsave(&chip->reg_lock, flags);
1961 snd_azf3328_ctrl_outl(chip, IDX_IO_TIMER_VALUE, delay); 1967 snd_azf3328_ctrl_outl(chip, IDX_IO_TIMER_VALUE, delay);
1962 spin_unlock_irqrestore(&chip->reg_lock, flags); 1968 spin_unlock_irqrestore(&chip->reg_lock, flags);
1963 snd_azf3328_dbgcallleave(); 1969 snd_azf3328_dbgcallleave();
1964 return 0; 1970 return 0;
1965 } 1971 }
1966 1972
1967 static int 1973 static int
1968 snd_azf3328_timer_stop(struct snd_timer *timer) 1974 snd_azf3328_timer_stop(struct snd_timer *timer)
1969 { 1975 {
1970 struct snd_azf3328 *chip; 1976 struct snd_azf3328 *chip;
1971 unsigned long flags; 1977 unsigned long flags;
1972 1978
1973 snd_azf3328_dbgcallenter(); 1979 snd_azf3328_dbgcallenter();
1974 chip = snd_timer_chip(timer); 1980 chip = snd_timer_chip(timer);
1975 spin_lock_irqsave(&chip->reg_lock, flags); 1981 spin_lock_irqsave(&chip->reg_lock, flags);
1976 /* disable timer countdown and interrupt */ 1982 /* disable timer countdown and interrupt */
1977 /* FIXME: should we write TIMER_IRQ_ACK here? */ 1983 /* FIXME: should we write TIMER_IRQ_ACK here? */
1978 snd_azf3328_ctrl_outb(chip, IDX_IO_TIMER_VALUE + 3, 0); 1984 snd_azf3328_ctrl_outb(chip, IDX_IO_TIMER_VALUE + 3, 0);
1979 spin_unlock_irqrestore(&chip->reg_lock, flags); 1985 spin_unlock_irqrestore(&chip->reg_lock, flags);
1980 snd_azf3328_dbgcallleave(); 1986 snd_azf3328_dbgcallleave();
1981 return 0; 1987 return 0;
1982 } 1988 }
1983 1989
1984 1990
1985 static int 1991 static int
1986 snd_azf3328_timer_precise_resolution(struct snd_timer *timer, 1992 snd_azf3328_timer_precise_resolution(struct snd_timer *timer,
1987 unsigned long *num, unsigned long *den) 1993 unsigned long *num, unsigned long *den)
1988 { 1994 {
1989 snd_azf3328_dbgcallenter(); 1995 snd_azf3328_dbgcallenter();
1990 *num = 1; 1996 *num = 1;
1991 *den = 1024000 / seqtimer_scaling; 1997 *den = 1024000 / seqtimer_scaling;
1992 snd_azf3328_dbgcallleave(); 1998 snd_azf3328_dbgcallleave();
1993 return 0; 1999 return 0;
1994 } 2000 }
1995 2001
1996 static struct snd_timer_hardware snd_azf3328_timer_hw = { 2002 static struct snd_timer_hardware snd_azf3328_timer_hw = {
1997 .flags = SNDRV_TIMER_HW_AUTO, 2003 .flags = SNDRV_TIMER_HW_AUTO,
1998 .resolution = 977, /* 1000000/1024000 = 0.9765625us */ 2004 .resolution = 977, /* 1000000/1024000 = 0.9765625us */
1999 .ticks = 1024000, /* max tick count, defined by the value register; actually it's not 1024000, but 1048576, but we don't care */ 2005 .ticks = 1024000, /* max tick count, defined by the value register; actually it's not 1024000, but 1048576, but we don't care */
2000 .start = snd_azf3328_timer_start, 2006 .start = snd_azf3328_timer_start,
2001 .stop = snd_azf3328_timer_stop, 2007 .stop = snd_azf3328_timer_stop,
2002 .precise_resolution = snd_azf3328_timer_precise_resolution, 2008 .precise_resolution = snd_azf3328_timer_precise_resolution,
2003 }; 2009 };
2004 2010
2005 static int __devinit 2011 static int __devinit
2006 snd_azf3328_timer(struct snd_azf3328 *chip, int device) 2012 snd_azf3328_timer(struct snd_azf3328 *chip, int device)
2007 { 2013 {
2008 struct snd_timer *timer = NULL; 2014 struct snd_timer *timer = NULL;
2009 struct snd_timer_id tid; 2015 struct snd_timer_id tid;
2010 int err; 2016 int err;
2011 2017
2012 snd_azf3328_dbgcallenter(); 2018 snd_azf3328_dbgcallenter();
2013 tid.dev_class = SNDRV_TIMER_CLASS_CARD; 2019 tid.dev_class = SNDRV_TIMER_CLASS_CARD;
2014 tid.dev_sclass = SNDRV_TIMER_SCLASS_NONE; 2020 tid.dev_sclass = SNDRV_TIMER_SCLASS_NONE;
2015 tid.card = chip->card->number; 2021 tid.card = chip->card->number;
2016 tid.device = device; 2022 tid.device = device;
2017 tid.subdevice = 0; 2023 tid.subdevice = 0;
2018 2024
2019 snd_azf3328_timer_hw.resolution *= seqtimer_scaling; 2025 snd_azf3328_timer_hw.resolution *= seqtimer_scaling;
2020 snd_azf3328_timer_hw.ticks /= seqtimer_scaling; 2026 snd_azf3328_timer_hw.ticks /= seqtimer_scaling;
2021 2027
2022 err = snd_timer_new(chip->card, "AZF3328", &tid, &timer); 2028 err = snd_timer_new(chip->card, "AZF3328", &tid, &timer);
2023 if (err < 0) 2029 if (err < 0)
2024 goto out; 2030 goto out;
2025 2031
2026 strcpy(timer->name, "AZF3328 timer"); 2032 strcpy(timer->name, "AZF3328 timer");
2027 timer->private_data = chip; 2033 timer->private_data = chip;
2028 timer->hw = snd_azf3328_timer_hw; 2034 timer->hw = snd_azf3328_timer_hw;
2029 2035
2030 chip->timer = timer; 2036 chip->timer = timer;
2031 2037
2032 snd_azf3328_timer_stop(timer); 2038 snd_azf3328_timer_stop(timer);
2033 2039
2034 err = 0; 2040 err = 0;
2035 2041
2036 out: 2042 out:
2037 snd_azf3328_dbgcallleave(); 2043 snd_azf3328_dbgcallleave();
2038 return err; 2044 return err;
2039 } 2045 }
2040 2046
2041 /******************************************************************/ 2047 /******************************************************************/
2042 2048
2043 static int 2049 static int
2044 snd_azf3328_free(struct snd_azf3328 *chip) 2050 snd_azf3328_free(struct snd_azf3328 *chip)
2045 { 2051 {
2046 if (chip->irq < 0) 2052 if (chip->irq < 0)
2047 goto __end_hw; 2053 goto __end_hw;
2048 2054
2049 /* reset (close) mixer: 2055 /* reset (close) mixer:
2050 * first mute master volume, then reset 2056 * first mute master volume, then reset
2051 */ 2057 */
2052 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_PLAY_MASTER, 1); 2058 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_PLAY_MASTER, 1);
2053 snd_azf3328_mixer_outw(chip, IDX_MIXER_RESET, 0x0000); 2059 snd_azf3328_mixer_outw(chip, IDX_MIXER_RESET, 0x0000);
2054 2060
2055 snd_azf3328_timer_stop(chip->timer); 2061 snd_azf3328_timer_stop(chip->timer);
2056 snd_azf3328_gameport_free(chip); 2062 snd_azf3328_gameport_free(chip);
2057 2063
2058 if (chip->irq >= 0) 2064 if (chip->irq >= 0)
2059 synchronize_irq(chip->irq); 2065 synchronize_irq(chip->irq);
2060 __end_hw: 2066 __end_hw:
2061 if (chip->irq >= 0) 2067 if (chip->irq >= 0)
2062 free_irq(chip->irq, chip); 2068 free_irq(chip->irq, chip);
2063 pci_release_regions(chip->pci); 2069 pci_release_regions(chip->pci);
2064 pci_disable_device(chip->pci); 2070 pci_disable_device(chip->pci);
2065 2071
2066 kfree(chip); 2072 kfree(chip);
2067 return 0; 2073 return 0;
2068 } 2074 }
2069 2075
2070 static int 2076 static int
2071 snd_azf3328_dev_free(struct snd_device *device) 2077 snd_azf3328_dev_free(struct snd_device *device)
2072 { 2078 {
2073 struct snd_azf3328 *chip = device->device_data; 2079 struct snd_azf3328 *chip = device->device_data;
2074 return snd_azf3328_free(chip); 2080 return snd_azf3328_free(chip);
2075 } 2081 }
2076 2082
2077 #if 0 2083 #if 0
2078 /* check whether a bit can be modified */ 2084 /* check whether a bit can be modified */
2079 static void 2085 static void
2080 snd_azf3328_test_bit(unsigned unsigned reg, int bit) 2086 snd_azf3328_test_bit(unsigned unsigned reg, int bit)
2081 { 2087 {
2082 unsigned char val, valoff, valon; 2088 unsigned char val, valoff, valon;
2083 2089
2084 val = inb(reg); 2090 val = inb(reg);
2085 2091
2086 outb(val & ~(1 << bit), reg); 2092 outb(val & ~(1 << bit), reg);
2087 valoff = inb(reg); 2093 valoff = inb(reg);
2088 2094
2089 outb(val|(1 << bit), reg); 2095 outb(val|(1 << bit), reg);
2090 valon = inb(reg); 2096 valon = inb(reg);
2091 2097
2092 outb(val, reg); 2098 outb(val, reg);
2093 2099
2094 printk(KERN_ERR "reg %04x bit %d: %02x %02x %02x\n", 2100 printk(KERN_DEBUG "reg %04x bit %d: %02x %02x %02x\n",
2095 reg, bit, val, valoff, valon 2101 reg, bit, val, valoff, valon
2096 ); 2102 );
2097 } 2103 }
2098 #endif 2104 #endif
2099 2105
2100 static inline void 2106 static inline void
2101 snd_azf3328_debug_show_ports(const struct snd_azf3328 *chip) 2107 snd_azf3328_debug_show_ports(const struct snd_azf3328 *chip)
2102 { 2108 {
2103 #if DEBUG_MISC 2109 #if DEBUG_MISC
2104 u16 tmp; 2110 u16 tmp;
2105 2111
2106 snd_azf3328_dbgmisc( 2112 snd_azf3328_dbgmisc(
2107 "ctrl_io 0x%lx, game_io 0x%lx, mpu_io 0x%lx, " 2113 "ctrl_io 0x%lx, game_io 0x%lx, mpu_io 0x%lx, "
2108 "opl3_io 0x%lx, mixer_io 0x%lx, irq %d\n", 2114 "opl3_io 0x%lx, mixer_io 0x%lx, irq %d\n",
2109 chip->ctrl_io, chip->game_io, chip->mpu_io, 2115 chip->ctrl_io, chip->game_io, chip->mpu_io,
2110 chip->opl3_io, chip->mixer_io, chip->irq 2116 chip->opl3_io, chip->mixer_io, chip->irq
2111 ); 2117 );
2112 2118
2113 snd_azf3328_dbgmisc("game %02x %02x %02x %02x %02x %02x\n", 2119 snd_azf3328_dbgmisc("game %02x %02x %02x %02x %02x %02x\n",
2114 snd_azf3328_game_inb(chip, 0), 2120 snd_azf3328_game_inb(chip, 0),
2115 snd_azf3328_game_inb(chip, 1), 2121 snd_azf3328_game_inb(chip, 1),
2116 snd_azf3328_game_inb(chip, 2), 2122 snd_azf3328_game_inb(chip, 2),
2117 snd_azf3328_game_inb(chip, 3), 2123 snd_azf3328_game_inb(chip, 3),
2118 snd_azf3328_game_inb(chip, 4), 2124 snd_azf3328_game_inb(chip, 4),
2119 snd_azf3328_game_inb(chip, 5) 2125 snd_azf3328_game_inb(chip, 5)
2120 ); 2126 );
2121 2127
2122 for (tmp = 0; tmp < 0x07; tmp += 1) 2128 for (tmp = 0; tmp < 0x07; tmp += 1)
2123 snd_azf3328_dbgmisc("mpu_io 0x%04x\n", inb(chip->mpu_io + tmp)); 2129 snd_azf3328_dbgmisc("mpu_io 0x%04x\n", inb(chip->mpu_io + tmp));
2124 2130
2125 for (tmp = 0; tmp <= 0x07; tmp += 1) 2131 for (tmp = 0; tmp <= 0x07; tmp += 1)
2126 snd_azf3328_dbgmisc("0x%02x: game200 0x%04x, game208 0x%04x\n", 2132 snd_azf3328_dbgmisc("0x%02x: game200 0x%04x, game208 0x%04x\n",
2127 tmp, inb(0x200 + tmp), inb(0x208 + tmp)); 2133 tmp, inb(0x200 + tmp), inb(0x208 + tmp));
2128 2134
2129 for (tmp = 0; tmp <= 0x01; tmp += 1) 2135 for (tmp = 0; tmp <= 0x01; tmp += 1)
2130 snd_azf3328_dbgmisc( 2136 snd_azf3328_dbgmisc(
2131 "0x%02x: mpu300 0x%04x, mpu310 0x%04x, mpu320 0x%04x, " 2137 "0x%02x: mpu300 0x%04x, mpu310 0x%04x, mpu320 0x%04x, "
2132 "mpu330 0x%04x opl388 0x%04x opl38c 0x%04x\n", 2138 "mpu330 0x%04x opl388 0x%04x opl38c 0x%04x\n",
2133 tmp, 2139 tmp,
2134 inb(0x300 + tmp), 2140 inb(0x300 + tmp),
2135 inb(0x310 + tmp), 2141 inb(0x310 + tmp),
2136 inb(0x320 + tmp), 2142 inb(0x320 + tmp),
2137 inb(0x330 + tmp), 2143 inb(0x330 + tmp),
2138 inb(0x388 + tmp), 2144 inb(0x388 + tmp),
2139 inb(0x38c + tmp) 2145 inb(0x38c + tmp)
2140 ); 2146 );
2141 2147
2142 for (tmp = 0; tmp < AZF_IO_SIZE_CTRL; tmp += 2) 2148 for (tmp = 0; tmp < AZF_IO_SIZE_CTRL; tmp += 2)
2143 snd_azf3328_dbgmisc("ctrl 0x%02x: 0x%04x\n", 2149 snd_azf3328_dbgmisc("ctrl 0x%02x: 0x%04x\n",
2144 tmp, snd_azf3328_ctrl_inw(chip, tmp) 2150 tmp, snd_azf3328_ctrl_inw(chip, tmp)
2145 ); 2151 );
2146 2152
2147 for (tmp = 0; tmp < AZF_IO_SIZE_MIXER; tmp += 2) 2153 for (tmp = 0; tmp < AZF_IO_SIZE_MIXER; tmp += 2)
2148 snd_azf3328_dbgmisc("mixer 0x%02x: 0x%04x\n", 2154 snd_azf3328_dbgmisc("mixer 0x%02x: 0x%04x\n",
2149 tmp, snd_azf3328_mixer_inw(chip, tmp) 2155 tmp, snd_azf3328_mixer_inw(chip, tmp)
2150 ); 2156 );
2151 #endif /* DEBUG_MISC */ 2157 #endif /* DEBUG_MISC */
2152 } 2158 }
2153 2159
2154 static int __devinit 2160 static int __devinit
2155 snd_azf3328_create(struct snd_card *card, 2161 snd_azf3328_create(struct snd_card *card,
2156 struct pci_dev *pci, 2162 struct pci_dev *pci,
2157 unsigned long device_type, 2163 unsigned long device_type,
2158 struct snd_azf3328 **rchip) 2164 struct snd_azf3328 **rchip)
2159 { 2165 {
2160 struct snd_azf3328 *chip; 2166 struct snd_azf3328 *chip;
2161 int err; 2167 int err;
2162 static struct snd_device_ops ops = { 2168 static struct snd_device_ops ops = {
2163 .dev_free = snd_azf3328_dev_free, 2169 .dev_free = snd_azf3328_dev_free,
2164 }; 2170 };
2165 u8 dma_init; 2171 u8 dma_init;
2166 enum snd_azf3328_codec_type codec_type; 2172 enum snd_azf3328_codec_type codec_type;
2167 2173
2168 *rchip = NULL; 2174 *rchip = NULL;
2169 2175
2170 err = pci_enable_device(pci); 2176 err = pci_enable_device(pci);
2171 if (err < 0) 2177 if (err < 0)
2172 return err; 2178 return err;
2173 2179
2174 chip = kzalloc(sizeof(*chip), GFP_KERNEL); 2180 chip = kzalloc(sizeof(*chip), GFP_KERNEL);
2175 if (chip == NULL) { 2181 if (chip == NULL) {
2176 err = -ENOMEM; 2182 err = -ENOMEM;
2177 goto out_err; 2183 goto out_err;
2178 } 2184 }
2179 spin_lock_init(&chip->reg_lock); 2185 spin_lock_init(&chip->reg_lock);
2180 chip->card = card; 2186 chip->card = card;
2181 chip->pci = pci; 2187 chip->pci = pci;
2182 chip->irq = -1; 2188 chip->irq = -1;
2183 2189
2184 /* check if we can restrict PCI DMA transfers to 24 bits */ 2190 /* check if we can restrict PCI DMA transfers to 24 bits */
2185 if (pci_set_dma_mask(pci, DMA_BIT_MASK(24)) < 0 || 2191 if (pci_set_dma_mask(pci, DMA_BIT_MASK(24)) < 0 ||
2186 pci_set_consistent_dma_mask(pci, DMA_BIT_MASK(24)) < 0) { 2192 pci_set_consistent_dma_mask(pci, DMA_BIT_MASK(24)) < 0) {
2187 snd_printk(KERN_ERR "architecture does not support " 2193 snd_printk(KERN_ERR "architecture does not support "
2188 "24bit PCI busmaster DMA\n" 2194 "24bit PCI busmaster DMA\n"
2189 ); 2195 );
2190 err = -ENXIO; 2196 err = -ENXIO;
2191 goto out_err; 2197 goto out_err;
2192 } 2198 }
2193 2199
2194 err = pci_request_regions(pci, "Aztech AZF3328"); 2200 err = pci_request_regions(pci, "Aztech AZF3328");
2195 if (err < 0) 2201 if (err < 0)
2196 goto out_err; 2202 goto out_err;
2197 2203
2198 chip->ctrl_io = pci_resource_start(pci, 0); 2204 chip->ctrl_io = pci_resource_start(pci, 0);
2199 chip->game_io = pci_resource_start(pci, 1); 2205 chip->game_io = pci_resource_start(pci, 1);
2200 chip->mpu_io = pci_resource_start(pci, 2); 2206 chip->mpu_io = pci_resource_start(pci, 2);
2201 chip->opl3_io = pci_resource_start(pci, 3); 2207 chip->opl3_io = pci_resource_start(pci, 3);
2202 chip->mixer_io = pci_resource_start(pci, 4); 2208 chip->mixer_io = pci_resource_start(pci, 4);
2203 2209
2204 chip->codecs[AZF_CODEC_PLAYBACK].io_base = 2210 chip->codecs[AZF_CODEC_PLAYBACK].io_base =
2205 chip->ctrl_io + AZF_IO_OFFS_CODEC_PLAYBACK; 2211 chip->ctrl_io + AZF_IO_OFFS_CODEC_PLAYBACK;
2206 chip->codecs[AZF_CODEC_PLAYBACK].name = "PLAYBACK"; 2212 chip->codecs[AZF_CODEC_PLAYBACK].name = "PLAYBACK";
2207 chip->codecs[AZF_CODEC_CAPTURE].io_base = 2213 chip->codecs[AZF_CODEC_CAPTURE].io_base =
2208 chip->ctrl_io + AZF_IO_OFFS_CODEC_CAPTURE; 2214 chip->ctrl_io + AZF_IO_OFFS_CODEC_CAPTURE;
2209 chip->codecs[AZF_CODEC_CAPTURE].name = "CAPTURE"; 2215 chip->codecs[AZF_CODEC_CAPTURE].name = "CAPTURE";
2210 chip->codecs[AZF_CODEC_I2S_OUT].io_base = 2216 chip->codecs[AZF_CODEC_I2S_OUT].io_base =
2211 chip->ctrl_io + AZF_IO_OFFS_CODEC_I2S_OUT; 2217 chip->ctrl_io + AZF_IO_OFFS_CODEC_I2S_OUT;
2212 chip->codecs[AZF_CODEC_I2S_OUT].name = "I2S_OUT"; 2218 chip->codecs[AZF_CODEC_I2S_OUT].name = "I2S_OUT";
2213 2219
2214 if (request_irq(pci->irq, snd_azf3328_interrupt, 2220 if (request_irq(pci->irq, snd_azf3328_interrupt,
2215 IRQF_SHARED, card->shortname, chip)) { 2221 IRQF_SHARED, card->shortname, chip)) {
2216 snd_printk(KERN_ERR "unable to grab IRQ %d\n", pci->irq); 2222 snd_printk(KERN_ERR "unable to grab IRQ %d\n", pci->irq);
2217 err = -EBUSY; 2223 err = -EBUSY;
2218 goto out_err; 2224 goto out_err;
2219 } 2225 }
2220 chip->irq = pci->irq; 2226 chip->irq = pci->irq;
2221 pci_set_master(pci); 2227 pci_set_master(pci);
2222 synchronize_irq(chip->irq); 2228 synchronize_irq(chip->irq);
2223 2229
2224 snd_azf3328_debug_show_ports(chip); 2230 snd_azf3328_debug_show_ports(chip);
2225 2231
2226 err = snd_device_new(card, SNDRV_DEV_LOWLEVEL, chip, &ops); 2232 err = snd_device_new(card, SNDRV_DEV_LOWLEVEL, chip, &ops);
2227 if (err < 0) 2233 if (err < 0)
2228 goto out_err; 2234 goto out_err;
2229 2235
2230 /* create mixer interface & switches */ 2236 /* create mixer interface & switches */
2231 err = snd_azf3328_mixer_new(chip); 2237 err = snd_azf3328_mixer_new(chip);
2232 if (err < 0) 2238 if (err < 0)
2233 goto out_err; 2239 goto out_err;
2234 2240
2235 /* standard codec init stuff */ 2241 /* standard codec init stuff */
2236 /* default DMA init value */ 2242 /* default DMA init value */
2237 dma_init = DMA_RUN_SOMETHING2|DMA_EPILOGUE_SOMETHING|DMA_SOMETHING_ELSE; 2243 dma_init = DMA_RUN_SOMETHING2|DMA_EPILOGUE_SOMETHING|DMA_SOMETHING_ELSE;
2238 2244
2239 for (codec_type = AZF_CODEC_PLAYBACK; 2245 for (codec_type = AZF_CODEC_PLAYBACK;
2240 codec_type <= AZF_CODEC_I2S_OUT; ++codec_type) { 2246 codec_type <= AZF_CODEC_I2S_OUT; ++codec_type) {
2241 struct snd_azf3328_codec_data *codec = 2247 struct snd_azf3328_codec_data *codec =
2242 &chip->codecs[codec_type]; 2248 &chip->codecs[codec_type];
2243 2249
2244 /* shutdown codecs to save power */ 2250 /* shutdown codecs to save power */
2245 /* have ...ctrl_codec_activity() act properly */ 2251 /* have ...ctrl_codec_activity() act properly */
2246 codec->running = 1; 2252 codec->running = 1;
2247 snd_azf3328_ctrl_codec_activity(chip, codec_type, 0); 2253 snd_azf3328_ctrl_codec_activity(chip, codec_type, 0);
2248 2254
2249 spin_lock_irq(&chip->reg_lock); 2255 spin_lock_irq(&chip->reg_lock);
2250 snd_azf3328_codec_outb(codec, IDX_IO_CODEC_DMA_FLAGS, 2256 snd_azf3328_codec_outb(codec, IDX_IO_CODEC_DMA_FLAGS,
2251 dma_init); 2257 dma_init);
2252 spin_unlock_irq(&chip->reg_lock); 2258 spin_unlock_irq(&chip->reg_lock);
2253 } 2259 }
2254 2260
2255 snd_card_set_dev(card, &pci->dev); 2261 snd_card_set_dev(card, &pci->dev);
2256 2262
2257 *rchip = chip; 2263 *rchip = chip;
2258 2264
2259 err = 0; 2265 err = 0;
2260 goto out; 2266 goto out;
2261 2267
2262 out_err: 2268 out_err:
2263 if (chip) 2269 if (chip)
2264 snd_azf3328_free(chip); 2270 snd_azf3328_free(chip);
2265 pci_disable_device(pci); 2271 pci_disable_device(pci);
2266 2272
2267 out: 2273 out:
2268 return err; 2274 return err;
2269 } 2275 }
2270 2276
2271 static int __devinit 2277 static int __devinit
2272 snd_azf3328_probe(struct pci_dev *pci, const struct pci_device_id *pci_id) 2278 snd_azf3328_probe(struct pci_dev *pci, const struct pci_device_id *pci_id)
2273 { 2279 {
2274 static int dev; 2280 static int dev;
2275 struct snd_card *card; 2281 struct snd_card *card;
2276 struct snd_azf3328 *chip; 2282 struct snd_azf3328 *chip;
2277 struct snd_opl3 *opl3; 2283 struct snd_opl3 *opl3;
2278 int err; 2284 int err;
2279 2285
2280 snd_azf3328_dbgcallenter(); 2286 snd_azf3328_dbgcallenter();
2281 if (dev >= SNDRV_CARDS) 2287 if (dev >= SNDRV_CARDS)
2282 return -ENODEV; 2288 return -ENODEV;
2283 if (!enable[dev]) { 2289 if (!enable[dev]) {
2284 dev++; 2290 dev++;
2285 return -ENOENT; 2291 return -ENOENT;
2286 } 2292 }
2287 2293
2288 err = snd_card_create(index[dev], id[dev], THIS_MODULE, 0, &card); 2294 err = snd_card_create(index[dev], id[dev], THIS_MODULE, 0, &card);
2289 if (err < 0) 2295 if (err < 0)
2290 return err; 2296 return err;
2291 2297
2292 strcpy(card->driver, "AZF3328"); 2298 strcpy(card->driver, "AZF3328");
2293 strcpy(card->shortname, "Aztech AZF3328 (PCI168)"); 2299 strcpy(card->shortname, "Aztech AZF3328 (PCI168)");
2294 2300
2295 err = snd_azf3328_create(card, pci, pci_id->driver_data, &chip); 2301 err = snd_azf3328_create(card, pci, pci_id->driver_data, &chip);
2296 if (err < 0) 2302 if (err < 0)
2297 goto out_err; 2303 goto out_err;
2298 2304
2299 card->private_data = chip; 2305 card->private_data = chip;
2300 2306
2307 /* chose to use MPU401_HW_AZT2320 ID instead of MPU401_HW_MPU401,
2308 since our hardware ought to be similar, thus use same ID. */
2301 err = snd_mpu401_uart_new( 2309 err = snd_mpu401_uart_new(
2302 card, 0, MPU401_HW_MPU401, chip->mpu_io, MPU401_INFO_INTEGRATED, 2310 card, 0,
2311 MPU401_HW_AZT2320, chip->mpu_io, MPU401_INFO_INTEGRATED,
2303 pci->irq, 0, &chip->rmidi 2312 pci->irq, 0, &chip->rmidi
2304 ); 2313 );
2305 if (err < 0) { 2314 if (err < 0) {
2306 snd_printk(KERN_ERR "azf3328: no MPU-401 device at 0x%lx?\n", 2315 snd_printk(KERN_ERR "azf3328: no MPU-401 device at 0x%lx?\n",
2307 chip->mpu_io 2316 chip->mpu_io
2308 ); 2317 );
2309 goto out_err; 2318 goto out_err;
2310 } 2319 }
2311 2320
2312 err = snd_azf3328_timer(chip, 0); 2321 err = snd_azf3328_timer(chip, 0);
2313 if (err < 0) 2322 if (err < 0)
2314 goto out_err; 2323 goto out_err;
2315 2324
2316 err = snd_azf3328_pcm(chip); 2325 err = snd_azf3328_pcm(chip);
2317 if (err < 0) 2326 if (err < 0)
2318 goto out_err; 2327 goto out_err;
2319 2328
2320 if (snd_opl3_create(card, chip->opl3_io, chip->opl3_io+2, 2329 if (snd_opl3_create(card, chip->opl3_io, chip->opl3_io+2,
2321 OPL3_HW_AUTO, 1, &opl3) < 0) { 2330 OPL3_HW_AUTO, 1, &opl3) < 0) {
2322 snd_printk(KERN_ERR "azf3328: no OPL3 device at 0x%lx-0x%lx?\n", 2331 snd_printk(KERN_ERR "azf3328: no OPL3 device at 0x%lx-0x%lx?\n",
2323 chip->opl3_io, chip->opl3_io+2 2332 chip->opl3_io, chip->opl3_io+2
2324 ); 2333 );
2325 } else { 2334 } else {
2326 /* need to use IDs 1, 2 since ID 0 is snd_azf3328_timer above */ 2335 /* need to use IDs 1, 2 since ID 0 is snd_azf3328_timer above */
2327 err = snd_opl3_timer_new(opl3, 1, 2); 2336 err = snd_opl3_timer_new(opl3, 1, 2);
2328 if (err < 0) 2337 if (err < 0)
2329 goto out_err; 2338 goto out_err;
2330 err = snd_opl3_hwdep_new(opl3, 0, 1, NULL); 2339 err = snd_opl3_hwdep_new(opl3, 0, 1, NULL);
2331 if (err < 0) 2340 if (err < 0)
2332 goto out_err; 2341 goto out_err;
2333 } 2342 }
2334 2343
2335 opl3->private_data = chip; 2344 opl3->private_data = chip;
2336 2345
2337 sprintf(card->longname, "%s at 0x%lx, irq %i", 2346 sprintf(card->longname, "%s at 0x%lx, irq %i",
2338 card->shortname, chip->ctrl_io, chip->irq); 2347 card->shortname, chip->ctrl_io, chip->irq);
2339 2348
2340 err = snd_card_register(card); 2349 err = snd_card_register(card);
2341 if (err < 0) 2350 if (err < 0)
2342 goto out_err; 2351 goto out_err;
2343 2352
2344 #ifdef MODULE 2353 #ifdef MODULE
2345 printk( 2354 printk(KERN_INFO
2346 "azt3328: Sound driver for Aztech AZF3328-based soundcards such as PCI168.\n" 2355 "azt3328: Sound driver for Aztech AZF3328-based soundcards such as PCI168.\n"
2347 "azt3328: Hardware was completely undocumented, unfortunately.\n" 2356 "azt3328: Hardware was completely undocumented, unfortunately.\n"
2348 "azt3328: Feel free to contact andi AT lisas.de for bug reports etc.!\n" 2357 "azt3328: Feel free to contact andi AT lisas.de for bug reports etc.!\n"
2349 "azt3328: User-scalable sequencer timer set to %dHz (1024000Hz / %d).\n", 2358 "azt3328: User-scalable sequencer timer set to %dHz (1024000Hz / %d).\n",
2350 1024000 / seqtimer_scaling, seqtimer_scaling); 2359 1024000 / seqtimer_scaling, seqtimer_scaling);
2351 #endif 2360 #endif
2352 2361
2353 snd_azf3328_gameport(chip, dev); 2362 snd_azf3328_gameport(chip, dev);
2354 2363
2355 pci_set_drvdata(pci, card); 2364 pci_set_drvdata(pci, card);
2356 dev++; 2365 dev++;
2357 2366
2358 err = 0; 2367 err = 0;
2359 goto out; 2368 goto out;
2360 2369
2361 out_err: 2370 out_err:
2362 snd_printk(KERN_ERR "azf3328: something failed, exiting\n"); 2371 snd_printk(KERN_ERR "azf3328: something failed, exiting\n");
2363 snd_card_free(card); 2372 snd_card_free(card);
2364 2373
2365 out: 2374 out:
2366 snd_azf3328_dbgcallleave(); 2375 snd_azf3328_dbgcallleave();
2367 return err; 2376 return err;
2368 } 2377 }
2369 2378
2370 static void __devexit 2379 static void __devexit
2371 snd_azf3328_remove(struct pci_dev *pci) 2380 snd_azf3328_remove(struct pci_dev *pci)
2372 { 2381 {
2373 snd_azf3328_dbgcallenter(); 2382 snd_azf3328_dbgcallenter();
2374 snd_card_free(pci_get_drvdata(pci)); 2383 snd_card_free(pci_get_drvdata(pci));
2375 pci_set_drvdata(pci, NULL); 2384 pci_set_drvdata(pci, NULL);
2376 snd_azf3328_dbgcallleave(); 2385 snd_azf3328_dbgcallleave();
2377 } 2386 }
2378 2387
2379 #ifdef CONFIG_PM 2388 #ifdef CONFIG_PM
2389 static inline void
2390 snd_azf3328_suspend_regs(unsigned long io_addr, unsigned count, u32 *saved_regs)
2391 {
2392 unsigned reg;
2393
2394 for (reg = 0; reg < count; ++reg) {
2395 *saved_regs = inl(io_addr);
2396 snd_azf3328_dbgpm("suspend: io 0x%04lx: 0x%08x\n",
2397 io_addr, *saved_regs);
2398 ++saved_regs;
2399 io_addr += sizeof(*saved_regs);
2400 }
2401 }
2402
2380 static int 2403 static int
2381 snd_azf3328_suspend(struct pci_dev *pci, pm_message_t state) 2404 snd_azf3328_suspend(struct pci_dev *pci, pm_message_t state)
2382 { 2405 {
2383 struct snd_card *card = pci_get_drvdata(pci); 2406 struct snd_card *card = pci_get_drvdata(pci);
2384 struct snd_azf3328 *chip = card->private_data; 2407 struct snd_azf3328 *chip = card->private_data;
2385 unsigned reg; 2408 u16 *saved_regs_ctrl_u16;
2386 2409
2387 snd_power_change_state(card, SNDRV_CTL_POWER_D3hot); 2410 snd_power_change_state(card, SNDRV_CTL_POWER_D3hot);
2388 2411
2389 snd_pcm_suspend_all(chip->pcm[AZF_CODEC_PLAYBACK]); 2412 snd_pcm_suspend_all(chip->pcm[AZF_CODEC_PLAYBACK]);
2390 snd_pcm_suspend_all(chip->pcm[AZF_CODEC_I2S_OUT]); 2413 snd_pcm_suspend_all(chip->pcm[AZF_CODEC_I2S_OUT]);
2391 2414
2392 for (reg = 0; reg < AZF_IO_SIZE_MIXER_PM / 2; ++reg) 2415 snd_azf3328_suspend_regs(chip->mixer_io,
2393 chip->saved_regs_mixer[reg] = inw(chip->mixer_io + reg * 2); 2416 ARRAY_SIZE(chip->saved_regs_mixer), chip->saved_regs_mixer);
2394 2417
2395 /* make sure to disable master volume etc. to prevent looping sound */ 2418 /* make sure to disable master volume etc. to prevent looping sound */
2396 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_PLAY_MASTER, 1); 2419 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_PLAY_MASTER, 1);
2397 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_WAVEOUT, 1); 2420 snd_azf3328_mixer_set_mute(chip, IDX_MIXER_WAVEOUT, 1);
2398 2421
2399 for (reg = 0; reg < AZF_IO_SIZE_CTRL_PM / 2; ++reg) 2422 snd_azf3328_suspend_regs(chip->ctrl_io,
2400 chip->saved_regs_ctrl[reg] = inw(chip->ctrl_io + reg * 2); 2423 ARRAY_SIZE(chip->saved_regs_ctrl), chip->saved_regs_ctrl);
2401 2424
2402 /* manually store the one currently relevant write-only reg, too */ 2425 /* manually store the one currently relevant write-only reg, too */
2403 chip->saved_regs_ctrl[IDX_IO_6AH / 2] = chip->shadow_reg_ctrl_6AH; 2426 saved_regs_ctrl_u16 = (u16 *)chip->saved_regs_ctrl;
2427 saved_regs_ctrl_u16[IDX_IO_6AH / 2] = chip->shadow_reg_ctrl_6AH;
2404 2428
2405 for (reg = 0; reg < AZF_IO_SIZE_GAME_PM / 2; ++reg) 2429 snd_azf3328_suspend_regs(chip->game_io,
2406 chip->saved_regs_game[reg] = inw(chip->game_io + reg * 2); 2430 ARRAY_SIZE(chip->saved_regs_game), chip->saved_regs_game);
2407 for (reg = 0; reg < AZF_IO_SIZE_MPU_PM / 2; ++reg) 2431 snd_azf3328_suspend_regs(chip->mpu_io,
2408 chip->saved_regs_mpu[reg] = inw(chip->mpu_io + reg * 2); 2432 ARRAY_SIZE(chip->saved_regs_mpu), chip->saved_regs_mpu);
2409 for (reg = 0; reg < AZF_IO_SIZE_OPL3_PM / 2; ++reg) 2433 snd_azf3328_suspend_regs(chip->opl3_io,
2410 chip->saved_regs_opl3[reg] = inw(chip->opl3_io + reg * 2); 2434 ARRAY_SIZE(chip->saved_regs_opl3), chip->saved_regs_opl3);
2411 2435
2412 pci_disable_device(pci); 2436 pci_disable_device(pci);
2413 pci_save_state(pci); 2437 pci_save_state(pci);
2414 pci_set_power_state(pci, pci_choose_state(pci, state)); 2438 pci_set_power_state(pci, pci_choose_state(pci, state));
2415 return 0; 2439 return 0;
2416 } 2440 }
2417 2441
2442 static inline void
2443 snd_azf3328_resume_regs(const u32 *saved_regs,
2444 unsigned long io_addr,
2445 unsigned count
2446 )
2447 {
2448 unsigned reg;
2449
2450 for (reg = 0; reg < count; ++reg) {
2451 outl(*saved_regs, io_addr);
2452 snd_azf3328_dbgpm("resume: io 0x%04lx: 0x%08x --> 0x%08x\n",
2453 io_addr, *saved_regs, inl(io_addr));
2454 ++saved_regs;
2455 io_addr += sizeof(*saved_regs);
2456 }
2457 }
2458
2418 static int 2459 static int
2419 snd_azf3328_resume(struct pci_dev *pci) 2460 snd_azf3328_resume(struct pci_dev *pci)
2420 { 2461 {
2421 struct snd_card *card = pci_get_drvdata(pci); 2462 struct snd_card *card = pci_get_drvdata(pci);
2422 const struct snd_azf3328 *chip = card->private_data; 2463 const struct snd_azf3328 *chip = card->private_data;
2423 unsigned reg;
2424 2464
2425 pci_set_power_state(pci, PCI_D0); 2465 pci_set_power_state(pci, PCI_D0);
2426 pci_restore_state(pci); 2466 pci_restore_state(pci);
2427 if (pci_enable_device(pci) < 0) { 2467 if (pci_enable_device(pci) < 0) {
2428 printk(KERN_ERR "azt3328: pci_enable_device failed, " 2468 printk(KERN_ERR "azt3328: pci_enable_device failed, "
2429 "disabling device\n"); 2469 "disabling device\n");
2430 snd_card_disconnect(card); 2470 snd_card_disconnect(card);
2431 return -EIO; 2471 return -EIO;
2432 } 2472 }
2433 pci_set_master(pci); 2473 pci_set_master(pci);
2434 2474
2435 for (reg = 0; reg < AZF_IO_SIZE_GAME_PM / 2; ++reg) 2475 snd_azf3328_resume_regs(chip->saved_regs_game, chip->game_io,
2436 outw(chip->saved_regs_game[reg], chip->game_io + reg * 2); 2476 ARRAY_SIZE(chip->saved_regs_game));
2437 for (reg = 0; reg < AZF_IO_SIZE_MPU_PM / 2; ++reg) 2477 snd_azf3328_resume_regs(chip->saved_regs_mpu, chip->mpu_io,
2438 outw(chip->saved_regs_mpu[reg], chip->mpu_io + reg * 2); 2478 ARRAY_SIZE(chip->saved_regs_mpu));
2439 for (reg = 0; reg < AZF_IO_SIZE_OPL3_PM / 2; ++reg) 2479 snd_azf3328_resume_regs(chip->saved_regs_opl3, chip->opl3_io,
2440 outw(chip->saved_regs_opl3[reg], chip->opl3_io + reg * 2); 2480 ARRAY_SIZE(chip->saved_regs_opl3));
2441 for (reg = 0; reg < AZF_IO_SIZE_MIXER_PM / 2; ++reg) 2481
2442 outw(chip->saved_regs_mixer[reg], chip->mixer_io + reg * 2); 2482 snd_azf3328_resume_regs(chip->saved_regs_mixer, chip->mixer_io,
2443 for (reg = 0; reg < AZF_IO_SIZE_CTRL_PM / 2; ++reg) 2483 ARRAY_SIZE(chip->saved_regs_mixer));
2444 outw(chip->saved_regs_ctrl[reg], chip->ctrl_io + reg * 2); 2484
2485 /* unfortunately with 32bit transfers, IDX_MIXER_PLAY_MASTER (0x02)
2486 and IDX_MIXER_RESET (offset 0x00) get touched at the same time,
2487 resulting in a mixer reset condition persisting until _after_
2488 master vol was restored. Thus master vol needs an extra restore. */
2489 outw(((u16 *)chip->saved_regs_mixer)[1], chip->mixer_io + 2);
2490
2491 snd_azf3328_resume_regs(chip->saved_regs_ctrl, chip->ctrl_io,
2492 ARRAY_SIZE(chip->saved_regs_ctrl));
2445 2493
2446 snd_power_change_state(card, SNDRV_CTL_POWER_D0); 2494 snd_power_change_state(card, SNDRV_CTL_POWER_D0);
2447 return 0; 2495 return 0;
2448 } 2496 }
2449 #endif /* CONFIG_PM */ 2497 #endif /* CONFIG_PM */
2450 2498
2451 2499
2452 static struct pci_driver driver = { 2500 static struct pci_driver driver = {
2453 .name = "AZF3328", 2501 .name = "AZF3328",
2454 .id_table = snd_azf3328_ids, 2502 .id_table = snd_azf3328_ids,
2455 .probe = snd_azf3328_probe, 2503 .probe = snd_azf3328_probe,
2456 .remove = __devexit_p(snd_azf3328_remove), 2504 .remove = __devexit_p(snd_azf3328_remove),
2457 #ifdef CONFIG_PM 2505 #ifdef CONFIG_PM
2458 .suspend = snd_azf3328_suspend, 2506 .suspend = snd_azf3328_suspend,
2459 .resume = snd_azf3328_resume, 2507 .resume = snd_azf3328_resume,
2460 #endif 2508 #endif
2461 }; 2509 };
2462 2510
2463 static int __init 2511 static int __init
2464 alsa_card_azf3328_init(void) 2512 alsa_card_azf3328_init(void)
2465 { 2513 {
2466 int err; 2514 int err;
2467 snd_azf3328_dbgcallenter(); 2515 snd_azf3328_dbgcallenter();
2468 err = pci_register_driver(&driver); 2516 err = pci_register_driver(&driver);
2469 snd_azf3328_dbgcallleave(); 2517 snd_azf3328_dbgcallleave();
2470 return err; 2518 return err;
2471 } 2519 }
2472 2520
2473 static void __exit 2521 static void __exit
2474 alsa_card_azf3328_exit(void) 2522 alsa_card_azf3328_exit(void)
2475 { 2523 {
2476 snd_azf3328_dbgcallenter(); 2524 snd_azf3328_dbgcallenter();
2477 pci_unregister_driver(&driver); 2525 pci_unregister_driver(&driver);
1 #ifndef __SOUND_AZT3328_H 1 #ifndef __SOUND_AZT3328_H
2 #define __SOUND_AZT3328_H 2 #define __SOUND_AZT3328_H
3 3
4 /* "PU" == "power-up value", as tested on PCI168 PCI rev. 10 4 /* "PU" == "power-up value", as tested on PCI168 PCI rev. 10
5 * "WRITE_ONLY" == register does not indicate actual bit values */ 5 * "WRITE_ONLY" == register does not indicate actual bit values */
6 6
7 /*** main I/O area port indices ***/ 7 /*** main I/O area port indices ***/
8 /* (only 0x70 of 0x80 bytes saved/restored by Windows driver) */ 8 /* (only 0x70 of 0x80 bytes saved/restored by Windows driver) */
9 #define AZF_IO_SIZE_CTRL 0x80 9 #define AZF_IO_SIZE_CTRL 0x80
10 #define AZF_IO_SIZE_CTRL_PM 0x70 10 #define AZF_IO_SIZE_CTRL_PM 0x70
11 11
12 /* the driver initialisation suggests a layout of 4 areas 12 /* the driver initialisation suggests a layout of 4 areas
13 * within the main card control I/O: 13 * within the main card control I/O:
14 * from 0x00 (playback codec), from 0x20 (recording codec) 14 * from 0x00 (playback codec), from 0x20 (recording codec)
15 * and from 0x40 (most certainly I2S out codec). 15 * and from 0x40 (most certainly I2S out codec).
16 * And another area from 0x60 to 0x6f (DirectX timer, IRQ management, 16 * And another area from 0x60 to 0x6f (DirectX timer, IRQ management,
17 * power management etc.???). */ 17 * power management etc.???). */
18 18
19 #define AZF_IO_OFFS_CODEC_PLAYBACK 0x00 19 #define AZF_IO_OFFS_CODEC_PLAYBACK 0x00
20 #define AZF_IO_OFFS_CODEC_CAPTURE 0x20 20 #define AZF_IO_OFFS_CODEC_CAPTURE 0x20
21 #define AZF_IO_OFFS_CODEC_I2S_OUT 0x40 21 #define AZF_IO_OFFS_CODEC_I2S_OUT 0x40
22 22
23 #define IDX_IO_CODEC_DMA_FLAGS 0x00 /* PU:0x0000 */ 23 #define IDX_IO_CODEC_DMA_FLAGS 0x00 /* PU:0x0000 */
24 /* able to reactivate output after output muting due to 8/16bit 24 /* able to reactivate output after output muting due to 8/16bit
25 * output change, just like 0x0002. 25 * output change, just like 0x0002.
26 * 0x0001 is the only bit that's able to start the DMA counter */ 26 * 0x0001 is the only bit that's able to start the DMA counter */
27 #define DMA_RESUME 0x0001 /* paused if cleared? */ 27 #define DMA_RESUME 0x0001 /* paused if cleared? */
28 /* 0x0002 *temporarily* set during DMA stopping. hmm 28 /* 0x0002 *temporarily* set during DMA stopping. hmm
29 * both 0x0002 and 0x0004 set in playback setup. */ 29 * both 0x0002 and 0x0004 set in playback setup. */
30 /* able to reactivate output after output muting due to 8/16bit 30 /* able to reactivate output after output muting due to 8/16bit
31 * output change, just like 0x0001. */ 31 * output change, just like 0x0001. */
32 #define DMA_RUN_SOMETHING1 0x0002 /* \ alternated (toggled) */ 32 #define DMA_RUN_SOMETHING1 0x0002 /* \ alternated (toggled) */
33 /* 0x0004: NOT able to reactivate output */ 33 /* 0x0004: NOT able to reactivate output */
34 #define DMA_RUN_SOMETHING2 0x0004 /* / bits */ 34 #define DMA_RUN_SOMETHING2 0x0004 /* / bits */
35 #define SOMETHING_ALMOST_ALWAYS_SET 0x0008 /* ???; can be modified */ 35 #define SOMETHING_ALMOST_ALWAYS_SET 0x0008 /* ???; can be modified */
36 #define DMA_EPILOGUE_SOMETHING 0x0010 36 #define DMA_EPILOGUE_SOMETHING 0x0010
37 #define DMA_SOMETHING_ELSE 0x0020 /* ??? */ 37 #define DMA_SOMETHING_ELSE 0x0020 /* ??? */
38 #define SOMETHING_UNMODIFIABLE 0xffc0 /* unused? not modifiable */ 38 #define SOMETHING_UNMODIFIABLE 0xffc0 /* unused? not modifiable */
39 #define IDX_IO_CODEC_IRQTYPE 0x02 /* PU:0x0001 */ 39 #define IDX_IO_CODEC_IRQTYPE 0x02 /* PU:0x0001 */
40 /* write back to flags in case flags are set, in order to ACK IRQ in handler 40 /* write back to flags in case flags are set, in order to ACK IRQ in handler
41 * (bit 1 of port 0x64 indicates interrupt for one of these three types) 41 * (bit 1 of port 0x64 indicates interrupt for one of these three types)
42 * sometimes in this case it just writes 0xffff to globally ACK all IRQs 42 * sometimes in this case it just writes 0xffff to globally ACK all IRQs
43 * settings written are not reflected when reading back, though. 43 * settings written are not reflected when reading back, though.
44 * seems to be IRQ, too (frequently used: port |= 0x07 !), but who knows? */ 44 * seems to be IRQ, too (frequently used: port |= 0x07 !), but who knows? */
45 #define IRQ_SOMETHING 0x0001 /* something & ACK */ 45 #define IRQ_SOMETHING 0x0001 /* something & ACK */
46 #define IRQ_FINISHED_DMABUF_1 0x0002 /* 1st dmabuf finished & ACK */ 46 #define IRQ_FINISHED_DMABUF_1 0x0002 /* 1st dmabuf finished & ACK */
47 #define IRQ_FINISHED_DMABUF_2 0x0004 /* 2nd dmabuf finished & ACK */ 47 #define IRQ_FINISHED_DMABUF_2 0x0004 /* 2nd dmabuf finished & ACK */
48 #define IRQMASK_SOME_STATUS_1 0x0008 /* \ related bits */ 48 #define IRQMASK_SOME_STATUS_1 0x0008 /* \ related bits */
49 #define IRQMASK_SOME_STATUS_2 0x0010 /* / (checked together in loop) */ 49 #define IRQMASK_SOME_STATUS_2 0x0010 /* / (checked together in loop) */
50 #define IRQMASK_UNMODIFIABLE 0xffe0 /* unused? not modifiable */ 50 #define IRQMASK_UNMODIFIABLE 0xffe0 /* unused? not modifiable */
51 /* start address of 1st DMA transfer area, PU:0x00000000 */ 51 /* start address of 1st DMA transfer area, PU:0x00000000 */
52 #define IDX_IO_CODEC_DMA_START_1 0x04 52 #define IDX_IO_CODEC_DMA_START_1 0x04
53 /* start address of 2nd DMA transfer area, PU:0x00000000 */ 53 /* start address of 2nd DMA transfer area, PU:0x00000000 */
54 #define IDX_IO_CODEC_DMA_START_2 0x08 54 #define IDX_IO_CODEC_DMA_START_2 0x08
55 /* both lengths of DMA transfer areas, PU:0x00000000 55 /* both lengths of DMA transfer areas, PU:0x00000000
56 length1: offset 0x0c, length2: offset 0x0e */ 56 length1: offset 0x0c, length2: offset 0x0e */
57 #define IDX_IO_CODEC_DMA_LENGTHS 0x0c 57 #define IDX_IO_CODEC_DMA_LENGTHS 0x0c
58 #define IDX_IO_CODEC_DMA_CURRPOS 0x10 /* current DMA position, PU:0x00000000 */ 58 #define IDX_IO_CODEC_DMA_CURRPOS 0x10 /* current DMA position, PU:0x00000000 */
59 /* offset within current DMA transfer area, PU:0x0000 */ 59 /* offset within current DMA transfer area, PU:0x0000 */
60 #define IDX_IO_CODEC_DMA_CURROFS 0x14 60 #define IDX_IO_CODEC_DMA_CURROFS 0x14
61 #define IDX_IO_CODEC_SOUNDFORMAT 0x16 /* PU:0x0010 */ 61 #define IDX_IO_CODEC_SOUNDFORMAT 0x16 /* PU:0x0010 */
62 /* all unspecified bits can't be modified */ 62 /* all unspecified bits can't be modified */
63 #define SOUNDFORMAT_FREQUENCY_MASK 0x000f 63 #define SOUNDFORMAT_FREQUENCY_MASK 0x000f
64 #define SOUNDFORMAT_XTAL1 0x00 64 #define SOUNDFORMAT_XTAL1 0x00
65 #define SOUNDFORMAT_XTAL2 0x01 65 #define SOUNDFORMAT_XTAL2 0x01
66 /* all _SUSPECTED_ values are not used by Windows drivers, so we don't 66 /* all _SUSPECTED_ values are not used by Windows drivers, so we don't
67 * have any hard facts, only rough measurements. 67 * have any hard facts, only rough measurements.
68 * All we know is that the crystal used on the board has 24.576MHz, 68 * All we know is that the crystal used on the board has 24.576MHz,
69 * like many soundcards (which results in the frequencies below when 69 * like many soundcards (which results in the frequencies below when
70 * using certain divider values selected by the values below) */ 70 * using certain divider values selected by the values below) */
71 #define SOUNDFORMAT_FREQ_SUSPECTED_4000 0x0c | SOUNDFORMAT_XTAL1 71 #define SOUNDFORMAT_FREQ_SUSPECTED_4000 0x0c | SOUNDFORMAT_XTAL1
72 #define SOUNDFORMAT_FREQ_SUSPECTED_4800 0x0a | SOUNDFORMAT_XTAL1 72 #define SOUNDFORMAT_FREQ_SUSPECTED_4800 0x0a | SOUNDFORMAT_XTAL1
73 #define SOUNDFORMAT_FREQ_5510 0x0c | SOUNDFORMAT_XTAL2 73 #define SOUNDFORMAT_FREQ_5510 0x0c | SOUNDFORMAT_XTAL2
74 #define SOUNDFORMAT_FREQ_6620 0x0a | SOUNDFORMAT_XTAL2 74 #define SOUNDFORMAT_FREQ_6620 0x0a | SOUNDFORMAT_XTAL2
75 #define SOUNDFORMAT_FREQ_8000 0x00 | SOUNDFORMAT_XTAL1 /* also 0x0e | SOUNDFORMAT_XTAL1? */ 75 #define SOUNDFORMAT_FREQ_8000 0x00 | SOUNDFORMAT_XTAL1 /* also 0x0e | SOUNDFORMAT_XTAL1? */
76 #define SOUNDFORMAT_FREQ_9600 0x08 | SOUNDFORMAT_XTAL1 76 #define SOUNDFORMAT_FREQ_9600 0x08 | SOUNDFORMAT_XTAL1
77 #define SOUNDFORMAT_FREQ_11025 0x00 | SOUNDFORMAT_XTAL2 /* also 0x0e | SOUNDFORMAT_XTAL2? */ 77 #define SOUNDFORMAT_FREQ_11025 0x00 | SOUNDFORMAT_XTAL2 /* also 0x0e | SOUNDFORMAT_XTAL2? */
78 #define SOUNDFORMAT_FREQ_SUSPECTED_13240 0x08 | SOUNDFORMAT_XTAL2 /* seems to be 6620 *2 */ 78 #define SOUNDFORMAT_FREQ_SUSPECTED_13240 0x08 | SOUNDFORMAT_XTAL2 /* seems to be 6620 *2 */
79 #define SOUNDFORMAT_FREQ_16000 0x02 | SOUNDFORMAT_XTAL1 79 #define SOUNDFORMAT_FREQ_16000 0x02 | SOUNDFORMAT_XTAL1
80 #define SOUNDFORMAT_FREQ_22050 0x02 | SOUNDFORMAT_XTAL2 80 #define SOUNDFORMAT_FREQ_22050 0x02 | SOUNDFORMAT_XTAL2
81 #define SOUNDFORMAT_FREQ_32000 0x04 | SOUNDFORMAT_XTAL1 81 #define SOUNDFORMAT_FREQ_32000 0x04 | SOUNDFORMAT_XTAL1
82 #define SOUNDFORMAT_FREQ_44100 0x04 | SOUNDFORMAT_XTAL2 82 #define SOUNDFORMAT_FREQ_44100 0x04 | SOUNDFORMAT_XTAL2
83 #define SOUNDFORMAT_FREQ_48000 0x06 | SOUNDFORMAT_XTAL1 83 #define SOUNDFORMAT_FREQ_48000 0x06 | SOUNDFORMAT_XTAL1
84 #define SOUNDFORMAT_FREQ_SUSPECTED_66200 0x06 | SOUNDFORMAT_XTAL2 /* 66200 (13240 * 5); 64000 may have been nicer :-\ */ 84 #define SOUNDFORMAT_FREQ_SUSPECTED_66200 0x06 | SOUNDFORMAT_XTAL2 /* 66200 (13240 * 5); 64000 may have been nicer :-\ */
85 #define SOUNDFORMAT_FLAG_16BIT 0x0010 85 #define SOUNDFORMAT_FLAG_16BIT 0x0010
86 #define SOUNDFORMAT_FLAG_2CHANNELS 0x0020 86 #define SOUNDFORMAT_FLAG_2CHANNELS 0x0020
87 87
88 88
89 /* define frequency helpers, for maximum value safety */ 89 /* define frequency helpers, for maximum value safety */
90 enum azf_freq_t { 90 enum azf_freq_t {
91 #define AZF_FREQ(rate) AZF_FREQ_##rate = rate 91 #define AZF_FREQ(rate) AZF_FREQ_##rate = rate
92 AZF_FREQ(4000), 92 AZF_FREQ(4000),
93 AZF_FREQ(4800), 93 AZF_FREQ(4800),
94 AZF_FREQ(5512), 94 AZF_FREQ(5512),
95 AZF_FREQ(6620), 95 AZF_FREQ(6620),
96 AZF_FREQ(8000), 96 AZF_FREQ(8000),
97 AZF_FREQ(9600), 97 AZF_FREQ(9600),
98 AZF_FREQ(11025), 98 AZF_FREQ(11025),
99 AZF_FREQ(13240), 99 AZF_FREQ(13240),
100 AZF_FREQ(16000), 100 AZF_FREQ(16000),
101 AZF_FREQ(22050), 101 AZF_FREQ(22050),
102 AZF_FREQ(32000), 102 AZF_FREQ(32000),
103 AZF_FREQ(44100), 103 AZF_FREQ(44100),
104 AZF_FREQ(48000), 104 AZF_FREQ(48000),
105 AZF_FREQ(66200), 105 AZF_FREQ(66200),
106 #undef AZF_FREQ 106 #undef AZF_FREQ
107 }; 107 };
108 108
109 /** DirectX timer, main interrupt area (FIXME: and something else?) **/ 109 /** DirectX timer, main interrupt area (FIXME: and something else?) **/
110 #define IDX_IO_TIMER_VALUE 0x60 /* found this timer area by pure luck :-) */ 110 #define IDX_IO_TIMER_VALUE 0x60 /* found this timer area by pure luck :-) */
111 /* timer countdown value; triggers IRQ when timer is finished */ 111 /* timer countdown value; triggers IRQ when timer is finished */
112 #define TIMER_VALUE_MASK 0x000fffffUL 112 #define TIMER_VALUE_MASK 0x000fffffUL
113 /* activate timer countdown */ 113 /* activate timer countdown */
114 #define TIMER_COUNTDOWN_ENABLE 0x01000000UL 114 #define TIMER_COUNTDOWN_ENABLE 0x01000000UL
115 /* trigger timer IRQ on zero transition */ 115 /* trigger timer IRQ on zero transition */
116 #define TIMER_IRQ_ENABLE 0x02000000UL 116 #define TIMER_IRQ_ENABLE 0x02000000UL
117 /* being set in IRQ handler in case port 0x00 (hmm, not port 0x64!?!?) 117 /* being set in IRQ handler in case port 0x00 (hmm, not port 0x64!?!?)
118 * had 0x0020 set upon IRQ handler */ 118 * had 0x0020 set upon IRQ handler */
119 #define TIMER_IRQ_ACK 0x04000000UL 119 #define TIMER_IRQ_ACK 0x04000000UL
120 #define IDX_IO_IRQSTATUS 0x64 120 #define IDX_IO_IRQSTATUS 0x64
121 /* some IRQ bit in here might also be used to signal a power-management timer 121 /* some IRQ bit in here might also be used to signal a power-management timer
122 * timeout, to request shutdown of the chip (e.g. AD1815JS has such a thing). 122 * timeout, to request shutdown of the chip (e.g. AD1815JS has such a thing).
123 * Some OPL3 hardware (e.g. in LM4560) has some special timer hardware which 123 * OPL3 hardware contains several timers which confusingly in most cases
124 * can trigger an OPL3 timer IRQ, so maybe there's such a thing as well... */ 124 * are NOT routed to an IRQ, but some designs (e.g. LM4560) DO support that,
125 * so I wouldn't be surprised at all to discover that AZF3328
126 * supports that thing as well... */
125 127
126 #define IRQ_PLAYBACK 0x0001 128 #define IRQ_PLAYBACK 0x0001
127 #define IRQ_RECORDING 0x0002 129 #define IRQ_RECORDING 0x0002
128 #define IRQ_I2S_OUT 0x0004 /* this IS I2S, right!? (untested) */ 130 #define IRQ_I2S_OUT 0x0004 /* this IS I2S, right!? (untested) */
129 #define IRQ_GAMEPORT 0x0008 /* Interrupt of Digital(ly) Enhanced Game Port */ 131 #define IRQ_GAMEPORT 0x0008 /* Interrupt of Digital(ly) Enhanced Game Port */
130 #define IRQ_MPU401 0x0010 132 #define IRQ_MPU401 0x0010
131 #define IRQ_TIMER 0x0020 /* DirectX timer */ 133 #define IRQ_TIMER 0x0020 /* DirectX timer */
132 #define IRQ_UNKNOWN2 0x0040 /* probably unused, or possibly I2S port? */ 134 #define IRQ_UNKNOWN2 0x0040 /* probably unused, or possibly OPL3 timer? */
133 #define IRQ_UNKNOWN3 0x0080 /* probably unused, or possibly I2S port? */ 135 #define IRQ_UNKNOWN3 0x0080 /* probably unused, or possibly OPL3 timer? */
134 #define IDX_IO_66H 0x66 /* writing 0xffff returns 0x0000 */ 136 #define IDX_IO_66H 0x66 /* writing 0xffff returns 0x0000 */
135 /* this is set to e.g. 0x3ff or 0x300, and writable; 137 /* this is set to e.g. 0x3ff or 0x300, and writable;
136 * maybe some buffer limit, but I couldn't find out more, PU:0x00ff: */ 138 * maybe some buffer limit, but I couldn't find out more, PU:0x00ff: */
137 #define IDX_IO_SOME_VALUE 0x68 139 #define IDX_IO_SOME_VALUE 0x68
138 #define IO_68_RANDOM_TOGGLE1 0x0100 /* toggles randomly */ 140 #define IO_68_RANDOM_TOGGLE1 0x0100 /* toggles randomly */
139 #define IO_68_RANDOM_TOGGLE2 0x0200 /* toggles randomly */ 141 #define IO_68_RANDOM_TOGGLE2 0x0200 /* toggles randomly */
140 /* umm, nope, behaviour of these bits changes depending on what we wrote 142 /* umm, nope, behaviour of these bits changes depending on what we wrote
141 * to 0x6b!! 143 * to 0x6b!!
142 * And they change upon playback/stop, too: 144 * And they change upon playback/stop, too:
143 * Writing a value to 0x68 will display this exact value during playback, 145 * Writing a value to 0x68 will display this exact value during playback,
144 * too but when stopped it can fall back to a rather different 146 * too but when stopped it can fall back to a rather different
145 * seemingly random value). Hmm, possibly this is a register which 147 * seemingly random value). Hmm, possibly this is a register which
146 * has a remote shadow which needs proper device supply which only exists 148 * has a remote shadow which needs proper device supply which only exists
147 * in case playback is active? Or is this driver-induced? 149 * in case playback is active? Or is this driver-induced?
148 */ 150 */
149 151
150 /* this WORD can be set to have bits 0x0028 activated (FIXME: correct??); 152 /* this WORD can be set to have bits 0x0028 activated (FIXME: correct??);
151 * actually inhibits PCM playback!!! maybe power management??: */ 153 * actually inhibits PCM playback!!! maybe power management??: */
152 #define IDX_IO_6AH 0x6A /* WRITE_ONLY! */ 154 #define IDX_IO_6AH 0x6A /* WRITE_ONLY! */
153 /* bit 5: enabling this will activate permanent counting of bytes 2/3 155 /* bit 5: enabling this will activate permanent counting of bytes 2/3
154 * at gameport I/O (0xb402/3) (equal values each) and cause 156 * at gameport I/O (0xb402/3) (equal values each) and cause
155 * gameport legacy I/O at 0x0200 to be _DISABLED_! 157 * gameport legacy I/O at 0x0200 to be _DISABLED_!
156 * Is this Digital Enhanced Game Port Enable??? Or maybe it's Testmode 158 * Is this Digital Enhanced Game Port Enable??? Or maybe it's Testmode
157 * for Enhanced Digital Gameport (see 4D Wave DX card): */ 159 * for Enhanced Digital Gameport (see 4D Wave DX card): */
158 #define IO_6A_SOMETHING1_GAMEPORT 0x0020 160 #define IO_6A_SOMETHING1_GAMEPORT 0x0020
159 /* bit 8; sure, this _pauses_ playback (later resumes at same spot!), 161 /* bit 8; sure, this _pauses_ playback (later resumes at same spot!),
160 * but what the heck is this really about??: */ 162 * but what the heck is this really about??: */
161 #define IO_6A_PAUSE_PLAYBACK_BIT8 0x0100 163 #define IO_6A_PAUSE_PLAYBACK_BIT8 0x0100
162 /* bit 9; sure, this _pauses_ playback (later resumes at same spot!), 164 /* bit 9; sure, this _pauses_ playback (later resumes at same spot!),
163 * but what the heck is this really about??: */ 165 * but what the heck is this really about??: */
164 #define IO_6A_PAUSE_PLAYBACK_BIT9 0x0200 166 #define IO_6A_PAUSE_PLAYBACK_BIT9 0x0200
165 /* BIT8 and BIT9 are _NOT_ able to affect OPL3 MIDI playback, 167 /* BIT8 and BIT9 are _NOT_ able to affect OPL3 MIDI playback,
166 * thus it suggests influence on PCM only!! 168 * thus it suggests influence on PCM only!!
167 * However OTOH there seems to be no bit anywhere around here 169 * However OTOH there seems to be no bit anywhere around here
168 * which is able to disable OPL3... */ 170 * which is able to disable OPL3... */
169 /* bit 10: enabling this actually changes values at legacy gameport 171 /* bit 10: enabling this actually changes values at legacy gameport
170 * I/O address (0x200); is this enabling of the Digital Enhanced Game Port??? 172 * I/O address (0x200); is this enabling of the Digital Enhanced Game Port???
171 * Or maybe this simply switches off the NE558 circuit, since enabling this 173 * Or maybe this simply switches off the NE558 circuit, since enabling this
172 * still lets us evaluate button states, but not axis states */ 174 * still lets us evaluate button states, but not axis states */
173 #define IO_6A_SOMETHING2_GAMEPORT 0x0400 175 #define IO_6A_SOMETHING2_GAMEPORT 0x0400
174 /* writing 0x0300: causes quite some crackling during 176 /* writing 0x0300: causes quite some crackling during
175 * PC activity such as switching windows (PCI traffic?? 177 * PC activity such as switching windows (PCI traffic??
176 * --> FIFO/timing settings???) */ 178 * --> FIFO/timing settings???) */
177 /* writing 0x0100 plus/or 0x0200 inhibits playback */ 179 /* writing 0x0100 plus/or 0x0200 inhibits playback */
178 /* since the Windows .INF file has Flag_Enable_JoyStick and 180 /* since the Windows .INF file has Flag_Enable_JoyStick and
179 * Flag_Enable_SB_DOS_Emulation directly together, it stands to reason 181 * Flag_Enable_SB_DOS_Emulation directly together, it stands to reason
180 * that some other bit in this same register might be responsible 182 * that some other bit in this same register might be responsible
181 * for SB DOS Emulation activation (note that the file did NOT define 183 * for SB DOS Emulation activation (note that the file did NOT define
182 * a switch for OPL3!) */ 184 * a switch for OPL3!) */
183 #define IDX_IO_6CH 0x6C /* unknown; fully read-writable */ 185 #define IDX_IO_6CH 0x6C /* unknown; fully read-writable */
184 #define IDX_IO_6EH 0x6E 186 #define IDX_IO_6EH 0x6E
185 /* writing 0xffff returns 0x83fe (or 0x03fe only). 187 /* writing 0xffff returns 0x83fe (or 0x03fe only).
186 * writing 0x83 (and only 0x83!!) to 0x6f will cause 0x6c to switch 188 * writing 0x83 (and only 0x83!!) to 0x6f will cause 0x6c to switch
187 * from 0000 to ffff. */ 189 * from 0000 to ffff. */
188 190
189 /* further I/O indices not saved/restored and not readable after writing, 191 /* further I/O indices not saved/restored and not readable after writing,
190 * so probably not used */ 192 * so probably not used */
191 193
192 194
193 /*** Gameport area port indices ***/ 195 /*** Gameport area port indices ***/
194 /* (only 0x06 of 0x08 bytes saved/restored by Windows driver) */ 196 /* (only 0x06 of 0x08 bytes saved/restored by Windows driver) */
195 #define AZF_IO_SIZE_GAME 0x08 197 #define AZF_IO_SIZE_GAME 0x08
196 #define AZF_IO_SIZE_GAME_PM 0x06 198 #define AZF_IO_SIZE_GAME_PM 0x06
197 199
198 enum { 200 enum {
199 AZF_GAME_LEGACY_IO_PORT = 0x200 201 AZF_GAME_LEGACY_IO_PORT = 0x200
200 }; 202 };
201 203
202 #define IDX_GAME_LEGACY_COMPATIBLE 0x00 204 #define IDX_GAME_LEGACY_COMPATIBLE 0x00
203 /* in some operation mode, writing anything to this port 205 /* in some operation mode, writing anything to this port
204 * triggers an interrupt: 206 * triggers an interrupt:
205 * yup, that's in case IDX_GAME_01H has one of the 207 * yup, that's in case IDX_GAME_01H has one of the
206 * axis measurement bits enabled 208 * axis measurement bits enabled
207 * (and of course one needs to have GAME_HWCFG_IRQ_ENABLE, too) */ 209 * (and of course one needs to have GAME_HWCFG_IRQ_ENABLE, too) */
208 210
209 #define IDX_GAME_AXES_CONFIG 0x01 211 #define IDX_GAME_AXES_CONFIG 0x01
210 /* NOTE: layout of this register awfully similar (read: "identical??") 212 /* NOTE: layout of this register awfully similar (read: "identical??")
211 * to AD1815JS.pdf (p.29) */ 213 * to AD1815JS.pdf (p.29) */
212 214
213 /* enables axis 1 (X axis) measurement: */ 215 /* enables axis 1 (X axis) measurement: */
214 #define GAME_AXES_ENABLE_1 0x01 216 #define GAME_AXES_ENABLE_1 0x01
215 /* enables axis 2 (Y axis) measurement: */ 217 /* enables axis 2 (Y axis) measurement: */
216 #define GAME_AXES_ENABLE_2 0x02 218 #define GAME_AXES_ENABLE_2 0x02
217 /* enables axis 3 (X axis) measurement: */ 219 /* enables axis 3 (X axis) measurement: */
218 #define GAME_AXES_ENABLE_3 0x04 220 #define GAME_AXES_ENABLE_3 0x04
219 /* enables axis 4 (Y axis) measurement: */ 221 /* enables axis 4 (Y axis) measurement: */
220 #define GAME_AXES_ENABLE_4 0x08 222 #define GAME_AXES_ENABLE_4 0x08
221 /* selects the current axis to read the measured value of 223 /* selects the current axis to read the measured value of
222 * (at IDX_GAME_AXIS_VALUE): 224 * (at IDX_GAME_AXIS_VALUE):
223 * 00 = axis 1, 01 = axis 2, 10 = axis 3, 11 = axis 4: */ 225 * 00 = axis 1, 01 = axis 2, 10 = axis 3, 11 = axis 4: */
224 #define GAME_AXES_READ_MASK 0x30 226 #define GAME_AXES_READ_MASK 0x30
225 /* enable to have the latch continuously accept ADC values 227 /* enable to have the latch continuously accept ADC values
226 * (and continuously cause interrupts in case interrupts are enabled); 228 * (and continuously cause interrupts in case interrupts are enabled);
227 * AD1815JS.pdf says it's ~16ms interval there: */ 229 * AD1815JS.pdf says it's ~16ms interval there: */
228 #define GAME_AXES_LATCH_ENABLE 0x40 230 #define GAME_AXES_LATCH_ENABLE 0x40
229 /* joystick data (measured axes) ready for reading: */ 231 /* joystick data (measured axes) ready for reading: */
230 #define GAME_AXES_SAMPLING_READY 0x80 232 #define GAME_AXES_SAMPLING_READY 0x80
231 233
232 /* NOTE: other card specs (SiS960 and others!) state that the 234 /* NOTE: other card specs (SiS960 and others!) state that the
233 * game position latches should be frozen when reading and be freed 235 * game position latches should be frozen when reading and be freed
234 * (== reset?) after reading!!! 236 * (== reset?) after reading!!!
235 * Freezing most likely means disabling 0x40 (GAME_AXES_LATCH_ENABLE), 237 * Freezing most likely means disabling 0x40 (GAME_AXES_LATCH_ENABLE),
236 * but how to free the value? */ 238 * but how to free the value? */
237 /* An internet search for "gameport latch ADC" should provide some insight 239 /* An internet search for "gameport latch ADC" should provide some insight
238 * into how to program such a gameport system. */ 240 * into how to program such a gameport system. */
239 241
240 /* writing 0xf0 to 01H once reset both counters to 0, in some special mode!? 242 /* writing 0xf0 to 01H once reset both counters to 0, in some special mode!?
241 * yup, in case 6AH 0x20 is not enabled 243 * yup, in case 6AH 0x20 is not enabled
242 * (and 0x40 is sufficient, 0xf0 is not needed) */ 244 * (and 0x40 is sufficient, 0xf0 is not needed) */
243 245
244 #define IDX_GAME_AXIS_VALUE 0x02 246 #define IDX_GAME_AXIS_VALUE 0x02
245 /* R: value of currently configured axis (word value!); 247 /* R: value of currently configured axis (word value!);
246 * W: trigger axis measurement */ 248 * W: trigger axis measurement */
247 249
248 #define IDX_GAME_HWCONFIG 0x04 250 #define IDX_GAME_HWCONFIG 0x04
249 /* note: bits 4 to 7 are never set (== 0) when reading! 251 /* note: bits 4 to 7 are never set (== 0) when reading!
250 * --> reserved bits? */ 252 * --> reserved bits? */
251 /* enables IRQ notification upon axes measurement ready: */ 253 /* enables IRQ notification upon axes measurement ready: */
252 #define GAME_HWCFG_IRQ_ENABLE 0x01 254 #define GAME_HWCFG_IRQ_ENABLE 0x01
253 /* these bits choose a different frequency for the 255 /* these bits choose a different frequency for the
254 * internal ADC counter increment. 256 * internal ADC counter increment.
255 * hmm, seems to be a combo of bits: 257 * hmm, seems to be a combo of bits:
256 * 00 --> standard frequency 258 * 00 --> standard frequency
257 * 10 --> 1/2 259 * 10 --> 1/2
258 * 01 --> 1/20 260 * 01 --> 1/20
259 * 11 --> 1/200: */ 261 * 11 --> 1/200: */
260 #define GAME_HWCFG_ADC_COUNTER_FREQ_MASK 0x06 262 #define GAME_HWCFG_ADC_COUNTER_FREQ_MASK 0x06
261 263
262 /* FIXME: these values might be reversed... */ 264 /* FIXME: these values might be reversed... */
263 #define GAME_HWCFG_ADC_COUNTER_FREQ_STD 0 265 #define GAME_HWCFG_ADC_COUNTER_FREQ_STD 0
264 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_2 1 266 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_2 1
265 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_20 2 267 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_20 2
266 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_200 3 268 #define GAME_HWCFG_ADC_COUNTER_FREQ_1_200 3
267 269
268 /* enable gameport legacy I/O address (0x200) 270 /* enable gameport legacy I/O address (0x200)
269 * I was unable to locate any configurability for a different address: */ 271 * I was unable to locate any configurability for a different address: */
270 #define GAME_HWCFG_LEGACY_ADDRESS_ENABLE 0x08 272 #define GAME_HWCFG_LEGACY_ADDRESS_ENABLE 0x08
271 273
272 /*** MPU401 ***/ 274 /*** MPU401 ***/
273 #define AZF_IO_SIZE_MPU 0x04 275 #define AZF_IO_SIZE_MPU 0x04
274 #define AZF_IO_SIZE_MPU_PM 0x04 276 #define AZF_IO_SIZE_MPU_PM 0x04
275 277
276 /*** OPL3 synth ***/ 278 /*** OPL3 synth ***/
279 /* (only 0x06 of 0x08 bytes saved/restored by Windows driver) */
277 #define AZF_IO_SIZE_OPL3 0x08 280 #define AZF_IO_SIZE_OPL3 0x08
278 #define AZF_IO_SIZE_OPL3_PM 0x06 281 #define AZF_IO_SIZE_OPL3_PM 0x06
279 /* hmm, given that a standard OPL3 has 4 registers only, 282 /* hmm, given that a standard OPL3 has 4 registers only,
280 * there might be some enhanced functionality lurking at the end 283 * there might be some enhanced functionality lurking at the end
281 * (especially since register 0x04 has a "non-empty" value 0xfe) */ 284 * (especially since register 0x04 has a "non-empty" value 0xfe) */
282 285
283 /*** mixer I/O area port indices ***/ 286 /*** mixer I/O area port indices ***/
284 /* (only 0x22 of 0x40 bytes saved/restored by Windows driver) 287 /* (only 0x22 of 0x40 bytes saved/restored by Windows driver)
285 * UNFORTUNATELY azf3328 is NOT truly AC97 compliant: see main file intro */ 288 * UNFORTUNATELY azf3328 is NOT truly AC97 compliant: see main file intro */
286 #define AZF_IO_SIZE_MIXER 0x40 289 #define AZF_IO_SIZE_MIXER 0x40
287 #define AZF_IO_SIZE_MIXER_PM 0x22 290 #define AZF_IO_SIZE_MIXER_PM 0x22
288 291
289 #define MIXER_VOLUME_RIGHT_MASK 0x001f 292 #define MIXER_VOLUME_RIGHT_MASK 0x001f
290 #define MIXER_VOLUME_LEFT_MASK 0x1f00 293 #define MIXER_VOLUME_LEFT_MASK 0x1f00
291 #define MIXER_MUTE_MASK 0x8000 294 #define MIXER_MUTE_MASK 0x8000
292 #define IDX_MIXER_RESET 0x00 /* does NOT seem to have AC97 ID bits */ 295 #define IDX_MIXER_RESET 0x00 /* does NOT seem to have AC97 ID bits */
293 #define IDX_MIXER_PLAY_MASTER 0x02 296 #define IDX_MIXER_PLAY_MASTER 0x02
294 #define IDX_MIXER_MODEMOUT 0x04 297 #define IDX_MIXER_MODEMOUT 0x04
295 #define IDX_MIXER_BASSTREBLE 0x06 298 #define IDX_MIXER_BASSTREBLE 0x06
296 #define MIXER_BASSTREBLE_TREBLE_VOLUME_MASK 0x000e 299 #define MIXER_BASSTREBLE_TREBLE_VOLUME_MASK 0x000e
297 #define MIXER_BASSTREBLE_BASS_VOLUME_MASK 0x0e00 300 #define MIXER_BASSTREBLE_BASS_VOLUME_MASK 0x0e00
298 #define IDX_MIXER_PCBEEP 0x08 301 #define IDX_MIXER_PCBEEP 0x08
299 #define IDX_MIXER_MODEMIN 0x0a 302 #define IDX_MIXER_MODEMIN 0x0a
300 #define IDX_MIXER_MIC 0x0c 303 #define IDX_MIXER_MIC 0x0c
301 #define MIXER_MIC_MICGAIN_20DB_ENHANCEMENT_MASK 0x0040 304 #define MIXER_MIC_MICGAIN_20DB_ENHANCEMENT_MASK 0x0040
302 #define IDX_MIXER_LINEIN 0x0e 305 #define IDX_MIXER_LINEIN 0x0e
303 #define IDX_MIXER_CDAUDIO 0x10 306 #define IDX_MIXER_CDAUDIO 0x10
304 #define IDX_MIXER_VIDEO 0x12 307 #define IDX_MIXER_VIDEO 0x12
305 #define IDX_MIXER_AUX 0x14 308 #define IDX_MIXER_AUX 0x14
306 #define IDX_MIXER_WAVEOUT 0x16 309 #define IDX_MIXER_WAVEOUT 0x16
307 #define IDX_MIXER_FMSYNTH 0x18 310 #define IDX_MIXER_FMSYNTH 0x18
308 #define IDX_MIXER_REC_SELECT 0x1a 311 #define IDX_MIXER_REC_SELECT 0x1a
309 #define MIXER_REC_SELECT_MIC 0x00 312 #define MIXER_REC_SELECT_MIC 0x00
310 #define MIXER_REC_SELECT_CD 0x01 313 #define MIXER_REC_SELECT_CD 0x01
311 #define MIXER_REC_SELECT_VIDEO 0x02 314 #define MIXER_REC_SELECT_VIDEO 0x02
312 #define MIXER_REC_SELECT_AUX 0x03 315 #define MIXER_REC_SELECT_AUX 0x03
313 #define MIXER_REC_SELECT_LINEIN 0x04 316 #define MIXER_REC_SELECT_LINEIN 0x04
314 #define MIXER_REC_SELECT_MIXSTEREO 0x05 317 #define MIXER_REC_SELECT_MIXSTEREO 0x05
315 #define MIXER_REC_SELECT_MIXMONO 0x06 318 #define MIXER_REC_SELECT_MIXMONO 0x06
316 #define MIXER_REC_SELECT_MONOIN 0x07 319 #define MIXER_REC_SELECT_MONOIN 0x07
317 #define IDX_MIXER_REC_VOLUME 0x1c 320 #define IDX_MIXER_REC_VOLUME 0x1c
318 #define IDX_MIXER_ADVCTL1 0x1e 321 #define IDX_MIXER_ADVCTL1 0x1e
319 /* unlisted bits are unmodifiable */ 322 /* unlisted bits are unmodifiable */
320 #define MIXER_ADVCTL1_3DWIDTH_MASK 0x000e 323 #define MIXER_ADVCTL1_3DWIDTH_MASK 0x000e
321 #define MIXER_ADVCTL1_HIFI3D_MASK 0x0300 /* yup, this is missing the high bit that official AC97 contains, plus it doesn't have linear bit value range behaviour but instead acts weirdly (possibly we're dealing with two *different* 3D settings here??) */ 324 #define MIXER_ADVCTL1_HIFI3D_MASK 0x0300 /* yup, this is missing the high bit that official AC97 contains, plus it doesn't have linear bit value range behaviour but instead acts weirdly (possibly we're dealing with two *different* 3D settings here??) */
322 #define IDX_MIXER_ADVCTL2 0x20 /* subset of AC97_GENERAL_PURPOSE reg! */ 325 #define IDX_MIXER_ADVCTL2 0x20 /* subset of AC97_GENERAL_PURPOSE reg! */
323 /* unlisted bits are unmodifiable */ 326 /* unlisted bits are unmodifiable */
324 #define MIXER_ADVCTL2_LPBK 0x0080 /* Loopback mode -- Win driver: "WaveOut3DBypass"? mutes WaveOut at LineOut */ 327 #define MIXER_ADVCTL2_LPBK 0x0080 /* Loopback mode -- Win driver: "WaveOut3DBypass"? mutes WaveOut at LineOut */
325 #define MIXER_ADVCTL2_MS 0x0100 /* Mic Select 0=Mic1, 1=Mic2 -- Win driver: "ModemOutSelect"?? */ 328 #define MIXER_ADVCTL2_MS 0x0100 /* Mic Select 0=Mic1, 1=Mic2 -- Win driver: "ModemOutSelect"?? */
326 #define MIXER_ADVCTL2_MIX 0x0200 /* Mono output select 0=Mix, 1=Mic; Win driver: "MonoSelectSource"?? */ 329 #define MIXER_ADVCTL2_MIX 0x0200 /* Mono output select 0=Mix, 1=Mic; Win driver: "MonoSelectSource"?? */
327 #define MIXER_ADVCTL2_3D 0x2000 /* 3D Enhancement 1=on */ 330 #define MIXER_ADVCTL2_3D 0x2000 /* 3D Enhancement 1=on */
328 #define MIXER_ADVCTL2_POP 0x8000 /* Pcm Out Path, 0=pre 3D, 1=post 3D */ 331 #define MIXER_ADVCTL2_POP 0x8000 /* Pcm Out Path, 0=pre 3D, 1=post 3D */
329 332
330 #define IDX_MIXER_SOMETHING30H 0x30 /* used, but unknown??? */ 333 #define IDX_MIXER_SOMETHING30H 0x30 /* used, but unknown??? */
331 334
332 /* driver internal flags */ 335 /* driver internal flags */
333 #define SET_CHAN_LEFT 1 336 #define SET_CHAN_LEFT 1
334 #define SET_CHAN_RIGHT 2 337 #define SET_CHAN_RIGHT 2
338
339 /* helper macro to align I/O port ranges to 32bit I/O width */
340 #define AZF_ALIGN(x) (((x) + 3) & (~3))
335 341
336 #endif /* __SOUND_AZT3328_H */ 342 #endif /* __SOUND_AZT3328_H */
337 343