diff --git a/mopidy/core.py b/mopidy/core.py index e8cc1897..118ed99a 100644 --- a/mopidy/core.py +++ b/mopidy/core.py @@ -24,7 +24,7 @@ from mopidy.utils import get_class from mopidy.utils.log import setup_logging from mopidy.utils.path import get_or_create_folder, get_or_create_file from mopidy.utils.process import (GObjectEventThread, exit_handler, - stop_all_actors) + stop_remaining_actors, stop_actors_by_class) from mopidy.utils.settings import list_settings_optparse_callback logger = logging.getLogger('mopidy.core') @@ -49,7 +49,11 @@ def main(): except Exception as e: logger.exception(e) finally: - stop_all_actors() + stop_frontends() + stop_backend() + stop_mixer() + stop_gstreamer() + stop_remaining_actors() def parse_options(): parser = optparse.OptionParser(version=u'Mopidy %s' % get_version()) @@ -88,15 +92,31 @@ def setup_gobject_loop(): def setup_gstreamer(): GStreamer.start() +def stop_gstreamer(): + stop_actors_by_class(GStreamer) + def setup_mixer(): get_class(settings.MIXER).start() +def stop_mixer(): + stop_actors_by_class(get_class(settings.MIXER)) + def setup_backend(): get_class(settings.BACKENDS[0]).start() +def stop_backend(): + stop_actors_by_class(get_class(settings.BACKENDS[0])) + def setup_frontends(): for frontend_class_name in settings.FRONTENDS: try: get_class(frontend_class_name).start() except OptionalDependencyError as e: logger.info(u'Disabled: %s (%s)', frontend_class_name, e) + +def stop_frontends(): + for frontend_class_name in settings.FRONTENDS: + try: + stop_actors_by_class(get_class(frontend_class_name)) + except OptionalDependencyError as e: + pass diff --git a/mopidy/utils/process.py b/mopidy/utils/process.py index c1d1c9f5..734b20c5 100644 --- a/mopidy/utils/process.py +++ b/mopidy/utils/process.py @@ -25,9 +25,17 @@ def exit_handler(signum, frame): logger.info(u'Got %s signal', signals[signum]) exit_process() -def stop_all_actors(): +def stop_actors_by_class(klass): + actors = ActorRegistry.get_by_class(klass) + logger.debug('Stopping %d instance(s) of %s', len(actors), klass.__name__) + for actor in actors: + actor.stop() + +def stop_remaining_actors(): num_actors = len(ActorRegistry.get_all()) while num_actors: + logger.error( + u'There are actor threads still running, this is probably a bug') logger.debug(u'Seeing %d actor and %d non-actor thread(s): %s', num_actors, threading.active_count() - num_actors, ', '.join([t.name for t in threading.enumerate()]))