Index: forte.c
===================================================================
RCS file: /home/mkp/Repository/forte/forte.c,v
retrieving revision 1.45
retrieving revision 1.51
diff -u -u -r1.45 -r1.51
--- forte.c	1 Aug 2002 22:34:09 -0000	1.45
+++ forte.c	26 Aug 2002 18:10:41 -0000	1.51
@@ -53,7 +53,7 @@
 #include <asm/hardirq.h>
 
 #define DRIVER_NAME	"forte"
-#define DRIVER_VERSION 	"$Id: forte.c,v 1.45 2002/08/01 22:34:09 mkp Exp $"
+#define DRIVER_VERSION 	"$Id: forte.c,v 1.51 2002/08/26 18:10:41 mkp Exp $"
 #define PFX 		DRIVER_NAME ": "
 
 #undef M_DEBUG
@@ -226,7 +226,7 @@
 
 	while ( (inw (chip->iobase + FORTE_AC97_CMD) & FORTE_AC97_PORT_BSY) 
 		&& i-- )
-		;
+		cpu_relax();
 
 	return i == 0;
 }
@@ -492,7 +492,7 @@
 	case 48000:	new_rate = 10; break;
 
 	default:
-		printk (KERN_ERR PFX "Unsupported rate: %d", rate);
+		DPRINTK ("Unsupported rate: %d", rate);
 		ret = -EINVAL;
 		goto out;
 	}
@@ -545,7 +545,7 @@
 		break;
 
 	default:
-		printk (KERN_ERR PFX "Unsupported audio format");
+		DPRINTK ("Unsupported audio format");
 		ret = -EINVAL;
 		break;
 	}
@@ -588,7 +588,7 @@
 		break;
 
 	default:
-		printk (KERN_ERR PFX "Unsupported channel format");
+		DPRINTK ("Unsupported channel format");
 		ret = -EINVAL;
 		break;
 	}
@@ -1167,12 +1167,24 @@
 
 			spin_unlock_irq (&chip->lock);
 		}
+		else if (rd) {
+			spin_lock_irq (&chip->lock);
+
+			if (ival & PCM_ENABLE_INPUT)
+				forte_channel_start (&chip->rec);
+			else {		
+				chip->trigger = 1;
+				forte_channel_prep (&chip->rec);
+				forte_channel_stop (&chip->rec);
+			}
+
+			spin_unlock_irq (&chip->lock);
+		}
 
 		return 0;
 		
 	default:
-		printk (KERN_ERR PFX "Unsupported ioctl: %x (%p)\n", cmd, 
-			(void *) arg);
+		DPRINTK ("Unsupported ioctl: %x (%p)\n", cmd, (void *) arg);
 		break;
 	}
 
@@ -1366,7 +1378,7 @@
 {
 	struct forte_chip *chip;
 	struct forte_channel *channel;
-	unsigned int i = bytes, ret = 0, sz = 0;
+	unsigned int i = bytes, sz = 0;
 	unsigned long flags;
 
 	if (ppos != &file->f_pos)
@@ -1397,8 +1409,8 @@
 
 			/* For trigger mode operation, get out */
 			if (chip->trigger) {
-				ret = -EAGAIN;
-				goto out;
+				spin_unlock_irqrestore (&chip->lock, flags);
+				return -EAGAIN;
 			}
 
 			/* Otherwise wait for buffers */
@@ -1430,6 +1442,8 @@
 		else
 			sz = i;
 
+		spin_unlock_irqrestore (&chip->lock, flags);
+
 		/* Clear the fragment so we don't get noise when copying
 		 * smaller buffers
 		 */
@@ -1437,10 +1451,11 @@
 
 		if (copy_from_user ((void *) channel->buf + channel->swptr, 
 				    buffer, sz)) {
-			ret = -EFAULT;
-			goto out;
+			return -EFAULT;
 		}
 
+		spin_lock_irqsave (&chip->lock, flags);
+
 		/* Advance software pointer */
 		buffer += sz;
 		channel->filled_frags++;
@@ -1453,11 +1468,9 @@
 			forte_channel_start (channel);
 	}
 
-	ret = bytes - i;
-
- out:
 	spin_unlock_irqrestore (&chip->lock, flags);
-	return ret;
+
+	return bytes - i;
 }
 
 
@@ -1496,15 +1509,20 @@
 	forte_channel_prep (channel);
 
 	/* Start recording */
