diff options
Diffstat (limited to 'src/main.c')
-rw-r--r-- | src/main.c | 169 |
1 files changed, 116 insertions, 53 deletions
diff --git a/src/main.c b/src/main.c index a500e2934..f7e7ba778 100644 --- a/src/main.c +++ b/src/main.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2003-2010 The Music Player Daemon Project + * Copyright (C) 2003-2011 The Music Player Daemon Project * http://www.musicpd.org * * This program is free software; you can redistribute it and/or modify @@ -20,7 +20,9 @@ #include "config.h" #include "main.h" #include "daemon.h" +#include "io_thread.h" #include "client.h" +#include "client_idle.h" #include "idle.h" #include "command.h" #include "playlist.h" @@ -37,11 +39,12 @@ #include "player_control.h" #include "stats.h" #include "sig_handlers.h" -#include "audio.h" +#include "audio_config.h" #include "output_all.h" #include "volume.h" #include "log.h" #include "permission.h" +#include "pcm_resample.h" #include "replay_gain_config.h" #include "decoder_list.h" #include "input_init.h" @@ -51,8 +54,6 @@ #include "dbUtils.h" #include "zeroconf.h" #include "event_pipe.h" -#include "dirvec.h" -#include "songvec.h" #include "tag_pool.h" #include "mpd_error.h" @@ -94,31 +95,56 @@ GMainLoop *main_loop; GCond *main_cond; -static void -glue_daemonize_init(const struct options *options) +struct player_control *global_player_control; + +static bool +glue_daemonize_init(const struct options *options, GError **error_r) { + GError *error = NULL; + + char *pid_file = config_dup_path(CONF_PID_FILE, &error); + if (pid_file == NULL && error != NULL) { + g_propagate_error(error_r, error); + return false; + } + daemonize_init(config_get_string(CONF_USER, NULL), config_get_string(CONF_GROUP, NULL), - config_get_path(CONF_PID_FILE)); + pid_file); + g_free(pid_file); if (options->kill) daemonize_kill(); + + return true; } -static void -glue_mapper_init(void) +static bool +glue_mapper_init(GError **error_r) { - const char *music_dir, *playlist_dir; + GError *error = NULL; + char *music_dir = config_dup_path(CONF_MUSIC_DIR, &error); + if (music_dir == NULL && error != NULL) { + g_propagate_error(error_r, error); + return false; + } + + char *playlist_dir = config_dup_path(CONF_PLAYLIST_DIR, &error); + if (playlist_dir == NULL && error != NULL) { + g_propagate_error(error_r, error); + return false; + } - music_dir = config_get_path(CONF_MUSIC_DIR); #if GLIB_CHECK_VERSION(2,14,0) if (music_dir == NULL) - music_dir = g_get_user_special_dir(G_USER_DIRECTORY_MUSIC); + music_dir = g_strdup(g_get_user_special_dir(G_USER_DIRECTORY_MUSIC)); #endif - playlist_dir = config_get_path(CONF_PLAYLIST_DIR); - mapper_init(music_dir, playlist_dir); + + g_free(music_dir); + g_free(playlist_dir); + return true; } /** @@ -129,38 +155,31 @@ glue_mapper_init(void) static bool glue_db_init_and_load(void) { - const char *path = config_get_path(CONF_DB_FILE); - bool ret; + const struct config_param *path = config_get_param(CONF_DB_FILE); + GError *error = NULL; + bool ret; if (!mapper_has_music_directory()) { if (path != NULL) g_message("Found " CONF_DB_FILE " setting without " CONF_MUSIC_DIR " - disabling database"); - db_init(NULL); + db_init(NULL, NULL); return true; } if (path == NULL) MPD_ERROR(CONF_DB_FILE " setting missing"); - db_init(path); + if (!db_init(path, &error)) + MPD_ERROR("%s", error->message); ret = db_load(&error); - if (!ret) { - g_warning("Failed to load database: %s", error->message); - g_error_free(error); - - if (!db_check()) - exit(EXIT_FAILURE); - - db_clear(); - - /* run database update after daemonization */ - return false; - } + if (!ret) + MPD_ERROR("%s", error->message); - return true; + /* run database update after daemonization? */ + return db_exists(); } /** @@ -170,20 +189,34 @@ static void glue_sticker_init(void) { #ifdef ENABLE_SQLITE - bool success; GError *error = NULL; + char *sticker_file = config_dup_path(CONF_STICKER_FILE, &error); + if (sticker_file == NULL && error != NULL) + MPD_ERROR("%s", error->message); - success = sticker_global_init(config_get_path(CONF_STICKER_FILE), - &error); - if (!success) + if (!sticker_global_init(config_get_string(CONF_STICKER_FILE, NULL), + &error)) MPD_ERROR("%s", error->message); + + g_free(sticker_file); #endif } -static void -glue_state_file_init(void) +static bool +glue_state_file_init(GError **error_r) { - state_file_init(config_get_path(CONF_STATE_FILE)); + GError *error = NULL; + + char *path = config_dup_path(CONF_STATE_FILE, &error); + if (path == NULL && error != NULL) { + g_propagate_error(error_r, error); + return false; + } + + state_file_init(path, global_player_control); + g_free(path); + + return true; } /** @@ -254,7 +287,7 @@ initialize_decoder_and_player(void) if (buffered_before_play > buffered_chunks) buffered_before_play = buffered_chunks; - pc_init(buffered_chunks, buffered_before_play); + global_player_control = pc_new(buffered_chunks, buffered_before_play); } /** @@ -308,10 +341,9 @@ int mpd_main(int argc, char *argv[]) /* enable GLib's thread safety code */ g_thread_init(NULL); + io_thread_init(); winsock_init(); idle_init(); - dirvec_init(); - songvec_init(); tag_pool_init(); config_global_init(); @@ -322,11 +354,20 @@ int mpd_main(int argc, char *argv[]) return EXIT_FAILURE; } - glue_daemonize_init(&options); + if (!glue_daemonize_init(&options, &error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } stats_global_init(); tag_lib_init(); - log_init(options.verbose, options.log_stderr); + + if (!log_init(options.verbose, options.log_stderr, &error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } success = listen_global_init(&error); if (!success) { @@ -346,13 +387,26 @@ int mpd_main(int argc, char *argv[]) event_pipe_register(PIPE_EVENT_SHUTDOWN, shutdown_event_emitted); path_global_init(); - glue_mapper_init(); + + if (!glue_mapper_init(&error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } + initPermissions(); playlist_global_init(); spl_global_init(); #ifdef ENABLE_ARCHIVE archive_plugin_init_all(); #endif + + if (!pcm_resample_global_init(&error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } + decoder_plugin_init_all(); update_global_init(); @@ -364,7 +418,7 @@ int mpd_main(int argc, char *argv[]) initialize_decoder_and_player(); volume_init(); initAudioConfig(); - audio_output_all_init(); + audio_output_all_init(global_player_control); client_manager_init(); replay_gain_global_init(); @@ -382,9 +436,15 @@ int mpd_main(int argc, char *argv[]) initSigHandlers(); + if (!io_thread_start(&error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } + initZeroconf(); - player_create(); + player_create(global_player_control); if (create_db) { /* the database failed to load: recreate the @@ -394,7 +454,11 @@ int mpd_main(int argc, char *argv[]) MPD_ERROR("directory update failed"); } - glue_state_file_init(); + if (!glue_state_file_init(&error)) { + g_warning("%s", error->message); + g_error_free(error); + return EXIT_FAILURE; + } success = config_get_bool(CONF_AUTO_UPDATE, false); #ifdef ENABLE_INOTIFY @@ -410,7 +474,7 @@ int mpd_main(int argc, char *argv[]) /* enable all audio outputs (if not already done by playlist_state_restore() */ - pc_update_audio(); + pc_update_audio(global_player_control); #ifdef WIN32 win32_app_started(); @@ -431,8 +495,8 @@ int mpd_main(int argc, char *argv[]) mpd_inotify_finish(); #endif - state_file_finish(); - pc_kill(); + state_file_finish(global_player_control); + pc_kill(global_player_control); finishZeroconf(); client_manager_deinit(); listen_global_finish(); @@ -457,7 +521,7 @@ int mpd_main(int argc, char *argv[]) mapper_finish(); path_global_finish(); finishPermissions(); - pc_deinit(); + pc_free(global_player_control); command_finish(); update_global_finish(); decoder_plugin_deinit_all(); @@ -466,10 +530,9 @@ int mpd_main(int argc, char *argv[]) #endif config_global_finish(); tag_pool_deinit(); - songvec_deinit(); - dirvec_deinit(); idle_deinit(); stats_global_finish(); + io_thread_deinit(); daemonize_finish(); #ifdef WIN32 WSACleanup(); |