git: 13fcc9caaf96 - main - sound: Standardize mixer_init() call order
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Fri, 18 Sep 2026 18:18:36 UTC
The branch main has been updated by christos:
URL: https://cgit.FreeBSD.org/src/commit/?id=13fcc9caaf968083254b92546e21dedb322a920b
commit 13fcc9caaf968083254b92546e21dedb322a920b
Author: Christos Margiolis <christos@FreeBSD.org>
AuthorDate: 2026-09-18 18:12:42 +0000
Commit: Christos Margiolis <christos@FreeBSD.org>
CommitDate: 2026-09-18 18:12:42 +0000
sound: Standardize mixer_init() call order
Device drivers call mixer_init() in a non-standard order - some before
pcm_init(), and some after pcm_register(). However, both approaches are
potentially risky, and logically weak, since pcm_register() is supposed
to be the function that finalizes sound(4) attach.
Standardize the call ordering by moving all mixer_init() calls after
pcm_init(). This is also necessary for a follow-up patch, which expects
pcm_init() to have run first and initialized the PCM lock.
Sponsored by: The FreeBSD Foundation
MFC after: 1 month
Differential Revision: https://reviews.freebsd.org/D59069
---
sys/arm/allwinner/a10_codec.c | 4 ++--
sys/arm/broadcom/bcm2835/bcm2835_audio.c | 4 ++--
sys/arm/freescale/imx/imx6_ssi.c | 3 ++-
sys/arm/freescale/vybrid/vf_sai.c | 4 ++--
sys/dev/sound/dummy.c | 2 +-
sys/dev/sound/fdt/audio_soc.c | 9 +++++----
sys/dev/sound/macio/aoa.c | 6 +++++-
sys/dev/sound/macio/aoa.h | 2 +-
sys/dev/sound/macio/davbus.c | 19 +++++++++++--------
sys/dev/sound/macio/i2s.c | 12 ++++++++----
sys/dev/sound/pci/als4000.c | 4 ++--
sys/dev/sound/pci/atiixp.c | 4 ++--
sys/dev/sound/pci/cmi.c | 4 ++--
sys/dev/sound/pci/cs4281.c | 4 ++--
sys/dev/sound/pci/csapcm.c | 2 +-
sys/dev/sound/pci/emu10k1.c | 2 +-
sys/dev/sound/pci/emu10kx-pcm.c | 2 +-
sys/dev/sound/pci/envy24.c | 3 ++-
sys/dev/sound/pci/envy24ht.c | 3 ++-
sys/dev/sound/pci/es137x.c | 2 +-
sys/dev/sound/pci/fm801.c | 2 +-
sys/dev/sound/pci/hda/hdaa.c | 12 ++++++------
sys/dev/sound/pci/hdsp-pcm.c | 4 ++--
sys/dev/sound/pci/hdspe-pcm.c | 4 ++--
sys/dev/sound/pci/ich.c | 4 ++--
sys/dev/sound/pci/maestro3.c | 2 +-
sys/dev/sound/pci/neomagic.c | 2 +-
sys/dev/sound/pci/solo.c | 3 ++-
sys/dev/sound/pci/t4dwave.c | 2 +-
sys/dev/sound/pci/via8233.c | 2 +-
sys/dev/sound/pci/via82c686.c | 2 +-
sys/dev/sound/pci/vibes.c | 3 ++-
sys/dev/sound/usb/uaudio.c | 15 ++++++++-------
33 files changed, 85 insertions(+), 67 deletions(-)
diff --git a/sys/arm/allwinner/a10_codec.c b/sys/arm/allwinner/a10_codec.c
index d3920eddc1f1..01f514af2e9a 100644
--- a/sys/arm/allwinner/a10_codec.c
+++ b/sys/arm/allwinner/a10_codec.c
@@ -1150,6 +1150,8 @@ a10codec_attach(device_t dev)
val |= DAC_DPC_EN_DA;
CODEC_WRITE(sc, AC_DAC_DPC(sc), val);
+ pcm_init(dev, sc);
+
if (mixer_init(dev, sc->cfg->mixer_class, sc)) {
device_printf(dev, "mixer_init failed\n");
goto fail;
@@ -1165,8 +1167,6 @@ a10codec_attach(device_t dev)
pcm_setflags(dev, pcm_getflags(dev) | SD_F_MPSAFE);
- pcm_init(dev, sc);
-
pcm_addchan(dev, PCMDIR_PLAY, &a10codec_chan_class, sc);
pcm_addchan(dev, PCMDIR_REC, &a10codec_chan_class, sc);
diff --git a/sys/arm/broadcom/bcm2835/bcm2835_audio.c b/sys/arm/broadcom/bcm2835/bcm2835_audio.c
index 556edce502f0..da6a00c3e3a1 100644
--- a/sys/arm/broadcom/bcm2835/bcm2835_audio.c
+++ b/sys/arm/broadcom/bcm2835/bcm2835_audio.c
@@ -1037,13 +1037,13 @@ bcm2835_audio_delayed_init(void *xsc)
sc->dest = DEST_AUTO;
sc->verbose_trace = 0;
+ pcm_init(sc->dev, sc);
+
if (mixer_init(sc->dev, &bcmmixer_class, sc)) {
device_printf(sc->dev, "mixer_init failed\n");
goto no;
}
- pcm_init(sc->dev, sc);
-
pcm_addchan(sc->dev, PCMDIR_PLAY, &bcmchan_class, sc);
snprintf(status, SND_STATUSLEN, "at VCHIQ");
if (pcm_register(sc->dev, status)) {
diff --git a/sys/arm/freescale/imx/imx6_ssi.c b/sys/arm/freescale/imx/imx6_ssi.c
index f4ef955761b4..738c2cc09a55 100644
--- a/sys/arm/freescale/imx/imx6_ssi.c
+++ b/sys/arm/freescale/imx/imx6_ssi.c
@@ -808,6 +808,8 @@ ssi_attach(device_t dev)
pcm_init(dev, scp);
+ mixer_init(dev, &ssimixer_class, scp);
+
scp->chnum = 0;
pcm_addchan(dev, PCMDIR_PLAY, &ssichan_class, scp);
scp->chnum++;
@@ -819,7 +821,6 @@ ssi_attach(device_t dev)
return (ENXIO);
}
- mixer_init(dev, &ssimixer_class, scp);
setup_ssi(sc);
imx_ccm_ssi_configure(dev);
diff --git a/sys/arm/freescale/vybrid/vf_sai.c b/sys/arm/freescale/vybrid/vf_sai.c
index d3a3ab93fe80..17a3d4fc799b 100644
--- a/sys/arm/freescale/vybrid/vf_sai.c
+++ b/sys/arm/freescale/vybrid/vf_sai.c
@@ -760,6 +760,8 @@ sai_attach(device_t dev)
pcm_init(dev, scp);
+ mixer_init(dev, &saimixer_class, scp);
+
scp->chnum = 0;
pcm_addchan(dev, PCMDIR_PLAY, &saichan_class, scp);
scp->chnum++;
@@ -771,8 +773,6 @@ sai_attach(device_t dev)
return (ENXIO);
}
- mixer_init(dev, &saimixer_class, scp);
-
setup_dma(scp);
setup_sai(sc);
diff --git a/sys/dev/sound/dummy.c b/sys/dev/sound/dummy.c
index 5791347c59df..7b456884040e 100644
--- a/sys/dev/sound/dummy.c
+++ b/sys/dev/sound/dummy.c
@@ -376,6 +376,7 @@ dummy_attach(device_t dev)
pcm_setflags(dev, pcm_getflags(dev) | SD_F_MPSAFE);
pcm_init(dev, sc);
+ mixer_init(dev, &dummy_mixer_class, sc);
for (i = 0; i < DUMMY_NPCHAN; i++)
pcm_addchan(dev, PCMDIR_PLAY, &dummy_chan_class, sc);
for (i = 0; i < DUMMY_NRCHAN; i++)
@@ -385,7 +386,6 @@ dummy_attach(device_t dev)
device_get_nameunit(device_get_parent(dev)));
if (pcm_register(dev, status))
return (ENXIO);
- mixer_init(dev, &dummy_mixer_class, sc);
/*
* Create an alias so that tests do not need to guess which one is the
diff --git a/sys/dev/sound/fdt/audio_soc.c b/sys/dev/sound/fdt/audio_soc.c
index 33269dc302fa..9cd913004c0e 100644
--- a/sys/dev/sound/fdt/audio_soc.c
+++ b/sys/dev/sound/fdt/audio_soc.c
@@ -398,6 +398,11 @@ audio_soc_init(void *arg)
pcm_init(sc->dev, sc);
+ AUDIO_DAI_SETUP_MIXER(sc->codec_dev, sc->dev);
+ SLIST_FOREACH(aux_node, &sc->aux_devs, link) {
+ AUDIO_DAI_SETUP_MIXER(aux_node->dev, sc->dev);
+ }
+
sc->play_channel.sc = sc;
sc->rec_channel.sc = sc;
@@ -410,10 +415,6 @@ audio_soc_init(void *arg)
}
AUDIO_DAI_SETUP_INTR(sc->cpu_dev, audio_soc_intr, sc);
- AUDIO_DAI_SETUP_MIXER(sc->codec_dev, sc->dev);
- SLIST_FOREACH(aux_node, &sc->aux_devs, link) {
- AUDIO_DAI_SETUP_MIXER(aux_node->dev, sc->dev);
- }
}
static int
diff --git a/sys/dev/sound/macio/aoa.c b/sys/dev/sound/macio/aoa.c
index ff8f17224384..db22dcc4a2d8 100644
--- a/sys/dev/sound/macio/aoa.c
+++ b/sys/dev/sound/macio/aoa.c
@@ -362,7 +362,7 @@ static kobj_method_t aoa_chan_methods[] = {
CHANNEL_DECLARE(aoa_chan);
int
-aoa_attach(void *xsc)
+aoa_attach(void *xsc, kobj_class_t mixer_class, void *mixer_devinfo)
{
char status[SND_STATUSLEN];
struct aoa_softc *sc;
@@ -374,6 +374,10 @@ aoa_attach(void *xsc)
pcm_init(self, sc);
+ /* Install the codec's mixer, if we have one. */
+ if (mixer_class != NULL)
+ mixer_init(self, mixer_class, mixer_devinfo);
+
err = pcm_getbuffersize(self, AOA_BUFFER_SIZE, AOA_BUFFER_SIZE,
AOA_BUFFER_SIZE);
DPRINTF(("pcm_getbuffersize returned %d\n", err));
diff --git a/sys/dev/sound/macio/aoa.h b/sys/dev/sound/macio/aoa.h
index 511fe345d74a..b14fad3b6500 100644
--- a/sys/dev/sound/macio/aoa.h
+++ b/sys/dev/sound/macio/aoa.h
@@ -41,6 +41,6 @@ struct aoa_softc {
};
void aoa_interrupt(void *);
-int aoa_attach(void *xsc);
+int aoa_attach(void *xsc, kobj_class_t mixer_class, void *mixer_devinfo);
#endif /* SOUND_AOA_H */
diff --git a/sys/dev/sound/macio/davbus.c b/sys/dev/sound/macio/davbus.c
index de15806e6d5c..10cf85cf98e0 100644
--- a/sys/dev/sound/macio/davbus.c
+++ b/sys/dev/sound/macio/davbus.c
@@ -495,6 +495,7 @@ davbus_attach(device_t self)
struct davbus_softc *sc;
struct resource *dbdma_irq, *cintr;
void *cookie;
+ kobj_class_t mixer_class;
char compat[64];
int rid, oirq, err;
@@ -557,16 +558,18 @@ davbus_attach(device_t self)
bus_write_4(sc->reg, DAVBUS_SOUND_CTRL, DAVBUS_INPUT_SUBFRAME0 |
DAVBUS_OUTPUT_SUBFRAME0 | DAVBUS_RATE_44100 | DAVBUS_INTR_PORTCHG);
- /* Attach DBDMA engine and PCM layer */
- err = aoa_attach(sc);
- if (err)
- return (err);
-
- /* Install codec module */
+ /* Pick the codec module */
if (strcmp(compat, "screamer") == 0)
- mixer_init(self, &screamer_mixer_class, sc);
+ mixer_class = &screamer_mixer_class;
else if (strcmp(compat, "burgundy") == 0)
- mixer_init(self, &burgundy_mixer_class, sc);
+ mixer_class = &burgundy_mixer_class;
+ else
+ mixer_class = NULL;
+
+ /* Attach DBDMA engine, codec mixer and PCM layer */
+ err = aoa_attach(sc, mixer_class, sc);
+ if (err)
+ return (err);
return (0);
}
diff --git a/sys/dev/sound/macio/i2s.c b/sys/dev/sound/macio/i2s.c
index 327fbe5fc0bd..711484fd0132 100644
--- a/sys/dev/sound/macio/i2s.c
+++ b/sys/dev/sound/macio/i2s.c
@@ -249,7 +249,7 @@ i2s_attach(device_t self)
if (config_intrhook_establish(i2s_delayed_attach) != 0)
return (ENOMEM);
- return (aoa_attach(sc));
+ return (0);
}
/*****************************************************************************
@@ -737,9 +737,13 @@ i2s_postattach(void *xsc)
/* Reset the codec. */
i2s_audio_hw_reset(sc);
- /* If we have a codec, initialize it. */
- if (i2s_mixer)
- mixer_init(self, i2s_mixer_class, i2s_mixer);
+ /*
+ * Attach the DBDMA engine and the PCM layer, along with the codec's
+ * mixer, if we have one. This is deferred until now because the codec
+ * only becomes available once the I2C controller has attached.
+ */
+ if (aoa_attach(sc, i2s_mixer_class, i2s_mixer) != 0)
+ device_printf(self, "could not attach PCM layer\n");
/* Read initial port status. */
i2s_cint(sc);
diff --git a/sys/dev/sound/pci/als4000.c b/sys/dev/sound/pci/als4000.c
index 0613f3ec2b97..b5aefa333d86 100644
--- a/sys/dev/sound/pci/als4000.c
+++ b/sys/dev/sound/pci/als4000.c
@@ -832,13 +832,13 @@ als_pci_attach(device_t dev)
goto bad_attach;
}
+ pcm_init(dev, sc);
+
if (mixer_init(dev, &als_mixer_class, sc)) {
device_printf(dev, "failed to initialize mixer\n");
goto bad_attach;
}
- pcm_init(dev, sc);
-
pcm_addchan(dev, PCMDIR_PLAY, &alspchan_class, sc);
pcm_addchan(dev, PCMDIR_REC, &alsrchan_class, sc);
diff --git a/sys/dev/sound/pci/atiixp.c b/sys/dev/sound/pci/atiixp.c
index 39ef2f375328..631205b273ab 100644
--- a/sys/dev/sound/pci/atiixp.c
+++ b/sys/dev/sound/pci/atiixp.c
@@ -1080,10 +1080,10 @@ atiixp_chip_post_init(void *arg)
break;
}
- mixer_init(sc->dev, ac97_getmixerclass(), sc->codec);
-
pcm_init(sc->dev, sc);
+ mixer_init(sc->dev, ac97_getmixerclass(), sc->codec);
+
for (i = 0; i < ATI_IXP_NPCHAN; i++)
pcm_addchan(sc->dev, PCMDIR_PLAY, &atiixp_chan_class, sc);
for (i = 0; i < ATI_IXP_NRCHAN; i++)
diff --git a/sys/dev/sound/pci/cmi.c b/sys/dev/sound/pci/cmi.c
index 58ab961b74e1..e53b46467f0b 100644
--- a/sys/dev/sound/pci/cmi.c
+++ b/sys/dev/sound/pci/cmi.c
@@ -980,11 +980,11 @@ cmi_attach(device_t dev)
if (cmi_init(sc))
goto bad;
+ pcm_init(dev, sc);
+
if (mixer_init(dev, &cmi_mixer_class, sc))
goto bad;
- pcm_init(dev, sc);
-
cmi_initsys(sc);
pcm_addchan(dev, PCMDIR_PLAY, &cmichan_class, sc);
diff --git a/sys/dev/sound/pci/cs4281.c b/sys/dev/sound/pci/cs4281.c
index ef5183331331..a30467566b36 100644
--- a/sys/dev/sound/pci/cs4281.c
+++ b/sys/dev/sound/pci/cs4281.c
@@ -837,10 +837,10 @@ cs4281_pci_attach(device_t dev)
if (codec == NULL)
goto bad;
- mixer_init(dev, ac97_getmixerclass(), codec);
-
pcm_init(dev, sc);
+ mixer_init(dev, ac97_getmixerclass(), codec);
+
pcm_addchan(dev, PCMDIR_PLAY, &cs4281chan_class, sc);
pcm_addchan(dev, PCMDIR_REC, &cs4281chan_class, sc);
diff --git a/sys/dev/sound/pci/csapcm.c b/sys/dev/sound/pci/csapcm.c
index 8fd18a2a4361..a40c4a083787 100644
--- a/sys/dev/sound/pci/csapcm.c
+++ b/sys/dev/sound/pci/csapcm.c
@@ -809,6 +809,7 @@ pcmcsa_attach(device_t dev)
}
if (csa->card->inv_eapd)
ac97_setflags(codec, AC97_F_EAPD_INV);
+ pcm_init(dev, csa);
if (mixer_init(dev, ac97_getmixerclass(), codec) == -1) {
ac97_destroy(codec);
csa_releaseres(csa, dev);
@@ -829,7 +830,6 @@ pcmcsa_attach(device_t dev)
csa_writemem(resp, BA1_CIE, (csa_readmem(resp, BA1_CIE) & ~0x0000003f) | 0x00000001);
csa_active(csa, -1);
- pcm_init(dev, csa);
pcm_addchan(dev, PCMDIR_REC, &csachan_class, csa);
pcm_addchan(dev, PCMDIR_PLAY, &csachan_class, csa);
if (pcm_register(dev, status)) {
diff --git a/sys/dev/sound/pci/emu10k1.c b/sys/dev/sound/pci/emu10k1.c
index d3afa8d4fe43..5120ec2411a1 100644
--- a/sys/dev/sound/pci/emu10k1.c
+++ b/sys/dev/sound/pci/emu10k1.c
@@ -2114,6 +2114,7 @@ emu_pci_attach(device_t dev)
codec = AC97_CREATE(dev, sc, emu_ac97);
if (codec == NULL) goto bad;
gotmic = (ac97_getcaps(codec) & AC97_CAP_MICCHANNEL) ? 1 : 0;
+ pcm_init(dev, sc);
if (mixer_init(dev, ac97_getmixerclass(), codec) == -1) goto bad;
emu_midiattach(sc);
@@ -2131,7 +2132,6 @@ emu_pci_attach(device_t dev)
rman_get_start(sc->reg), rman_get_start(sc->irq),
device_get_nameunit(device_get_parent(dev)));
- pcm_init(dev, sc);
for (i = 0; i < sc->nchans; i++)
pcm_addchan(dev, PCMDIR_PLAY, &emupchan_class, sc);
for (i = 0; i < (gotmic ? 3 : 2); i++)
diff --git a/sys/dev/sound/pci/emu10kx-pcm.c b/sys/dev/sound/pci/emu10kx-pcm.c
index 0a15b8ba3448..55b1b4d8cc1c 100644
--- a/sys/dev/sound/pci/emu10kx-pcm.c
+++ b/sys/dev/sound/pci/emu10kx-pcm.c
@@ -1393,6 +1393,7 @@ emu_pcm_attach(device_t dev)
sc->emu10k1_volcache[1][1] = 75;
BUS_READ_IVAR(device_get_parent(dev), dev, EMU_VAR_ROUTE, &route);
sc->route = route;
+ pcm_init(dev, sc);
switch (route) {
case RT_FRONT:
sc->rt.amounts_left[0] = 0xff;
@@ -1474,7 +1475,6 @@ emu_pcm_attach(device_t dev)
pcm_setflags(dev, pcm_getflags(dev) | SD_F_MPSAFE);
/* XXX we should better get number of available channels from parent */
- pcm_init(dev, sc);
sc->pnum = 0;
if (route != RT_MCHRECORD)
pcm_addchan(dev, PCMDIR_PLAY, &emupchan_class, sc);
diff --git a/sys/dev/sound/pci/envy24.c b/sys/dev/sound/pci/envy24.c
index df9c680b9414..533c8aeddeb3 100644
--- a/sys/dev/sound/pci/envy24.c
+++ b/sys/dev/sound/pci/envy24.c
@@ -2570,11 +2570,12 @@ envy24_pci_attach(device_t dev)
goto bad;
}
+ pcm_init(dev, sc);
+
/* set multi track mixer */
mixer_init(dev, &envy24mixer_class, sc);
/* set channel information */
- pcm_init(dev, sc);
sc->chnum = 0;
for (i = 0; i < 5; i++) {
pcm_addchan(dev, PCMDIR_PLAY, &envy24chan_class, sc);
diff --git a/sys/dev/sound/pci/envy24ht.c b/sys/dev/sound/pci/envy24ht.c
index 19a4ee39eacd..34052ee869db 100644
--- a/sys/dev/sound/pci/envy24ht.c
+++ b/sys/dev/sound/pci/envy24ht.c
@@ -2474,11 +2474,12 @@ envy24ht_pci_attach(device_t dev)
goto bad;
}
+ pcm_init(dev, sc);
+
/* set multi track mixer */
mixer_init(dev, &envy24htmixer_class, sc);
/* set channel information */
- pcm_init(dev, sc);
sc->chnum = 0;
/* for (i = 0; i < 5; i++) { */
pcm_addchan(dev, PCMDIR_PLAY, &envy24htchan_class, sc);
diff --git a/sys/dev/sound/pci/es137x.c b/sys/dev/sound/pci/es137x.c
index ab8a6db74640..f67bb41e4542 100644
--- a/sys/dev/sound/pci/es137x.c
+++ b/sys/dev/sound/pci/es137x.c
@@ -1798,6 +1798,7 @@ es_pci_attach(device_t dev)
es->escfg = ES_SET_NUMREC(es->escfg, 1);
devid = pci_get_devid(dev);
+ pcm_init(dev, es);
switch (devid) {
case ES1371_PCI_ID:
case ES1371_PCI_ID2:
@@ -1858,7 +1859,6 @@ es_pci_attach(device_t dev)
rman_get_start(es->reg), rman_get_start(es->irq),
device_get_nameunit(device_get_parent(dev)));
- pcm_init(dev, es);
for (i = 0; i < numplay; i++)
pcm_addchan(dev, PCMDIR_PLAY, ct, es);
pcm_addchan(dev, PCMDIR_REC, ct, es);
diff --git a/sys/dev/sound/pci/fm801.c b/sys/dev/sound/pci/fm801.c
index 69c74ad91303..65e1987abc6a 100644
--- a/sys/dev/sound/pci/fm801.c
+++ b/sys/dev/sound/pci/fm801.c
@@ -613,6 +613,7 @@ fm801_pci_attach(device_t dev)
codec = AC97_CREATE(dev, fm801, fm801_ac97);
if (codec == NULL) goto oops;
+ pcm_init(dev, fm801);
if (mixer_init(dev, ac97_getmixerclass(), codec) == -1) goto oops;
fm801->irqid = 0;
@@ -642,7 +643,6 @@ fm801_pci_attach(device_t dev)
device_get_nameunit(device_get_parent(dev)));
#define FM801_MAXPLAYCH 1
- pcm_init(dev, fm801);
pcm_addchan(dev, PCMDIR_PLAY, &fm801ch_class, fm801);
pcm_addchan(dev, PCMDIR_REC, &fm801ch_class, fm801);
if (pcm_register(dev, status))
diff --git a/sys/dev/sound/pci/hda/hdaa.c b/sys/dev/sound/pci/hda/hdaa.c
index 44cca506751f..c11ce3c0bf6a 100644
--- a/sys/dev/sound/pci/hda/hdaa.c
+++ b/sys/dev/sound/pci/hda/hdaa.c
@@ -7114,12 +7114,6 @@ hdaa_pcm_attach(device_t dev)
*/
pcm_setflags(dev, pcm_getflags(dev) | SD_F_MPSAFE);
- HDA_BOOTHVERBOSE(
- device_printf(dev, "OSS mixer initialization...\n");
- );
- if (mixer_init(dev, &hdaa_audio_ctl_ossmixer_class, pdevinfo) != 0)
- device_printf(dev, "Can't register mixer\n");
-
HDA_BOOTHVERBOSE(
device_printf(dev, "Registering PCM channels...\n");
);
@@ -7127,6 +7121,12 @@ hdaa_pcm_attach(device_t dev)
pdevinfo->registered++;
+ HDA_BOOTHVERBOSE(
+ device_printf(dev, "OSS mixer initialization...\n");
+ );
+ if (mixer_init(dev, &hdaa_audio_ctl_ossmixer_class, pdevinfo) != 0)
+ device_printf(dev, "Can't register mixer\n");
+
d = device_get_softc(dev);
if (pdevinfo->playas >= 0) {
as = &devinfo->as[pdevinfo->playas];
diff --git a/sys/dev/sound/pci/hdsp-pcm.c b/sys/dev/sound/pci/hdsp-pcm.c
index 7f4f7dc76557..46bdc1f6ea7e 100644
--- a/sys/dev/sound/pci/hdsp-pcm.c
+++ b/sys/dev/sound/pci/hdsp-pcm.c
@@ -1070,6 +1070,8 @@ hdsp_pcm_attach(device_t dev)
pcm_init(dev, scp);
+ mixer_init(dev, &hdspmixer_class, scp);
+
play = (hdsp_channel_play_ports(scp->hc)) ? 1 : 0;
rec = (hdsp_channel_rec_ports(scp->hc)) ? 1 : 0;
@@ -1094,8 +1096,6 @@ hdsp_pcm_attach(device_t dev)
return (ENXIO);
}
- mixer_init(dev, &hdspmixer_class, scp);
-
/* Register the PCM child for interrupt dispatch. */
mtx_lock(&sc->lock);
for (i = 0; i < HDSP_MAX_PCMDEV; i++) {
diff --git a/sys/dev/sound/pci/hdspe-pcm.c b/sys/dev/sound/pci/hdspe-pcm.c
index a814c80127b1..ffd3a2cee1dc 100644
--- a/sys/dev/sound/pci/hdspe-pcm.c
+++ b/sys/dev/sound/pci/hdspe-pcm.c
@@ -1064,6 +1064,8 @@ hdspe_pcm_attach(device_t dev)
pcm_init(dev, scp);
+ mixer_init(dev, &hdspemixer_class, scp);
+
play = (hdspe_channel_play_ports(scp->hc)) ? 1 : 0;
rec = (hdspe_channel_rec_ports(scp->hc)) ? 1 : 0;
@@ -1088,8 +1090,6 @@ hdspe_pcm_attach(device_t dev)
return (ENXIO);
}
- mixer_init(dev, &hdspemixer_class, scp);
-
/* Register the PCM child for interrupt dispatch. */
mtx_lock(&sc->lock);
for (i = 0; i < HDSPE_MAX_PCMDEV; i++) {
diff --git a/sys/dev/sound/pci/ich.c b/sys/dev/sound/pci/ich.c
index 1295e7eb5bc1..7cb0983b17ef 100644
--- a/sys/dev/sound/pci/ich.c
+++ b/sys/dev/sound/pci/ich.c
@@ -1029,6 +1029,8 @@ ich_pci_attach(device_t dev)
break;
}
+ pcm_init(dev, sc);
+
mixer_init(dev, ac97_getmixerclass(), sc->codec);
/* check and set VRA function */
@@ -1067,8 +1069,6 @@ ich_pci_attach(device_t dev)
ich_setmap, sc, 0))
goto bad;
- pcm_init(dev, sc);
-
pcm_addchan(dev, PCMDIR_PLAY, &ichchan_class, sc); /* play */
pcm_addchan(dev, PCMDIR_REC, &ichchan_class, sc); /* record */
if (sc->hasmic)
diff --git a/sys/dev/sound/pci/maestro3.c b/sys/dev/sound/pci/maestro3.c
index 5bf420c86c95..4f101ccdbfe6 100644
--- a/sys/dev/sound/pci/maestro3.c
+++ b/sys/dev/sound/pci/maestro3.c
@@ -1416,6 +1416,7 @@ m3_pci_attach(device_t dev)
device_printf(dev, "ac97_create error\n");
goto bad;
}
+ pcm_init(dev, sc);
if (mixer_init(dev, ac97_getmixerclass(), codec)) {
device_printf(dev, "mixer_init error\n");
goto bad;
@@ -1423,7 +1424,6 @@ m3_pci_attach(device_t dev)
m3_enable_ints(sc);
- pcm_init(dev, sc);
for (i=0 ; i<dacn ; i++) {
if (pcm_addchan(dev, PCMDIR_PLAY, &m3_pch_class, sc)) {
device_printf(dev, "pcm_addchan (play) error\n");
diff --git a/sys/dev/sound/pci/neomagic.c b/sys/dev/sound/pci/neomagic.c
index 0e0af654b734..2813c7de57b3 100644
--- a/sys/dev/sound/pci/neomagic.c
+++ b/sys/dev/sound/pci/neomagic.c
@@ -692,6 +692,7 @@ nm_pci_attach(device_t dev)
codec = AC97_CREATE(dev, sc, nm_ac97);
if (codec == NULL) goto bad;
+ pcm_init(dev, sc);
if (mixer_init(dev, ac97_getmixerclass(), codec) == -1) goto bad;
sc->irqid = 0;
@@ -707,7 +708,6 @@ nm_pci_attach(device_t dev)
rman_get_start(sc->irq),
device_get_nameunit(device_get_parent(dev)));
- pcm_init(dev, sc);
pcm_addchan(dev, PCMDIR_REC, &nmchan_class, sc);
pcm_addchan(dev, PCMDIR_PLAY, &nmchan_class, sc);
if (pcm_register(dev, status))
diff --git a/sys/dev/sound/pci/solo.c b/sys/dev/sound/pci/solo.c
index 21054973d9a2..71da677167bf 100644
--- a/sys/dev/sound/pci/solo.c
+++ b/sys/dev/sound/pci/solo.c
@@ -1017,6 +1017,8 @@ ess_attach(device_t dev)
if (sc->newspeed)
ess_setmixer(sc, 0x71, 0x2a);
+ pcm_init(dev, sc);
+
if (mixer_init(dev, &solomixer_class, sc))
goto no;
@@ -1025,7 +1027,6 @@ ess_attach(device_t dev)
rman_get_start(sc->irq),
device_get_nameunit(device_get_parent(dev)));
- pcm_init(dev, sc);
pcm_addchan(dev, PCMDIR_REC, &esschan_class, sc);
pcm_addchan(dev, PCMDIR_PLAY, &esschan_class, sc);
if (pcm_register(dev, status))
diff --git a/sys/dev/sound/pci/t4dwave.c b/sys/dev/sound/pci/t4dwave.c
index d4650cfa07e2..83416976f603 100644
--- a/sys/dev/sound/pci/t4dwave.c
+++ b/sys/dev/sound/pci/t4dwave.c
@@ -874,6 +874,7 @@ tr_pci_attach(device_t dev)
codec = AC97_CREATE(dev, tr, tr_ac97);
if (codec == NULL) goto bad;
+ pcm_init(dev, tr);
if (mixer_init(dev, ac97_getmixerclass(), codec) == -1) goto bad;
tr->irqid = 0;
@@ -922,7 +923,6 @@ tr_pci_attach(device_t dev)
rman_get_start(tr->reg), rman_get_start(tr->irq),
device_get_nameunit(device_get_parent(dev)));
- pcm_init(dev, tr);
pcm_addchan(dev, PCMDIR_REC, &trrchan_class, tr);
for (i = 0; i < dacn; i++)
pcm_addchan(dev, PCMDIR_PLAY, &trpchan_class, tr);
diff --git a/sys/dev/sound/pci/via8233.c b/sys/dev/sound/pci/via8233.c
index 90e966b864e3..69ffc6a9e3be 100644
--- a/sys/dev/sound/pci/via8233.c
+++ b/sys/dev/sound/pci/via8233.c
@@ -1331,6 +1331,7 @@ via_attach(device_t dev)
if (!via->codec)
goto bad;
+ pcm_init(dev, via);
mixer_init(dev, ac97_getmixerclass(), via->codec);
via->codec_caps = ac97_getextcaps(via->codec);
@@ -1350,7 +1351,6 @@ via_attach(device_t dev)
device_get_nameunit(device_get_parent(dev)));
/* Register */
- pcm_init(dev, via);
for (i = 0; i < via_dxs_chnum; i++)
pcm_addchan(dev, PCMDIR_PLAY, &via8233dxs_class, via);
for (i = 0; i < via_sgd_chnum; i++)
diff --git a/sys/dev/sound/pci/via82c686.c b/sys/dev/sound/pci/via82c686.c
index 85356cc64145..b9fc1f9953fd 100644
--- a/sys/dev/sound/pci/via82c686.c
+++ b/sys/dev/sound/pci/via82c686.c
@@ -535,6 +535,7 @@ via_attach(device_t dev)
if (!via->codec)
goto bad;
+ pcm_init(dev, via);
if (mixer_init(dev, ac97_getmixerclass(), via->codec))
goto bad;
@@ -585,7 +586,6 @@ via_attach(device_t dev)
device_get_nameunit(device_get_parent(dev)));
/* Register */
- pcm_init(dev, via);
pcm_addchan(dev, PCMDIR_PLAY, &viachan_class, via);
pcm_addchan(dev, PCMDIR_REC, &viachan_class, via);
if (pcm_register(dev, status))
diff --git a/sys/dev/sound/pci/vibes.c b/sys/dev/sound/pci/vibes.c
index 08ba83a54d2a..445b8295085a 100644
--- a/sys/dev/sound/pci/vibes.c
+++ b/sys/dev/sound/pci/vibes.c
@@ -785,6 +785,8 @@ sv_attach(device_t dev) {
sv_power(sc, 0);
sv_init(sc);
+ pcm_init(dev, sc);
+
if (mixer_init(dev, &sv_mixer_class, sc) != 0) {
device_printf(dev, "sv_attach: Mixer failed to initialize\n");
goto fail;
@@ -867,7 +869,6 @@ sv_attach(device_t dev) {
if (bootverbose)
printf("Sonicvibes: revision %d.\n", sc->rev);
- pcm_init(dev, sc);
pcm_addchan(dev, PCMDIR_PLAY, &svpchan_class, sc);
pcm_addchan(dev, PCMDIR_REC, &svrchan_class, sc);
diff --git a/sys/dev/sound/usb/uaudio.c b/sys/dev/sound/usb/uaudio.c
index 491827c87f84..4e1d7c4c89d5 100644
--- a/sys/dev/sound/usb/uaudio.c
+++ b/sys/dev/sound/usb/uaudio.c
@@ -1204,13 +1204,6 @@ uaudio_attach_sub(device_t dev, kobj_class_t mixer_class, kobj_class_t chan_clas
DPRINTF("device needs bitperfect by default\n");
uaudio_pcm_setflags(dev, SD_F_BITPERFECT);
}
- if (mixer_init(dev, mixer_class, sc))
- goto detach;
- mix_set(sc->sc_child[i].mixer_dev, SOUND_MIXER_MONITOR,
- UAUDIO_DEFAULT_MONITOR, UAUDIO_DEFAULT_MONITOR);
- sc->sc_child[i].mixer_init = 1;
-
- mixer_hwvol_init(dev);
device_set_descf(dev, "%s %s",
usb_get_manufacturer(sc->sc_udev),
@@ -1223,6 +1216,14 @@ uaudio_attach_sub(device_t dev, kobj_class_t mixer_class, kobj_class_t chan_clas
uaudio_pcm_setflags(dev, SD_F_MPSAFE);
+ if (mixer_init(dev, mixer_class, sc))
+ goto detach;
+ mix_set(sc->sc_child[i].mixer_dev, SOUND_MIXER_MONITOR,
+ UAUDIO_DEFAULT_MONITOR, UAUDIO_DEFAULT_MONITOR);
+ sc->sc_child[i].mixer_init = 1;
+
+ mixer_hwvol_init(dev);
+
if (sc->sc_play_chan[i].num_alt > 0) {
sc->sc_play_chan[i].priv_sc = sc;
pcm_addchan(dev, PCMDIR_PLAY, chan_class,