Skip to content

Commit 445ecd5

Browse files
committed
ASoC: SOF: Intel: hda: fix error handling during FW boot
If get_stream_with_tag() returns a NULL pointer, the stream prepared in cl_stream_prepare() should still be cleaned up. But, this is impossible because if the tag returned by cl_stream_prepare() is valid, get_stream_with_tag() would theoretically never fail to find a valid stream and there is no need to check the error case. This can be simplified by returning a pointer to struct hdac_ext_stream from cl_stream_prepare() if a stream is successfully prepared or NULL otherwise. If cl_stream_prepare() is successful, it must be cleaned up after FW boot irrespective of whether boot is successful or not. This change renders the function get_stream_with_tag() redundant and can be removed. Signed-off-by: Ranjani Sridharan <ranjani.sridharan@linux.intel.com>
1 parent 427aa3c commit 445ecd5

1 file changed

Lines changed: 19 additions & 54 deletions

File tree

sound/soc/sof/intel/hda-loader.c

Lines changed: 19 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,9 @@
2525
#define HDA_FW_BOOT_ATTEMPTS 3
2626
#define HDA_CL_STREAM_FORMAT 0x40
2727

28-
static int cl_stream_prepare(struct snd_sof_dev *sdev, unsigned int format,
29-
unsigned int size, struct snd_dma_buffer *dmab,
30-
int direction)
28+
static struct hdac_ext_stream *cl_stream_prepare(struct snd_sof_dev *sdev, unsigned int format,
29+
unsigned int size, struct snd_dma_buffer *dmab,
30+
int direction)
3131
{
3232
struct hdac_ext_stream *dsp_stream;
3333
struct hdac_stream *hstream;
@@ -38,7 +38,7 @@ static int cl_stream_prepare(struct snd_sof_dev *sdev, unsigned int format,
3838

3939
if (!dsp_stream) {
4040
dev_err(sdev->dev, "error: no stream available\n");
41-
return -ENODEV;
41+
return ERR_PTR(-ENODEV);
4242
}
4343
hstream = &dsp_stream->hstream;
4444
hstream->substream = NULL;
@@ -69,12 +69,12 @@ static int cl_stream_prepare(struct snd_sof_dev *sdev, unsigned int format,
6969
hda_dsp_stream_spib_config(sdev, dsp_stream, HDA_DSP_SPIB_ENABLE, size);
7070
}
7171

72-
return hstream->stream_tag;
72+
return dsp_stream;
7373

7474
error:
7575
hda_dsp_stream_put(sdev, direction, hstream->stream_tag);
7676
snd_dma_free_pages(dmab);
77-
return ret;
77+
return ERR_PTR(ret);
7878
}
7979

8080
/*
@@ -208,20 +208,6 @@ static int cl_trigger(struct snd_sof_dev *sdev,
208208
}
209209
}
210210

211-
static struct hdac_ext_stream *get_stream_with_tag(struct snd_sof_dev *sdev,
212-
int tag, int direction)
213-
{
214-
struct hdac_bus *bus = sof_to_bus(sdev);
215-
struct hdac_stream *s;
216-
217-
/* get stream with tag */
218-
list_for_each_entry(s, &bus->stream_list, list)
219-
if (s->direction == direction && s->stream_tag == tag)
220-
return stream_to_hdac_ext_stream(s);
221-
222-
return NULL;
223-
}
224-
225211
static int cl_cleanup(struct snd_sof_dev *sdev, struct snd_dma_buffer *dmab,
226212
struct hdac_ext_stream *stream)
227213
{
@@ -300,7 +286,6 @@ int hda_dsp_cl_boot_firmware_iccmax(struct snd_sof_dev *sdev)
300286
struct hdac_bus *bus = sof_to_bus(sdev);
301287
struct firmware stripped_firmware;
302288
int ret, ret1;
303-
int iccmax_tag;
304289
u8 original_gb;
305290

306291
/* save the original LTRP guardband value */
@@ -314,21 +299,14 @@ int hda_dsp_cl_boot_firmware_iccmax(struct snd_sof_dev *sdev)
314299
stripped_firmware.size = plat_data->fw->size - plat_data->fw_offset;
315300

316301
/* prepare capture stream for ICCMAX */
317-
iccmax_tag = cl_stream_prepare(sdev, HDA_CL_STREAM_FORMAT, stripped_firmware.size,
318-
&sdev->dmab_bdl, SNDRV_PCM_STREAM_CAPTURE);
319-
if (iccmax_tag < 0) {
320-
dev_err(sdev->dev, "error: dma prepare for ICCMAX %x\n", iccmax_tag);
321-
return iccmax_tag;
302+
iccmax_stream = cl_stream_prepare(sdev, HDA_CL_STREAM_FORMAT, stripped_firmware.size,
303+
&sdev->dmab_bdl, SNDRV_PCM_STREAM_CAPTURE);
304+
if (IS_ERR(iccmax_stream)) {
305+
dev_err(sdev->dev, "error: dma prepare for ICCMAX stream failed\n");
306+
return PTR_ERR(iccmax_stream);
322307
}
323308

324-
/* get stream with tag */
325-
iccmax_stream = get_stream_with_tag(sdev, iccmax_tag, SNDRV_PCM_STREAM_CAPTURE);
326-
if (!iccmax_stream) {
327-
dev_err(sdev->dev, "error: could not get stream with stream tag %d\n", iccmax_tag);
328-
ret = -ENODEV;
329-
} else {
330-
ret = hda_dsp_cl_boot_firmware(sdev);
331-
}
309+
ret = hda_dsp_cl_boot_firmware(sdev);
332310

333311
/*
334312
* Perform iccmax stream cleanup. This should be done even if firmware loading fails.
@@ -356,7 +334,7 @@ int hda_dsp_cl_boot_firmware(struct snd_sof_dev *sdev)
356334
const struct sof_intel_dsp_desc *chip_info;
357335
struct hdac_ext_stream *stream;
358336
struct firmware stripped_firmware;
359-
int ret, ret1, tag, i;
337+
int ret, ret1, i;
360338

361339
chip_info = desc->chip_info;
362340

@@ -372,23 +350,11 @@ int hda_dsp_cl_boot_firmware(struct snd_sof_dev *sdev)
372350
init_waitqueue_head(&sdev->boot_wait);
373351

374352
/* prepare DMA for code loader stream */
375-
tag = cl_stream_prepare(sdev, HDA_CL_STREAM_FORMAT, stripped_firmware.size,
376-
&sdev->dmab, SNDRV_PCM_STREAM_PLAYBACK);
377-
378-
if (tag < 0) {
379-
dev_err(sdev->dev, "error: dma prepare for fw loading err: %x\n",
380-
tag);
381-
return tag;
382-
}
383-
384-
/* get stream with tag */
385-
stream = get_stream_with_tag(sdev, tag, SNDRV_PCM_STREAM_PLAYBACK);
386-
if (!stream) {
387-
dev_err(sdev->dev,
388-
"error: could not get stream with stream tag %d\n",
389-
tag);
390-
ret = -ENODEV;
391-
goto err;
353+
stream = cl_stream_prepare(sdev, HDA_CL_STREAM_FORMAT, stripped_firmware.size,
354+
&sdev->dmab, SNDRV_PCM_STREAM_PLAYBACK);
355+
if (IS_ERR(stream)) {
356+
dev_err(sdev->dev, "error: dma prepare for fw loading failed\n");
357+
return PTR_ERR(stream);
392358
}
393359

394360
memcpy(sdev->dmab.area, stripped_firmware.data,
@@ -399,7 +365,7 @@ int hda_dsp_cl_boot_firmware(struct snd_sof_dev *sdev)
399365
dev_dbg(sdev->dev,
400366
"Attempting iteration %d of Core En/ROM load...\n", i);
401367

402-
ret = cl_dsp_init(sdev, tag, i + 1);
368+
ret = cl_dsp_init(sdev, stream->hstream.stream_tag, i + 1);
403369

404370
/* don't retry anymore if successful */
405371
if (!ret)
@@ -468,7 +434,6 @@ int hda_dsp_cl_boot_firmware(struct snd_sof_dev *sdev)
468434
return chip_info->init_core_mask;
469435

470436
/* dump dsp registers and disable DSP upon error */
471-
err:
472437
hda_dsp_dump(sdev, SOF_DBG_REGS | SOF_DBG_PCI | SOF_DBG_MBOX);
473438

474439
/* disable DSP */

0 commit comments

Comments
 (0)