Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion sound/soc/sof/intel/hda-loader.c
Original file line number Diff line number Diff line change
Expand Up @@ -249,7 +249,7 @@ int hda_cl_trigger(struct device *dev, struct hdac_ext_stream *hext_stream, int
hstream->running = true;
return 0;
default:
return hda_dsp_stream_trigger(sdev, hext_stream, cmd);
return hda_dsp_stream_trigger(sdev, hext_stream, cmd, false);
}
}
EXPORT_SYMBOL_NS(hda_cl_trigger, SND_SOC_SOF_INTEL_HDA_COMMON);
Expand Down
12 changes: 11 additions & 1 deletion sound/soc/sof/intel/hda-pcm.c
Original file line number Diff line number Diff line change
Expand Up @@ -172,8 +172,18 @@ int hda_dsp_pcm_trigger(struct snd_sof_dev *sdev,
{
struct hdac_stream *hstream = substream->runtime->private_data;
struct hdac_ext_stream *hext_stream = stream_to_hdac_ext_stream(hstream);
struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct snd_soc_component *scomp = sdev->component;
struct snd_sof_pcm *spcm;

spcm = snd_sof_find_spcm_dai(scomp, rtd);
if (!spcm) {
dev_warn_ratelimited(sdev->dev, "warn: can't find PCM with DAI ID %d\n",
rtd->dai_link->id);
return 0;
}

return hda_dsp_stream_trigger(sdev, hext_stream, cmd);
return hda_dsp_stream_trigger(sdev, hext_stream, cmd, spcm->use_chain);
}
EXPORT_SYMBOL_NS(hda_dsp_pcm_trigger, SND_SOC_SOF_INTEL_HDA_COMMON);

Expand Down
2 changes: 1 addition & 1 deletion sound/soc/sof/intel/hda-probes.c
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ static int hda_probes_compr_trigger(struct sof_client_dev *cdev,
struct hdac_ext_stream *hext_stream = hda_compr_get_stream(cstream);
struct snd_sof_dev *sdev = sof_client_dev_to_sof_dev(cdev);

return hda_dsp_stream_trigger(sdev, hext_stream, cmd);
return hda_dsp_stream_trigger(sdev, hext_stream, cmd, false);
}

static int hda_probes_compr_pointer(struct sof_client_dev *cdev,
Expand Down
7 changes: 4 additions & 3 deletions sound/soc/sof/intel/hda-stream.c
Original file line number Diff line number Diff line change
Expand Up @@ -331,7 +331,7 @@ static int hda_dsp_stream_reset(struct snd_sof_dev *sdev, struct hdac_stream *hs
}

int hda_dsp_stream_trigger(struct snd_sof_dev *sdev,
struct hdac_ext_stream *hext_stream, int cmd)
struct hdac_ext_stream *hext_stream, int cmd, bool use_chain)
{
struct hdac_stream *hstream = &hext_stream->hstream;
int sd_offset = SOF_STREAM_SD_OFFSET(hstream);
Expand All @@ -342,7 +342,7 @@ int hda_dsp_stream_trigger(struct snd_sof_dev *sdev,
/* cmd must be for audio stream */
switch (cmd) {
case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
if (!sdev->dspless_mode_selected)
if (!use_chain && !sdev->dspless_mode_selected)
break;
fallthrough;
case SNDRV_PCM_TRIGGER_START:
Expand Down Expand Up @@ -372,11 +372,12 @@ int hda_dsp_stream_trigger(struct snd_sof_dev *sdev,

break;
case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
if (!sdev->dspless_mode_selected)
if ((!use_chain && !sdev->dspless_mode_selected))
break;
fallthrough;
case SNDRV_PCM_TRIGGER_SUSPEND:
case SNDRV_PCM_TRIGGER_STOP:
dev_dbg(sdev->dev, "hda_stream_trigger stop cmd %d\n", cmd);
snd_sof_dsp_update_bits(sdev, HDA_DSP_HDA_BAR,
sd_offset,
SOF_HDA_SD_CTL_DMA_START |
Expand Down
2 changes: 1 addition & 1 deletion sound/soc/sof/intel/hda-trace.c
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,6 @@ int hda_dsp_trace_trigger(struct snd_sof_dev *sdev, int cmd)
{
struct sof_intel_hda_dev *hda = sdev->pdata->hw_pdata;

return hda_dsp_stream_trigger(sdev, hda->dtrace_stream, cmd);
return hda_dsp_stream_trigger(sdev, hda->dtrace_stream, cmd, false);
}
EXPORT_SYMBOL_NS(hda_dsp_trace_trigger, SND_SOC_SOF_INTEL_HDA_COMMON);
2 changes: 1 addition & 1 deletion sound/soc/sof/intel/hda.h
Original file line number Diff line number Diff line change
Expand Up @@ -656,7 +656,7 @@ int hda_dsp_iccmax_stream_hw_params(struct snd_sof_dev *sdev,
struct snd_dma_buffer *dmab,
struct snd_pcm_hw_params *params);
int hda_dsp_stream_trigger(struct snd_sof_dev *sdev,
struct hdac_ext_stream *hext_stream, int cmd);
struct hdac_ext_stream *hext_stream, int cmd, bool use_chain);
irqreturn_t hda_dsp_stream_threaded_handler(int irq, void *context);
int hda_dsp_stream_setup_bdl(struct snd_sof_dev *sdev,
struct snd_dma_buffer *dmab,
Expand Down
16 changes: 16 additions & 0 deletions sound/soc/sof/ipc4-pcm.c
Original file line number Diff line number Diff line change
Expand Up @@ -807,13 +807,29 @@ static int sof_ipc4_pcm_hw_params(struct snd_soc_component *component,
{
struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);
struct snd_sof_pcm_stream_pipeline_list *pipeline_list;
struct sof_ipc4_timestamp_info *time_info;
struct snd_sof_widget *pipe_widget;
struct sof_ipc4_pipeline *pipeline;
struct snd_sof_pipeline *spipe;
struct snd_sof_pcm *spcm;

spcm = snd_sof_find_spcm_dai(component, rtd);
if (!spcm)
return -EINVAL;

pipeline_list = &spcm->stream[substream->stream].pipeline_list;

/* nothing to trigger if the list is empty */
if (pipeline_list->pipelines && pipeline_list->count) {
spipe = pipeline_list->pipelines[0];
pipe_widget = spipe->pipe_widget;
pipeline = pipe_widget->private;

if (pipeline->use_chain_dma)
spcm->use_chain = true;
}

time_info = spcm->stream[substream->stream].private;
/* delay calculation is not supported by current fw_reg ABI */
if (!time_info)
Expand Down
8 changes: 5 additions & 3 deletions sound/soc/sof/pcm.c
Original file line number Diff line number Diff line change
Expand Up @@ -304,7 +304,8 @@ static int sof_pcm_trigger(struct snd_soc_component *component,

switch (cmd) {
case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
ipc_first = true;
if (!spcm->use_chain)
ipc_first = true;
break;
case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
if (pcm_ops && pcm_ops->ipc_first_on_start)
Expand Down Expand Up @@ -343,7 +344,8 @@ static int sof_pcm_trigger(struct snd_soc_component *component,

fallthrough;
case SNDRV_PCM_TRIGGER_STOP:
ipc_first = true;
if (!spcm->use_chain)
ipc_first = true;
if (pcm_ops && pcm_ops->reset_hw_params_during_stop)
reset_hw_params = true;
break;
Expand All @@ -369,7 +371,7 @@ static int sof_pcm_trigger(struct snd_soc_component *component,
case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
case SNDRV_PCM_TRIGGER_STOP:
/* invoke platform trigger to stop DMA even if pcm_ops isn't set or if it failed */
if (!pcm_ops || !pcm_ops->platform_stop_during_hw_free)
if (spcm->use_chain || !pcm_ops || !pcm_ops->platform_stop_during_hw_free)
snd_sof_pcm_platform_trigger(sdev, substream, cmd);
break;
default:
Expand Down
1 change: 1 addition & 0 deletions sound/soc/sof/sof-audio.h
Original file line number Diff line number Diff line change
Expand Up @@ -341,6 +341,7 @@ struct snd_sof_pcm {
struct list_head list; /* list in sdev pcm list */
struct snd_pcm_hw_params params[2];
bool prepared[2]; /* PCM_PARAMS set successfully */
bool use_chain;
};

struct snd_sof_led_control {
Expand Down