diff --git a/RELNOTES b/RELNOTES --- a/RELNOTES +++ b/RELNOTES @@ -10,6 +10,9 @@ Changes to this file should not be MFCed. +8fef193e14e2: + As a side-effect of retiring the unit.* code in sound(4), the + hw.snd.maxunit loader(8) tunable is also retired. 6d5ce2bb6344: The default value of the nfs_reserved_port_only rc.conf(5) setting has changed. The FreeBSD NFS server now requires the source port of diff --git a/sys/conf/files b/sys/conf/files --- a/sys/conf/files +++ b/sys/conf/files @@ -3072,7 +3072,6 @@ dev/smc/if_smc_acpi.c optional smc acpi dev/smc/if_smc_fdt.c optional smc fdt dev/snp/snp.c optional snp -dev/sound/unit.c optional sound dev/sound/pci/als4000.c optional snd_als4000 pci dev/sound/pci/atiixp.c optional snd_atiixp pci dev/sound/pci/cmi.c optional snd_cmi pci diff --git a/sys/dev/sound/pcm/channel.h b/sys/dev/sound/pcm/channel.h --- a/sys/dev/sound/pcm/channel.h +++ b/sys/dev/sound/pcm/channel.h @@ -104,6 +104,7 @@ void *devinfo; device_t dev; int unit; + int type; char name[CHN_NAMELEN]; char comm[MAXCOMLEN + 1]; struct mtx *lock; @@ -224,7 +225,7 @@ #define CHN_INSERT_SORT(w, x, y, z) do { \ struct pcm_channel *t, *a = NULL; \ CHN_FOREACH(t, x, z) { \ - if ((y)->unit w t->unit) \ + if ((y)->type w t->type) \ a = t; \ else \ break; \ @@ -235,13 +236,9 @@ CHN_INSERT_HEAD(x, y, z); \ } while (0) -#define CHN_INSERT_SORT_ASCEND(x, y, z) CHN_INSERT_SORT(>, x, y, z) +#define CHN_INSERT_SORT_ASCEND(x, y, z) CHN_INSERT_SORT(>=, x, y, z) #define CHN_INSERT_SORT_DESCEND(x, y, z) CHN_INSERT_SORT(<, x, y, z) -#define CHN_UNIT(x) (snd_unit2u((x)->unit)) -#define CHN_DEV(x) (snd_unit2d((x)->unit)) -#define CHN_CHAN(x) (snd_unit2c((x)->unit)) - #define CHN_BUF_PARENT(x, y) \ (((x) != NULL && (x)->parentchannel != NULL && \ (x)->parentchannel->bufhard != NULL) ? \ diff --git a/sys/dev/sound/pcm/dsp.h b/sys/dev/sound/pcm/dsp.h --- a/sys/dev/sound/pcm/dsp.h +++ b/sys/dev/sound/pcm/dsp.h @@ -35,7 +35,7 @@ int dsp_make_dev(device_t); void dsp_destroy_dev(device_t); -char *dsp_unit2name(char *, size_t, int); +char *dsp_unit2name(char *, size_t, struct pcm_channel *); int dsp_oss_audioinfo(struct cdev *, oss_audioinfo *); #endif /* !_PCMDSP_H_ */ diff --git a/sys/dev/sound/pcm/dsp.c b/sys/dev/sound/pcm/dsp.c --- a/sys/dev/sound/pcm/dsp.c +++ b/sys/dev/sound/pcm/dsp.c @@ -444,7 +444,7 @@ if (DSP_F_READ(flags)) { /* open for read */ rderror = pcm_chnalloc(d, &rdch, PCMDIR_REC, - td->td_proc->p_pid, td->td_proc->p_comm, -1); + td->td_proc->p_pid, td->td_proc->p_comm); if (rderror == 0 && chn_reset(rdch, fmt, spd) != 0) rderror = ENXIO; @@ -472,7 +472,7 @@ if (DSP_F_WRITE(flags)) { /* open for write */ wrerror = pcm_chnalloc(d, &wrch, PCMDIR_PLAY, - td->td_proc->p_pid, td->td_proc->p_comm, -1); + td->td_proc->p_pid, td->td_proc->p_comm); if (wrerror == 0 && chn_reset(wrch, fmt, spd) != 0) wrerror = ENXIO; @@ -629,69 +629,13 @@ return (dsp_io_ops(priv, buf)); } -static int -dsp_get_volume_channel(struct dsp_cdevpriv *priv, struct pcm_channel **volch) -{ - struct snddev_info *d; - struct pcm_channel *c; - int unit; - - KASSERT(volch != NULL, - ("%s(): NULL query priv=%p volch=%p", __func__, priv, volch)); - - d = priv->sc; - if (!PCM_REGISTERED(d)) { - *volch = NULL; - return (EINVAL); - } - - PCM_UNLOCKASSERT(d); - - *volch = NULL; - - c = priv->volch; - if (c != NULL) { - if (!(c->feederflags & (1 << FEEDER_VOLUME))) - return (-1); - *volch = c; - return (0); - } - - PCM_LOCK(d); - PCM_WAIT(d); - PCM_ACQUIRE(d); - - unit = dev2unit(d->dsp_dev); - - CHN_FOREACH(c, d, channels.pcm) { - CHN_LOCK(c); - if (c->unit != unit) { - CHN_UNLOCK(c); - continue; - } - *volch = c; - pcm_chnref(c, 1); - priv->volch = c; - CHN_UNLOCK(c); - PCM_RELEASE(d); - PCM_UNLOCK(d); - return ((c->feederflags & (1 << FEEDER_VOLUME)) ? 0 : -1); - } - - PCM_RELEASE(d); - PCM_UNLOCK(d); - - return (EINVAL); -} - static int dsp_ioctl_channel(struct dsp_cdevpriv *priv, struct pcm_channel *volch, u_long cmd, caddr_t arg) { struct snddev_info *d; struct pcm_channel *rdch, *wrch; - int j, devtype, ret; - int left, right, center, mute; + int j, left, right, center, mute; d = priv->sc; if (!PCM_REGISTERED(d) || !(pcm_getflags(d->dev) & SD_F_VPC)) @@ -716,19 +660,6 @@ volch = wrch; } - devtype = PCMDEV(d->dsp_dev); - - /* Look super harder */ - if (volch == NULL && - (devtype == SND_DEV_DSPHW_PLAY || devtype == SND_DEV_DSPHW_VPLAY || - devtype == SND_DEV_DSPHW_REC || devtype == SND_DEV_DSPHW_VREC)) { - ret = dsp_get_volume_channel(priv, &volch); - if (ret != 0) - return (ret); - if (volch == NULL) - return (EINVAL); - } - /* Final validation */ if (volch == NULL) return (EINVAL); @@ -2105,8 +2036,6 @@ { if (dsp_ehtag != NULL) return; - /* initialize unit numbering */ - snd_unit_init(); dsp_ehtag = EVENTHANDLER_REGISTER(dev_clone, dsp_clone, 0, 1000); } @@ -2123,20 +2052,19 @@ SYSUNINIT(dsp_sysuninit, SI_SUB_DRIVERS, SI_ORDER_MIDDLE, dsp_sysuninit, NULL); char * -dsp_unit2name(char *buf, size_t len, int unit) +dsp_unit2name(char *buf, size_t len, struct pcm_channel *ch) { - int i, dtype; + int i; KASSERT(buf != NULL && len != 0, ("bogus buf=%p len=%ju", buf, (uintmax_t)len)); - dtype = snd_unit2d(unit); - for (i = 0; i < nitems(dsp_cdevs); i++) { - if (dtype != dsp_cdevs[i].type || dsp_cdevs[i].alias != NULL) + if (ch->type != dsp_cdevs[i].type || dsp_cdevs[i].alias != NULL) continue; - snprintf(buf, len, "%s%d%s%d", dsp_cdevs[i].name, - snd_unit2u(unit), dsp_cdevs[i].sep, snd_unit2c(unit)); + snprintf(buf, len, "%s%d%s%d", + dsp_cdevs[i].name, device_get_unit(ch->dev), + dsp_cdevs[i].sep, ch->unit); return (buf); } @@ -2224,12 +2152,10 @@ if (devfs_foreach_cdevpriv(i_dev, dsp_oss_audioinfo_cb, ch) != 0) { devname = dsp_unit2name(buf, - sizeof(buf), ch->unit); + sizeof(buf), ch); } - } else if (ai->dev == nchan) { - devname = dsp_unit2name(buf, sizeof(buf), - ch->unit); - } + } else if (ai->dev == nchan) + devname = dsp_unit2name(buf, sizeof(buf), ch); if (devname != NULL) break; CHN_UNLOCK(ch); diff --git a/sys/dev/sound/pcm/feeder.c b/sys/dev/sound/pcm/feeder.c --- a/sys/dev/sound/pcm/feeder.c +++ b/sys/dev/sound/pcm/feeder.c @@ -82,9 +82,7 @@ if (snd_verbose < 0 || snd_verbose > 4) snd_verbose = 1; - /* initialize unit numbering */ - snd_unit_init(); - if (snd_unit < 0 || snd_unit > PCMMAXUNIT) + if (snd_unit < 0) snd_unit = -1; if (snd_maxautovchans < 0 || diff --git a/sys/dev/sound/pcm/mixer.c b/sys/dev/sound/pcm/mixer.c --- a/sys/dev/sound/pcm/mixer.c +++ b/sys/dev/sound/pcm/mixer.c @@ -727,7 +727,7 @@ u_int16_t v; struct cdev *pdev; const char *name; - int i, unit, devunit, val; + int i, unit, val; snddev = device_get_softc(dev); if (snddev == NULL) @@ -764,8 +764,7 @@ mixer_setrecsrc(m, 0); /* Set default input. */ - devunit = snd_mkunit(unit, SND_DEV_CTL, 0); - pdev = make_dev(&mixer_cdevsw, devunit, UID_ROOT, GID_WHEEL, 0666, + pdev = make_dev(&mixer_cdevsw, SND_DEV_CTL, UID_ROOT, GID_WHEEL, 0666, "mixer%d", unit); pdev->si_drv1 = m; snddev->mixer_dev = pdev; diff --git a/sys/dev/sound/pcm/sound.h b/sys/dev/sound/pcm/sound.h --- a/sys/dev/sound/pcm/sound.h +++ b/sys/dev/sound/pcm/sound.h @@ -88,7 +88,6 @@ #include #include #include -#include #define PCM_SOFTC_SIZE (sizeof(struct snddev_info)) @@ -100,21 +99,6 @@ #define SOUND_PREFVER SOUND_MODVER #define SOUND_MAXVER SOUND_MODVER -/* - * We're abusing the fact that MAXMINOR still have enough room - * for our bit twiddling and nobody ever need 512 unique soundcards, - * 32 unique device types and 1024 unique cloneable devices for the - * next 100 years... - */ - -#define PCMMAXUNIT (snd_max_u()) -#define PCMMAXDEV (snd_max_d()) -#define PCMMAXCHAN (snd_max_c()) - -#define PCMUNIT(x) (snd_unit2u(dev2unit(x))) -#define PCMDEV(x) (snd_unit2d(dev2unit(x))) -#define PCMCHAN(x) (snd_unit2c(dev2unit(x))) - /* * By design, limit possible channels for each direction. */ @@ -311,7 +295,7 @@ int pcm_setvchans(struct snddev_info *d, int direction, int newcnt, int num); int pcm_chnalloc(struct snddev_info *d, struct pcm_channel **ch, int direction, - pid_t pid, char *comm, int devunit); + pid_t pid, char *comm); int pcm_chnrelease(struct pcm_channel *c); int pcm_chnref(struct pcm_channel *c, int ref); diff --git a/sys/dev/sound/pcm/sound.c b/sys/dev/sound/pcm/sound.c --- a/sys/dev/sound/pcm/sound.c +++ b/sys/dev/sound/pcm/sound.c @@ -244,98 +244,63 @@ /* return error status and a locked channel */ int pcm_chnalloc(struct snddev_info *d, struct pcm_channel **ch, int direction, - pid_t pid, char *comm, int devunit) + pid_t pid, char *comm) { struct pcm_channel *c; int err, vchancount, vchan_num; + bool retry; - KASSERT(d != NULL && ch != NULL && (devunit == -1 || - !(devunit & ~(SND_U_MASK | SND_D_MASK | SND_C_MASK))) && + KASSERT(d != NULL && ch != NULL && (direction == PCMDIR_PLAY || direction == PCMDIR_REC), - ("%s(): invalid d=%p ch=%p direction=%d pid=%d devunit=%d", - __func__, d, ch, direction, pid, devunit)); + ("%s(): invalid d=%p ch=%p direction=%d pid=%d", + __func__, d, ch, direction, pid)); PCM_BUSYASSERT(d); - /* Double check again. */ - if (devunit != -1) { - switch (snd_unit2d(devunit)) { - case SND_DEV_DSPHW_PLAY: - case SND_DEV_DSPHW_VPLAY: - if (direction != PCMDIR_PLAY) - return (ENOTSUP); - break; - case SND_DEV_DSPHW_REC: - case SND_DEV_DSPHW_VREC: - if (direction != PCMDIR_REC) - return (ENOTSUP); - break; - default: - if (!(direction == PCMDIR_PLAY || - direction == PCMDIR_REC)) - return (ENOTSUP); - break; - } - } - *ch = NULL; vchan_num = 0; vchancount = (direction == PCMDIR_PLAY) ? d->pvchancount : d->rvchancount; + retry = false; retry_chnalloc: err = ENOTSUP; /* scan for a free channel */ CHN_FOREACH(c, d, channels.pcm) { CHN_LOCK(c); - if (devunit == -1 && c->direction == direction && - (c->flags & CHN_F_VIRTUAL)) { + if (c->direction == direction && (c->flags & CHN_F_VIRTUAL)) { if (vchancount < snd_maxautovchans && - vchan_num < CHN_CHAN(c)) { + vchan_num < c->unit) { CHN_UNLOCK(c); goto vchan_alloc; } vchan_num++; } - if (c->direction == direction && !(c->flags & CHN_F_BUSY) && - (devunit == -1 || devunit == -2 || c->unit == devunit)) { + if (c->direction == direction && !(c->flags & CHN_F_BUSY)) { c->flags |= CHN_F_BUSY; c->pid = pid; strlcpy(c->comm, (comm != NULL) ? comm : CHN_COMM_UNKNOWN, sizeof(c->comm)); *ch = c; return (0); - } else if (c->unit == devunit) { - if (c->direction != direction) - err = ENOTSUP; - else if (c->flags & CHN_F_BUSY) - err = EBUSY; - else - err = EINVAL; - CHN_UNLOCK(c); - return (err); - } else if ((devunit == -1 || devunit == -2) && - c->direction == direction && (c->flags & CHN_F_BUSY)) + } else if (c->direction == direction && (c->flags & CHN_F_BUSY)) err = EBUSY; CHN_UNLOCK(c); } - if (devunit == -2) + /* + * We came from retry_chnalloc and still didn't find a free channel. + */ + if (retry) return (err); vchan_alloc: /* no channel available */ - if (devunit == -1 || snd_unit2d(devunit) == SND_DEV_DSPHW_VPLAY || - snd_unit2d(devunit) == SND_DEV_DSPHW_VREC) { - if (!(vchancount > 0 && vchancount < snd_maxautovchans) && - (devunit == -1 || snd_unit2c(devunit) < snd_maxautovchans)) - return (err); - err = pcm_setvchans(d, direction, vchancount + 1, - (devunit == -1) ? -1 : snd_unit2c(devunit)); - if (err == 0) { - if (devunit == -1) - devunit = -2; - goto retry_chnalloc; - } + if (!(vchancount > 0 && vchancount < snd_maxautovchans)) + return (err); + err = pcm_setvchans(d, direction, vchancount + 1, -1); + if (err == 0) { + retry = true; + goto retry_chnalloc; } return (err); @@ -445,7 +410,7 @@ { struct pcm_channel *ch; int direction, err, rpnum, *pnum, max; - int udc, device, chan; + int type, unit; char *dirs, *devname, buf[CHN_NAMELEN]; PCM_BUSYASSERT(d); @@ -457,56 +422,54 @@ dirs = "play"; direction = PCMDIR_PLAY; pnum = &d->playcount; - device = SND_DEV_DSPHW_PLAY; + type = SND_DEV_DSPHW_PLAY; max = SND_MAXHWCHAN; break; case PCMDIR_PLAY_VIRTUAL: dirs = "virtual_play"; direction = PCMDIR_PLAY; pnum = &d->pvchancount; - device = SND_DEV_DSPHW_VPLAY; + type = SND_DEV_DSPHW_VPLAY; max = SND_MAXVCHANS; break; case PCMDIR_REC: dirs = "record"; direction = PCMDIR_REC; pnum = &d->reccount; - device = SND_DEV_DSPHW_REC; + type = SND_DEV_DSPHW_REC; max = SND_MAXHWCHAN; break; case PCMDIR_REC_VIRTUAL: dirs = "virtual_record"; direction = PCMDIR_REC; pnum = &d->rvchancount; - device = SND_DEV_DSPHW_VREC; + type = SND_DEV_DSPHW_VREC; max = SND_MAXVCHANS; break; default: return (NULL); } - chan = (num == -1) ? 0 : num; + unit = (num == -1) ? 0 : num; - if (*pnum >= max || chan >= max) + if (*pnum >= max || unit >= max) return (NULL); rpnum = 0; CHN_FOREACH(ch, d, channels.pcm) { - if (CHN_DEV(ch) != device) + if (ch->type != type) continue; - if (chan == CHN_CHAN(ch)) { - if (num != -1) { - device_printf(d->dev, - "channel num=%d allocated!\n", chan); - return (NULL); - } - chan++; - if (chan >= max) { - device_printf(d->dev, - "chan=%d > %d\n", chan, max); - return (NULL); - } + if (unit == ch->unit && num != -1) { + device_printf(d->dev, + "channel num=%d allocated!\n", unit); + return (NULL); + } + unit++; + if (unit >= max) { + device_printf(d->dev, + "chan=%d > %d\n", unit, max); + return (NULL); } rpnum++; } @@ -518,25 +481,24 @@ return (NULL); } - udc = snd_mkunit(device_get_unit(d->dev), device, chan); - devname = dsp_unit2name(buf, sizeof(buf), udc); - - if (devname == NULL) { - device_printf(d->dev, - "Failed to query device name udc=0x%08x\n", udc); - return (NULL); - } - PCM_UNLOCK(d); ch = malloc(sizeof(*ch), M_DEVBUF, M_WAITOK | M_ZERO); ch->methods = kobj_create(cls, M_DEVBUF, M_WAITOK | M_ZERO); - ch->unit = udc; + ch->type = type; + ch->unit = unit; ch->pid = -1; strlcpy(ch->comm, CHN_COMM_UNUSED, sizeof(ch->comm)); ch->parentsnddev = d; ch->parentchannel = parent; ch->dev = d->dev; ch->trigger = PCMTRIG_STOP; + devname = dsp_unit2name(buf, sizeof(buf), ch); + if (devname == NULL) { + device_printf(d->dev, "Failed to query device name"); + kobj_delete(ch->methods, M_DEVBUF); + free(ch, M_DEVBUF); + return (NULL); + } snprintf(ch->name, sizeof(ch->name), "%s:%s:%s", device_get_nameunit(ch->dev), dirs, devname); @@ -585,7 +547,7 @@ CHN_INSERT_SORT_ASCEND(d, ch, channels.pcm); - switch (CHN_DEV(ch)) { + switch (ch->type) { case SND_DEV_DSPHW_PLAY: d->playcount++; break; @@ -625,7 +587,7 @@ CHN_REMOVE(d, ch, channels.pcm); - switch (CHN_DEV(ch)) { + switch (ch->type) { case SND_DEV_DSPHW_PLAY: d->playcount--; break; @@ -939,14 +901,6 @@ return EINVAL; } - if (device_get_unit(dev) > PCMMAXUNIT) { - device_printf(dev, "PCMMAXUNIT reached : unit=%d > %d\n", - device_get_unit(dev), PCMMAXUNIT); - device_printf(dev, - "Use 'hw.snd.maxunit' tunable to raise the limit.\n"); - return ENODEV; - } - d = device_get_softc(dev); d->dev = dev; d->lock = snd_mtxcreate(device_get_nameunit(dev), "sound cdev"); diff --git a/sys/dev/sound/pcm/vchan.c b/sys/dev/sound/pcm/vchan.c --- a/sys/dev/sound/pcm/vchan.c +++ b/sys/dev/sound/pcm/vchan.c @@ -923,7 +923,7 @@ if (snd_passthrough_verbose != 0) { char *devname, buf[CHN_NAMELEN]; - devname = dsp_unit2name(buf, sizeof(buf), c->unit); + devname = dsp_unit2name(buf, sizeof(buf), c); device_printf(c->dev, "%s(%s/%s) %s() -> re-sync err=%d\n", __func__, (devname != NULL) ? devname : "dspX", c->comm, diff --git a/sys/dev/sound/unit.h b/sys/dev/sound/unit.h deleted file mode 100644 --- a/sys/dev/sound/unit.h +++ /dev/null @@ -1,52 +0,0 @@ -/*- - * SPDX-License-Identifier: BSD-2-Clause - * - * Copyright (c) 2007 Ariff Abdullah - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -#ifndef _SND_UNIT_H_ -#define _SND_UNIT_H_ - -#define SND_UNIT_UMIN 16 -#define SND_UNIT_UMAX 2048 - -int snd_max_u(void); -int snd_max_d(void); -int snd_max_c(void); -int snd_unit2u(int); -int snd_unit2d(int); -int snd_unit2c(int); -int snd_u2unit(int); -int snd_d2unit(int); -int snd_c2unit(int); -int snd_mkunit(int, int, int); - -void snd_unit_init(void); - -#define SND_U_MASK (snd_u2unit(snd_max_u())) -#define SND_D_MASK (snd_d2unit(snd_max_d())) -#define SND_C_MASK (snd_c2unit(snd_max_c())) - -#endif /* !_SND_UNIT_H_ */ diff --git a/sys/dev/sound/unit.c b/sys/dev/sound/unit.c deleted file mode 100644 --- a/sys/dev/sound/unit.c +++ /dev/null @@ -1,188 +0,0 @@ -/*- - * SPDX-License-Identifier: BSD-2-Clause - * - * Copyright (c) 2007 Ariff Abdullah - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -#include -#include - -#ifdef HAVE_KERNEL_OPTION_HEADERS -#include "opt_snd.h" -#endif - -#include - -/* - * Unit magic allocator for sound driver. - * - * 'u' = Unit of attached soundcards - * 'd' = Device type - * 'c' = Channel number - * - * eg: dsp0.p1 - u=0, d=p, c=1 - * dsp1.vp0 - u=1, d=vp, c=0 - * - * Maximum unit of soundcards can be tuned through "hw.snd.maxunit", which is - * between SND_UNIT_UMIN (16) and SND_UNIT_UMAX (2048). By design, the maximum - * allowable allocated channel is 256. - */ - -/* Default width */ -static int snd_u_shift = 9; /* 0 - 0x1ff : 512 distinct soundcards */ -static int snd_d_shift = 5; /* 0 - 0x1f : 32 distinct device types */ -static int snd_c_shift = 10; /* 0 - 0x3ff : 1024 distinct channels - (256 limit "by design") */ - -static int snd_unit_initialized = 0; - -#ifdef SND_DIAGNOSTIC -#define SND_UNIT_ASSERT() do { \ - if (snd_unit_initialized == 0) \ - panic("%s(): Uninitialized sound unit!", __func__); \ -} while (0) -#else -#define SND_UNIT_ASSERT() KASSERT(snd_unit_initialized != 0, \ - ("%s(): Uninitialized sound unit!", \ - __func__)) -#endif - -#define MKMASK(x) ((1 << snd_##x##_shift) - 1) - -int -snd_max_u(void) -{ - SND_UNIT_ASSERT(); - - return (MKMASK(u)); -} - -int -snd_max_d(void) -{ - SND_UNIT_ASSERT(); - - return (MKMASK(d)); -} - -int -snd_max_c(void) -{ - SND_UNIT_ASSERT(); - - return (MKMASK(c)); -} - -int -snd_unit2u(int unit) -{ - SND_UNIT_ASSERT(); - - return ((unit >> (snd_c_shift + snd_d_shift)) & MKMASK(u)); -} - -int -snd_unit2d(int unit) -{ - SND_UNIT_ASSERT(); - - return ((unit >> snd_c_shift) & MKMASK(d)); -} - -int -snd_unit2c(int unit) -{ - SND_UNIT_ASSERT(); - - return (unit & MKMASK(c)); -} - -int -snd_u2unit(int u) -{ - SND_UNIT_ASSERT(); - - return ((u & MKMASK(u)) << (snd_c_shift + snd_d_shift)); -} - -int -snd_d2unit(int d) -{ - SND_UNIT_ASSERT(); - - return ((d & MKMASK(d)) << snd_c_shift); -} - -int -snd_c2unit(int c) -{ - SND_UNIT_ASSERT(); - - return (c & MKMASK(c)); -} - -int -snd_mkunit(int u, int d, int c) -{ - SND_UNIT_ASSERT(); - - return ((c & MKMASK(c)) | ((d & MKMASK(d)) << snd_c_shift) | - ((u & MKMASK(u)) << (snd_c_shift + snd_d_shift))); -} - -/* - * This *must* be called first before any of the functions above!!! - */ -void -snd_unit_init(void) -{ - int i; - - if (snd_unit_initialized != 0) - return; - - snd_unit_initialized = 1; - - if (getenv_int("hw.snd.maxunit", &i) != 0) { - if (i < SND_UNIT_UMIN) - i = SND_UNIT_UMIN; - else if (i > SND_UNIT_UMAX) - i = SND_UNIT_UMAX; - else - i = roundup2(i, 2); - - for (snd_u_shift = 0; (i >> (snd_u_shift + 1)) != 0; - snd_u_shift++) - ; - - /* Make room for channels to fit within 24bit MAXMINOR limit. */ - snd_c_shift = 24 - snd_u_shift - snd_d_shift; - } - - if (bootverbose != 0) - printf("%s() u=0x%08x [%d] d=0x%08x [%d] c=0x%08x [%d]\n", - __func__, SND_U_MASK, snd_max_u() + 1, - SND_D_MASK, snd_max_d() + 1, SND_C_MASK, snd_max_c() + 1); -} diff --git a/sys/modules/sound/sound/Makefile b/sys/modules/sound/sound/Makefile --- a/sys/modules/sound/sound/Makefile +++ b/sys/modules/sound/sound/Makefile @@ -17,7 +17,7 @@ SRCS+= mpu_if.h mpufoi_if.h synth_if.h SRCS+= mpu_if.c mpufoi_if.c synth_if.c SRCS+= ac97.c ac97_patch.c buffer.c channel.c dsp.c -SRCS+= mixer.c sndstat.c sound.c unit.c vchan.c +SRCS+= mixer.c sndstat.c sound.c vchan.c SRCS+= midi.c mpu401.c sequencer.c feeder_eq_gen.h: ${SYSDIR}/tools/sound/feeder_eq_mkfilter.awk