xref: /OK3568_Linux_fs/kernel/include/sound/opl3.h (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0-or-later */
2*4882a593Smuzhiyun #ifndef __SOUND_OPL3_H
3*4882a593Smuzhiyun #define __SOUND_OPL3_H
4*4882a593Smuzhiyun 
5*4882a593Smuzhiyun /*
6*4882a593Smuzhiyun  * Definitions of the OPL-3 registers.
7*4882a593Smuzhiyun  *
8*4882a593Smuzhiyun  * Copyright (c) by Jaroslav Kysela <perex@perex.cz>,
9*4882a593Smuzhiyun  *                  Hannu Savolainen 1993-1996
10*4882a593Smuzhiyun  *
11*4882a593Smuzhiyun  *      The OPL-3 mode is switched on by writing 0x01, to the offset 5
12*4882a593Smuzhiyun  *      of the right side.
13*4882a593Smuzhiyun  *
14*4882a593Smuzhiyun  *      Another special register at the right side is at offset 4. It contains
15*4882a593Smuzhiyun  *      a bit mask defining which voices are used as 4 OP voices.
16*4882a593Smuzhiyun  *
17*4882a593Smuzhiyun  *      The percussive mode is implemented in the left side only.
18*4882a593Smuzhiyun  *
19*4882a593Smuzhiyun  *      With the above exceptions the both sides can be operated independently.
20*4882a593Smuzhiyun  *
21*4882a593Smuzhiyun  *      A 4 OP voice can be created by setting the corresponding
22*4882a593Smuzhiyun  *      bit at offset 4 of the right side.
23*4882a593Smuzhiyun  *
24*4882a593Smuzhiyun  *      For example setting the rightmost bit (0x01) changes the
25*4882a593Smuzhiyun  *      first voice on the right side to the 4 OP mode. The fourth
26*4882a593Smuzhiyun  *      voice is made inaccessible.
27*4882a593Smuzhiyun  *
28*4882a593Smuzhiyun  *      If a voice is set to the 2 OP mode, it works like 2 OP modes
29*4882a593Smuzhiyun  *      of the original YM3812 (AdLib). In addition the voice can
30*4882a593Smuzhiyun  *      be connected the left, right or both stereo channels. It can
31*4882a593Smuzhiyun  *      even be left unconnected. This works with 4 OP voices also.
32*4882a593Smuzhiyun  *
33*4882a593Smuzhiyun  *      The stereo connection bits are located in the FEEDBACK_CONNECTION
34*4882a593Smuzhiyun  *      register of the voice (0xC0-0xC8). In 4 OP voices these bits are
35*4882a593Smuzhiyun  *      in the second half of the voice.
36*4882a593Smuzhiyun  */
37*4882a593Smuzhiyun 
38*4882a593Smuzhiyun #include <sound/core.h>
39*4882a593Smuzhiyun #include <sound/hwdep.h>
40*4882a593Smuzhiyun #include <sound/timer.h>
41*4882a593Smuzhiyun #include <sound/seq_midi_emul.h>
42*4882a593Smuzhiyun #include <sound/seq_oss.h>
43*4882a593Smuzhiyun #include <sound/seq_oss_legacy.h>
44*4882a593Smuzhiyun #include <sound/seq_device.h>
45*4882a593Smuzhiyun #include <sound/asound_fm.h>
46*4882a593Smuzhiyun 
47*4882a593Smuzhiyun /*
48*4882a593Smuzhiyun  *    Register numbers for the global registers
49*4882a593Smuzhiyun  */
50*4882a593Smuzhiyun 
51*4882a593Smuzhiyun #define OPL3_REG_TEST			0x01
52*4882a593Smuzhiyun #define   OPL3_ENABLE_WAVE_SELECT	0x20
53*4882a593Smuzhiyun 
54*4882a593Smuzhiyun #define OPL3_REG_TIMER1			0x02
55*4882a593Smuzhiyun #define OPL3_REG_TIMER2			0x03
56*4882a593Smuzhiyun #define OPL3_REG_TIMER_CONTROL		0x04	/* Left side */
57*4882a593Smuzhiyun #define   OPL3_IRQ_RESET		0x80
58*4882a593Smuzhiyun #define   OPL3_TIMER1_MASK		0x40
59*4882a593Smuzhiyun #define   OPL3_TIMER2_MASK		0x20
60*4882a593Smuzhiyun #define   OPL3_TIMER1_START		0x01
61*4882a593Smuzhiyun #define   OPL3_TIMER2_START		0x02
62*4882a593Smuzhiyun 
63*4882a593Smuzhiyun #define OPL3_REG_CONNECTION_SELECT	0x04	/* Right side */
64*4882a593Smuzhiyun #define   OPL3_LEFT_4OP_0		0x01
65*4882a593Smuzhiyun #define   OPL3_LEFT_4OP_1		0x02
66*4882a593Smuzhiyun #define   OPL3_LEFT_4OP_2		0x04
67*4882a593Smuzhiyun #define   OPL3_RIGHT_4OP_0		0x08
68*4882a593Smuzhiyun #define   OPL3_RIGHT_4OP_1		0x10
69*4882a593Smuzhiyun #define   OPL3_RIGHT_4OP_2		0x20
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun #define OPL3_REG_MODE			0x05	/* Right side */
72*4882a593Smuzhiyun #define   OPL3_OPL3_ENABLE		0x01	/* OPL3 mode */
73*4882a593Smuzhiyun #define   OPL3_OPL4_ENABLE		0x02	/* OPL4 mode */
74*4882a593Smuzhiyun 
75*4882a593Smuzhiyun #define OPL3_REG_KBD_SPLIT		0x08	/* Left side */
76*4882a593Smuzhiyun #define   OPL3_COMPOSITE_SINE_WAVE_MODE	0x80	/* Don't use with OPL-3? */
77*4882a593Smuzhiyun #define   OPL3_KEYBOARD_SPLIT		0x40
78*4882a593Smuzhiyun 
79*4882a593Smuzhiyun #define OPL3_REG_PERCUSSION		0xbd	/* Left side only */
80*4882a593Smuzhiyun #define   OPL3_TREMOLO_DEPTH		0x80
81*4882a593Smuzhiyun #define   OPL3_VIBRATO_DEPTH		0x40
82*4882a593Smuzhiyun #define	  OPL3_PERCUSSION_ENABLE	0x20
83*4882a593Smuzhiyun #define   OPL3_BASSDRUM_ON		0x10
84*4882a593Smuzhiyun #define   OPL3_SNAREDRUM_ON		0x08
85*4882a593Smuzhiyun #define   OPL3_TOMTOM_ON		0x04
86*4882a593Smuzhiyun #define   OPL3_CYMBAL_ON		0x02
87*4882a593Smuzhiyun #define   OPL3_HIHAT_ON			0x01
88*4882a593Smuzhiyun 
89*4882a593Smuzhiyun /*
90*4882a593Smuzhiyun  *    Offsets to the register banks for operators. To get the
91*4882a593Smuzhiyun  *      register number just add the operator offset to the bank offset
92*4882a593Smuzhiyun  *
93*4882a593Smuzhiyun  *      AM/VIB/EG/KSR/Multiple (0x20 to 0x35)
94*4882a593Smuzhiyun  */
95*4882a593Smuzhiyun #define OPL3_REG_AM_VIB			0x20
96*4882a593Smuzhiyun #define   OPL3_TREMOLO_ON		0x80
97*4882a593Smuzhiyun #define   OPL3_VIBRATO_ON		0x40
98*4882a593Smuzhiyun #define   OPL3_SUSTAIN_ON		0x20
99*4882a593Smuzhiyun #define   OPL3_KSR			0x10	/* Key scaling rate */
100*4882a593Smuzhiyun #define   OPL3_MULTIPLE_MASK		0x0f	/* Frequency multiplier */
101*4882a593Smuzhiyun 
102*4882a593Smuzhiyun  /*
103*4882a593Smuzhiyun   *   KSL/Total level (0x40 to 0x55)
104*4882a593Smuzhiyun   */
105*4882a593Smuzhiyun #define OPL3_REG_KSL_LEVEL		0x40
106*4882a593Smuzhiyun #define   OPL3_KSL_MASK			0xc0	/* Envelope scaling bits */
107*4882a593Smuzhiyun #define   OPL3_TOTAL_LEVEL_MASK		0x3f	/* Strength (volume) of OP */
108*4882a593Smuzhiyun 
109*4882a593Smuzhiyun /*
110*4882a593Smuzhiyun  *    Attack / Decay rate (0x60 to 0x75)
111*4882a593Smuzhiyun  */
112*4882a593Smuzhiyun #define OPL3_REG_ATTACK_DECAY		0x60
113*4882a593Smuzhiyun #define   OPL3_ATTACK_MASK		0xf0
114*4882a593Smuzhiyun #define   OPL3_DECAY_MASK		0x0f
115*4882a593Smuzhiyun 
116*4882a593Smuzhiyun /*
117*4882a593Smuzhiyun  * Sustain level / Release rate (0x80 to 0x95)
118*4882a593Smuzhiyun  */
119*4882a593Smuzhiyun #define OPL3_REG_SUSTAIN_RELEASE	0x80
120*4882a593Smuzhiyun #define   OPL3_SUSTAIN_MASK		0xf0
121*4882a593Smuzhiyun #define   OPL3_RELEASE_MASK		0x0f
122*4882a593Smuzhiyun 
123*4882a593Smuzhiyun /*
124*4882a593Smuzhiyun  * Wave select (0xE0 to 0xF5)
125*4882a593Smuzhiyun  */
126*4882a593Smuzhiyun #define OPL3_REG_WAVE_SELECT		0xe0
127*4882a593Smuzhiyun #define   OPL3_WAVE_SELECT_MASK		0x07
128*4882a593Smuzhiyun 
129*4882a593Smuzhiyun /*
130*4882a593Smuzhiyun  *    Offsets to the register banks for voices. Just add to the
131*4882a593Smuzhiyun  *      voice number to get the register number.
132*4882a593Smuzhiyun  *
133*4882a593Smuzhiyun  *      F-Number low bits (0xA0 to 0xA8).
134*4882a593Smuzhiyun  */
135*4882a593Smuzhiyun #define OPL3_REG_FNUM_LOW		0xa0
136*4882a593Smuzhiyun 
137*4882a593Smuzhiyun /*
138*4882a593Smuzhiyun  *    F-number high bits / Key on / Block (octave) (0xB0 to 0xB8)
139*4882a593Smuzhiyun  */
140*4882a593Smuzhiyun #define OPL3_REG_KEYON_BLOCK		0xb0
141*4882a593Smuzhiyun #define	  OPL3_KEYON_BIT		0x20
142*4882a593Smuzhiyun #define	  OPL3_BLOCKNUM_MASK		0x1c
143*4882a593Smuzhiyun #define   OPL3_FNUM_HIGH_MASK		0x03
144*4882a593Smuzhiyun 
145*4882a593Smuzhiyun /*
146*4882a593Smuzhiyun  *    Feedback / Connection (0xc0 to 0xc8)
147*4882a593Smuzhiyun  *
148*4882a593Smuzhiyun  *      These registers have two new bits when the OPL-3 mode
149*4882a593Smuzhiyun  *      is selected. These bits controls connecting the voice
150*4882a593Smuzhiyun  *      to the stereo channels. For 4 OP voices this bit is
151*4882a593Smuzhiyun  *      defined in the second half of the voice (add 3 to the
152*4882a593Smuzhiyun  *      register offset).
153*4882a593Smuzhiyun  *
154*4882a593Smuzhiyun  *      For 4 OP voices the connection bit is used in the
155*4882a593Smuzhiyun  *      both halves (gives 4 ways to connect the operators).
156*4882a593Smuzhiyun  */
157*4882a593Smuzhiyun #define OPL3_REG_FEEDBACK_CONNECTION	0xc0
158*4882a593Smuzhiyun #define   OPL3_FEEDBACK_MASK		0x0e	/* Valid just for 1st OP of a voice */
159*4882a593Smuzhiyun #define   OPL3_CONNECTION_BIT		0x01
160*4882a593Smuzhiyun /*
161*4882a593Smuzhiyun  *    In the 4 OP mode there is four possible configurations how the
162*4882a593Smuzhiyun  *      operators can be connected together (in 2 OP modes there is just
163*4882a593Smuzhiyun  *      AM or FM). The 4 OP connection mode is defined by the rightmost
164*4882a593Smuzhiyun  *      bit of the FEEDBACK_CONNECTION (0xC0-0xC8) on the both halves.
165*4882a593Smuzhiyun  *
166*4882a593Smuzhiyun  *      First half      Second half     Mode
167*4882a593Smuzhiyun  *
168*4882a593Smuzhiyun  *                                       +---+
169*4882a593Smuzhiyun  *                                       v   |
170*4882a593Smuzhiyun  *      0               0               >+-1-+--2--3--4-->
171*4882a593Smuzhiyun  *
172*4882a593Smuzhiyun  *
173*4882a593Smuzhiyun  *
174*4882a593Smuzhiyun  *                                       +---+
175*4882a593Smuzhiyun  *                                       |   |
176*4882a593Smuzhiyun  *      0               1               >+-1-+--2-+
177*4882a593Smuzhiyun  *                                                |->
178*4882a593Smuzhiyun  *                                      >--3----4-+
179*4882a593Smuzhiyun  *
180*4882a593Smuzhiyun  *                                       +---+
181*4882a593Smuzhiyun  *                                       |   |
182*4882a593Smuzhiyun  *      1               0               >+-1-+-----+
183*4882a593Smuzhiyun  *                                                 |->
184*4882a593Smuzhiyun  *                                      >--2--3--4-+
185*4882a593Smuzhiyun  *
186*4882a593Smuzhiyun  *                                       +---+
187*4882a593Smuzhiyun  *                                       |   |
188*4882a593Smuzhiyun  *      1               1               >+-1-+--+
189*4882a593Smuzhiyun  *                                              |
190*4882a593Smuzhiyun  *                                      >--2--3-+->
191*4882a593Smuzhiyun  *                                              |
192*4882a593Smuzhiyun  *                                      >--4----+
193*4882a593Smuzhiyun  */
194*4882a593Smuzhiyun #define   OPL3_STEREO_BITS		0x30	/* OPL-3 only */
195*4882a593Smuzhiyun #define     OPL3_VOICE_TO_LEFT		0x10
196*4882a593Smuzhiyun #define     OPL3_VOICE_TO_RIGHT		0x20
197*4882a593Smuzhiyun 
198*4882a593Smuzhiyun /*
199*4882a593Smuzhiyun 
200*4882a593Smuzhiyun  */
201*4882a593Smuzhiyun 
202*4882a593Smuzhiyun #define OPL3_LEFT		0x0000
203*4882a593Smuzhiyun #define OPL3_RIGHT		0x0100
204*4882a593Smuzhiyun 
205*4882a593Smuzhiyun #define OPL3_HW_AUTO		0x0000
206*4882a593Smuzhiyun #define OPL3_HW_OPL2		0x0200
207*4882a593Smuzhiyun #define OPL3_HW_OPL3		0x0300
208*4882a593Smuzhiyun #define OPL3_HW_OPL3_SV		0x0301	/* S3 SonicVibes */
209*4882a593Smuzhiyun #define OPL3_HW_OPL3_CS		0x0302	/* CS4232/CS4236+ */
210*4882a593Smuzhiyun #define OPL3_HW_OPL3_FM801	0x0303	/* FM801 */
211*4882a593Smuzhiyun #define OPL3_HW_OPL3_CS4281	0x0304	/* CS4281 */
212*4882a593Smuzhiyun #define OPL3_HW_OPL4		0x0400	/* YMF278B/YMF295 */
213*4882a593Smuzhiyun #define OPL3_HW_OPL4_ML		0x0401	/* YMF704/YMF721 */
214*4882a593Smuzhiyun #define OPL3_HW_MASK		0xff00
215*4882a593Smuzhiyun 
216*4882a593Smuzhiyun #define MAX_OPL2_VOICES		9
217*4882a593Smuzhiyun #define MAX_OPL3_VOICES		18
218*4882a593Smuzhiyun 
219*4882a593Smuzhiyun struct snd_opl3;
220*4882a593Smuzhiyun 
221*4882a593Smuzhiyun /*
222*4882a593Smuzhiyun  * Instrument record, aka "Patch"
223*4882a593Smuzhiyun  */
224*4882a593Smuzhiyun 
225*4882a593Smuzhiyun /* FM operator */
226*4882a593Smuzhiyun struct fm_operator {
227*4882a593Smuzhiyun 	unsigned char am_vib;
228*4882a593Smuzhiyun 	unsigned char ksl_level;
229*4882a593Smuzhiyun 	unsigned char attack_decay;
230*4882a593Smuzhiyun 	unsigned char sustain_release;
231*4882a593Smuzhiyun 	unsigned char wave_select;
232*4882a593Smuzhiyun } __attribute__((packed));
233*4882a593Smuzhiyun 
234*4882a593Smuzhiyun /* Instrument data */
235*4882a593Smuzhiyun struct fm_instrument {
236*4882a593Smuzhiyun 	struct fm_operator op[4];
237*4882a593Smuzhiyun 	unsigned char feedback_connection[2];
238*4882a593Smuzhiyun 	unsigned char echo_delay;
239*4882a593Smuzhiyun 	unsigned char echo_atten;
240*4882a593Smuzhiyun 	unsigned char chorus_spread;
241*4882a593Smuzhiyun 	unsigned char trnsps;
242*4882a593Smuzhiyun 	unsigned char fix_dur;
243*4882a593Smuzhiyun 	unsigned char modes;
244*4882a593Smuzhiyun 	unsigned char fix_key;
245*4882a593Smuzhiyun };
246*4882a593Smuzhiyun 
247*4882a593Smuzhiyun /* type */
248*4882a593Smuzhiyun #define FM_PATCH_OPL2	0x01		/* OPL2 2 operators FM instrument */
249*4882a593Smuzhiyun #define FM_PATCH_OPL3	0x02		/* OPL3 4 operators FM instrument */
250*4882a593Smuzhiyun 
251*4882a593Smuzhiyun /* Instrument record */
252*4882a593Smuzhiyun struct fm_patch {
253*4882a593Smuzhiyun 	unsigned char prog;
254*4882a593Smuzhiyun 	unsigned char bank;
255*4882a593Smuzhiyun 	unsigned char type;
256*4882a593Smuzhiyun 	struct fm_instrument inst;
257*4882a593Smuzhiyun 	char name[24];
258*4882a593Smuzhiyun 	struct fm_patch *next;
259*4882a593Smuzhiyun };
260*4882a593Smuzhiyun 
261*4882a593Smuzhiyun 
262*4882a593Smuzhiyun /*
263*4882a593Smuzhiyun  * A structure to keep track of each hardware voice
264*4882a593Smuzhiyun  */
265*4882a593Smuzhiyun struct snd_opl3_voice {
266*4882a593Smuzhiyun 	int  state;		/* status */
267*4882a593Smuzhiyun #define SNDRV_OPL3_ST_OFF		0	/* Not playing */
268*4882a593Smuzhiyun #define SNDRV_OPL3_ST_ON_2OP	1	/* 2op voice is allocated */
269*4882a593Smuzhiyun #define SNDRV_OPL3_ST_ON_4OP	2	/* 4op voice is allocated */
270*4882a593Smuzhiyun #define SNDRV_OPL3_ST_NOT_AVAIL	-1	/* voice is not available */
271*4882a593Smuzhiyun 
272*4882a593Smuzhiyun 	unsigned int time;	/* An allocation time */
273*4882a593Smuzhiyun 	unsigned char note;	/* Note currently assigned to this voice */
274*4882a593Smuzhiyun 
275*4882a593Smuzhiyun 	unsigned long note_off;	/* note-off time */
276*4882a593Smuzhiyun 	int note_off_check;	/* check note-off time */
277*4882a593Smuzhiyun 
278*4882a593Smuzhiyun 	unsigned char keyon_reg;	/* KON register shadow */
279*4882a593Smuzhiyun 
280*4882a593Smuzhiyun 	struct snd_midi_channel *chan;	/* Midi channel for this note */
281*4882a593Smuzhiyun };
282*4882a593Smuzhiyun 
283*4882a593Smuzhiyun struct snd_opl3 {
284*4882a593Smuzhiyun 	unsigned long l_port;
285*4882a593Smuzhiyun 	unsigned long r_port;
286*4882a593Smuzhiyun 	struct resource *res_l_port;
287*4882a593Smuzhiyun 	struct resource *res_r_port;
288*4882a593Smuzhiyun 	unsigned short hardware;
289*4882a593Smuzhiyun 	/* hardware access */
290*4882a593Smuzhiyun 	void (*command) (struct snd_opl3 * opl3, unsigned short cmd, unsigned char val);
291*4882a593Smuzhiyun 	unsigned short timer_enable;
292*4882a593Smuzhiyun 	int seq_dev_num;	/* sequencer device number */
293*4882a593Smuzhiyun 	struct snd_timer *timer1;
294*4882a593Smuzhiyun 	struct snd_timer *timer2;
295*4882a593Smuzhiyun 	spinlock_t timer_lock;
296*4882a593Smuzhiyun 
297*4882a593Smuzhiyun 	void *private_data;
298*4882a593Smuzhiyun 	void (*private_free)(struct snd_opl3 *);
299*4882a593Smuzhiyun 
300*4882a593Smuzhiyun 	struct snd_hwdep *hwdep;
301*4882a593Smuzhiyun 	spinlock_t reg_lock;
302*4882a593Smuzhiyun 	struct snd_card *card;		/* The card that this belongs to */
303*4882a593Smuzhiyun 	unsigned char fm_mode;		/* OPL mode, see SNDRV_DM_FM_MODE_XXX */
304*4882a593Smuzhiyun 	unsigned char rhythm;		/* percussion mode flag */
305*4882a593Smuzhiyun 	unsigned char max_voices;	/* max number of voices */
306*4882a593Smuzhiyun #if IS_ENABLED(CONFIG_SND_SEQUENCER)
307*4882a593Smuzhiyun #define SNDRV_OPL3_MODE_SYNTH 0		/* OSS - voices allocated by application */
308*4882a593Smuzhiyun #define SNDRV_OPL3_MODE_SEQ 1		/* ALSA - driver handles voice allocation */
309*4882a593Smuzhiyun 	int synth_mode;			/* synth mode */
310*4882a593Smuzhiyun 	int seq_client;
311*4882a593Smuzhiyun 
312*4882a593Smuzhiyun 	struct snd_seq_device *seq_dev;	/* sequencer device */
313*4882a593Smuzhiyun 	struct snd_midi_channel_set * chset;
314*4882a593Smuzhiyun 
315*4882a593Smuzhiyun #if IS_ENABLED(CONFIG_SND_SEQUENCER_OSS)
316*4882a593Smuzhiyun 	struct snd_seq_device *oss_seq_dev;	/* OSS sequencer device */
317*4882a593Smuzhiyun 	struct snd_midi_channel_set * oss_chset;
318*4882a593Smuzhiyun #endif
319*4882a593Smuzhiyun 
320*4882a593Smuzhiyun #define OPL3_PATCH_HASH_SIZE	32
321*4882a593Smuzhiyun 	struct fm_patch *patch_table[OPL3_PATCH_HASH_SIZE];
322*4882a593Smuzhiyun 
323*4882a593Smuzhiyun 	struct snd_opl3_voice voices[MAX_OPL3_VOICES]; /* Voices (OPL3 'channel') */
324*4882a593Smuzhiyun 	int use_time;			/* allocation counter */
325*4882a593Smuzhiyun 
326*4882a593Smuzhiyun 	unsigned short connection_reg;	/* connection reg shadow */
327*4882a593Smuzhiyun 	unsigned char drum_reg;		/* percussion reg shadow */
328*4882a593Smuzhiyun 
329*4882a593Smuzhiyun 	spinlock_t voice_lock;		/* Lock for voice access */
330*4882a593Smuzhiyun 
331*4882a593Smuzhiyun 	struct timer_list tlist;	/* timer for note-offs and effects */
332*4882a593Smuzhiyun 	int sys_timer_status;		/* system timer run status */
333*4882a593Smuzhiyun 	spinlock_t sys_timer_lock;	/* Lock for system timer access */
334*4882a593Smuzhiyun #endif
335*4882a593Smuzhiyun };
336*4882a593Smuzhiyun 
337*4882a593Smuzhiyun /* opl3.c */
338*4882a593Smuzhiyun void snd_opl3_interrupt(struct snd_hwdep * hw);
339*4882a593Smuzhiyun int snd_opl3_new(struct snd_card *card, unsigned short hardware,
340*4882a593Smuzhiyun 		 struct snd_opl3 **ropl3);
341*4882a593Smuzhiyun int snd_opl3_init(struct snd_opl3 *opl3);
342*4882a593Smuzhiyun int snd_opl3_create(struct snd_card *card,
343*4882a593Smuzhiyun 		    unsigned long l_port, unsigned long r_port,
344*4882a593Smuzhiyun 		    unsigned short hardware,
345*4882a593Smuzhiyun 		    int integrated,
346*4882a593Smuzhiyun 		    struct snd_opl3 ** opl3);
347*4882a593Smuzhiyun int snd_opl3_timer_new(struct snd_opl3 * opl3, int timer1_dev, int timer2_dev);
348*4882a593Smuzhiyun int snd_opl3_hwdep_new(struct snd_opl3 * opl3, int device, int seq_device,
349*4882a593Smuzhiyun 		       struct snd_hwdep ** rhwdep);
350*4882a593Smuzhiyun 
351*4882a593Smuzhiyun /* opl3_synth */
352*4882a593Smuzhiyun int snd_opl3_open(struct snd_hwdep * hw, struct file *file);
353*4882a593Smuzhiyun int snd_opl3_ioctl(struct snd_hwdep * hw, struct file *file,
354*4882a593Smuzhiyun 		   unsigned int cmd, unsigned long arg);
355*4882a593Smuzhiyun int snd_opl3_release(struct snd_hwdep * hw, struct file *file);
356*4882a593Smuzhiyun 
357*4882a593Smuzhiyun void snd_opl3_reset(struct snd_opl3 * opl3);
358*4882a593Smuzhiyun 
359*4882a593Smuzhiyun #if IS_ENABLED(CONFIG_SND_SEQUENCER)
360*4882a593Smuzhiyun long snd_opl3_write(struct snd_hwdep *hw, const char __user *buf, long count,
361*4882a593Smuzhiyun 		    loff_t *offset);
362*4882a593Smuzhiyun int snd_opl3_load_patch(struct snd_opl3 *opl3,
363*4882a593Smuzhiyun 			int prog, int bank, int type,
364*4882a593Smuzhiyun 			const char *name,
365*4882a593Smuzhiyun 			const unsigned char *ext,
366*4882a593Smuzhiyun 			const unsigned char *data);
367*4882a593Smuzhiyun struct fm_patch *snd_opl3_find_patch(struct snd_opl3 *opl3, int prog, int bank,
368*4882a593Smuzhiyun 				     int create_patch);
369*4882a593Smuzhiyun void snd_opl3_clear_patches(struct snd_opl3 *opl3);
370*4882a593Smuzhiyun #else
371*4882a593Smuzhiyun #define snd_opl3_write	NULL
snd_opl3_clear_patches(struct snd_opl3 * opl3)372*4882a593Smuzhiyun static inline void snd_opl3_clear_patches(struct snd_opl3 *opl3) {}
373*4882a593Smuzhiyun #endif
374*4882a593Smuzhiyun 
375*4882a593Smuzhiyun #endif /* __SOUND_OPL3_H */
376