xref: /linux/sound/isa/sb/sb16_csp.c (revision 55a42f78ffd386e01a5404419f8c5ded7db70a21)
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  *  Copyright (c) 1999 by Uros Bizjak <uros@kss-loka.si>
4  *                        Takashi Iwai <tiwai@suse.de>
5  *
6  *  SB16ASP/AWE32 CSP control
7  *
8  *  CSP microcode loader:
9  *   alsa-tools/sb16_csp/
10  */
11 
12 #include <linux/delay.h>
13 #include <linux/init.h>
14 #include <linux/slab.h>
15 #include <linux/module.h>
16 #include <linux/string_choices.h>
17 #include <sound/core.h>
18 #include <sound/control.h>
19 #include <sound/info.h>
20 #include <sound/sb16_csp.h>
21 #include <sound/initval.h>
22 
23 MODULE_AUTHOR("Uros Bizjak <uros@kss-loka.si>");
24 MODULE_DESCRIPTION("ALSA driver for SB16 Creative Signal Processor");
25 MODULE_LICENSE("GPL");
26 MODULE_FIRMWARE("sb16/mulaw_main.csp");
27 MODULE_FIRMWARE("sb16/alaw_main.csp");
28 MODULE_FIRMWARE("sb16/ima_adpcm_init.csp");
29 MODULE_FIRMWARE("sb16/ima_adpcm_playback.csp");
30 MODULE_FIRMWARE("sb16/ima_adpcm_capture.csp");
31 
32 #ifdef SNDRV_LITTLE_ENDIAN
33 #define CSP_HDR_VALUE(a,b,c,d)	((a) | ((b)<<8) | ((c)<<16) | ((d)<<24))
34 #else
35 #define CSP_HDR_VALUE(a,b,c,d)	((d) | ((c)<<8) | ((b)<<16) | ((a)<<24))
36 #endif
37 
38 #define RIFF_HEADER	CSP_HDR_VALUE('R', 'I', 'F', 'F')
39 #define CSP__HEADER	CSP_HDR_VALUE('C', 'S', 'P', ' ')
40 #define LIST_HEADER	CSP_HDR_VALUE('L', 'I', 'S', 'T')
41 #define FUNC_HEADER	CSP_HDR_VALUE('f', 'u', 'n', 'c')
42 #define CODE_HEADER	CSP_HDR_VALUE('c', 'o', 'd', 'e')
43 #define INIT_HEADER	CSP_HDR_VALUE('i', 'n', 'i', 't')
44 #define MAIN_HEADER	CSP_HDR_VALUE('m', 'a', 'i', 'n')
45 
46 /*
47  * RIFF data format
48  */
49 struct riff_header {
50 	__le32 name;
51 	__le32 len;
52 };
53 
54 struct desc_header {
55 	struct riff_header info;
56 	__le16 func_nr;
57 	__le16 VOC_type;
58 	__le16 flags_play_rec;
59 	__le16 flags_16bit_8bit;
60 	__le16 flags_stereo_mono;
61 	__le16 flags_rates;
62 };
63 
64 /*
65  * prototypes
66  */
67 static void snd_sb_csp_free(struct snd_hwdep *hw);
68 static int snd_sb_csp_open(struct snd_hwdep * hw, struct file *file);
69 static int snd_sb_csp_ioctl(struct snd_hwdep * hw, struct file *file, unsigned int cmd, unsigned long arg);
70 static int snd_sb_csp_release(struct snd_hwdep * hw, struct file *file);
71 
72 static int csp_detect(struct snd_sb *chip, int *version);
73 static int set_codec_parameter(struct snd_sb *chip, unsigned char par, unsigned char val);
74 static int set_register(struct snd_sb *chip, unsigned char reg, unsigned char val);
75 static int read_register(struct snd_sb *chip, unsigned char reg);
76 static int set_mode_register(struct snd_sb *chip, unsigned char mode);
77 static int get_version(struct snd_sb *chip);
78 
79 static int snd_sb_csp_riff_load(struct snd_sb_csp * p,
80 				struct snd_sb_csp_microcode __user * code);
81 static int snd_sb_csp_unload(struct snd_sb_csp * p);
82 static int snd_sb_csp_load_user(struct snd_sb_csp * p, const unsigned char __user *buf, int size, int load_flags);
83 static int snd_sb_csp_autoload(struct snd_sb_csp * p, snd_pcm_format_t pcm_sfmt, int play_rec_mode);
84 static int snd_sb_csp_check_version(struct snd_sb_csp * p);
85 
86 static int snd_sb_csp_use(struct snd_sb_csp * p);
87 static int snd_sb_csp_unuse(struct snd_sb_csp * p);
88 static int snd_sb_csp_start(struct snd_sb_csp * p, int sample_width, int channels);
89 static int snd_sb_csp_stop(struct snd_sb_csp * p);
90 static int snd_sb_csp_pause(struct snd_sb_csp * p);
91 static int snd_sb_csp_restart(struct snd_sb_csp * p);
92 
93 static int snd_sb_qsound_build(struct snd_sb_csp * p);
94 static void snd_sb_qsound_destroy(struct snd_sb_csp * p);
95 static int snd_sb_csp_qsound_transfer(struct snd_sb_csp * p);
96 
97 static int init_proc_entry(struct snd_sb_csp * p, int device);
98 static void info_read(struct snd_info_entry *entry, struct snd_info_buffer *buffer);
99 
100 /*
101  * Detect CSP chip and create a new instance
102  */
103 int snd_sb_csp_new(struct snd_sb *chip, int device, struct snd_hwdep ** rhwdep)
104 {
105 	struct snd_sb_csp *p;
106 	int version;
107 	int err;
108 	struct snd_hwdep *hw;
109 
110 	if (rhwdep)
111 		*rhwdep = NULL;
112 
113 	if (csp_detect(chip, &version))
114 		return -ENODEV;
115 
116 	err = snd_hwdep_new(chip->card, "SB16-CSP", device, &hw);
117 	if (err < 0)
118 		return err;
119 
120 	p = kzalloc(sizeof(*p), GFP_KERNEL);
121 	if (!p) {
122 		snd_device_free(chip->card, hw);
123 		return -ENOMEM;
124 	}
125 	p->chip = chip;
126 	p->version = version;
127 
128 	/* CSP operators */
129 	p->ops.csp_use = snd_sb_csp_use;
130 	p->ops.csp_unuse = snd_sb_csp_unuse;
131 	p->ops.csp_autoload = snd_sb_csp_autoload;
132 	p->ops.csp_start = snd_sb_csp_start;
133 	p->ops.csp_stop = snd_sb_csp_stop;
134 	p->ops.csp_qsound_transfer = snd_sb_csp_qsound_transfer;
135 
136 	mutex_init(&p->access_mutex);
137 	sprintf(hw->name, "CSP v%d.%d", (version >> 4), (version & 0x0f));
138 	hw->iface = SNDRV_HWDEP_IFACE_SB16CSP;
139 	hw->private_data = p;
140 	hw->private_free = snd_sb_csp_free;
141 
142 	/* operators - only write/ioctl */
143 	hw->ops.open = snd_sb_csp_open;
144 	hw->ops.ioctl = snd_sb_csp_ioctl;
145 	hw->ops.release = snd_sb_csp_release;
146 
147 	/* create a proc entry */
148 	init_proc_entry(p, device);
149 	if (rhwdep)
150 		*rhwdep = hw;
151 	return 0;
152 }
153 
154 /*
155  * free_private for hwdep instance
156  */
157 static void snd_sb_csp_free(struct snd_hwdep *hwdep)
158 {
159 	int i;
160 	struct snd_sb_csp *p = hwdep->private_data;
161 	if (p) {
162 		if (p->running & SNDRV_SB_CSP_ST_RUNNING)
163 			snd_sb_csp_stop(p);
164 		for (i = 0; i < ARRAY_SIZE(p->csp_programs); ++i)
165 			release_firmware(p->csp_programs[i]);
166 		kfree(p);
167 	}
168 }
169 
170 /* ------------------------------ */
171 
172 /*
173  * open the device exclusively
174  */
175 static int snd_sb_csp_open(struct snd_hwdep * hw, struct file *file)
176 {
177 	struct snd_sb_csp *p = hw->private_data;
178 	return (snd_sb_csp_use(p));
179 }
180 
181 /*
182  * ioctl for hwdep device:
183  */
184 static int snd_sb_csp_ioctl(struct snd_hwdep * hw, struct file *file, unsigned int cmd, unsigned long arg)
185 {
186 	struct snd_sb_csp *p = hw->private_data;
187 	struct snd_sb_csp_info info;
188 	struct snd_sb_csp_start start_info;
189 	int err;
190 
191 	if (snd_BUG_ON(!p))
192 		return -EINVAL;
193 
194 	if (snd_sb_csp_check_version(p))
195 		return -ENODEV;
196 
197 	switch (cmd) {
198 		/* get information */
199 	case SNDRV_SB_CSP_IOCTL_INFO:
200 		memset(&info, 0, sizeof(info));
201 		*info.codec_name = *p->codec_name;
202 		info.func_nr = p->func_nr;
203 		info.acc_format = p->acc_format;
204 		info.acc_channels = p->acc_channels;
205 		info.acc_width = p->acc_width;
206 		info.acc_rates = p->acc_rates;
207 		info.csp_mode = p->mode;
208 		info.run_channels = p->run_channels;
209 		info.run_width = p->run_width;
210 		info.version = p->version;
211 		info.state = p->running;
212 		if (copy_to_user((void __user *)arg, &info, sizeof(info)))
213 			err = -EFAULT;
214 		else
215 			err = 0;
216 		break;
217 
218 		/* load CSP microcode */
219 	case SNDRV_SB_CSP_IOCTL_LOAD_CODE:
220 		err = (p->running & SNDRV_SB_CSP_ST_RUNNING ?
221 		       -EBUSY : snd_sb_csp_riff_load(p, (struct snd_sb_csp_microcode __user *) arg));
222 		break;
223 	case SNDRV_SB_CSP_IOCTL_UNLOAD_CODE:
224 		err = (p->running & SNDRV_SB_CSP_ST_RUNNING ?
225 		       -EBUSY : snd_sb_csp_unload(p));
226 		break;
227 
228 		/* change CSP running state */
229 	case SNDRV_SB_CSP_IOCTL_START:
230 		if (copy_from_user(&start_info, (void __user *) arg, sizeof(start_info)))
231 			err = -EFAULT;
232 		else
233 			err = snd_sb_csp_start(p, start_info.sample_width, start_info.channels);
234 		break;
235 	case SNDRV_SB_CSP_IOCTL_STOP:
236 		err = snd_sb_csp_stop(p);
237 		break;
238 	case SNDRV_SB_CSP_IOCTL_PAUSE:
239 		err = snd_sb_csp_pause(p);
240 		break;
241 	case SNDRV_SB_CSP_IOCTL_RESTART:
242 		err = snd_sb_csp_restart(p);
243 		break;
244 	default:
245 		err = -ENOTTY;
246 		break;
247 	}
248 
249 	return err;
250 }
251 
252 /*
253  * close the device
254  */
255 static int snd_sb_csp_release(struct snd_hwdep * hw, struct file *file)
256 {
257 	struct snd_sb_csp *p = hw->private_data;
258 	return (snd_sb_csp_unuse(p));
259 }
260 
261 /* ------------------------------ */
262 
263 /*
264  * acquire device
265  */
266 static int snd_sb_csp_use(struct snd_sb_csp * p)
267 {
268 	guard(mutex)(&p->access_mutex);
269 	if (p->used)
270 		return -EAGAIN;
271 	p->used++;
272 	return 0;
273 
274 }
275 
276 /*
277  * release device
278  */
279 static int snd_sb_csp_unuse(struct snd_sb_csp * p)
280 {
281 	guard(mutex)(&p->access_mutex);
282 	p->used--;
283 	return 0;
284 }
285 
286 /*
287  * load microcode via ioctl:
288  * code is user-space pointer
289  */
290 static int snd_sb_csp_riff_load(struct snd_sb_csp * p,
291 				struct snd_sb_csp_microcode __user * mcode)
292 {
293 	struct snd_sb_csp_mc_header info;
294 	struct device *dev = p->chip->card->dev;
295 
296 	unsigned char __user *data_ptr;
297 	unsigned char __user *data_end;
298 	unsigned short func_nr = 0;
299 
300 	struct riff_header file_h, item_h, code_h;
301 	__le32 item_type;
302 	struct desc_header funcdesc_h;
303 
304 	int err;
305 
306 	if (copy_from_user(&info, mcode, sizeof(info)))
307 		return -EFAULT;
308 	data_ptr = mcode->data;
309 
310 	if (copy_from_user(&file_h, data_ptr, sizeof(file_h)))
311 		return -EFAULT;
312 	if ((le32_to_cpu(file_h.name) != RIFF_HEADER) ||
313 	    (le32_to_cpu(file_h.len) >= SNDRV_SB_CSP_MAX_MICROCODE_FILE_SIZE - sizeof(file_h))) {
314 		dev_dbg(dev, "%s: Invalid RIFF header\n", __func__);
315 		return -EINVAL;
316 	}
317 	data_ptr += sizeof(file_h);
318 	data_end = data_ptr + le32_to_cpu(file_h.len);
319 
320 	if (copy_from_user(&item_type, data_ptr, sizeof(item_type)))
321 		return -EFAULT;
322 	if (le32_to_cpu(item_type) != CSP__HEADER) {
323 		dev_dbg(dev, "%s: Invalid RIFF file type\n", __func__);
324 		return -EINVAL;
325 	}
326 	data_ptr += sizeof (item_type);
327 
328 	for (; data_ptr < data_end; data_ptr += le32_to_cpu(item_h.len)) {
329 		if (copy_from_user(&item_h, data_ptr, sizeof(item_h)))
330 			return -EFAULT;
331 		data_ptr += sizeof(item_h);
332 		if (le32_to_cpu(item_h.name) != LIST_HEADER)
333 			continue;
334 
335 		if (copy_from_user(&item_type, data_ptr, sizeof(item_type)))
336 			 return -EFAULT;
337 		switch (le32_to_cpu(item_type)) {
338 		case FUNC_HEADER:
339 			if (copy_from_user(&funcdesc_h, data_ptr + sizeof(item_type), sizeof(funcdesc_h)))
340 				return -EFAULT;
341 			func_nr = le16_to_cpu(funcdesc_h.func_nr);
342 			break;
343 		case CODE_HEADER:
344 			if (func_nr != info.func_req)
345 				break;	/* not required function, try next */
346 			data_ptr += sizeof(item_type);
347 
348 			/* destroy QSound mixer element */
349 			if (p->mode == SNDRV_SB_CSP_MODE_QSOUND) {
350 				snd_sb_qsound_destroy(p);
351 			}
352 			/* Clear all flags */
353 			p->running = 0;
354 			p->mode = 0;
355 
356 			/* load microcode blocks */
357 			for (;;) {
358 				if (data_ptr >= data_end)
359 					return -EINVAL;
360 				if (copy_from_user(&code_h, data_ptr, sizeof(code_h)))
361 					return -EFAULT;
362 
363 				/* init microcode blocks */
364 				if (le32_to_cpu(code_h.name) != INIT_HEADER)
365 					break;
366 				data_ptr += sizeof(code_h);
367 				err = snd_sb_csp_load_user(p, data_ptr, le32_to_cpu(code_h.len),
368 						      SNDRV_SB_CSP_LOAD_INITBLOCK);
369 				if (err)
370 					return err;
371 				data_ptr += le32_to_cpu(code_h.len);
372 			}
373 			/* main microcode block */
374 			if (copy_from_user(&code_h, data_ptr, sizeof(code_h)))
375 				return -EFAULT;
376 
377 			if (le32_to_cpu(code_h.name) != MAIN_HEADER) {
378 				dev_dbg(dev, "%s: Missing 'main' microcode\n", __func__);
379 				return -EINVAL;
380 			}
381 			data_ptr += sizeof(code_h);
382 			err = snd_sb_csp_load_user(p, data_ptr,
383 						   le32_to_cpu(code_h.len), 0);
384 			if (err)
385 				return err;
386 
387 			/* fill in codec header */
388 			strscpy(p->codec_name, info.codec_name, sizeof(p->codec_name));
389 			p->func_nr = func_nr;
390 			p->mode = le16_to_cpu(funcdesc_h.flags_play_rec);
391 			switch (le16_to_cpu(funcdesc_h.VOC_type)) {
392 			case 0x0001:	/* QSound decoder */
393 				if (le16_to_cpu(funcdesc_h.flags_play_rec) == SNDRV_SB_CSP_MODE_DSP_WRITE) {
394 					if (snd_sb_qsound_build(p) == 0)
395 						/* set QSound flag and clear all other mode flags */
396 						p->mode = SNDRV_SB_CSP_MODE_QSOUND;
397 				}
398 				p->acc_format = 0;
399 				break;
400 			case 0x0006:	/* A Law codec */
401 				p->acc_format = SNDRV_PCM_FMTBIT_A_LAW;
402 				break;
403 			case 0x0007:	/* Mu Law codec */
404 				p->acc_format = SNDRV_PCM_FMTBIT_MU_LAW;
405 				break;
406 			case 0x0011:	/* what Creative thinks is IMA ADPCM codec */
407 			case 0x0200:	/* Creative ADPCM codec */
408 				p->acc_format = SNDRV_PCM_FMTBIT_IMA_ADPCM;
409 				break;
410 			case    201:	/* Text 2 Speech decoder */
411 				/* TODO: Text2Speech handling routines */
412 				p->acc_format = 0;
413 				break;
414 			case 0x0202:	/* Fast Speech 8 codec */
415 			case 0x0203:	/* Fast Speech 10 codec */
416 				p->acc_format = SNDRV_PCM_FMTBIT_SPECIAL;
417 				break;
418 			default:	/* other codecs are unsupported */
419 				p->acc_format = p->acc_width = p->acc_rates = 0;
420 				p->mode = 0;
421 				dev_dbg(dev, "%s: Unsupported CSP codec type: 0x%04x\n",
422 					__func__,
423 					le16_to_cpu(funcdesc_h.VOC_type));
424 				return -EINVAL;
425 			}
426 			p->acc_channels = le16_to_cpu(funcdesc_h.flags_stereo_mono);
427 			p->acc_width = le16_to_cpu(funcdesc_h.flags_16bit_8bit);
428 			p->acc_rates = le16_to_cpu(funcdesc_h.flags_rates);
429 
430 			/* Decouple CSP from IRQ and DMAREQ lines */
431 			guard(spinlock_irqsave)(&p->chip->reg_lock);
432 			set_mode_register(p->chip, 0xfc);
433 			set_mode_register(p->chip, 0x00);
434 
435 			/* finished loading successfully */
436 			p->running = SNDRV_SB_CSP_ST_LOADED;	/* set LOADED flag */
437 			return 0;
438 		}
439 	}
440 	dev_dbg(dev, "%s: Function #%d not found\n", __func__, info.func_req);
441 	return -EINVAL;
442 }
443 
444 /*
445  * unload CSP microcode
446  */
447 static int snd_sb_csp_unload(struct snd_sb_csp * p)
448 {
449 	if (p->running & SNDRV_SB_CSP_ST_RUNNING)
450 		return -EBUSY;
451 	if (!(p->running & SNDRV_SB_CSP_ST_LOADED))
452 		return -ENXIO;
453 
454 	/* clear supported formats */
455 	p->acc_format = 0;
456 	p->acc_channels = p->acc_width = p->acc_rates = 0;
457 	/* destroy QSound mixer element */
458 	if (p->mode == SNDRV_SB_CSP_MODE_QSOUND) {
459 		snd_sb_qsound_destroy(p);
460 	}
461 	/* clear all flags */
462 	p->running = 0;
463 	p->mode = 0;
464 	return 0;
465 }
466 
467 /*
468  * send command sequence to DSP
469  */
470 static inline int command_seq(struct snd_sb *chip, const unsigned char *seq, int size)
471 {
472 	int i;
473 	for (i = 0; i < size; i++) {
474 		if (!snd_sbdsp_command(chip, seq[i]))
475 			return -EIO;
476 	}
477 	return 0;
478 }
479 
480 /*
481  * set CSP codec parameter
482  */
483 static int set_codec_parameter(struct snd_sb *chip, unsigned char par, unsigned char val)
484 {
485 	unsigned char dsp_cmd[3];
486 
487 	dsp_cmd[0] = 0x05;	/* CSP set codec parameter */
488 	dsp_cmd[1] = val;	/* Parameter value */
489 	dsp_cmd[2] = par;	/* Parameter */
490 	command_seq(chip, dsp_cmd, 3);
491 	snd_sbdsp_command(chip, 0x03);	/* DSP read? */
492 	if (snd_sbdsp_get_byte(chip) != par)
493 		return -EIO;
494 	return 0;
495 }
496 
497 /*
498  * set CSP register
499  */
500 static int set_register(struct snd_sb *chip, unsigned char reg, unsigned char val)
501 {
502 	unsigned char dsp_cmd[3];
503 
504 	dsp_cmd[0] = 0x0e;	/* CSP set register */
505 	dsp_cmd[1] = reg;	/* CSP Register */
506 	dsp_cmd[2] = val;	/* value */
507 	return command_seq(chip, dsp_cmd, 3);
508 }
509 
510 /*
511  * read CSP register
512  * return < 0 -> error
513  */
514 static int read_register(struct snd_sb *chip, unsigned char reg)
515 {
516 	unsigned char dsp_cmd[2];
517 
518 	dsp_cmd[0] = 0x0f;	/* CSP read register */
519 	dsp_cmd[1] = reg;	/* CSP Register */
520 	command_seq(chip, dsp_cmd, 2);
521 	return snd_sbdsp_get_byte(chip);	/* Read DSP value */
522 }
523 
524 /*
525  * set CSP mode register
526  */
527 static int set_mode_register(struct snd_sb *chip, unsigned char mode)
528 {
529 	unsigned char dsp_cmd[2];
530 
531 	dsp_cmd[0] = 0x04;	/* CSP set mode register */
532 	dsp_cmd[1] = mode;	/* mode */
533 	return command_seq(chip, dsp_cmd, 2);
534 }
535 
536 /*
537  * Detect CSP
538  * return 0 if CSP exists.
539  */
540 static int csp_detect(struct snd_sb *chip, int *version)
541 {
542 	unsigned char csp_test1, csp_test2;
543 
544 	guard(spinlock_irqsave)(&chip->reg_lock);
545 
546 	set_codec_parameter(chip, 0x00, 0x00);
547 	set_mode_register(chip, 0xfc);		/* 0xfc = ?? */
548 
549 	csp_test1 = read_register(chip, 0x83);
550 	set_register(chip, 0x83, ~csp_test1);
551 	csp_test2 = read_register(chip, 0x83);
552 	if (csp_test2 != (csp_test1 ^ 0xff))
553 		return -ENODEV;
554 
555 	set_register(chip, 0x83, csp_test1);
556 	csp_test2 = read_register(chip, 0x83);
557 	if (csp_test2 != csp_test1)
558 		return -ENODEV;
559 
560 	set_mode_register(chip, 0x00);		/* 0x00 = ? */
561 
562 	*version = get_version(chip);
563 	snd_sbdsp_reset(chip);	/* reset DSP after getversion! */
564 	if (*version >= 0x10 && *version <= 0x1f)
565 		return 0;		/* valid version id */
566 
567 	return -ENODEV;
568 }
569 
570 /*
571  * get CSP version number
572  */
573 static int get_version(struct snd_sb *chip)
574 {
575 	unsigned char dsp_cmd[2];
576 
577 	dsp_cmd[0] = 0x08;	/* SB_DSP_!something! */
578 	dsp_cmd[1] = 0x03;	/* get chip version id? */
579 	command_seq(chip, dsp_cmd, 2);
580 
581 	return (snd_sbdsp_get_byte(chip));
582 }
583 
584 /*
585  * check if the CSP version is valid
586  */
587 static int snd_sb_csp_check_version(struct snd_sb_csp * p)
588 {
589 	if (p->version < 0x10 || p->version > 0x1f) {
590 		dev_dbg(p->chip->card->dev,
591 			"%s: Invalid CSP version: 0x%x\n",
592 			__func__, p->version);
593 		return 1;
594 	}
595 	return 0;
596 }
597 
598 /*
599  * download microcode to CSP (microcode should have one "main" block).
600  */
601 static int snd_sb_csp_load(struct snd_sb_csp * p, const unsigned char *buf, int size, int load_flags)
602 {
603 	int status, i;
604 	int err;
605 
606 	guard(spinlock_irqsave)(&p->chip->reg_lock);
607 	snd_sbdsp_command(p->chip, 0x01);	/* CSP download command */
608 	if (snd_sbdsp_get_byte(p->chip)) {
609 		dev_dbg(p->chip->card->dev, "%s: Download command failed\n", __func__);
610 		return -EIO;
611 	}
612 	/* Send CSP low byte (size - 1) */
613 	snd_sbdsp_command(p->chip, (unsigned char)(size - 1));
614 	/* Send high byte */
615 	snd_sbdsp_command(p->chip, (unsigned char)((size - 1) >> 8));
616 	/* send microcode sequence */
617 	/* load from kernel space */
618 	while (size--) {
619 		if (!snd_sbdsp_command(p->chip, *buf++))
620 			return -EIO;
621 	}
622 	if (snd_sbdsp_get_byte(p->chip))
623 		return -EIO;
624 
625 	if (load_flags & SNDRV_SB_CSP_LOAD_INITBLOCK) {
626 		i = 0;
627 		/* some codecs (FastSpeech) take some time to initialize */
628 		while (1) {
629 			snd_sbdsp_command(p->chip, 0x03);
630 			status = snd_sbdsp_get_byte(p->chip);
631 			if (status == 0x55 || ++i >= 10)
632 				break;
633 			udelay (10);
634 		}
635 		if (status != 0x55) {
636 			dev_dbg(p->chip->card->dev,
637 				"%s: Microcode initialization failed\n",
638 				__func__);
639 			return -EIO;
640 		}
641 	} else {
642 		/*
643 		 * Read mixer register SB_DSP4_DMASETUP after loading 'main' code.
644 		 * Start CSP chip if no 16bit DMA channel is set - some kind
645 		 * of autorun or perhaps a bugfix?
646 		 */
647 		scoped_guard(spinlock, &p->chip->mixer_lock) {
648 			status = snd_sbmixer_read(p->chip, SB_DSP4_DMASETUP);
649 		}
650 		if (!(status & (SB_DMASETUP_DMA7 | SB_DMASETUP_DMA6 | SB_DMASETUP_DMA5))) {
651 			err = (set_codec_parameter(p->chip, 0xaa, 0x00) ||
652 			       set_codec_parameter(p->chip, 0xff, 0x00));
653 			snd_sbdsp_reset(p->chip);		/* really! */
654 			if (err)
655 				return -EIO;
656 			set_mode_register(p->chip, 0xc0);	/* c0 = STOP */
657 			set_mode_register(p->chip, 0x70);	/* 70 = RUN */
658 		}
659 	}
660 
661 	return 0;
662 }
663 
664 static int snd_sb_csp_load_user(struct snd_sb_csp * p, const unsigned char __user *buf, int size, int load_flags)
665 {
666 	int err;
667 	unsigned char *kbuf;
668 
669 	kbuf = memdup_user(buf, size);
670 	if (IS_ERR(kbuf))
671 		return PTR_ERR(kbuf);
672 
673 	err = snd_sb_csp_load(p, kbuf, size, load_flags);
674 
675 	kfree(kbuf);
676 	return err;
677 }
678 
679 static int snd_sb_csp_firmware_load(struct snd_sb_csp *p, int index, int flags)
680 {
681 	static const char *const names[] = {
682 		"sb16/mulaw_main.csp",
683 		"sb16/alaw_main.csp",
684 		"sb16/ima_adpcm_init.csp",
685 		"sb16/ima_adpcm_playback.csp",
686 		"sb16/ima_adpcm_capture.csp",
687 	};
688 	const struct firmware *program;
689 
690 	BUILD_BUG_ON(ARRAY_SIZE(names) != CSP_PROGRAM_COUNT);
691 	program = p->csp_programs[index];
692 	if (!program) {
693 		int err = request_firmware(&program, names[index],
694 				       p->chip->card->dev);
695 		if (err < 0)
696 			return err;
697 		p->csp_programs[index] = program;
698 	}
699 	return snd_sb_csp_load(p, program->data, program->size, flags);
700 }
701 
702 /*
703  * autoload hardware codec if necessary
704  * return 0 if CSP is loaded and ready to run (p->running != 0)
705  */
706 static int snd_sb_csp_autoload(struct snd_sb_csp * p, snd_pcm_format_t pcm_sfmt, int play_rec_mode)
707 {
708 	int err = 0;
709 
710 	/* if CSP is running or manually loaded then exit */
711 	if (p->running & (SNDRV_SB_CSP_ST_RUNNING | SNDRV_SB_CSP_ST_LOADED))
712 		return -EBUSY;
713 
714 	/* autoload microcode only if requested hardware codec is not already loaded */
715 	if (((1U << (__force int)pcm_sfmt) & p->acc_format) && (play_rec_mode & p->mode)) {
716 		p->running = SNDRV_SB_CSP_ST_AUTO;
717 	} else {
718 		switch (pcm_sfmt) {
719 		case SNDRV_PCM_FORMAT_MU_LAW:
720 			err = snd_sb_csp_firmware_load(p, CSP_PROGRAM_MULAW, 0);
721 			p->acc_format = SNDRV_PCM_FMTBIT_MU_LAW;
722 			p->mode = SNDRV_SB_CSP_MODE_DSP_READ | SNDRV_SB_CSP_MODE_DSP_WRITE;
723 			break;
724 		case SNDRV_PCM_FORMAT_A_LAW:
725 			err = snd_sb_csp_firmware_load(p, CSP_PROGRAM_ALAW, 0);
726 			p->acc_format = SNDRV_PCM_FMTBIT_A_LAW;
727 			p->mode = SNDRV_SB_CSP_MODE_DSP_READ | SNDRV_SB_CSP_MODE_DSP_WRITE;
728 			break;
729 		case SNDRV_PCM_FORMAT_IMA_ADPCM:
730 			err = snd_sb_csp_firmware_load(p, CSP_PROGRAM_ADPCM_INIT,
731 						       SNDRV_SB_CSP_LOAD_INITBLOCK);
732 			if (err)
733 				break;
734 			if (play_rec_mode == SNDRV_SB_CSP_MODE_DSP_WRITE) {
735 				err = snd_sb_csp_firmware_load
736 					(p, CSP_PROGRAM_ADPCM_PLAYBACK, 0);
737 				p->mode = SNDRV_SB_CSP_MODE_DSP_WRITE;
738 			} else {
739 				err = snd_sb_csp_firmware_load
740 					(p, CSP_PROGRAM_ADPCM_CAPTURE, 0);
741 				p->mode = SNDRV_SB_CSP_MODE_DSP_READ;
742 			}
743 			p->acc_format = SNDRV_PCM_FMTBIT_IMA_ADPCM;
744 			break;
745 		default:
746 			/* Decouple CSP from IRQ and DMAREQ lines */
747 			if (p->running & SNDRV_SB_CSP_ST_AUTO) {
748 				guard(spinlock_irqsave)(&p->chip->reg_lock);
749 				set_mode_register(p->chip, 0xfc);
750 				set_mode_register(p->chip, 0x00);
751 				p->running = 0;			/* clear autoloaded flag */
752 			}
753 			return -EINVAL;
754 		}
755 		if (err) {
756 			p->acc_format = 0;
757 			p->acc_channels = p->acc_width = p->acc_rates = 0;
758 
759 			p->running = 0;				/* clear autoloaded flag */
760 			p->mode = 0;
761 			return (err);
762 		} else {
763 			p->running = SNDRV_SB_CSP_ST_AUTO;	/* set autoloaded flag */
764 			p->acc_width = SNDRV_SB_CSP_SAMPLE_16BIT;	/* only 16 bit data */
765 			p->acc_channels = SNDRV_SB_CSP_MONO | SNDRV_SB_CSP_STEREO;
766 			p->acc_rates = SNDRV_SB_CSP_RATE_ALL;	/* HW codecs accept all rates */
767 		}
768 
769 	}
770 	return (p->running & SNDRV_SB_CSP_ST_AUTO) ? 0 : -ENXIO;
771 }
772 
773 /*
774  * start CSP
775  */
776 static int snd_sb_csp_start(struct snd_sb_csp * p, int sample_width, int channels)
777 {
778 	struct device *dev = p->chip->card->dev;
779 	unsigned char s_type;	/* sample type */
780 	unsigned char mixL, mixR;
781 	int result = -EIO;
782 
783 	if (!(p->running & (SNDRV_SB_CSP_ST_LOADED | SNDRV_SB_CSP_ST_AUTO))) {
784 		dev_dbg(dev, "%s: Microcode not loaded\n", __func__);
785 		return -ENXIO;
786 	}
787 	if (p->running & SNDRV_SB_CSP_ST_RUNNING) {
788 		dev_dbg(dev, "%s: CSP already running\n", __func__);
789 		return -EBUSY;
790 	}
791 	if (!(sample_width & p->acc_width)) {
792 		dev_dbg(dev, "%s: Unsupported PCM sample width\n", __func__);
793 		return -EINVAL;
794 	}
795 	if (!(channels & p->acc_channels)) {
796 		dev_dbg(dev, "%s: Invalid number of channels\n", __func__);
797 		return -EINVAL;
798 	}
799 
800 	/* Mute PCM volume */
801 	scoped_guard(spinlock_irqsave, &p->chip->mixer_lock) {
802 		mixL = snd_sbmixer_read(p->chip, SB_DSP4_PCM_DEV);
803 		mixR = snd_sbmixer_read(p->chip, SB_DSP4_PCM_DEV + 1);
804 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV, mixL & 0x7);
805 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV + 1, mixR & 0x7);
806 	}
807 
808 	scoped_guard(spinlock, &p->chip->reg_lock) {
809 		set_mode_register(p->chip, 0xc0);	/* c0 = STOP */
810 		set_mode_register(p->chip, 0x70);	/* 70 = RUN */
811 
812 		s_type = 0x00;
813 		if (channels == SNDRV_SB_CSP_MONO)
814 			s_type = 0x11;	/* 000n 000n    (n = 1 if mono) */
815 		if (sample_width == SNDRV_SB_CSP_SAMPLE_8BIT)
816 			s_type |= 0x22;	/* 00dX 00dX    (d = 1 if 8 bit samples) */
817 
818 		if (set_codec_parameter(p->chip, 0x81, s_type)) {
819 			dev_dbg(dev, "%s: Set sample type command failed\n", __func__);
820 			break;
821 		}
822 		if (set_codec_parameter(p->chip, 0x80, 0x00)) {
823 			dev_dbg(dev, "%s: Codec start command failed\n", __func__);
824 			break;
825 		}
826 		p->run_width = sample_width;
827 		p->run_channels = channels;
828 
829 		p->running |= SNDRV_SB_CSP_ST_RUNNING;
830 
831 		if (p->mode & SNDRV_SB_CSP_MODE_QSOUND) {
832 			set_codec_parameter(p->chip, 0xe0, 0x01);
833 			/* enable QSound decoder */
834 			set_codec_parameter(p->chip, 0x00, 0xff);
835 			set_codec_parameter(p->chip, 0x01, 0xff);
836 			p->running |= SNDRV_SB_CSP_ST_QSOUND;
837 			/* set QSound startup value */
838 			snd_sb_csp_qsound_transfer(p);
839 		}
840 		result = 0;
841 	}
842 
843 	/* restore PCM volume */
844 	if (result < 0) {
845 		guard(spinlock_irqsave)(&p->chip->mixer_lock);
846 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV, mixL);
847 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV + 1, mixR);
848 	}
849 
850 	return result;
851 }
852 
853 /*
854  * stop CSP
855  */
856 static int snd_sb_csp_stop(struct snd_sb_csp * p)
857 {
858 	int result;
859 	unsigned char mixL, mixR;
860 
861 	if (!(p->running & SNDRV_SB_CSP_ST_RUNNING))
862 		return 0;
863 
864 	/* Mute PCM volume */
865 	scoped_guard(spinlock_irqsave, &p->chip->mixer_lock) {
866 		mixL = snd_sbmixer_read(p->chip, SB_DSP4_PCM_DEV);
867 		mixR = snd_sbmixer_read(p->chip, SB_DSP4_PCM_DEV + 1);
868 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV, mixL & 0x7);
869 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV + 1, mixR & 0x7);
870 	}
871 
872 	scoped_guard(spinlock, &p->chip->reg_lock) {
873 		if (p->running & SNDRV_SB_CSP_ST_QSOUND) {
874 			set_codec_parameter(p->chip, 0xe0, 0x01);
875 			/* disable QSound decoder */
876 			set_codec_parameter(p->chip, 0x00, 0x00);
877 			set_codec_parameter(p->chip, 0x01, 0x00);
878 
879 			p->running &= ~SNDRV_SB_CSP_ST_QSOUND;
880 		}
881 		result = set_mode_register(p->chip, 0xc0);	/* c0 = STOP */
882 	}
883 
884 	/* restore PCM volume */
885 	scoped_guard(spinlock_irqsave, &p->chip->mixer_lock) {
886 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV, mixL);
887 		snd_sbmixer_write(p->chip, SB_DSP4_PCM_DEV + 1, mixR);
888 	}
889 
890 	if (!(result))
891 		p->running &= ~(SNDRV_SB_CSP_ST_PAUSED | SNDRV_SB_CSP_ST_RUNNING);
892 	return result;
893 }
894 
895 /*
896  * pause CSP codec and hold DMA transfer
897  */
898 static int snd_sb_csp_pause(struct snd_sb_csp * p)
899 {
900 	int result;
901 
902 	if (!(p->running & SNDRV_SB_CSP_ST_RUNNING))
903 		return -EBUSY;
904 
905 	scoped_guard(spinlock_irqsave, &p->chip->reg_lock) {
906 		result = set_codec_parameter(p->chip, 0x80, 0xff);
907 	}
908 	if (!(result))
909 		p->running |= SNDRV_SB_CSP_ST_PAUSED;
910 
911 	return result;
912 }
913 
914 /*
915  * restart CSP codec and resume DMA transfer
916  */
917 static int snd_sb_csp_restart(struct snd_sb_csp * p)
918 {
919 	int result;
920 
921 	if (!(p->running & SNDRV_SB_CSP_ST_PAUSED))
922 		return -EBUSY;
923 
924 	scoped_guard(spinlock_irqsave, &p->chip->reg_lock) {
925 		result = set_codec_parameter(p->chip, 0x80, 0x00);
926 	}
927 	if (!(result))
928 		p->running &= ~SNDRV_SB_CSP_ST_PAUSED;
929 
930 	return result;
931 }
932 
933 /* ------------------------------ */
934 
935 /*
936  * QSound mixer control for PCM
937  */
938 
939 #define snd_sb_qsound_switch_info	snd_ctl_boolean_mono_info
940 
941 static int snd_sb_qsound_switch_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
942 {
943 	struct snd_sb_csp *p = snd_kcontrol_chip(kcontrol);
944 
945 	ucontrol->value.integer.value[0] = p->q_enabled ? 1 : 0;
946 	return 0;
947 }
948 
949 static int snd_sb_qsound_switch_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
950 {
951 	struct snd_sb_csp *p = snd_kcontrol_chip(kcontrol);
952 	int change;
953 	unsigned char nval;
954 
955 	nval = ucontrol->value.integer.value[0] & 0x01;
956 	guard(spinlock_irqsave)(&p->q_lock);
957 	change = p->q_enabled != nval;
958 	p->q_enabled = nval;
959 	return change;
960 }
961 
962 static int snd_sb_qsound_space_info(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_info *uinfo)
963 {
964 	uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;
965 	uinfo->count = 2;
966 	uinfo->value.integer.min = 0;
967 	uinfo->value.integer.max = SNDRV_SB_CSP_QSOUND_MAX_RIGHT;
968 	return 0;
969 }
970 
971 static int snd_sb_qsound_space_get(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
972 {
973 	struct snd_sb_csp *p = snd_kcontrol_chip(kcontrol);
974 
975 	guard(spinlock_irqsave)(&p->q_lock);
976 	ucontrol->value.integer.value[0] = p->qpos_left;
977 	ucontrol->value.integer.value[1] = p->qpos_right;
978 	return 0;
979 }
980 
981 static int snd_sb_qsound_space_put(struct snd_kcontrol *kcontrol, struct snd_ctl_elem_value *ucontrol)
982 {
983 	struct snd_sb_csp *p = snd_kcontrol_chip(kcontrol);
984 	int change;
985 	unsigned char nval1, nval2;
986 
987 	nval1 = ucontrol->value.integer.value[0];
988 	if (nval1 > SNDRV_SB_CSP_QSOUND_MAX_RIGHT)
989 		nval1 = SNDRV_SB_CSP_QSOUND_MAX_RIGHT;
990 	nval2 = ucontrol->value.integer.value[1];
991 	if (nval2 > SNDRV_SB_CSP_QSOUND_MAX_RIGHT)
992 		nval2 = SNDRV_SB_CSP_QSOUND_MAX_RIGHT;
993 	guard(spinlock_irqsave)(&p->q_lock);
994 	change = p->qpos_left != nval1 || p->qpos_right != nval2;
995 	p->qpos_left = nval1;
996 	p->qpos_right = nval2;
997 	p->qpos_changed = change;
998 	return change;
999 }
1000 
1001 static const struct snd_kcontrol_new snd_sb_qsound_switch = {
1002 	.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1003 	.name = "3D Control - Switch",
1004 	.info = snd_sb_qsound_switch_info,
1005 	.get = snd_sb_qsound_switch_get,
1006 	.put = snd_sb_qsound_switch_put
1007 };
1008 
1009 static const struct snd_kcontrol_new snd_sb_qsound_space = {
1010 	.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
1011 	.name = "3D Control - Space",
1012 	.info = snd_sb_qsound_space_info,
1013 	.get = snd_sb_qsound_space_get,
1014 	.put = snd_sb_qsound_space_put
1015 };
1016 
1017 static int snd_sb_qsound_build(struct snd_sb_csp * p)
1018 {
1019 	struct snd_card *card;
1020 	struct snd_kcontrol *kctl;
1021 	int err;
1022 
1023 	if (snd_BUG_ON(!p))
1024 		return -EINVAL;
1025 
1026 	card = p->chip->card;
1027 	p->qpos_left = p->qpos_right = SNDRV_SB_CSP_QSOUND_MAX_RIGHT / 2;
1028 	p->qpos_changed = 0;
1029 
1030 	spin_lock_init(&p->q_lock);
1031 
1032 	kctl = snd_ctl_new1(&snd_sb_qsound_switch, p);
1033 	err = snd_ctl_add(card, kctl);
1034 	if (err < 0)
1035 		goto __error;
1036 	p->qsound_switch = kctl;
1037 	kctl = snd_ctl_new1(&snd_sb_qsound_space, p);
1038 	err = snd_ctl_add(card, kctl);
1039 	if (err < 0)
1040 		goto __error;
1041 	p->qsound_space = kctl;
1042 
1043 	return 0;
1044 
1045      __error:
1046 	snd_sb_qsound_destroy(p);
1047 	return err;
1048 }
1049 
1050 static void snd_sb_qsound_destroy(struct snd_sb_csp * p)
1051 {
1052 	struct snd_card *card;
1053 
1054 	if (snd_BUG_ON(!p))
1055 		return;
1056 
1057 	card = p->chip->card;
1058 
1059 	snd_ctl_remove(card, p->qsound_switch);
1060 	p->qsound_switch = NULL;
1061 	snd_ctl_remove(card, p->qsound_space);
1062 	p->qsound_space = NULL;
1063 
1064 	/* cancel pending transfer of QSound parameters */
1065 	guard(spinlock_irqsave)(&p->q_lock);
1066 	p->qpos_changed = 0;
1067 }
1068 
1069 /*
1070  * Transfer qsound parameters to CSP,
1071  * function should be called from interrupt routine
1072  */
1073 static int snd_sb_csp_qsound_transfer(struct snd_sb_csp * p)
1074 {
1075 	int err = -ENXIO;
1076 
1077 	guard(spinlock)(&p->q_lock);
1078 	if (p->running & SNDRV_SB_CSP_ST_QSOUND) {
1079 		set_codec_parameter(p->chip, 0xe0, 0x01);
1080 		/* left channel */
1081 		set_codec_parameter(p->chip, 0x00, p->qpos_left);
1082 		set_codec_parameter(p->chip, 0x02, 0x00);
1083 		/* right channel */
1084 		set_codec_parameter(p->chip, 0x00, p->qpos_right);
1085 		set_codec_parameter(p->chip, 0x03, 0x00);
1086 		err = 0;
1087 	}
1088 	p->qpos_changed = 0;
1089 	return err;
1090 }
1091 
1092 /* ------------------------------ */
1093 
1094 /*
1095  * proc interface
1096  */
1097 static int init_proc_entry(struct snd_sb_csp * p, int device)
1098 {
1099 	char name[16];
1100 
1101 	sprintf(name, "cspD%d", device);
1102 	snd_card_ro_proc_new(p->chip->card, name, p, info_read);
1103 	return 0;
1104 }
1105 
1106 static void info_read(struct snd_info_entry *entry, struct snd_info_buffer *buffer)
1107 {
1108 	struct snd_sb_csp *p = entry->private_data;
1109 
1110 	snd_iprintf(buffer, "Creative Signal Processor [v%d.%d]\n", (p->version >> 4), (p->version & 0x0f));
1111 	snd_iprintf(buffer, "State: %cx%c%c%c\n", ((p->running & SNDRV_SB_CSP_ST_QSOUND) ? 'Q' : '-'),
1112 		    ((p->running & SNDRV_SB_CSP_ST_PAUSED) ? 'P' : '-'),
1113 		    ((p->running & SNDRV_SB_CSP_ST_RUNNING) ? 'R' : '-'),
1114 		    ((p->running & SNDRV_SB_CSP_ST_LOADED) ? 'L' : '-'));
1115 	if (p->running & SNDRV_SB_CSP_ST_LOADED) {
1116 		snd_iprintf(buffer, "Codec: %s [func #%d]\n", p->codec_name, p->func_nr);
1117 		snd_iprintf(buffer, "Sample rates: ");
1118 		if (p->acc_rates == SNDRV_SB_CSP_RATE_ALL) {
1119 			snd_iprintf(buffer, "All\n");
1120 		} else {
1121 			snd_iprintf(buffer, "%s%s%s%s\n",
1122 				    ((p->acc_rates & SNDRV_SB_CSP_RATE_8000) ? "8000Hz " : ""),
1123 				    ((p->acc_rates & SNDRV_SB_CSP_RATE_11025) ? "11025Hz " : ""),
1124 				    ((p->acc_rates & SNDRV_SB_CSP_RATE_22050) ? "22050Hz " : ""),
1125 				    ((p->acc_rates & SNDRV_SB_CSP_RATE_44100) ? "44100Hz" : ""));
1126 		}
1127 		if (p->mode == SNDRV_SB_CSP_MODE_QSOUND) {
1128 			snd_iprintf(buffer, "QSound decoder %s\n",
1129 				    str_enabled_disabled(p->q_enabled));
1130 		} else {
1131 			snd_iprintf(buffer, "PCM format ID: 0x%x (%s/%s) [%s/%s] [%s/%s]\n",
1132 				    p->acc_format,
1133 				    ((p->acc_width & SNDRV_SB_CSP_SAMPLE_16BIT) ? "16bit" : "-"),
1134 				    ((p->acc_width & SNDRV_SB_CSP_SAMPLE_8BIT) ? "8bit" : "-"),
1135 				    ((p->acc_channels & SNDRV_SB_CSP_MONO) ? "mono" : "-"),
1136 				    ((p->acc_channels & SNDRV_SB_CSP_STEREO) ? "stereo" : "-"),
1137 				    ((p->mode & SNDRV_SB_CSP_MODE_DSP_WRITE) ? "playback" : "-"),
1138 				    ((p->mode & SNDRV_SB_CSP_MODE_DSP_READ) ? "capture" : "-"));
1139 		}
1140 	}
1141 	if (p->running & SNDRV_SB_CSP_ST_AUTO) {
1142 		snd_iprintf(buffer, "Autoloaded Mu-Law, A-Law or Ima-ADPCM hardware codec\n");
1143 	}
1144 	if (p->running & SNDRV_SB_CSP_ST_RUNNING) {
1145 		snd_iprintf(buffer, "Processing %dbit %s PCM samples\n",
1146 			    ((p->run_width & SNDRV_SB_CSP_SAMPLE_16BIT) ? 16 : 8),
1147 			    ((p->run_channels & SNDRV_SB_CSP_MONO) ? "mono" : "stereo"));
1148 	}
1149 	if (p->running & SNDRV_SB_CSP_ST_QSOUND) {
1150 		snd_iprintf(buffer, "Qsound position: left = 0x%x, right = 0x%x\n",
1151 			    p->qpos_left, p->qpos_right);
1152 	}
1153 }
1154 
1155 /* */
1156 
1157 EXPORT_SYMBOL(snd_sb_csp_new);
1158