The branch stable/14 has been updated by christos:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=858504a1d89f3e1cb89f6126b3b59e80716fb3df

commit 858504a1d89f3e1cb89f6126b3b59e80716fb3df
Author:     Christos Margiolis <chris...@freebsd.org>
AuthorDate: 2025-02-25 11:44:37 +0000
Commit:     Christos Margiolis <chris...@freebsd.org>
CommitDate: 2025-03-04 15:46:06 +0000

    sound: Call chn_kill() in chn_init() failure
    
    Sponsored by:   The FreeBSD Foundation
    MFC after:      1 week
    Differential Revision:  https://reviews.freebsd.org/D48966
    
    (cherry picked from commit bc7e65e950154572d8c9a04dc033075bf37aae40)
---
 sys/dev/sound/pcm/channel.c | 50 ++++++++++++++-------------------------------
 1 file changed, 15 insertions(+), 35 deletions(-)

diff --git a/sys/dev/sound/pcm/channel.c b/sys/dev/sound/pcm/channel.c
index c3ee50d51c4b..0a0059411399 100644
--- a/sys/dev/sound/pcm/channel.c
+++ b/sys/dev/sound/pcm/channel.c
@@ -1179,11 +1179,19 @@ chn_init(struct snddev_info *d, struct pcm_channel 
*parent, kobj_class_t cls,
 
        switch (dir) {
        case PCMDIR_PLAY:
+               d->playcount++;
+               /* FALLTHROUGH */
        case PCMDIR_PLAY_VIRTUAL:
+               if (dir == PCMDIR_PLAY_VIRTUAL)
+                       d->pvchancount++;
                direction = PCMDIR_PLAY;
                break;
        case PCMDIR_REC:
+               d->reccount++;
+               /* FALLTHROUGH */
        case PCMDIR_REC_VIRTUAL:
+               if (dir == PCMDIR_REC_VIRTUAL)
+                       d->rvchancount++;
                direction = PCMDIR_REC;
                break;
        default:
@@ -1292,40 +1300,10 @@ chn_init(struct snddev_info *d, struct pcm_channel 
*parent, kobj_class_t cls,
        if ((c->flags & CHN_F_VIRTUAL) == 0)
                CHN_INSERT_SORT_ASCEND(d, c, channels.pcm.primary);
 
-       switch (c->type) {
-       case PCMDIR_PLAY:
-               d->playcount++;
-               break;
-       case PCMDIR_PLAY_VIRTUAL:
-               d->pvchancount++;
-               break;
-       case PCMDIR_REC:
-               d->reccount++;
-               break;
-       case PCMDIR_REC_VIRTUAL:
-               d->rvchancount++;
-               break;
-       default:
-               __assert_unreachable();
-       }
-
        return (c);
 
 fail:
-       free_unr(chn_getunr(d, c->type), c->unit);
-       feeder_remove(c);
-       if (c->devinfo && CHANNEL_FREE(c->methods, c->devinfo))
-               sndbuf_free(b);
-       if (bs)
-               sndbuf_destroy(bs);
-       if (b)
-               sndbuf_destroy(b);
-       CHN_LOCK(c);
-       chn_lockdestroy(c);
-
-       kobj_delete(c->methods, M_DEVBUF);
-       free(c, M_DEVBUF);
-
+       chn_kill(c);
        PCM_LOCK(d);
 
        return (NULL);
@@ -1368,12 +1346,14 @@ chn_kill(struct pcm_channel *c)
                chn_trigger(c, PCMTRIG_ABORT);
                CHN_UNLOCK(c);
        }
-       free_unr(chn_getunr(c->parentsnddev, c->type), c->unit);
+       free_unr(chn_getunr(d, c->type), c->unit);
        feeder_remove(c);
-       if (CHANNEL_FREE(c->methods, c->devinfo))
+       if (c->devinfo && CHANNEL_FREE(c->methods, c->devinfo))
                sndbuf_free(b);
-       sndbuf_destroy(bs);
-       sndbuf_destroy(b);
+       if (bs)
+               sndbuf_destroy(bs);
+       if (b)
+               sndbuf_destroy(b);
        CHN_LOCK(c);
        c->flags |= CHN_F_DEAD;
        chn_lockdestroy(c);

Reply via email to