Commit ffd16b55 authored by Max Kellermann's avatar Max Kellermann

StoragePlugin: add method MapToRelativeUTF8()

Replaces map_to_relative_path() from Mapper.cxx.
parent d744c997
...@@ -1777,6 +1777,7 @@ test_test_translate_song_SOURCES = \ ...@@ -1777,6 +1777,7 @@ test_test_translate_song_SOURCES = \
test_test_translate_song_CPPFLAGS = $(AM_CPPFLAGS) $(CPPUNIT_CFLAGS) -DCPPUNIT_HAVE_RTTI=0 test_test_translate_song_CPPFLAGS = $(AM_CPPFLAGS) $(CPPUNIT_CFLAGS) -DCPPUNIT_HAVE_RTTI=0
test_test_translate_song_CXXFLAGS = $(AM_CXXFLAGS) -Wno-error=deprecated-declarations test_test_translate_song_CXXFLAGS = $(AM_CXXFLAGS) -Wno-error=deprecated-declarations
test_test_translate_song_LDADD = \ test_test_translate_song_LDADD = \
$(STORAGE_LIBS) \
libtag.a \ libtag.a \
libfs.a \ libfs.a \
libsystem.a \ libsystem.a \
......
...@@ -160,21 +160,6 @@ mapper_get_music_directory_fs(void) ...@@ -160,21 +160,6 @@ mapper_get_music_directory_fs(void)
#endif #endif
const char *
map_to_relative_path(const char *path_utf8)
{
#ifdef ENABLE_DATABASE
return !music_dir_utf8.empty() &&
memcmp(path_utf8, music_dir_utf8.c_str(),
music_dir_utf8_length) == 0 &&
PathTraitsUTF8::IsSeparator(path_utf8[music_dir_utf8_length])
? path_utf8 + music_dir_utf8_length + 1
: path_utf8;
#else
return path_utf8;
#endif
}
#ifdef ENABLE_DATABASE #ifdef ENABLE_DATABASE
AllocatedPath AllocatedPath
......
...@@ -71,15 +71,6 @@ mapper_has_music_directory(void) ...@@ -71,15 +71,6 @@ mapper_has_music_directory(void)
#endif #endif
/**
* If the specified absolute path points inside the music directory,
* this function converts it to a relative path. If not, it returns
* the unmodified string pointer.
*/
gcc_pure
const char *
map_to_relative_path(const char *path_utf8);
#ifdef ENABLE_DATABASE #ifdef ENABLE_DATABASE
/** /**
......
...@@ -20,8 +20,8 @@ ...@@ -20,8 +20,8 @@
#include "config.h" #include "config.h"
#include "SongLoader.hxx" #include "SongLoader.hxx"
#include "client/Client.hxx" #include "client/Client.hxx"
#include "Mapper.hxx"
#include "db/DatabaseSong.hxx" #include "db/DatabaseSong.hxx"
#include "storage/StorageInterface.hxx"
#include "ls.hxx" #include "ls.hxx"
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/Traits.hxx" #include "fs/Traits.hxx"
...@@ -45,14 +45,13 @@ DetachedSong * ...@@ -45,14 +45,13 @@ DetachedSong *
SongLoader::LoadFile(const char *path_utf8, Error &error) const SongLoader::LoadFile(const char *path_utf8, Error &error) const
{ {
#ifdef ENABLE_DATABASE #ifdef ENABLE_DATABASE
/* TODO fs_charset vs utf8? */ if (storage != nullptr) {
const char *suffix = map_to_relative_path(path_utf8); const char *suffix = storage->MapToRelativeUTF8(path_utf8);
assert(suffix != nullptr); if (suffix != nullptr)
/* this path was relative to the music
if (suffix != path_utf8) directory - obtain it from the database */
/* this path was relative to the music directory -
obtain it from the database */
return LoadSong(suffix, error); return LoadSong(suffix, error);
}
#endif #endif
if (client != nullptr) { if (client != nullptr) {
......
...@@ -20,10 +20,10 @@ ...@@ -20,10 +20,10 @@
#include "config.h" #include "config.h"
#include "SongPrint.hxx" #include "SongPrint.hxx"
#include "db/LightSong.hxx" #include "db/LightSong.hxx"
#include "storage/StorageInterface.hxx"
#include "DetachedSong.hxx" #include "DetachedSong.hxx"
#include "TimePrint.hxx" #include "TimePrint.hxx"
#include "TagPrint.hxx" #include "TagPrint.hxx"
#include "Mapper.hxx"
#include "client/Client.hxx" #include "client/Client.hxx"
#include "util/UriUtil.hxx" #include "util/UriUtil.hxx"
...@@ -32,12 +32,20 @@ ...@@ -32,12 +32,20 @@
static void static void
song_print_uri(Client &client, const char *uri) song_print_uri(Client &client, const char *uri)
{ {
#ifdef ENABLE_DATABASE
const Storage *storage = client.GetStorage();
if (storage != nullptr) {
const char *suffix = storage->MapToRelativeUTF8(uri);
if (suffix != nullptr)
uri = suffix;
}
#endif
const std::string allocated = uri_remove_auth(uri); const std::string allocated = uri_remove_auth(uri);
if (!allocated.empty()) if (!allocated.empty())
uri = allocated.c_str(); uri = allocated.c_str();
client_printf(client, "%s%s\n", SONG_FILE, client_printf(client, "%s%s\n", SONG_FILE, uri);
map_to_relative_path(uri));
} }
void void
......
...@@ -29,13 +29,13 @@ ...@@ -29,13 +29,13 @@
#include "db/Uri.hxx" #include "db/Uri.hxx"
#include "storage/StorageInterface.hxx" #include "storage/StorageInterface.hxx"
#include "playlist/PlaylistRegistry.hxx" #include "playlist/PlaylistRegistry.hxx"
#include "Mapper.hxx"
#include "ExcludeList.hxx" #include "ExcludeList.hxx"
#include "config/ConfigGlobal.hxx" #include "config/ConfigGlobal.hxx"
#include "config/ConfigOption.hxx" #include "config/ConfigOption.hxx"
#include "fs/AllocatedPath.hxx" #include "fs/AllocatedPath.hxx"
#include "fs/Traits.hxx" #include "fs/Traits.hxx"
#include "fs/FileSystem.hxx" #include "fs/FileSystem.hxx"
#include "fs/Charset.hxx"
#include "storage/FileInfo.hxx" #include "storage/FileInfo.hxx"
#include "util/Alloc.hxx" #include "util/Alloc.hxx"
#include "util/UriUtil.hxx" #include "util/UriUtil.hxx"
...@@ -274,8 +274,13 @@ UpdateWalk::SkipSymlink(const Directory *directory, ...@@ -274,8 +274,13 @@ UpdateWalk::SkipSymlink(const Directory *directory,
if (PathTraitsFS::IsAbsolute(target_str)) { if (PathTraitsFS::IsAbsolute(target_str)) {
/* if the symlink points to an absolute path, see if /* if the symlink points to an absolute path, see if
that path is inside the music directory */ that path is inside the music directory */
const char *relative = map_to_relative_path(target_str); const auto target_utf8 = PathToUTF8(target_str);
return relative > target_str if (target_utf8.empty())
return true;
const char *relative =
storage.MapToRelativeUTF8(target_utf8.c_str());
return relative != nullptr
? !follow_inside_symlinks ? !follow_inside_symlinks
: !follow_outside_symlinks; : !follow_outside_symlinks;
} }
......
...@@ -68,6 +68,14 @@ public: ...@@ -68,6 +68,14 @@ public:
gcc_pure gcc_pure
AllocatedPath MapChildFS(const char *uri_utf8, AllocatedPath MapChildFS(const char *uri_utf8,
const char *child_utf8) const; const char *child_utf8) const;
/**
* Check if the given URI points inside this storage. If yes,
* then it returns a relative URI (pointing inside the given
* string); if not, returns nullptr.
*/
gcc_pure
virtual const char *MapToRelativeUTF8(const char *uri_utf8) const = 0;
}; };
#endif #endif
...@@ -68,6 +68,8 @@ public: ...@@ -68,6 +68,8 @@ public:
virtual AllocatedPath MapFS(const char *uri_utf8) const override; virtual AllocatedPath MapFS(const char *uri_utf8) const override;
virtual const char *MapToRelativeUTF8(const char *uri_utf8) const override;
private: private:
AllocatedPath MapFS(const char *uri_utf8, Error &error) const; AllocatedPath MapFS(const char *uri_utf8, Error &error) const;
}; };
...@@ -130,6 +132,12 @@ LocalStorage::MapFS(const char *uri_utf8) const ...@@ -130,6 +132,12 @@ LocalStorage::MapFS(const char *uri_utf8) const
return MapFS(uri_utf8, IgnoreError()); return MapFS(uri_utf8, IgnoreError());
} }
const char *
LocalStorage::MapToRelativeUTF8(const char *uri_utf8) const
{
return PathTraitsUTF8::Relative(base_utf8.c_str(), uri_utf8);
}
bool bool
LocalStorage::GetInfo(const char *uri_utf8, bool follow, FileInfo &info, LocalStorage::GetInfo(const char *uri_utf8, bool follow, FileInfo &info,
Error &error) Error &error)
......
...@@ -69,6 +69,8 @@ public: ...@@ -69,6 +69,8 @@ public:
Error &error) override; Error &error) override;
virtual std::string MapUTF8(const char *uri_utf8) const override; virtual std::string MapUTF8(const char *uri_utf8) const override;
virtual const char *MapToRelativeUTF8(const char *uri_utf8) const override;
}; };
std::string std::string
...@@ -82,6 +84,12 @@ SmbclientStorage::MapUTF8(const char *uri_utf8) const ...@@ -82,6 +84,12 @@ SmbclientStorage::MapUTF8(const char *uri_utf8) const
return PathTraitsUTF8::Build(base.c_str(), uri_utf8); return PathTraitsUTF8::Build(base.c_str(), uri_utf8);
} }
const char *
SmbclientStorage::MapToRelativeUTF8(const char *uri_utf8) const
{
return PathTraitsUTF8::Relative(base.c_str(), uri_utf8);
}
static bool static bool
GetInfo(const char *path, FileInfo &info, Error &error) GetInfo(const char *path, FileInfo &info, Error &error)
{ {
......
...@@ -14,6 +14,7 @@ ...@@ -14,6 +14,7 @@
#include "ls.hxx" #include "ls.hxx"
#include "Log.hxx" #include "Log.hxx"
#include "db/DatabaseSong.hxx" #include "db/DatabaseSong.hxx"
#include "storage/plugins/LocalStorage.hxx"
#include "util/Error.hxx" #include "util/Error.hxx"
#include "Mapper.hxx" #include "Mapper.hxx"
...@@ -38,16 +39,8 @@ uri_supported_scheme(const char *uri) ...@@ -38,16 +39,8 @@ uri_supported_scheme(const char *uri)
} }
const char *const music_directory = "/music"; const char *const music_directory = "/music";
static Storage *const storage = CreateLocalStorage(music_directory,
const char * Path::FromFS(music_directory));
map_to_relative_path(const char *path_utf8)
{
size_t length = strlen(music_directory);
if (memcmp(path_utf8, music_directory, length) == 0 &&
path_utf8[length] == '/')
path_utf8 += length + 1;
return path_utf8;
}
static void static void
BuildTag(gcc_unused TagBuilder &tag) BuildTag(gcc_unused TagBuilder &tag)
...@@ -118,7 +111,7 @@ static const char *uri2 = "foo/bar.ogg"; ...@@ -118,7 +111,7 @@ static const char *uri2 = "foo/bar.ogg";
DetachedSong * DetachedSong *
DatabaseDetachSong(gcc_unused const Database &db, DatabaseDetachSong(gcc_unused const Database &db,
gcc_unused const Storage &storage, gcc_unused const Storage &_storage,
const char *uri, const char *uri,
gcc_unused Error &error) gcc_unused Error &error)
{ {
...@@ -148,7 +141,7 @@ Client::GetDatabase(gcc_unused Error &error) const ...@@ -148,7 +141,7 @@ Client::GetDatabase(gcc_unused Error &error) const
const Storage * const Storage *
Client::GetStorage() const Client::GetStorage() const
{ {
return reinterpret_cast<const Storage *>(this); return ::storage;
} }
bool bool
...@@ -252,7 +245,7 @@ class TranslateSongTest : public CppUnit::TestFixture { ...@@ -252,7 +245,7 @@ class TranslateSongTest : public CppUnit::TestFixture {
void TestInDatabase() { void TestInDatabase() {
const SongLoader loader(reinterpret_cast<const Database *>(1), const SongLoader loader(reinterpret_cast<const Database *>(1),
reinterpret_cast<const Storage *>(2)); storage);
DetachedSong song1("doesntexist"); DetachedSong song1("doesntexist");
CPPUNIT_ASSERT(!playlist_check_translate_song(song1, nullptr, CPPUNIT_ASSERT(!playlist_check_translate_song(song1, nullptr,
...@@ -275,10 +268,9 @@ class TranslateSongTest : public CppUnit::TestFixture { ...@@ -275,10 +268,9 @@ class TranslateSongTest : public CppUnit::TestFixture {
void TestRelative() { void TestRelative() {
const Database &db = *reinterpret_cast<const Database *>(1); const Database &db = *reinterpret_cast<const Database *>(1);
const Storage &storage = *reinterpret_cast<const Storage *>(2); const SongLoader secure_loader(&db, storage);
const SongLoader secure_loader(&db, &storage);
const SongLoader insecure_loader(*reinterpret_cast<const Client *>(1), const SongLoader insecure_loader(*reinterpret_cast<const Client *>(1),
&db, &storage); &db, storage);
/* map to music_directory */ /* map to music_directory */
DetachedSong song1("bar.ogg", MakeTag2b()); DetachedSong song1("bar.ogg", MakeTag2b());
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment