Subject: Re: kern/14819: changing ym /dev/audio encoding is unreliable
To: None <collver@linuxfreemail.com>
From: ITOH Yasufumi <itohy@netbsd.org>
List: netbsd-bugs
Date: 03/22/2002 23:44:12
  Hello,

Will you try again with following change?
This checks unexpected busy state of the device and print diagnosis.

Regards,
-- 
ITOH Yasufumi

Index: ad1848.c
===================================================================
RCS file: /cvsroot/syssrc/sys/dev/ic/ad1848.c,v
retrieving revision 1.13
diff -u -r1.13 ad1848.c
--- ad1848.c	2002/03/06 07:12:02	1.13
+++ ad1848.c	2002/03/22 12:58:18
@@ -236,12 +236,23 @@
 	int reg;
 {
 	int x;
+	int t = 0;
 
+	for ( ; t < 10000 && ADREAD(sc, AD1848_IADDR) & SP_IN_INIT; t++)
+		delay(10);
+	if (t) printf("ad_read: %d (unknown location)\n", t);
 	ADWRITE(sc, AD1848_IADDR, (reg & 0xff) | sc->MCE_bit);
 	x = ADREAD(sc, AD1848_IDATA);
 	/*  printf("(%02x<-%02x) ", reg|sc->MCE_bit, x); */
 	return x;
 }
+#define ad_read(sc, reg) ({						\
+	int t = 0;							\
+	for ( ; t < 10000 && ADREAD(sc, AD1848_IADDR) & SP_IN_INIT; t++)\
+		delay(10);						\
+	if (t) printf("%s:%d: ad_read: %d\n", __FILE__, __LINE__, t);	\
+	ADWRITE(sc, AD1848_IADDR, ((reg) & 0xff) | (sc)->MCE_bit);	\
+	ADREAD(sc, AD1848_IDATA); })
 
 __inline void
 ad_write(sc, reg, data)
@@ -249,10 +260,23 @@
 	int reg;
 	int data;
 {
+	int t = 0;
+
+	for ( ; t < 10000 && ADREAD(sc, AD1848_IADDR) & SP_IN_INIT; t++)
+		delay(10);
+	if (t) printf("ad_write: %d (unknown location)\n", t);
 	ADWRITE(sc, AD1848_IADDR, (reg & 0xff) | sc->MCE_bit);
 	ADWRITE(sc, AD1848_IDATA, data & 0xff);
 	/* printf("(%02x->%02x) ", reg|sc->MCE_bit, data); */
 }
+#define ad_write(sc, reg, data) do {					\
+	int t = 0;							\
+	for ( ; t < 10000 && ADREAD(sc, AD1848_IADDR) & SP_IN_INIT; t++)\
+		delay(10);						\
+	if (t) printf("%s:%d: ad_write: %d\n", __FILE__, __LINE__, t);	\
+	ADWRITE(sc, AD1848_IADDR, ((reg) & 0xff) | (sc)->MCE_bit);	\
+	ADWRITE(sc, AD1848_IDATA, (data) & 0xff);			\
+} while (0)
 
 /*
  * extended registers (mode 3) require an additional level of