| Kernel v2.4.21-pre5-ac3 /forte-1.55-1.63.diff |
|---|
| Filename: | /forte-1.55-1.63.diff |
| Lines Added: | 683 |
| Lines Deleted: | 0 |
| Also changed in: |
(Previous) (Following) |
 2.4.21-pre5-ac3
 forte-1.55-1.63.diff
diff -u --new-file --recursive --exclude-from /usr/src/exclude linux.21pre5/forte-1.55-1.63.diff linux.21pre5-ac3/forte-1.55-1.63.di+
ff
--- linux.21pre5/forte-1.55-1.63.diff 1970-01-01 01:00:00.000000000 +0100
+++ linux.21pre5-ac3/forte-1.55-1.63.diff 2003-03-01 05:33:26.000000000 +0000
@@ -0,0 +1,683 @@
+Index: forte.c
+===================================================================
+RCS file: /home/mkp/Repository/forte/forte.c,v
+retrieving revision 1.55
+retrieving revision 1.63
+diff -u -u -r1.55 -r1.63
+--- forte.c 2 Oct 2002 00:01:42 -0000 1.55
++++ forte.c 1 Mar 2003 05:32:42 -0000 1.63
+@@ -3,6 +3,9 @@
+ *
+ * Written by Martin K. Petersen <mkp@mkp.net>
+ * Copyright (C) 2002 Hewlett-Packard Company
++ * Portions Copyright (C) 2003 Martin K. Petersen
++ *
++ * Latest version: http://mkp.net/forte/
+ *
+ * Based upon the ALSA FM801 driver by Jaroslav Kysela and OSS drivers
+ * by Thomas Sailer, Alan Cox, Zach Brown, and Jeff Garzik. Thanks
+@@ -24,15 +27,6 @@
+ *
+ */
+
+-/*
+- * TODO:
+- * MMIO
+- * Multichannelize
+- * Multichipify
+- * MPU401
+- * M^Gameport
+- */
+-
+ #include <linux/config.h>
+ #include <linux/module.h>
+ #include <linux/kernel.h>
+@@ -55,7 +49,7 @@
+ #include <asm/hardirq.h>
+
+ #define DRIVER_NAME "forte"
+-#define DRIVER_VERSION "$Id: forte.c,v 1.55 2002/10/02 00:01:42 mkp Exp $"
++#define DRIVER_VERSION "$Id: forte.c,v 1.63 2003/03/01 05:32:42 mkp Exp $"
+ #define PFX DRIVER_NAME ": "
+
+ #undef M_DEBUG
+@@ -76,10 +70,11 @@
+ #define FORTE_MIN_FRAG_SIZE 256
+ #define FORTE_MAX_FRAG_SIZE PAGE_SIZE
+ #define FORTE_DEF_FRAG_SIZE 256
+-#define FORTE_MIN_FRAGMENTS 16
++#define FORTE_MIN_FRAGMENTS 2
+ #define FORTE_MAX_FRAGMENTS 256
+-#define FORTE_DEF_FRAGMENTS 16
+-#define FORTE_MIN_BUF 16386
++#define FORTE_DEF_FRAGMENTS 2
++#define FORTE_MIN_BUF_MSECS 500
++#define FORTE_MAX_BUF_MSECS 1000
+
+ /* PCI BARs */
+ #define FORTE_PCM_VOL 0x00 /* PCM Output Volume */
+@@ -168,6 +163,7 @@
+
+ unsigned int frag_sz; /* Current fragment size */
+ unsigned int frag_num; /* Current # of fragments */
++ unsigned int frag_msecs; /* Milliseconds per frag */
+ unsigned int buf_sz; /* Current buffer size */
+
+ unsigned int hwptr; /* Tail */
+@@ -175,14 +171,13 @@
+ unsigned int filled_frags; /* Fragments currently full */
+ unsigned int next_buf; /* Index of next buffer */
+
+- unsigned int blocked; /* Blocked on I/O */
+- unsigned int drain; /* Drain queued buffers */
+ unsigned int active; /* Channel currently in use */
+ unsigned int mapped; /* mmap */
+
+ unsigned int buf_pages; /* Real size of buffer */
+ unsigned int nr_irqs; /* Number of interrupts */
+ unsigned int bytes; /* Total bytes */
++ unsigned int residue; /* Partial fragment */
+ };
+
+
+@@ -404,12 +399,11 @@
+ channel->next_buf = 1;
+ channel->swptr = 0;
+ channel->filled_frags = 0;
+- channel->blocked = 0;
+- channel->drain = 0;
+ channel->active = 0;
+ channel->bytes = 0;
+ channel->nr_irqs = 0;
+ channel->mapped = 0;
++ channel->residue = 0;
+ }
+
+
+@@ -423,12 +417,11 @@
+ static void inline
+ forte_channel_start (struct forte_channel *channel)
+ {
+- if (!channel || !channel->iobase)
++ if (!channel || !channel->iobase || channel->active)
+ return;
+
+- DPRINTK ("%s: channel = %s\n", __FUNCTION__, channel->name);
+-
+- channel->ctrl &= ~(FORTE_PAUSE | FORTE_BUF1_LAST | FORTE_BUF2_LAST);
++ channel->ctrl &= ~(FORTE_PAUSE | FORTE_BUF1_LAST | FORTE_BUF2_LAST
++ | FORTE_IMMED_STOP);
+ channel->ctrl |= FORTE_START;
+ channel->active = 1;
+ outw (channel->ctrl, channel->iobase + FORTE_PLY_CTRL);
+@@ -448,9 +441,29 @@
+ if (!channel || !channel->iobase)
+ return;
+
+- DPRINTK ("%s: channel = %s\n", __FUNCTION__, channel->name);
++ channel->ctrl &= ~(FORTE_START | FORTE_PAUSE);
++ channel->ctrl |= FORTE_IMMED_STOP;
++
++ channel->active = 0;
++ outw (channel->ctrl, channel->iobase + FORTE_PLY_CTRL);
++}
++
++
++/**
++ * forte_channel_pause:
++ * @channel: Channel to pause
++ *
++ * Locking: Must be called with lock held.
++ */
++
++static void inline
++forte_channel_pause (struct forte_channel *channel)
++{
++ if (!channel || !channel->iobase)
++ return;
++
++ channel->ctrl |= FORTE_PAUSE;
+
+- channel->ctrl &= ~FORTE_START;
+ channel->active = 0;
+ outw (channel->ctrl, channel->iobase + FORTE_PLY_CTRL);
+ }
+@@ -584,38 +597,61 @@
+ * @channel: Channel whose buffer to set up
+ *
+ * Locking: Must be called with lock held.
+- *
+- * FIXME: Buffer scaling dependent on rate/channels/bits
+ */
+
+ static void
+ forte_channel_buffer (struct forte_channel *channel, int sz, int num)
+ {
++ unsigned int msecs, shift;
++
+ /* Go away, I'm busy */
+ if (channel->filled_frags || channel->bytes)
+ return;
+
+- channel->frag_sz = sz;
+- channel->frag_num = num;
++ /* Fragment size must be a power of 2 */
++ shift = 0; sz++;
++ while (sz >>= 1)
++ shift++;
++ channel->frag_sz = 1 << shift;
+
++ /* Round fragment size to something reasonable */
+ if (channel->frag_sz < FORTE_MIN_FRAG_SIZE)
+ channel->frag_sz = FORTE_MIN_FRAG_SIZE;
+
+ if (channel->frag_sz > FORTE_MAX_FRAG_SIZE)
+ channel->frag_sz = FORTE_MAX_FRAG_SIZE;
+
++ /* Find fragment length in milliseconds */
++ msecs = channel->frag_sz /
++ (channel->format == AFMT_S16_LE ? 2 : 1) /
++ (channel->stereo ? 2 : 1) /
++ (channel->rate / 1000);
++
++ channel->frag_msecs = msecs;
++
++ /* Pick a suitable number of fragments */
++ if (msecs * num < FORTE_MIN_BUF_MSECS)
++ num = FORTE_MIN_BUF_MSECS / msecs;
++
++ if (msecs * num > FORTE_MAX_BUF_MSECS)
++ num = FORTE_MAX_BUF_MSECS / msecs;
++
++ /* Fragment number must be a power of 2 */
++ shift = 0;
++ while (num >>= 1)
++ shift++;
++ channel->frag_num = 1 << (shift + 1);
++
++ /* Round fragment number to something reasonable */
+ if (channel->frag_num < FORTE_MIN_FRAGMENTS)
+ channel->frag_num = FORTE_MIN_FRAGMENTS;
+
+ if (channel->frag_num > FORTE_MAX_FRAGMENTS)
+ channel->frag_num = FORTE_MAX_FRAGMENTS;
+
+- if (channel->frag_sz * channel->frag_num < FORTE_MIN_BUF)
+- channel->frag_num = FORTE_MIN_BUF / channel->frag_sz;
+-
+ channel->buf_sz = channel->frag_sz * channel->frag_num;
+
+- DPRINTK ("%s: %s frag_sz = %d, frag_num = %d, buf_sz = %d\n",
++ DPRINTK ("%s: %s frag_sz = %d, frag_num = %d, buf_sz = %d\n",
+ __FUNCTION__, channel->name, channel->frag_sz,
+ channel->frag_num, channel->buf_sz);
+ }
+@@ -637,6 +673,7 @@
+ if (channel->buf)
+ return;
+
++ forte_channel_buffer (channel, channel->frag_sz, channel->frag_num);
+ channel->buf_pages = channel->buf_sz >> PAGE_SHIFT;
+
+ if (channel->buf_sz % PAGE_SIZE)
+@@ -688,8 +725,7 @@
+ DECLARE_WAITQUEUE (wait, current);
+ unsigned long flags;
+
+- if (!channel->active)
+- return 0;
++ DPRINTK ("%s\n", __FUNCTION__);
+
+ if (channel->mapped) {
+ spin_lock_irqsave (&forte->lock, flags);
+@@ -698,24 +734,26 @@
+ return 0;
+ }
+
+- channel->drain = 1;
++ spin_lock_irqsave (&forte->lock, flags);
+ add_wait_queue (&channel->wait, &wait);
+
+ for (;;) {
+- spin_lock_irqsave (&forte->lock, flags);
+-
+- if (channel->active == 0 || channel->filled_frags < 1)
++ if (channel->active == 0 || channel->filled_frags == 1)
+ break;
+
+ spin_unlock_irqrestore (&forte->lock, flags);
++
+ __set_current_state (TASK_INTERRUPTIBLE);
+ schedule();
++
++ spin_lock_irqsave (&forte->lock, flags);
+ }
+
+- channel->drain = 0;
+- spin_unlock_irqrestore (&forte->lock, flags);
++ forte_channel_stop (channel);
++ forte_channel_reset (channel);
+ set_current_state (TASK_RUNNING);
+ remove_wait_queue (&channel->wait, &wait);
++ spin_unlock_irqrestore (&forte->lock, flags);
+
+ return 0;
+ }
+@@ -765,8 +803,8 @@
+ forte_channel_stereo (channel, 1);
+ forte_channel_format (channel, AFMT_S16_LE);
+ forte_channel_rate (channel, 48000);
+- forte_channel_buffer (channel, FORTE_DEF_FRAG_SIZE,
+- FORTE_DEF_FRAGMENTS);
++ channel->frag_sz = FORTE_DEF_FRAG_SIZE;
++ channel->frag_num = FORTE_DEF_FRAGMENTS;
+
+ chip->trigger = 0;
+ spin_unlock_irq (&chip->lock);
+@@ -967,12 +1005,8 @@
+ case SNDCTL_DSP_SYNC:
+ DPRINTK ("%s: SYNC\n", __FUNCTION__);
+
+- if (wr) {
++ if (wr)
+ ret = forte_channel_drain (&chip->play);
+- spin_lock_irq (&chip->lock);
+- forte_channel_reset (&chip->play);
+- spin_unlock_irq (&chip->lock);
+- }
+
+ return 0;
+
+@@ -981,7 +1015,10 @@
+
+ if (wr) {
+ spin_lock_irq (&chip->lock);
+- forte_channel_reset (&chip->play);
++
++ if (chip->play.filled_frags)
++ forte_channel_start (&chip->play);
++
+ spin_unlock_irq (&chip->lock);
+ }
+
+@@ -1059,7 +1096,7 @@
+ case SNDCTL_DSP_GETOSPACE:
+ if (!wr)
+ return -EINVAL;
+-
++
+ spin_lock_irq (&chip->lock);
+
+ abi.fragstotal = chip->play.frag_num;
+@@ -1072,7 +1109,12 @@
+ else {
+ abi.fragments = chip->play.frag_num -
+ chip->play.filled_frags;
+- abi.bytes = abi.fragments * abi.fragsize;
++
++ if (chip->play.residue)
++ abi.fragments--;
++
++ abi.bytes = abi.fragments * abi.fragsize +
++ chip->play.residue;
+ }
+
+ spin_unlock_irq (&chip->lock);
+@@ -1099,20 +1141,23 @@
+ return copy_to_user ((void *) arg, &cinfo, sizeof (cinfo));
+
+ case SNDCTL_DSP_GETODELAY:
+- if (!chip->play.active)
+- return 0;
+-
+ if (!wr)
+ return -EINVAL;
+
+ spin_lock_irq (&chip->lock);
+
+- if (chip->play.mapped) {
++ if (!chip->play.active) {
++ ival = 0;
++ }
++ else if (chip->play.mapped) {
+ count = inw (chip->play.iobase + FORTE_PLY_COUNT) + 1;
+ ival = chip->play.frag_sz - count;
+ }
+ else {
+ ival = chip->play.filled_frags * chip->play.frag_sz;
++
++ if (chip->play.residue)
++ ival += chip->play.frag_sz - chip->play.residue;
+ }
+
+ spin_unlock_irq (&chip->lock);
+@@ -1170,13 +1215,18 @@
+ return put_user (chip->play.rate, (int *) arg);
+
+ case SOUND_PCM_READ_CHANNELS:
+- DPRINTK ("%s: PCM_READ_CHANNELS\n", __FUNCTION__);
++ DPRINTK ("%s: PCM_READ_CHANNELS\n", __FUNCTION__);
+ return put_user (chip->play.stereo, (int *) arg);
+
+ case SOUND_PCM_READ_BITS:
+ DPRINTK ("%s: PCM_READ_BITS\n", __FUNCTION__);
+ return put_user (chip->play.format, (int *) arg);
+
++ case SNDCTL_DSP_NONBLOCK:
++ DPRINTK ("%s: DSP_NONBLOCK\n", __FUNCTION__);
++ file->f_flags |= O_NONBLOCK;
++ return 0;
++
+ default:
+ DPRINTK ("Unsupported ioctl: %x (%p)\n", cmd, (void *) arg);
+ break;
+@@ -1195,14 +1245,22 @@
+ {
+ struct forte_chip *chip = forte; /* FIXME: HACK FROM HELL! */
+
+- if (down_interruptible (&chip->open_sem)) {
+- DPRINTK ("%s: returning -ERESTARTSYS\n", __FUNCTION__);
+- return -ERESTARTSYS;
++ if (file->f_flags & O_NONBLOCK) {
++ if (down_trylock (&chip->open_sem)) {
++ DPRINTK ("%s: returning -EAGAIN\n", __FUNCTION__);
++ return -EAGAIN;
++ }
++ }
++ else {
++ if (down_interruptible (&chip->open_sem)) {
++ DPRINTK ("%s: returning -ERESTARTSYS\n", __FUNCTION__);
++ return -ERESTARTSYS;
++ }
+ }
+
+ file->private_data = forte;
+
+- DPRINTK ("%s: chip @ %p\n", __FUNCTION__, file->private_data);
++ DPRINTK ("%s: dsp opened by %d\n", __FUNCTION__, current->pid);
+
+ if (file->f_mode & FMODE_WRITE)
+ forte_channel_init (forte, &forte->play);
+@@ -1231,9 +1289,7 @@
+
+ spin_lock_irq (&chip->lock);
+
+- chip->play.ctrl |= FORTE_IMMED_STOP;
+- forte_channel_stop (&chip->play);
+- forte_channel_free (chip, &chip->play);
++ forte_channel_free (chip, &chip->play);
+
+ spin_unlock_irq (&chip->lock);
+ }
+@@ -1244,7 +1300,6 @@
+
+ spin_lock_irq (&chip->lock);
+
+- chip->play.ctrl |= FORTE_IMMED_STOP;
+ forte_channel_stop (&chip->rec);
+ forte_channel_free (chip, &chip->rec);
+
+@@ -1260,7 +1315,6 @@
+ /**
+ * forte_dsp_poll:
+ *
+- * FIXME: Racy
+ */
+
+ static unsigned int
+@@ -1278,8 +1332,12 @@
+ if (channel->active)
+ poll_wait (file, &channel->wait, wait);
+
+- if (channel->filled_frags)
++ spin_lock_irq (&chip->lock);
++
++ if (channel->frag_num - channel->filled_frags > 0)
+ mask |= POLLOUT | POLLWRNORM;
++
++ spin_unlock_irq (&chip->lock);
+ }
+
+ if (file->f_mode & FMODE_READ) {
+@@ -1288,8 +1346,12 @@
+ if (channel->active)
+ poll_wait (file, &channel->wait, wait);
+
++ spin_lock_irq (&chip->lock);
++
+ if (channel->filled_frags > 0)
+ mask |= POLLIN | POLLRDNORM;
++
++ spin_unlock_irq (&chip->lock);
+ }
+
+ return mask;
+@@ -1405,62 +1467,64 @@
+ if (channel->frag_num - channel->filled_frags == 0) {
+ DECLARE_WAITQUEUE (wait, current);
+
+- /* For trigger mode operation, get out */
+- if (chip->trigger) {
++ /* For trigger or non-blocking operation, get out */
++ if (chip->trigger || file->f_flags & O_NONBLOCK) {
+ spin_unlock_irqrestore (&chip->lock, flags);
+ return -EAGAIN;
+ }
+
+ /* Otherwise wait for buffers */
+- channel->blocked = 1;
+ add_wait_queue (&channel->wait, &wait);
+
+ for (;;) {
+- if (channel->active == 0)
+- break;
+-
+- if (channel->frag_num - channel->filled_frags)
+- break;
+-
+ spin_unlock_irqrestore (&chip->lock, flags);
+
+ set_current_state (TASK_INTERRUPTIBLE);
+- schedule();
++ schedule();
+
+ spin_lock_irqsave (&chip->lock, flags);
++
++ if (channel->frag_num - channel->filled_frags)
++ break;
+ }
+
+- set_current_state (TASK_RUNNING);
+ remove_wait_queue (&channel->wait, &wait);
+- channel->blocked = 0;
++ set_current_state (TASK_RUNNING);
++
++ if (signal_pending (current)) {
++ spin_unlock_irqrestore (&chip->lock, flags);
++ return -ERESTARTSYS;
++ }
+ }
+
+- if (i > channel->frag_sz)
++ if (channel->residue)
++ sz = channel->residue;
++ else if (i > channel->frag_sz)
+ sz = channel->frag_sz;
+ else
+ sz = i;
+
+ spin_unlock_irqrestore (&chip->lock, flags);
+
+- /* Clear the fragment so we don't get noise when copying
+- * smaller buffers
+- */
+- memset ((void *) channel->buf + channel->swptr, 0x0, sz);
+-
+- if (copy_from_user ((void *) channel->buf + channel->swptr,
+- buffer, sz)) {
++ if (copy_from_user ((void *) channel->buf + channel->swptr, buffer, sz))
+ return -EFAULT;
+- }
+
+ spin_lock_irqsave (&chip->lock, flags);
+
+ /* Advance software pointer */
+ buffer += sz;
+- channel->filled_frags++;
+- channel->swptr += channel->frag_sz;
++ channel->swptr += sz;
+ channel->swptr %= channel->buf_sz;
+ i -= sz;
+
++ /* Only bump filled_frags if a full fragment has been written */
++ if (channel->swptr % channel->frag_sz == 0) {
++ channel->filled_frags++;
++ channel->residue = 0;
++ }
++ else
++ channel->residue = channel->frag_sz - sz;
++
+ /* If playback isn't active, start it */
+ if (channel->active == 0 && chip->trigger == 0)
+ forte_channel_start (channel);
+@@ -1521,7 +1585,6 @@
+ return -EAGAIN;
+ }
+
+- channel->blocked = 1;
+ add_wait_queue (&channel->wait, &wait);
+
+ for (;;) {
+@@ -1541,7 +1604,6 @@
+
+ set_current_state (TASK_RUNNING);
+ remove_wait_queue (&channel->wait, &wait);
+- channel->blocked = 0;
+ }
+
+ if (i > channel->frag_sz)
+@@ -1560,7 +1622,8 @@
+
+ /* Advance software pointer */
+ buffer += sz;
+- channel->filled_frags--;
++ if (channel->filled_frags > 0)
++ channel->filled_frags--;
+ channel->swptr += channel->frag_sz;
+ channel->swptr %= channel->buf_sz;
+ i -= sz;
+@@ -1607,23 +1670,16 @@
+
+ if (status & FORTE_IRQ_PLAYBACK) {
+ channel = &chip->play;
+- spin_lock (&chip->lock);
+-
+- /* Declare a fragment done */
+- channel->filled_frags--;
+
+- /* Get # of completed bytes */
+- count = inw (channel->iobase + FORTE_PLY_COUNT) + 1;
+- channel->bytes += count;
++ spin_lock (&chip->lock);
+
+- if (count == 0) {
+- DPRINTK ("%s: last, filled_frags = %d\n", __FUNCTION__,
+- channel->filled_frags);
+- channel->filled_frags = 0;
+- forte_channel_stop (channel);
++ if (channel->frag_sz == 0)
+ goto pack;
+- }
+
++ /* Declare a fragment done */
++ if (channel->filled_frags > 0)
++ channel->filled_frags--;
++ channel->bytes += channel->frag_sz;
+ channel->nr_irqs++;
+
+ /* Flip-flop between buffer I and II */
+@@ -1639,17 +1695,18 @@
+ channel->iobase + FORTE_PLY_BUF1 :
+ channel->iobase + FORTE_PLY_BUF2);
+
+- /* If the currently playing fragment is last, schedule stop */
+- if (channel->filled_frags == 1)
+- forte_channel_stop (channel);
++ /* If the currently playing fragment is last, schedule pause */
++ if (channel->filled_frags == 1)
++ forte_channel_pause (channel);
++
+ pack:
+ /* Acknowledge interrupt */
+ outw (FORTE_IRQ_PLAYBACK, chip->iobase + FORTE_IRQ_STATUS);
+
+- spin_unlock (&chip->lock);
++ if (waitqueue_active (&channel->wait))
++ wake_up_all (&channel->wait);
+
+- if (channel->blocked || channel->drain)
+- wake_up_interruptible (&channel->wait);
++ spin_unlock (&chip->lock);
+ }
+
+ if (status & FORTE_IRQ_CAPTURE) {
+@@ -1668,7 +1725,7 @@
+ channel->filled_frags = 0;
+ goto rack;
+ }
+-
++
+ /* Buffer I or buffer II BAR */
+ outl (channel->buf_handle + channel->hwptr,
+ channel->next_buf == 0 ?
+@@ -1691,7 +1748,7 @@
+
+ spin_unlock (&chip->lock);
+
+- if (channel->blocked)
++ if (waitqueue_active (&channel->wait))
+ wake_up_all (&channel->wait);
+ }
+
+@@ -1710,7 +1767,7 @@
+ int i = 0, p_rate, p_chan, r_rate;
+ unsigned short p_reg, r_reg;
+
+- i += sprintf (page, "ForteMedia FM801 OSS Lite driver\n%s\n\n",
++ i += sprintf (page, "ForteMedia FM801 OSS Lite driver\n%s\n \n",
+ DRIVER_VERSION);
+
+ if (!forte->iobase)
+@@ -1745,7 +1802,14 @@
+ "Rate : %-5d %-5d\n"
+ "Channels : %-5d -\n"
+ "16-bit : %-3s %-3s\n"
+- "Stereo : %-3s %-3s\n",
++ "Stereo : %-3s %-3s\n"
++ " \n"
++ "Buffer Sz : %-6d %-6d\n"
++ "Frag Sz : %-6d %-6d\n"
++ "Frag Num : %-6d %-6d\n"
++ "Frag msecs : %-6d %-6d\n"
++ "Used Frags : %-6d %-6d\n"
++ "Mapped : %-3s %-3s\n",
+ p_reg & 1<<0 ? "yes" : "no",
+ r_reg & 1<<0 ? "yes" : "no",
+ p_reg & 1<<1 ? "yes" : "no",
+@@ -1763,7 +1827,15 @@
+ p_reg & 1<<14 ? "yes" : "no",
+ r_reg & 1<<14 ? "yes" : "no",
+ p_reg & 1<<15 ? "yes" : "no",
+- r_reg & 1<<15 ? "yes" : "no");
++ r_reg & 1<<15 ? "yes" : "no",
++ forte->play.buf_sz, forte->rec.buf_sz,
++ forte->play.frag_sz, forte->rec.frag_sz,
++ forte->play.frag_num, forte->rec.frag_num,
++ forte->play.frag_msecs, forte->rec.frag_msecs,
++ forte->play.filled_frags, forte->rec.filled_frags,
++ forte->play.mapped ? "yes" : "no",
++ forte->rec.mapped ? "yes" : "no"
++ );
+
+ return i;
+ }
|