Subject: kern/7427: ess driver can't detect ES18[67][89].
To: None <gnats-bugs@gnats.netbsd.org>
From: None <AW9K-NNK@asahi-net.or.jp>
List: netbsd-bugs
Date: 04/20/1999 09:06:22
>Number: 7427
>Category: kern
>Synopsis: ess driver can't detect ES18[67][89]
>Confidential: no
>Severity: non-critical
>Priority: low
>Responsible: kern-bug-people (Kernel Bug People)
>State: open
>Class: change-request
>Submitter-Id: net
>Arrival-Date: Tue Apr 20 09:05:00 1999
>Last-Modified:
>Originator: Nonaka Kimihiro
>Organization:
>Release: NetBSD-current 19990419
>Environment:
System: NetBSD koharu 1.4_ALPHA NetBSD 1.4_ALPHA (KOHARU) #236: Sun Apr 18 01:37:11 JST 1999 nonaka@koharu:/usr/src/sys/arch/i386/compile/KOHARU i386
>Description:
ess driver can't detect ES18[67][89].
ES18[67]8 is detected ES1788.
ES18[67]9 is detected ES1887.
>How-To-Repeat:
attach ess driver with ES18[67][89].
>Fix:
Apply the following patch.
ES18[67][89] treat as ES1788. (use audio1 interface for playing.)
diff -uNr sys.orig/dev/isa/ess.c sys/dev/isa/ess.c
--- sys.orig/dev/isa/ess.c Mon Mar 22 21:14:50 1999
+++ sys/dev/isa/ess.c Tue Apr 20 23:50:18 1999
@@ -170,7 +170,7 @@
u_int ess_srtofc __P((u_int));
u_char ess_get_dsp_status __P((struct ess_softc *));
u_char ess_dsp_read_ready __P((struct ess_softc *));
-u_char ess_dsp_write_ready __P((struct ess_softc *sc));
+u_char ess_dsp_write_ready __P((struct ess_softc *));
int ess_rdsp __P((struct ess_softc *));
int ess_wdsp __P((struct ess_softc *, u_char));
u_char ess_read_x_reg __P((struct ess_softc *, u_char));
@@ -181,13 +181,18 @@
void ess_write_mix_reg __P((struct ess_softc *, u_char, u_char));
void ess_clear_mreg_bits __P((struct ess_softc *, u_char, u_char));
void ess_set_mreg_bits __P((struct ess_softc *, u_char, u_char));
+void ess_read_multi_mix_reg __P((struct ess_softc *, u_char, u_int8_t *, bus_size_t));
static char *essmodel[] = {
"unsupported",
"1888",
"1887",
"888",
- "1788"
+ "1788",
+ "1869",
+ "1879",
+ "1868",
+ "1878",
};
struct audio_device ess_device = {
@@ -276,7 +281,7 @@
sc->sc_audio1.drq, sc->sc_audio1.irq, sc->sc_audio1.nintr,
sc->sc_audio1.intr, sc->sc_audio1.arg);
- if (sc->sc_model != ESS_1788) {
+ if (!ESS_USE_AUDIO1(sc->sc_model)) {
printf("audio2: dmachan %d irq %d nintr %lu intr %p arg %p\n",
sc->sc_audio2.drq, sc->sc_audio2.irq, sc->sc_audio2.nintr,
sc->sc_audio2.intr, sc->sc_audio2.arg);
@@ -508,7 +513,7 @@
}
ess_write_x_reg(sc, ESS_XCMD_IRQ_CTRL, v);
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
return;
if (sc->sc_audio2.polled) {
@@ -553,7 +558,7 @@
/* Set DRQ1 */
ess_write_x_reg(sc, ESS_XCMD_DRQ_CTRL, v);
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
return;
/* Configure DRQ2 */
@@ -613,10 +618,12 @@
u_char reg1;
u_char reg2;
u_char reg3;
+ u_int8_t ident[4];
sc->sc_model = ESS_UNSUPPORTED;
sc->sc_version = 0;
+ memset(ident, 0, sizeof(ident));
/*
* 1. Check legacy ID bytes. These should be 0x68 0x8n, where
@@ -677,6 +684,21 @@
if (ess_read_mix_reg(sc, ESS_MREG_SAMPLE_RATE) != reg2) {
/* If we got this far before failing, it's a 1788. */
sc->sc_model = ESS_1788;
+
+ /*
+ * Identify ESS model for ES18[67]8.
+ */
+ ess_read_multi_mix_reg(sc, 0x40, ident, sizeof(ident));
+ if(ident[0] == 0x18) {
+ switch(ident[1]) {
+ case 0x68:
+ sc->sc_model = ESS_1868;
+ break;
+ case 0x78:
+ sc->sc_model = ESS_1878;
+ break;
+ }
+ }
} else {
/*
* 4. Determine if we can change bit 5 in mixer register 0x64.
@@ -697,6 +719,21 @@
* Restore the original value of mixer register 0x64.
*/
ess_write_mix_reg(sc, ESS_MREG_VOLUME_CTRL, reg1);
+
+ /*
+ * Identify ESS model for ES18[67]9.
+ */
+ ess_read_multi_mix_reg(sc, 0x40, ident, sizeof(ident));
+ if(ident[0] == 0x18) {
+ switch(ident[1]) {
+ case 0x69:
+ sc->sc_model = ESS_1869;
+ break;
+ case 0x79:
+ sc->sc_model = ESS_1879;
+ break;
+ }
+ }
} else {
/*
* 5. Determine if we can change the value of mixer
@@ -785,7 +822,7 @@
}
if (!isa_drq_isfree(sc->sc_ic, sc->sc_audio1.drq))
return (0);
- if (sc->sc_model != ESS_1788) {
+ if (!ESS_USE_AUDIO1(sc->sc_model)) {
if (!ESS_DRQ2_VALID(sc->sc_audio2.drq)) {
printf("ess: play drq %d invalid\n", sc->sc_audio2.drq);
return (0);
@@ -815,7 +852,7 @@
printf("ess: record irq %d invalid\n", sc->sc_audio1.irq);
return (0);
}
- if (sc->sc_model != ESS_1788) {
+ if (!ESS_USE_AUDIO1(sc->sc_model)) {
if (sc->sc_audio2.irq != -1 &&
!ESS_IRQ2_VALID(sc->sc_audio2.irq)) {
printf("ess: play irq %d invalid\n", sc->sc_audio2.irq);
@@ -856,9 +893,6 @@
printf(": ESS Technology ES%s [version 0x%04x]\n",
essmodel[sc->sc_model], sc->sc_version);
-
- sc->sc_audio1.irq = -1;
- sc->sc_audio2.irq = -1;
sc->sc_audio1.polled = sc->sc_audio1.irq == -1;
if (!sc->sc_audio1.polled) {
@@ -876,7 +910,7 @@
return;
}
- if (sc->sc_model != ESS_1788) {
+ if (!ESS_USE_AUDIO1(sc->sc_model)) {
sc->sc_audio2.polled = sc->sc_audio2.irq == -1;
if (!sc->sc_audio2.polled) {
sc->sc_audio2.ih = isa_intr_establish(sc->sc_ic,
@@ -909,11 +943,11 @@
* Set volume of Audio 1 to zero and disable Audio 1 DAC input
* to playback mixer, since playback is always through Audio 2.
*/
- if (sc->sc_model != ESS_1788)
+ if (!ESS_USE_AUDIO1(sc->sc_model))
ess_write_mix_reg(sc, ESS_MREG_VOLUME_VOICE, 0);
ess_wdsp(sc, ESS_ACMD_DISABLE_SPKR);
- if (sc->sc_model == ESS_1788) {
+ if (ESS_USE_AUDIO1(sc->sc_model)) {
ess_write_mix_reg(sc, ESS_MREG_ADC_SOURCE, ESS_SOURCE_MIC);
sc->in_port = ESS_SOURCE_MIC;
sc->ndevs = ESS_1788_NDEVS;
@@ -966,7 +1000,7 @@
sprintf(ess_device.name, "ES%s", essmodel[sc->sc_model]);
sprintf(ess_device.version, "0x%04x", sc->sc_version);
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
audio_attach_mi(&ess_1788_hw_if, sc, &sc->sc_dev);
else
audio_attach_mi(&ess_1888_hw_if, sc, &sc->sc_dev);
@@ -1227,7 +1261,7 @@
ess_write_x_reg(sc, ESS_XCMD_SAMPLE_RATE, ess_srtotc(rate));
ess_write_x_reg(sc, ESS_XCMD_FILTER_CLOCK, ess_srtofc(rate));
- if (sc->sc_model != ESS_1788) {
+ if (!ESS_USE_AUDIO1(sc->sc_model)) {
ess_write_mix_reg(sc, ESS_MREG_SAMPLE_RATE, ess_srtotc(rate));
ess_write_mix_reg(sc, ESS_MREG_FILTER_CLOCK, ess_srtofc(rate));
}
@@ -1682,7 +1716,7 @@
return (0);
case ESS_RECORD_SOURCE:
- if (sc->sc_model == ESS_1788) {
+ if (ESS_USE_AUDIO1(sc->sc_model)) {
if (cp->type == AUDIO_MIXER_ENUM)
return (ess_set_in_port(sc, cp->un.ord));
else
@@ -1710,7 +1744,7 @@
return (0);
}
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
return (EINVAL);
switch (cp->dev) {
@@ -1804,7 +1838,7 @@
return (0);
case ESS_RECORD_SOURCE:
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
cp->un.ord = sc->in_port;
else
cp->un.mask = sc->in_mask;
@@ -1816,7 +1850,7 @@
return (0);
}
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
return (EINVAL);
switch (cp->dev) {
@@ -1883,7 +1917,7 @@
case ESS_MIC_PLAY_VOL:
dip->mixer_class = ESS_INPUT_CLASS;
dip->prev = AUDIO_MIXER_LAST;
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
dip->next = AUDIO_MIXER_LAST;
else
dip->next = ESS_MIC_PREAMP;
@@ -1974,7 +2008,7 @@
dip->mixer_class = ESS_RECORD_CLASS;
dip->next = dip->prev = AUDIO_MIXER_LAST;
strcpy(dip->label.name, AudioNsource);
- if (sc->sc_model == ESS_1788) {
+ if (ESS_USE_AUDIO1(sc->sc_model)) {
/*
* The 1788 doesn't use the input mixer control that
* the 1888 uses, because it's a pain when you only
@@ -2039,7 +2073,7 @@
return (0);
}
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
return (ENXIO);
switch (dip->index) {
@@ -2124,7 +2158,7 @@
struct ess_softc *sc = addr;
int drq;
- if (sc->sc_model != ESS_1788 && direction == AUMODE_PLAY)
+ if ((!ESS_USE_AUDIO1(sc->sc_model)) && direction == AUMODE_PLAY)
drq = sc->sc_audio2.drq;
else
drq = sc->sc_audio1.drq;
@@ -2232,7 +2266,7 @@
src = ESS_MREG_VOLUME_MASTER;
break;
case ESS_DAC_PLAY_VOL:
- if (sc->sc_model == ESS_1788)
+ if (ESS_USE_AUDIO1(sc->sc_model))
src = ESS_MREG_VOLUME_VOICE;
else
src = 0x7C;
@@ -2283,7 +2317,7 @@
}
/* 1788 doesn't have a separate recording mixer */
- if (sc->sc_model == ESS_1788 && mix && src > 0x62)
+ if (ESS_USE_AUDIO1(sc->sc_model) && mix && src > 0x62)
return;
if (on) {
@@ -2637,4 +2671,21 @@
u_char mask;
{
ess_write_mix_reg(sc, reg, ess_read_mix_reg(sc, reg) | mask);
+}
+
+void
+ess_read_multi_mix_reg(sc, reg, datap, count)
+ struct ess_softc *sc;
+ u_char reg;
+ u_int8_t *datap;
+ bus_size_t count;
+{
+ bus_space_tag_t iot = sc->sc_iot;
+ bus_space_handle_t ioh = sc->sc_ioh;
+ int s;
+
+ s = splaudio();
+ EWRITE1(iot, ioh, ESS_MIX_REG_SELECT, reg);
+ bus_space_read_multi_1(iot, ioh, ESS_MIX_REG_DATA, datap, count);
+ splx(s);
}
diff -uNr sys.orig/dev/isa/ess_isa.c sys/dev/isa/ess_isa.c
--- sys.orig/dev/isa/ess_isa.c Fri Mar 19 21:11:21 1999
+++ sys/dev/isa/ess_isa.c Sun Apr 18 19:04:36 1999
@@ -97,7 +97,7 @@
DPRINTF(("ess_isa_probe succeeded (score %d)\n", ret));
ia->ia_iosize = ESS_NPORT;
} else
- DPRINTF(("ess_isa_probe failed]n"));
+ DPRINTF(("ess_isa_probe failed\n"));
return ret;
}
diff -uNr sys.orig/dev/isa/essreg.h sys/dev/isa/essreg.h
--- sys.orig/dev/isa/essreg.h Mon Mar 22 21:14:50 1999
+++ sys/dev/isa/essreg.h Sun Apr 18 19:07:20 1999
@@ -164,6 +164,7 @@
* Macros to detect valid hardware configuration data.
*/
#define ESS_BASE_VALID(base) ((base) == 0x220 || (base) == 0x230 || (base) == 0x240 || (base) == 0x250)
+
#define ESS_IRQ1_VALID(irq) ((irq) == 5 || (irq) == 7 || (irq) == 9 || (irq) == 10)
#define ESS_IRQ2_VALID(irq) ((irq) == 15)
@@ -174,7 +175,7 @@
#define ESS_DRQ2_VALID(chan) ((chan) == 0 || (chan) == 1 || (chan) == 3 || (chan) == 5)
-#define ESS_BASE_VALID(base) ((base) == 0x220 || (base) == 0x230 || (base) == 0x240 || (base) == 0x250)
+#define ESS_USE_AUDIO1(model) (((model) == ESS_1788) || ((model) == ESS_1868) || ((model) == ESS_1878) || ((model) == ESS_1869) || ((model) == ESS_1879))
/*
* Macros to manipulate gain values
diff -uNr sys.orig/dev/isa/essvar.h sys/dev/isa/essvar.h
--- sys.orig/dev/isa/essvar.h Thu Mar 18 21:14:14 1999
+++ sys/dev/isa/essvar.h Mon Mar 29 21:24:48 1999
@@ -148,6 +148,10 @@
#define ESS_1887 2
#define ESS_888 3
#define ESS_1788 4
+#define ESS_1869 5
+#define ESS_1879 6
+#define ESS_1868 7
+#define ESS_1878 8
u_int sc_version; /* Legacy ES688/ES1688 ID */
};
diff -uNr sys.orig/dev/isapnp/ess_isapnp.c sys/dev/isapnp/ess_isapnp.c
--- sys.orig/dev/isapnp/ess_isapnp.c Mon Mar 22 21:14:52 1999
+++ sys/dev/isapnp/ess_isapnp.c Tue Apr 20 23:33:02 1999
@@ -71,7 +71,7 @@
*/
/*
- * Probe for the soundblaster hardware.
+ * Probe for the ess hardware.
*/
int
ess_isapnp_match(parent, match, aux)
>Audit-Trail:
>Unformatted: