int stream_tag;
        int ret;
 
-       link_dev = hda_link_stream_assign(bus, substream);
-       if (!link_dev)
-               return -EBUSY;
+       /* get stored dma data if resuming from system suspend */
+       link_dev = snd_soc_dai_get_dma_data(dai, substream);
+       if (!link_dev) {
+               link_dev = hda_link_stream_assign(bus, substream);
+               if (!link_dev)
+                       return -EBUSY;
+       }
 
        stream_tag = hdac_stream(link_dev)->stream_tag;
 
        case SNDRV_PCM_TRIGGER_SUSPEND:
        case SNDRV_PCM_TRIGGER_STOP:
                /*
-                * clear and release link DMA channel. It will be assigned when
+                * clear link DMA channel. It will be assigned when
                 * hw_params is set up again after resume.
                 */
                ret = hda_link_config_ipc(hda_stream, dai->name,
                        return ret;
                stream_tag = hdac_stream(link_dev)->stream_tag;
                snd_hdac_ext_link_clear_stream_id(link, stream_tag);
-               snd_hdac_ext_stream_release(link_dev,
-                                           HDAC_EXT_STREAM_TYPE_LINK);
                link_dev->link_prepared = 0;
 
                /* fallthrough */
 
        stream_tag = hdac_stream(link_dev)->stream_tag;
        snd_hdac_ext_link_clear_stream_id(link, stream_tag);
+       snd_soc_dai_set_dma_data(dai, substream, NULL);
        snd_hdac_ext_stream_release(link_dev, HDAC_EXT_STREAM_TYPE_LINK);
        link_dev->link_prepared = 0;
 
 
                stream = stream_to_hdac_ext_stream(s);
 
                /*
-                * clear and release stream. This should already be taken care
-                * for running streams when the SUSPEND trigger is called.
-                * But paused streams do not get suspended, so this needs to be
-                * done explicitly during suspend.
+                * clear stream. This should already be taken care for running
+                * streams when the SUSPEND trigger is called. But paused
+                * streams do not get suspended, so this needs to be done
+                * explicitly during suspend.
                 */
                if (stream->link_substream) {
                        rtd = snd_pcm_substream_chip(stream->link_substream);
                                return -EINVAL;
                        stream_tag = hdac_stream(stream)->stream_tag;
                        snd_hdac_ext_link_clear_stream_id(link, stream_tag);
-                       snd_hdac_ext_stream_release(stream,
-                                                   HDAC_EXT_STREAM_TYPE_LINK);
                        stream->link_prepared = 0;
                }
        }