Fork us on GitHub Follow us on Facebook Follow us on Twitter

Changeset 0d59ea7e in mainline


Ignore:
Timestamp:
2022-07-02T14:34:36Z (7 weeks ago)
Author:
Jiri Svoboda <jiri@…>
Branches:
master
Children:
055dff5, 232c6b88, 6ab7aad4, bde6bb16, c0edd55, d9dda26, e080a1c0, ebb70d8
Parents:
9e9d9bc6
Message:

Multiple HD Audio converters cannot pull from a single stream

We select one arbitrary output converter for out PCM output, similar to what
we do for input.

We filter the 'other' VirtualBox? output converters based on rates/formats
being zero.

Location:
uspace/drv/audio/hdaudio
Files:
7 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/audio/hdaudio/codec.c

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    512512        codec->address = address;
    513513        codec->in_aw = -1;
     514        codec->out_aw = -1;
    514515
    515516        rc = hda_get_subnc(codec, 0, &sfg, &nfg);
     
    584585                                        goto error;
    585586                        } else if (awtype == awt_audio_output) {
    586                                 codec->out_aw_list[codec->out_aw_num++] = aw;
    587 
    588587                                rc = hda_get_supp_rates(codec, aw, &rates);
    589588                                if (rc != EOK)
     
    594593                                        goto error;
    595594
    596                                 ddf_msg(LVL_DEBUG, "Output widget %d: rates=0x%x formats=0x%x",
     595                                if (rates != 0 && formats != 0 &&
     596                                    codec->out_aw < 0) {
     597                                        ddf_msg(LVL_DEBUG, "Selected output "
     598                                            "widget %d\n", aw);
     599                                        codec->out_aw = aw;
     600                                } else {
     601                                        ddf_msg(LVL_DEBUG, "Ignoring output "
     602                                            "widget %d\n", aw);
     603                                }
     604
     605                                ddf_msg(LVL_NOTE, "Output widget %d: rates=0x%x formats=0x%x",
    597606                                    aw, rates, formats);
     607                                codec->out_aw_rates = rates;
     608                                codec->out_aw_formats = formats;
    598609                        } else if (awtype == awt_audio_input) {
    599610                                if (codec->in_aw < 0) {
     
    616627                                ddf_msg(LVL_DEBUG, "Input widget %d: rates=0x%x formats=0x%x",
    617628                                    aw, rates, formats);
     629                                codec->in_aw_rates = rates;
     630                                codec->in_aw_formats = formats;
    618631                        }
    619632
     
    644657{
    645658        errno_t rc;
    646         int out_aw;
    647         int i;
    648 
    649         for (i = 0; i < codec->out_aw_num; i++) {
    650                 out_aw = codec->out_aw_list[i];
    651 
    652                 /* Configure converter */
    653 
    654                 ddf_msg(LVL_DEBUG, "Configure output converter format");
    655                 rc = hda_set_converter_fmt(codec, out_aw, stream->fmt);
    656                 if (rc != EOK)
    657                         goto error;
    658 
    659                 ddf_msg(LVL_DEBUG, "Configure output converter stream, channel");
    660                 rc = hda_set_converter_ctl(codec, out_aw, stream->sid, 0);
    661                 if (rc != EOK)
    662                         goto error;
    663         }
     659
     660        /* Configure converter */
     661        ddf_msg(LVL_DEBUG, "Configure output converter format / %d",
     662            codec->out_aw);
     663        rc = hda_set_converter_fmt(codec, codec->out_aw, stream->fmt);
     664        if (rc != EOK)
     665                goto error;
     666
     667        ddf_msg(LVL_DEBUG, "Configure output converter stream, channel");
     668        rc = hda_set_converter_ctl(codec, codec->out_aw, stream->sid, 0);
     669        if (rc != EOK)
     670                goto error;
    664671
    665672        return EOK;
  • uspace/drv/audio/hdaudio/codec.h

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    3939#include "stream.h"
    4040
    41 #define MAX_OUT_AW 256
    42 
    4341typedef struct hda_codec {
    4442        hda_t *hda;
    4543        uint8_t address;
    46         uint8_t out_aw_list[MAX_OUT_AW];
     44        int out_aw;
     45        uint32_t out_aw_rates;
     46        uint32_t out_aw_formats;
    4747        int out_aw_num;
    4848        int out_aw_sel;
    4949        int in_aw;
     50        uint32_t in_aw_rates;
     51        uint32_t in_aw_formats;
    5052} hda_codec_t;
    5153
  • uspace/drv/audio/hdaudio/hdactl.c

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    670670}
    671671
     672static void hda_ctl_check_fifo_error(hda_ctl_t *ctl)
     673{
     674        int i;
     675        uint8_t sts;
     676
     677        /*
     678         * XXX Ideally the interrupt handler would tell us which stream
     679         * has the error.
     680         */
     681
     682        for (i = 0; i < 30; i++) {
     683                sts = hda_reg8_read(&ctl->hda->regs->sdesc[i].sts);
     684                if ((sts & BIT_V(uint8_t, sdsts_fifoe)) != 0 && (sts & 0x80) == 0) {
     685                        ddf_msg(LVL_WARN, "sts[%d] = 0x%hhx\n", i, sts);
     686                        hda_reg8_write(&ctl->hda->regs->sdesc[i].sts,
     687                            BIT_V(uint8_t, sdsts_fifoe));
     688                }
     689        }
     690}
     691
    672692void hda_ctl_interrupt(hda_ctl_t *ctl)
    673693{
     694        ddf_msg(LVL_DEBUG, "hda_ctl_interrupt");
     695        hda_ctl_check_fifo_error(ctl);
    674696        hda_ctl_process_rirb(ctl);
    675697}
  • uspace/drv/audio/hdaudio/hdaudio.c

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    140140                .cmd = CMD_PIO_WRITE_8,
    141141                .addr = NULL, /* sdesc[x].sts */
    142                 .value = 0x4 /* XXX sdesc.sts.BCIS */
     142                .value = BIT_V(uint8_t, sdsts_bcis)
    143143        },
    144144        /* 4 */
  • uspace/drv/audio/hdaudio/pcm_iface.c

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    132132            *channels, *rate, *format);
    133133
    134         if (*channels != 1) {
     134        if (*channels != 2) {
    135135                *channels = 2;
    136136                rc = ELIMIT;
  • uspace/drv/audio/hdaudio/spec/regs.h

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    165165} hda_regs_t;
    166166
     167/** Stream Descriptor Control bits */
    167168typedef enum {
    168169        /** Descriptor Error Interrupt Enable */
     
    177178        sdctl1_srst = 0
    178179} hda_sdesc_ctl1_bits;
     180
     181/** Stream Descriptor Status bits */
     182typedef enum {
     183        /** FIFO Ready */
     184        sdctl1_fifordy = 3,
     185        /** Descriptor Error */
     186        sdsts_dese = 2,
     187        /** FIFO Error */
     188        sdsts_fifoe = 1,
     189        /** Buffer Completion Interrupt Status */
     190        sdsts_bcis = 2
     191} hda_sdesc_sts_bits;
    179192
    180193typedef enum {
  • uspace/drv/audio/hdaudio/stream.c

    r9e9d9bc6 r0d59ea7e  
    11/*
    2  * Copyright (c) 2014 Jiri Svoboda
     2 * Copyright (c) 2022 Jiri Svoboda
    33 * All rights reserved.
    44 *
     
    166166        uint8_t ctl3;
    167167
     168        /* Stream ID */
    168169        ctl3 = (stream->sid << 4);
    169         ctl1 = 0x4;
     170
     171        /* Interrupt on buffer completion */
     172        ctl1 = BIT_V(uint8_t, sdctl1_ioce);
    170173
    171174        sdregs = &stream->hda->regs->sdesc[stream->sdid];
Note: See TracChangeset for help on using the changeset viewer.