-	forte_channel_start (channel);
+	if (!chip->trigger)
+		forte_channel_start (channel);
 
 	while (i) {
-		DPRINTK ("%s: i = %d\n", __FUNCTION__, i);
-
 		/* No fragment buffers in use -> wait */
 		if (channel->filled_frags == 0) {
 			DECLARE_WAITQUEUE (wait, current);
 
+			/* For trigger mode operation, get out */
+			if (chip->trigger) {
+				spin_unlock_irqrestore (&chip->lock, flags);
+				return -EAGAIN;
+			}
+
 			channel->blocked = 1;
 			add_wait_queue (&channel->wait, &wait);
 
@@ -1533,35 +1551,33 @@
 		else
 			sz = i;
 
+		spin_unlock_irqrestore (&chip->lock, flags);
+
 		if (copy_to_user (buffer, (void *)channel->buf+channel->swptr, sz)) {
-			ret = -EFAULT;
 			DPRINTK ("%s: copy_to_user failed\n", __FUNCTION__);
-			goto out;
+			return -EFAULT;
 		}
 
+		spin_lock_irqsave (&chip->lock, flags);
+
 		/* Advance software pointer */
 		buffer += sz;
 		channel->filled_frags--;
 		channel->swptr += channel->frag_sz;
 		channel->swptr %= channel->buf_sz;
 		i -= sz;
-
-		DPRINTK ("%s: filled_frags = %d, swptr = %x\n", __FUNCTION__,
-			 channel->filled_frags, channel->swptr);
 	}
 
-	ret = bytes - i;
-
- out:
 	spin_unlock_irqrestore (&chip->lock, flags);
-	return ret;
+
+	return bytes - i;
 }
 
 
 static struct file_operations forte_dsp_fops = {
 	owner:			THIS_MODULE,
 	llseek:     		&no_llseek,
-//	read:       		&forte_dsp_read,
+	read:       		&forte_dsp_read,
 	write:      		&forte_dsp_write,
 	poll:       		&forte_dsp_poll,
 	ioctl:      		&forte_dsp_ioctl,
@@ -1593,7 +1609,7 @@
 	
 	if (status & FORTE_IRQ_PLAYBACK) {
 		channel = &chip->play;
-		spin_lock_irq (&chip->lock);
+		spin_lock (&chip->lock);
 
 		/* Declare a fragment done */
 		channel->filled_frags--;
@@ -1632,7 +1648,7 @@
 		/* Acknowledge interrupt */
                 outw (FORTE_IRQ_PLAYBACK, chip->iobase + FORTE_IRQ_STATUS);
 
-		spin_unlock_irq (&chip->lock);
+		spin_unlock (&chip->lock);
 
 		if (channel->blocked || channel->drain)
 			wake_up_interruptible (&channel->wait);
@@ -1640,14 +1656,11 @@
 
 	if (status & FORTE_IRQ_CAPTURE) {
 		channel = &chip->rec;
-		spin_lock_irq (&chip->lock);
+		spin_lock (&chip->lock);
 
 		/* One fragment filled */
 		channel->filled_frags++;
 
-		DPRINTK ("%s: filled_frags = %d\n", __FUNCTION__,
-			 channel->filled_frags);
-
 		/* Get # of completed bytes */
 		count = inw (channel->iobase + FORTE_PLY_COUNT) + 1;
 
@@ -1671,8 +1684,6 @@
 		channel->hwptr += channel->frag_sz;
 		channel->hwptr %= channel->buf_sz;
 
-		DPRINTK ("%s: hwptr = %x\n", __FUNCTION__, channel->hwptr);
-
 		/* Out of buffers */
 		if (channel->filled_frags == channel->frag_num - 1)
 			forte_channel_stop (channel);
@@ -1680,7 +1691,7 @@
 		/* Acknowledge interrupt */
                 outw (FORTE_IRQ_CAPTURE, chip->iobase + FORTE_IRQ_STATUS);
 
-		spin_unlock_irq (&chip->lock);
+		spin_unlock (&chip->lock);
 
 		if (channel->blocked)
 			wake_up_all (&channel->wait);		
@@ -1761,7 +1772,7 @@
 	codec->id = 0;
 
 	if (ac97_probe_codec (codec) == 0) {
-		printk(KERN_ERR PFX "codec probe failed\n");
+		printk (KERN_ERR PFX "codec probe failed\n");
 		kfree (codec);
 		return -1;
 	}
