diff --git a/modules/module-pipewire.c b/modules/module-pipewire.c
index 986bd5dd3ed8143aba689485445444488b7be4ed..fbcf04fcc552ae97d10006cde8fdb68735c8a2d6 100644
--- a/modules/module-pipewire.c
+++ b/modules/module-pipewire.c
@@ -110,14 +110,24 @@ on_remote_state_changed (void *d, enum pw_remote_state old_state,
         &data->registry_listener, &registry_events, data);
     break;
 
-  case PW_REMOTE_STATE_UNCONNECTED:
-    // TODO quit wireplumber
+  case PW_REMOTE_STATE_UNCONNECTED: {
+    g_autoptr (WpCore) core = wp_module_get_core (data->module);
+    if (core) {
+      g_message ("disconnected from PipeWire");
+      g_main_loop_quit (wp_core_get_global (core,
+              g_quark_from_string ("main-loop")));
+    }
     break;
-
-  case PW_REMOTE_STATE_ERROR:
-    // TODO quit wireplumber
+  }
+  case PW_REMOTE_STATE_ERROR: {
+    g_autoptr (WpCore) core = wp_module_get_core (data->module);
+    if (core) {
+      g_message ("PipeWire remote error: %s", error);
+      g_main_loop_quit (wp_core_get_global (core,
+              g_quark_from_string ("main-loop")));
+    }
     break;
-
+  }
   default:
     break;
   }
diff --git a/src/main.c b/src/main.c
index 5c70c7ce53c21c9cb056423ed313f7e36cee7f97..2774002106f339b755a65f9bf748756d520840ab 100644
--- a/src/main.c
+++ b/src/main.c
@@ -197,6 +197,8 @@ main (gint argc, gchar **argv)
 
   /* init main loop */
   data.loop = loop = g_main_loop_new (NULL, FALSE);
+  wp_core_register_global (core, g_quark_from_static_string ("main-loop"),
+      g_main_loop_ref (loop), (GDestroyNotify) g_main_loop_unref);
 
   /* watch for exit signals */