alsa: post error message when audio device disappears
authorTim-Philipp Müller <tim@centricular.net>
Sat, 15 Dec 2012 19:36:56 +0000 (19:36 +0000)
committerTim-Philipp Müller <tim@centricular.net>
Sun, 16 Dec 2012 01:00:43 +0000 (01:00 +0000)
Don't loop forever if an USB audio device gets disconnected
while in use. Post an error message instead. This is not
enough yet though, we still need to make the base class
and/or the ring buffer bail out.

https://bugzilla.gnome.org/show_bug.cgi?id=690197

ext/alsa/gstalsasink.c
ext/alsa/gstalsasrc.c

index 27a8bd8..1ef6b91 100644 (file)
@@ -955,7 +955,7 @@ gst_alsasink_close (GstAudioSink * asink)
 static gint
 xrun_recovery (GstAlsaSink * alsa, snd_pcm_t * handle, gint err)
 {
-  GST_DEBUG_OBJECT (alsa, "xrun recovery %d", err);
+  GST_DEBUG_OBJECT (alsa, "xrun recovery %d: %s", err, g_strerror (err));
 
   if (err == -EPIPE) {          /* under-run */
     err = snd_pcm_prepare (handle);
@@ -1019,6 +1019,8 @@ gst_alsasink_write (GstAudioSink * asink, gpointer data, guint length)
       GST_DEBUG_OBJECT (asink, "Write error: %s", snd_strerror (err));
       if (err == -EAGAIN) {
         continue;
+      } else if (err == -ENODEV) {
+        goto device_disappeared;
       } else if (xrun_recovery (alsa, alsa->handle, err) < 0) {
         goto write_error;
       }
@@ -1037,6 +1039,13 @@ write_error:
     GST_ALSA_SINK_UNLOCK (asink);
     return length;              /* skip one period */
   }
+device_disappeared:
+  {
+    GST_ELEMENT_ERROR (asink, RESOURCE, WRITE,
+        (_("Error outputting to audio device. "
+                "The device has been disconnected.")), (NULL));
+    goto write_error;
+  }
 }
 
 static guint
index f97da9b..3b2f4bb 100644 (file)
@@ -805,7 +805,7 @@ gst_alsasrc_close (GstAudioSrc * asrc)
 static gint
 xrun_recovery (GstAlsaSrc * alsa, snd_pcm_t * handle, gint err)
 {
-  GST_DEBUG_OBJECT (alsa, "xrun recovery %d", err);
+  GST_DEBUG_OBJECT (alsa, "xrun recovery %d: %s", err, g_strerror (err));
 
   if (err == -EPIPE) {          /* under-run */
     err = snd_pcm_prepare (handle);
@@ -907,6 +907,8 @@ gst_alsasrc_read (GstAudioSrc * asrc, gpointer data, guint length,
       if (err == -EAGAIN) {
         GST_DEBUG_OBJECT (asrc, "Read error: %s", snd_strerror (err));
         continue;
+      } else if (err == -ENODEV) {
+        goto device_disappeared;
       } else if (xrun_recovery (alsa, alsa->handle, err) < 0) {
         goto read_error;
       }
@@ -929,6 +931,13 @@ read_error:
     GST_ALSA_SRC_UNLOCK (asrc);
     return length;              /* skip one period */
   }
+device_disappeared:
+  {
+    GST_ELEMENT_ERROR (asrc, RESOURCE, READ,
+        (_("Error recording from audio device. "
+                "The device has been disconnected.")), (NULL));
+    goto read_error;
+  }
 }
 
 static guint