aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Makefile.am1
-rw-r--r--src/Instance.cxx14
-rw-r--r--src/Instance.hxx10
-rw-r--r--src/Main.cxx18
-rw-r--r--src/PlaylistPrint.cxx5
-rw-r--r--src/SongLoader.cxx7
-rw-r--r--src/SongLoader.hxx13
-rw-r--r--src/StateFile.cxx8
-rw-r--r--src/Stats.cxx7
-rw-r--r--src/client/Client.cxx12
-rw-r--r--src/client/Client.hxx6
-rw-r--r--src/command/DatabaseCommands.cxx2
-rw-r--r--src/command/PlaylistCommands.cxx3
-rw-r--r--src/command/StickerCommands.cxx5
-rw-r--r--src/db/DatabaseGlue.cxx91
-rw-r--r--src/db/DatabaseGlue.hxx28
-rw-r--r--src/db/DatabasePrint.cxx7
-rw-r--r--src/db/DatabaseQueue.cxx3
-rw-r--r--src/db/DatabaseSimple.hxx4
-rw-r--r--src/db/plugins/SimpleDatabasePlugin.hxx3
-rw-r--r--test/test_translate_song.cxx11
21 files changed, 106 insertions, 152 deletions
diff --git a/Makefile.am b/Makefile.am
index 6f2e9e388..5e3f3b260 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -205,7 +205,6 @@ src_mpd_SOURCES += \
src/db/Uri.hxx \
src/db/Directory.cxx src/db/Directory.hxx \
src/db/DirectorySave.cxx src/db/DirectorySave.hxx \
- src/db/DatabaseSimple.hxx \
src/db/DatabaseGlue.cxx src/db/DatabaseGlue.hxx \
src/db/DatabaseSong.cxx src/db/DatabaseSong.hxx \
src/db/DatabasePrint.cxx src/db/DatabasePrint.hxx \
diff --git a/src/Instance.cxx b/src/Instance.cxx
index 229af0268..42d62ac7c 100644
--- a/src/Instance.cxx
+++ b/src/Instance.cxx
@@ -22,10 +22,18 @@
#include "Partition.hxx"
#include "Idle.hxx"
#include "Stats.hxx"
-#include "db/DatabaseGlue.hxx"
+#include "db/DatabaseError.hxx"
#ifdef ENABLE_DATABASE
+Database *
+Instance::GetDatabase(Error &error)
+{
+ if (database == nullptr)
+ error.Set(db_domain, DB_DISABLED, "No database");
+ return database;
+}
+
void
Instance::DeleteSong(const char *uri)
{
@@ -35,8 +43,10 @@ Instance::DeleteSong(const char *uri)
void
Instance::DatabaseModified()
{
+ assert(database != nullptr);
+
stats_invalidate();
- partition->DatabaseModified(*GetDatabase());
+ partition->DatabaseModified(*database);
idle_add(IDLE_DATABASE);
}
diff --git a/src/Instance.hxx b/src/Instance.hxx
index ea60072cb..9e3f92458 100644
--- a/src/Instance.hxx
+++ b/src/Instance.hxx
@@ -30,9 +30,11 @@ class NeighborGlue;
#ifdef ENABLE_DATABASE
#include "db/DatabaseListener.hxx"
+class Database;
class UpdateService;
#endif
+class Error;
class ClientList;
struct Partition;
@@ -55,6 +57,8 @@ struct Instance final
#endif
#ifdef ENABLE_DATABASE
+ Database *database;
+
UpdateService *update;
#endif
@@ -69,6 +73,12 @@ struct Instance final
}
#ifdef ENABLE_DATABASE
+ /**
+ * Returns the global #Database instance. May return nullptr
+ * if this MPD configuration has no database (no
+ * music_directory was configured).
+ */
+ Database *GetDatabase(Error &error);
void DeleteSong(const char *uri);
diff --git a/src/Main.cxx b/src/Main.cxx
index d7d13e2b3..8a5ed7506 100644
--- a/src/Main.cxx
+++ b/src/Main.cxx
@@ -195,22 +195,26 @@ glue_db_init_and_load(void)
if (param == nullptr)
return true;
+ bool is_simple;
Error error;
- if (!DatabaseGlobalInit(*main_loop, *instance, *param, error))
+ instance->database = DatabaseGlobalInit(*main_loop, *instance, *param,
+ is_simple, error);
+ if (instance->database == nullptr)
FatalError(error);
delete allocated;
- if (!DatabaseGlobalOpen(error))
+ if (!instance->database->Open(error))
FatalError(error);
- if (!db_is_simple())
+ if (!is_simple)
return true;
- instance->update = new UpdateService(*main_loop, db_get_simple());
+ SimpleDatabase &db = *(SimpleDatabase *)instance->database;
+ instance->update = new UpdateService(*main_loop, db);
/* run database update after daemonization? */
- return db_exists();
+ return db.FileExists();
}
#endif
@@ -577,8 +581,8 @@ int mpd_main(int argc, char *argv[])
#ifdef ENABLE_DATABASE
delete instance->update;
-
- DatabaseGlobalDeinit();
+ instance->database->Close();
+ delete instance->database;
#endif
#ifdef ENABLE_SQLITE
diff --git a/src/PlaylistPrint.cxx b/src/PlaylistPrint.cxx
index 377da25c9..2e29ac6a2 100644
--- a/src/PlaylistPrint.cxx
+++ b/src/PlaylistPrint.cxx
@@ -23,7 +23,8 @@
#include "Playlist.hxx"
#include "queue/QueuePrint.hxx"
#include "SongPrint.hxx"
-#include "db/DatabaseGlue.hxx"
+#include "Partition.hxx"
+#include "Instance.hxx"
#include "db/DatabasePlugin.hxx"
#include "client/Client.hxx"
#include "input/InputStream.hxx"
@@ -115,7 +116,7 @@ playlist_print_changes_position(Client &client,
static bool
PrintSongDetails(Client &client, const char *uri_utf8)
{
- const Database *db = GetDatabase();
+ const Database *db = client.partition.instance.database;
if (db == nullptr)
return false;
diff --git a/src/SongLoader.cxx b/src/SongLoader.cxx
index 90df42824..08aa01296 100644
--- a/src/SongLoader.cxx
+++ b/src/SongLoader.cxx
@@ -33,6 +33,13 @@
#include <assert.h>
#include <string.h>
+#ifdef ENABLE_DATABASE
+
+SongLoader::SongLoader(const Client &_client)
+ :client(&_client), db(_client.GetDatabase(IgnoreError())) {}
+
+#endif
+
DetachedSong *
SongLoader::LoadFile(const char *path_utf8, Error &error) const
{
diff --git a/src/SongLoader.hxx b/src/SongLoader.hxx
index 997c0fb18..9914db8e6 100644
--- a/src/SongLoader.hxx
+++ b/src/SongLoader.hxx
@@ -45,19 +45,16 @@ class SongLoader {
public:
#ifdef ENABLE_DATABASE
- SongLoader(const Client *_client, const Database *_db=nullptr)
- :client(_client), db(_db) {}
- explicit SongLoader(const Client &_client)
- :client(&_client), db(nullptr) {}
+ explicit SongLoader(const Client &_client);
explicit SongLoader(const Database *_db)
:client(nullptr), db(_db) {}
- explicit SongLoader(std::nullptr_t)
- :client(nullptr), db(nullptr) {}
+ explicit SongLoader(const Client &_client, const Database *_db)
+ :client(&_client), db(_db) {}
#else
explicit SongLoader(const Client &_client)
:client(&_client) {}
- explicit SongLoader(const Client *_client)
- :client(_client) {}
+ explicit SongLoader(std::nullptr_t)
+ :client(nullptr) {}
#endif
gcc_nonnull_all
diff --git a/src/StateFile.cxx b/src/StateFile.cxx
index 6c01be53c..e46af1c3e 100644
--- a/src/StateFile.cxx
+++ b/src/StateFile.cxx
@@ -23,9 +23,9 @@
#include "PlaylistState.hxx"
#include "fs/TextFile.hxx"
#include "Partition.hxx"
+#include "Instance.hxx"
#include "mixer/Volume.hxx"
#include "SongLoader.hxx"
-#include "db/DatabaseGlue.hxx"
#include "fs/FileSystem.hxx"
#include "util/Domain.hxx"
#include "Log.hxx"
@@ -98,7 +98,11 @@ StateFile::Read()
return;
}
- const SongLoader song_loader(nullptr, GetDatabase());
+#ifdef ENABLE_DATABASE
+ const SongLoader song_loader(partition.instance.database);
+#else
+ const SongLoader song_loader(nullptr);
+#endif
const char *line;
while ((line = file.ReadLine()) != NULL) {
diff --git a/src/Stats.cxx b/src/Stats.cxx
index 4051d8049..c5fcc69e2 100644
--- a/src/Stats.cxx
+++ b/src/Stats.cxx
@@ -21,8 +21,9 @@
#include "Stats.hxx"
#include "PlayerControl.hxx"
#include "client/Client.hxx"
+#include "Partition.hxx"
+#include "Instance.hxx"
#include "db/Selection.hxx"
-#include "db/DatabaseGlue.hxx"
#include "db/DatabasePlugin.hxx"
#include "util/Error.hxx"
#include "system/Clock.hxx"
@@ -60,8 +61,6 @@ void stats_global_init(void)
void
stats_invalidate()
{
- assert(GetDatabase() != nullptr);
-
stats_validity = StatsValidity::INVALID;
}
@@ -132,7 +131,7 @@ stats_print(Client &client)
(unsigned long)(client.player_control.GetTotalPlayTime() + 0.5));
#ifdef ENABLE_DATABASE
- const Database *db = GetDatabase();
+ const Database *db = client.partition.instance.database;
if (db != nullptr)
db_stats_print(client, *db);
#endif
diff --git a/src/client/Client.cxx b/src/client/Client.cxx
index ce99faa89..c62c759e9 100644
--- a/src/client/Client.cxx
+++ b/src/client/Client.cxx
@@ -20,5 +20,17 @@
#include "config.h"
#include "ClientInternal.hxx"
#include "util/Domain.hxx"
+#include "Partition.hxx"
+#include "Instance.hxx"
const Domain client_domain("client");
+
+#ifdef ENABLE_DATABASE
+
+const Database *
+Client::GetDatabase(Error &error) const
+{
+ return partition.instance.GetDatabase(error);
+}
+
+#endif
diff --git a/src/client/Client.hxx b/src/client/Client.hxx
index 708b0d03d..006ffc98c 100644
--- a/src/client/Client.hxx
+++ b/src/client/Client.hxx
@@ -38,6 +38,7 @@ struct sockaddr;
class EventLoop;
class Path;
struct Partition;
+class Database;
class Client final : private FullyBufferedSocket, TimeoutMonitor {
public:
@@ -169,6 +170,11 @@ public:
*/
bool AllowFile(Path path_fs, Error &error) const;
+ /**
+ * Wrapper for Instance::GetDatabase().
+ */
+ const Database *GetDatabase(Error &error) const;
+
private:
/* virtual methods from class BufferedSocket */
virtual InputResult OnSocketInput(void *data, size_t length) override;
diff --git a/src/command/DatabaseCommands.cxx b/src/command/DatabaseCommands.cxx
index b458b3756..ef6fb922e 100644
--- a/src/command/DatabaseCommands.cxx
+++ b/src/command/DatabaseCommands.cxx
@@ -120,7 +120,7 @@ handle_searchaddpl(Client &client, int argc, char *argv[])
}
Error error;
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return print_error(client, error);
diff --git a/src/command/PlaylistCommands.cxx b/src/command/PlaylistCommands.cxx
index 07cc177d6..0997cc68d 100644
--- a/src/command/PlaylistCommands.cxx
+++ b/src/command/PlaylistCommands.cxx
@@ -19,7 +19,6 @@
#include "config.h"
#include "PlaylistCommands.hxx"
-#include "db/DatabaseGlue.hxx"
#include "db/DatabasePlaylist.hxx"
#include "CommandError.hxx"
#include "PlaylistPrint.hxx"
@@ -193,7 +192,7 @@ handle_playlistadd(Client &client, gcc_unused int argc, char *argv[])
success = spl_append_uri(playlist, loader, uri, error);
} else {
#ifdef ENABLE_DATABASE
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return print_error(client, error);
diff --git a/src/command/StickerCommands.cxx b/src/command/StickerCommands.cxx
index 9e526b0e0..bf3660b85 100644
--- a/src/command/StickerCommands.cxx
+++ b/src/command/StickerCommands.cxx
@@ -28,6 +28,9 @@
#include "sticker/StickerDatabase.hxx"
#include "CommandError.hxx"
#include "protocol/Result.hxx"
+#include "client/Client.hxx"
+#include "Partition.hxx"
+#include "Instance.hxx"
#include "util/Error.hxx"
#include <string.h>
@@ -52,7 +55,7 @@ static CommandResult
handle_sticker_song(Client &client, int argc, char *argv[])
{
Error error;
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return print_error(client, error);
diff --git a/src/db/DatabaseGlue.cxx b/src/db/DatabaseGlue.cxx
index f320633c7..30c244334 100644
--- a/src/db/DatabaseGlue.cxx
+++ b/src/db/DatabaseGlue.cxx
@@ -19,30 +19,18 @@
#include "config.h"
#include "DatabaseGlue.hxx"
-#include "DatabaseSimple.hxx"
#include "Registry.hxx"
#include "DatabaseError.hxx"
-#include "Directory.hxx"
#include "util/Error.hxx"
#include "config/ConfigData.hxx"
-#include "Stats.hxx"
#include "DatabasePlugin.hxx"
-#include "plugins/SimpleDatabasePlugin.hxx"
-#include <assert.h>
#include <string.h>
-static Database *db;
-static bool db_is_open;
-static bool is_simple;
-
-bool
+Database *
DatabaseGlobalInit(EventLoop &loop, DatabaseListener &listener,
- const config_param &param, Error &error)
+ const config_param &param, bool &is_simple, Error &error)
{
- assert(db == nullptr);
- assert(!db_is_open);
-
const char *plugin_name =
param.GetBlockValue("plugin", "simple");
is_simple = strcmp(plugin_name, "simple") == 0;
@@ -51,79 +39,8 @@ DatabaseGlobalInit(EventLoop &loop, DatabaseListener &listener,
if (plugin == nullptr) {
error.Format(db_domain,
"No such database plugin: %s", plugin_name);
- return false;
+ return nullptr;
}
- db = plugin->create(loop, listener, param, error);
- return db != nullptr;
-}
-
-void
-DatabaseGlobalDeinit(void)
-{
- if (db_is_open)
- db->Close();
-
- if (db != nullptr)
- delete db;
-}
-
-const Database *
-GetDatabase()
-{
- assert(db == nullptr || db_is_open);
-
- return db;
-}
-
-const Database *
-GetDatabase(Error &error)
-{
- assert(db == nullptr || db_is_open);
-
- if (db == nullptr)
- error.Set(db_domain, DB_DISABLED, "No database");
-
- return db;
-}
-
-bool
-db_is_simple(void)
-{
- assert(db == nullptr || db_is_open);
-
- return is_simple;
-}
-
-SimpleDatabase &
-db_get_simple()
-{
- assert(is_simple);
- assert(db != nullptr);
-
- return *(SimpleDatabase *)db;
-}
-
-bool
-DatabaseGlobalOpen(Error &error)
-{
- assert(db != nullptr);
- assert(!db_is_open);
-
- if (!db->Open(error))
- return false;
-
- db_is_open = true;
-
- return true;
-}
-
-bool
-db_exists()
-{
- assert(db != nullptr);
- assert(db_is_open);
- assert(db_is_simple());
-
- return ((SimpleDatabase *)db)->GetUpdateStamp() > 0;
+ return plugin->create(loop, listener, param, error);
}
diff --git a/src/db/DatabaseGlue.hxx b/src/db/DatabaseGlue.hxx
index 78032edb2..f562b6d41 100644
--- a/src/db/DatabaseGlue.hxx
+++ b/src/db/DatabaseGlue.hxx
@@ -32,31 +32,11 @@ class Error;
* Initialize the database library.
*
* @param param the database configuration block
+ * @param is_simple returns whether this is the "simple" database
+ * plugin
*/
-bool
+Database *
DatabaseGlobalInit(EventLoop &loop, DatabaseListener &listener,
- const config_param &param, Error &error);
-
-void
-DatabaseGlobalDeinit(void);
-
-bool
-DatabaseGlobalOpen(Error &error);
-
-/**
- * Returns the global #Database instance. May return nullptr if this MPD
- * configuration has no database (no music_directory was configured).
- */
-gcc_const
-const Database *
-GetDatabase();
-
-/**
- * Returns the global #Database instance. May return nullptr if this MPD
- * configuration has no database (no music_directory was configured).
- */
-gcc_pure
-const Database *
-GetDatabase(Error &error);
+ const config_param &param, bool &is_simple, Error &error);
#endif
diff --git a/src/db/DatabasePrint.cxx b/src/db/DatabasePrint.cxx
index 9ed0b0826..669a804be 100644
--- a/src/db/DatabasePrint.cxx
+++ b/src/db/DatabasePrint.cxx
@@ -28,7 +28,6 @@
#include "LightSong.hxx"
#include "LightDirectory.hxx"
#include "PlaylistInfo.hxx"
-#include "DatabaseGlue.hxx"
#include "DatabasePlugin.hxx"
#include <functional>
@@ -129,7 +128,7 @@ bool
db_selection_print(Client &client, const DatabaseSelection &selection,
bool full, Error &error)
{
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return false;
@@ -173,7 +172,7 @@ searchStatsForSongsIn(Client &client, const char *name,
const SongFilter *filter,
Error &error)
{
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return false;
@@ -229,7 +228,7 @@ listAllUniqueTags(Client &client, int type,
const SongFilter *filter,
Error &error)
{
- const Database *db = GetDatabase(error);
+ const Database *db = client.GetDatabase(error);
if (db == nullptr)
return false;
diff --git a/src/db/DatabaseQueue.cxx b/src/db/DatabaseQueue.cxx
index ee1dbd57c..f2a0951a6 100644
--- a/src/db/DatabaseQueue.cxx
+++ b/src/db/DatabaseQueue.cxx
@@ -22,6 +22,7 @@
#include "DatabaseGlue.hxx"
#include "DatabasePlugin.hxx"
#include "Partition.hxx"
+#include "Instance.hxx"
#include "util/Error.hxx"
#include "DetachedSong.hxx"
#include "Mapper.hxx"
@@ -47,7 +48,7 @@ bool
AddFromDatabase(Partition &partition, const DatabaseSelection &selection,
Error &error)
{
- const Database *db = GetDatabase(error);
+ const Database *db = partition.instance.GetDatabase(error);
if (db == nullptr)
return false;
diff --git a/src/db/DatabaseSimple.hxx b/src/db/DatabaseSimple.hxx
index c0f84ab79..1e527958f 100644
--- a/src/db/DatabaseSimple.hxx
+++ b/src/db/DatabaseSimple.hxx
@@ -35,10 +35,6 @@ class Error;
bool
db_is_simple(void);
-gcc_pure
-SimpleDatabase &
-db_get_simple();
-
/**
* Returns true if there is a valid database file on the disk.
*
diff --git a/src/db/plugins/SimpleDatabasePlugin.hxx b/src/db/plugins/SimpleDatabasePlugin.hxx
index 8c7978a91..83434393c 100644
--- a/src/db/plugins/SimpleDatabasePlugin.hxx
+++ b/src/db/plugins/SimpleDatabasePlugin.hxx
@@ -59,6 +59,9 @@ public:
bool Save(Error &error);
+ /**
+ * Returns true if there is a valid database file on the disk.
+ */
bool FileExists() const {
return mtime > 0;
}
diff --git a/test/test_translate_song.cxx b/test/test_translate_song.cxx
index 3c94ed4bc..bc1ae82d6 100644
--- a/test/test_translate_song.cxx
+++ b/test/test_translate_song.cxx
@@ -137,6 +137,12 @@ DetachedSong::Update()
return false;
}
+const Database *
+Client::GetDatabase(gcc_unused Error &error) const
+{
+ return reinterpret_cast<const Database *>(this);
+}
+
bool
Client::AllowFile(gcc_unused Path path_fs, gcc_unused Error &error) const
{
@@ -220,7 +226,7 @@ class TranslateSongTest : public CppUnit::TestFixture {
void TestInsecure() {
/* illegal because secure=false */
DetachedSong song1 (uri1);
- const SongLoader loader(reinterpret_cast<const Client *>(1));
+ const SongLoader loader(*reinterpret_cast<const Client *>(1));
CPPUNIT_ASSERT(!playlist_check_translate_song(song1, nullptr,
loader));
}
@@ -261,7 +267,8 @@ class TranslateSongTest : public CppUnit::TestFixture {
void TestRelative() {
const Database &db = *reinterpret_cast<const Database *>(1);
const SongLoader secure_loader(&db);
- const SongLoader insecure_loader(reinterpret_cast<const Client *>(1), &db);
+ const SongLoader insecure_loader(*reinterpret_cast<const Client *>(1),
+ &db);
/* map to music_directory */
DetachedSong song1("bar.ogg", MakeTag2b());