Skip to content

SOF_HDA: need to clean-up exit sequences #299

Closed

Description

@plbossart

we are missing a lot of hdac library calls, such as snd_hdac_ext_bus_device_remove(bus), both in the .remove calls as well as in error handling.

The goal is to release ALL the resources allocated, no exceptions. This will be mandatory for upstream.

Activity

  1. added
    bugSomething isn't working
    P1Blocker bugs or important features
    and removed
    bugSomething isn't working
    on Nov 26, 2018
  2. bardliao commented on Nov 27, 2018

    @bardliao
    Collaborator

    @plbossart It seems we didn't use hdac stream control APIs. I think that's why we don't use snd_hdac_ext_stop_streams(). And hda_dsp_stream_free() do things similar to snd_hdac_stream_free_all() + snd_hdac_bus_free_stream_pages()

    snd_hdac_bus_free_stream_pages()
                    bus->io_ops->dma_free_pages(bus, &s->bdl);
                    bus->io_ops->dma_free_pages(bus, &bus->rb);
                    bus->io_ops->dma_free_pages(bus, &bus->posbuf);
    
    snd_hdac_stream_free_all()
                    snd_hdac_ext_stream_decouple(bus, stream, false);
                    list_del(&s->list);
                    kfree(stream);
    
    hda_dsp_stream_free()
                    snd_dma_free_pages(&bus->posbuf);
                    snd_dma_free_pages(&bus->rb);
                    snd_dma_free_pages(&s->bdl);
    		list_del(&s->list);
    		devm_kfree(sdev->dev, stream);
    

    The only thing we missed here is snd_hdac_ext_stream_decouple(). But I don't know if we need to do it or it is done in somewhere else.

    void snd_hdac_ext_stream_decouple(struct hdac_bus *bus,
                                    struct hdac_ext_stream *stream, bool decouple)
    {
            struct hdac_stream *hstream = &stream->hstream;
            u32 val;
            int mask = AZX_PPCTL_PROCEN(hstream->index);
    
            spin_lock_irq(&bus->reg_lock);
            val = readw(bus->ppcap + AZX_REG_PP_PPCTL) & mask;
    
            if (decouple && !val)
                    snd_hdac_updatel(bus->ppcap, AZX_REG_PP_PPCTL, mask, mask);
            else if (!decouple && val)
                    snd_hdac_updatel(bus->ppcap, AZX_REG_PP_PPCTL, mask, 0);
    
            stream->decoupled = decouple;
            spin_unlock_irq(&bus->reg_lock);
    }
    

    snd_hdac_ext_bus_exit() and snd_hdac_link_free_all() are add in #311

  3. plbossart commented on Nov 27, 2018

    @plbossart
    MemberAuthor

    snd_hdac_ext_stream_decouple() is used in hda-dai.c

    snd_hdac_ext_stream_decouple(bus, stream, false);

    I have absolutely no idea why it's only called on TRIGGER_SUSPEND, makes no sense to me.

  4. bardliao commented on Dec 3, 2018

    @bardliao
    Collaborator

    @plbossart I just checked snd_hdac_ext_stream_decouple(). I believe that we need to call snd_hdac_ext_stream_decouple(false) in hda_dsp_stream_free(). I didn't get SNDRV_PCM_TRIGGER_SUSPEND cmd even when the system is suspended. And hdac_ext_link_stream_assign() will call snd_hdac_ext_stream_decouple(true) when system boots up.
    I will send a PR for it tomorrow.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

P1Blocker bugs or important featuresenhancementNew feature or request

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions