Update minidlna to latest commit Cherry pick commits from https://github.com/xavery/minidlna Signed-off-by: Daniel Engberg <daniel.engberg.lists@pyret.net>lilik-openwrt-22.03
@ -0,0 +1,125 @@ | |||||
From d297624e533d6d4274c750e3769749c3d7f121c8 Mon Sep 17 00:00:00 2001 | |||||
From: Daniel Kamil Kozar <dkk089@gmail.com> | |||||
Date: Sat, 15 Dec 2018 16:34:30 +0100 | |||||
Subject: [PATCH] Mark all instances of magic_container_s as const | |||||
--- | |||||
containers.c | 38 +++++++++++++++++++------------------- | |||||
containers.h | 6 +++--- | |||||
scanner.c | 2 +- | |||||
upnpsoap.c | 6 +++--- | |||||
4 files changed, 26 insertions(+), 26 deletions(-) | |||||
--- a/containers.c | |||||
+++ b/containers.c | |||||
@@ -25,23 +25,23 @@ | |||||
#define NINETY_DAYS "7776000" | |||||
-const char *music_id = MUSIC_ID; | |||||
-const char *music_all_id = MUSIC_ALL_ID; | |||||
-const char *music_genre_id = MUSIC_GENRE_ID; | |||||
-const char *music_artist_id = MUSIC_ARTIST_ID; | |||||
-const char *music_album_id = MUSIC_ALBUM_ID; | |||||
-const char *music_plist_id = MUSIC_PLIST_ID; | |||||
-const char *music_dir_id = MUSIC_DIR_ID; | |||||
-const char *video_id = VIDEO_ID; | |||||
-const char *video_all_id = VIDEO_ALL_ID; | |||||
-const char *video_dir_id = VIDEO_DIR_ID; | |||||
-const char *image_id = IMAGE_ID; | |||||
-const char *image_all_id = IMAGE_ALL_ID; | |||||
-const char *image_date_id = IMAGE_DATE_ID; | |||||
-const char *image_camera_id = IMAGE_CAMERA_ID; | |||||
-const char *image_dir_id = IMAGE_DIR_ID; | |||||
+static const char *music_id = MUSIC_ID; | |||||
+static const char *music_all_id = MUSIC_ALL_ID; | |||||
+static const char *music_genre_id = MUSIC_GENRE_ID; | |||||
+static const char *music_artist_id = MUSIC_ARTIST_ID; | |||||
+static const char *music_album_id = MUSIC_ALBUM_ID; | |||||
+static const char *music_plist_id = MUSIC_PLIST_ID; | |||||
+static const char *music_dir_id = MUSIC_DIR_ID; | |||||
+static const char *video_id = VIDEO_ID; | |||||
+static const char *video_all_id = VIDEO_ALL_ID; | |||||
+static const char *video_dir_id = VIDEO_DIR_ID; | |||||
+static const char *image_id = IMAGE_ID; | |||||
+static const char *image_all_id = IMAGE_ALL_ID; | |||||
+static const char *image_date_id = IMAGE_DATE_ID; | |||||
+static const char *image_camera_id = IMAGE_CAMERA_ID; | |||||
+static const char *image_dir_id = IMAGE_DIR_ID; | |||||
-struct magic_container_s magic_containers[] = | |||||
+const struct magic_container_s magic_containers[] = | |||||
{ | |||||
/* Alternate root container */ | |||||
{ NULL, | |||||
@@ -124,7 +124,7 @@ struct magic_container_s magic_container | |||||
{ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, 0, 0 } | |||||
}; | |||||
-struct magic_container_s * | |||||
+const struct magic_container_s * | |||||
in_magic_container(const char *id, int flags, const char **real_id) | |||||
{ | |||||
size_t len; | |||||
@@ -154,7 +154,7 @@ in_magic_container(const char *id, int f | |||||
return NULL; | |||||
} | |||||
-struct magic_container_s * | |||||
+const struct magic_container_s * | |||||
check_magic_container(const char *id, int flags) | |||||
{ | |||||
int i; | |||||
--- a/containers.h | |||||
+++ b/containers.h | |||||
@@ -30,7 +30,7 @@ struct magic_container_s { | |||||
int required_flags; | |||||
}; | |||||
-extern struct magic_container_s magic_containers[]; | |||||
+extern const struct magic_container_s magic_containers[]; | |||||
-struct magic_container_s *in_magic_container(const char *id, int flags, const char **real_id); | |||||
-struct magic_container_s *check_magic_container(const char *id, int flags); | |||||
+const struct magic_container_s *in_magic_container(const char *id, int flags, const char **real_id); | |||||
+const struct magic_container_s *check_magic_container(const char *id, int flags); | |||||
--- a/scanner.c | |||||
+++ b/scanner.c | |||||
@@ -587,7 +587,7 @@ CreateDatabase(void) | |||||
} | |||||
for( i=0; magic_containers[i].objectid_match; i++ ) | |||||
{ | |||||
- struct magic_container_s *magic = &magic_containers[i]; | |||||
+ const struct magic_container_s *magic = &magic_containers[i]; | |||||
if (!magic->name) | |||||
continue; | |||||
if( sql_get_int_field(db, "SELECT 1 from OBJECTS where OBJECT_ID = '%s'", magic->objectid_match) == 0 ) | |||||
--- a/upnpsoap.c | |||||
+++ b/upnpsoap.c | |||||
@@ -800,7 +800,7 @@ add_res(char *size, char *duration, char | |||||
} | |||||
static int | |||||
-get_child_count(const char *object, struct magic_container_s *magic) | |||||
+get_child_count(const char *object, const struct magic_container_s *magic) | |||||
{ | |||||
int ret; | |||||
@@ -1292,7 +1292,7 @@ BrowseContentDirectory(struct upnphttp * | |||||
"<Result>" | |||||
"<DIDL-Lite" | |||||
CONTENT_DIRECTORY_SCHEMAS; | |||||
- struct magic_container_s *magic; | |||||
+ const struct magic_container_s *magic; | |||||
char *zErrMsg = NULL; | |||||
char *sql, *ptr; | |||||
struct Response args; | |||||
@@ -1807,7 +1807,7 @@ SearchContentDirectory(struct upnphttp * | |||||
"<Result>" | |||||
"<DIDL-Lite" | |||||
CONTENT_DIRECTORY_SCHEMAS; | |||||
- struct magic_container_s *magic; | |||||
+ const struct magic_container_s *magic; | |||||
char *zErrMsg = NULL; | |||||
char *sql, *ptr; | |||||
struct Response args; |
@ -0,0 +1,118 @@ | |||||
From e0065b8343bc963a89556449e00f1d20086cc1f1 Mon Sep 17 00:00:00 2001 | |||||
From: Daniel Kamil Kozar <dkk089@gmail.com> | |||||
Date: Sat, 15 Dec 2018 16:26:37 +0100 | |||||
Subject: [PATCH] Wrap container definitions into a structure | |||||
--- | |||||
containers.c | 25 +++++++++++++++++++++++++ | |||||
containers.h | 8 ++++++++ | |||||
scanner.c | 33 ++++++--------------------------- | |||||
3 files changed, 39 insertions(+), 27 deletions(-) | |||||
--- a/containers.c | |||||
+++ b/containers.c | |||||
@@ -23,6 +23,31 @@ | |||||
#include "containers.h" | |||||
#include "log.h" | |||||
+const struct container_s containers[] = { | |||||
+ { "0","-1", "root" }, | |||||
+ { MUSIC_ID, "0", "Music" }, | |||||
+ { MUSIC_ALL_ID, MUSIC_ID, "All Music" }, | |||||
+ { MUSIC_GENRE_ID, MUSIC_ID, "Genre" }, | |||||
+ { MUSIC_ARTIST_ID, MUSIC_ID, "Artist" }, | |||||
+ { MUSIC_ALBUM_ID, MUSIC_ID, "Album" }, | |||||
+ { MUSIC_DIR_ID, MUSIC_ID, "Folders" }, | |||||
+ { MUSIC_PLIST_ID, MUSIC_ID, "Playlists" }, | |||||
+ | |||||
+ { VIDEO_ID, "0", "Video" }, | |||||
+ { VIDEO_ALL_ID, VIDEO_ID, "All Video" }, | |||||
+ { VIDEO_DIR_ID, VIDEO_ID, "Folders" }, | |||||
+ | |||||
+ { IMAGE_ID, "0", "Pictures" }, | |||||
+ { IMAGE_ALL_ID, IMAGE_ID, "All Pictures" }, | |||||
+ { IMAGE_DATE_ID, IMAGE_ID, "Date Taken" }, | |||||
+ { IMAGE_CAMERA_ID, IMAGE_ID, "Camera" }, | |||||
+ { IMAGE_DIR_ID, IMAGE_ID, "Folders" }, | |||||
+ | |||||
+ { BROWSEDIR_ID, "0", "Browse Folders" }, | |||||
+ | |||||
+ { 0, 0, 0 } | |||||
+}; | |||||
+ | |||||
#define NINETY_DAYS "7776000" | |||||
static const char *music_id = MUSIC_ID; | |||||
--- a/containers.h | |||||
+++ b/containers.h | |||||
@@ -16,6 +16,14 @@ | |||||
* along with MiniDLNA. If not, see <http://www.gnu.org/licenses/>. | |||||
*/ | |||||
+struct container_s { | |||||
+ const char *object_id; | |||||
+ const char *parent_id; | |||||
+ const char *name; | |||||
+}; | |||||
+ | |||||
+extern const struct container_s containers[]; | |||||
+ | |||||
struct magic_container_s { | |||||
const char *name; | |||||
const char *objectid_match; | |||||
--- a/scanner.c | |||||
+++ b/scanner.c | |||||
@@ -529,30 +529,7 @@ insert_file(const char *name, const char | |||||
int | |||||
CreateDatabase(void) | |||||
{ | |||||
- int ret, i; | |||||
- const char *containers[] = { "0","-1", "root", | |||||
- MUSIC_ID, "0", _("Music"), | |||||
- MUSIC_ALL_ID, MUSIC_ID, _("All Music"), | |||||
- MUSIC_GENRE_ID, MUSIC_ID, _("Genre"), | |||||
- MUSIC_ARTIST_ID, MUSIC_ID, _("Artist"), | |||||
- MUSIC_ALBUM_ID, MUSIC_ID, _("Album"), | |||||
- MUSIC_DIR_ID, MUSIC_ID, _("Folders"), | |||||
- MUSIC_PLIST_ID, MUSIC_ID, _("Playlists"), | |||||
- | |||||
- VIDEO_ID, "0", _("Video"), | |||||
- VIDEO_ALL_ID, VIDEO_ID, _("All Video"), | |||||
- VIDEO_DIR_ID, VIDEO_ID, _("Folders"), | |||||
- | |||||
- IMAGE_ID, "0", _("Pictures"), | |||||
- IMAGE_ALL_ID, IMAGE_ID, _("All Pictures"), | |||||
- IMAGE_DATE_ID, IMAGE_ID, _("Date Taken"), | |||||
- IMAGE_CAMERA_ID, IMAGE_ID, _("Camera"), | |||||
- IMAGE_DIR_ID, IMAGE_ID, _("Folders"), | |||||
- | |||||
- BROWSEDIR_ID, "0", _("Browse Folders"), | |||||
- 0 }; | |||||
- | |||||
- ret = sql_exec(db, create_objectTable_sqlite); | |||||
+ int ret = sql_exec(db, create_objectTable_sqlite); | |||||
if( ret != SQLITE_OK ) | |||||
goto sql_failed; | |||||
ret = sql_exec(db, create_detailTable_sqlite); | |||||
@@ -576,16 +553,18 @@ CreateDatabase(void) | |||||
ret = sql_exec(db, "INSERT into SETTINGS values ('UPDATE_ID', '0')"); | |||||
if( ret != SQLITE_OK ) | |||||
goto sql_failed; | |||||
- for( i=0; containers[i]; i=i+3 ) | |||||
+ for( int i=0; containers[i].name; ++i ) | |||||
{ | |||||
+ const struct container_s *c = &containers[i]; | |||||
+ const char *name = _(c->name); | |||||
ret = sql_exec(db, "INSERT into OBJECTS (OBJECT_ID, PARENT_ID, DETAIL_ID, CLASS, NAME)" | |||||
" values " | |||||
"('%s', '%s', %lld, 'container.storageFolder', '%q')", | |||||
- containers[i], containers[i+1], GetFolderMetadata(containers[i+2], NULL, NULL, NULL, 0), containers[i+2]); | |||||
+ c->object_id, c->parent_id, GetFolderMetadata(name, NULL, NULL, NULL, 0), name); | |||||
if( ret != SQLITE_OK ) | |||||
goto sql_failed; | |||||
} | |||||
- for( i=0; magic_containers[i].objectid_match; i++ ) | |||||
+ for( int i=0; magic_containers[i].objectid_match; i++ ) | |||||
{ | |||||
const struct magic_container_s *magic = &magic_containers[i]; | |||||
if (!magic->name) |
@ -0,0 +1,192 @@ | |||||
From be9de8b2e0864b46498496af9ffdc31c0e7b764a Mon Sep 17 00:00:00 2001 | |||||
From: Daniel Kamil Kozar <dkk089@gmail.com> | |||||
Date: Sun, 16 Dec 2018 14:21:58 +0100 | |||||
Subject: [PATCH] Reduce duplication in sql.c | |||||
--- | |||||
sql.c | 166 ++++++++++++++++++++-------------------------------------- | |||||
1 file changed, 58 insertions(+), 108 deletions(-) | |||||
--- a/sql.c | |||||
+++ b/sql.c | |||||
@@ -65,122 +65,72 @@ sql_get_table(sqlite3 *db, const char *s | |||||
return ret; | |||||
} | |||||
+#define sql_get_field(type, column_get_fn) \ | |||||
+ va_list ap;\ | |||||
+ int counter, result;\ | |||||
+ char *sql;\ | |||||
+ type ret;\ | |||||
+ sqlite3_stmt *stmt;\ | |||||
+ \ | |||||
+ va_start(ap, fmt);\ | |||||
+ sql = sqlite3_vmprintf(fmt, ap);\ | |||||
+ va_end(ap);\ | |||||
+\ | |||||
+ /*DPRINTF(E_DEBUG, L_DB_SQL, "sql: %s\n", sql); */ \ | |||||
+\ | |||||
+ switch (sqlite3_prepare_v2(db, sql, -1, &stmt, NULL))\ | |||||
+ {\ | |||||
+ case SQLITE_OK:\ | |||||
+ break;\ | |||||
+ default:\ | |||||
+ DPRINTF(E_ERROR, L_DB_SQL, "prepare failed: %s\n%s\n", sqlite3_errmsg(db), sql);\ | |||||
+ sqlite3_free(sql);\ | |||||
+ return -1;\ | |||||
+ }\ | |||||
+\ | |||||
+ for (counter = 0;\ | |||||
+ ((result = sqlite3_step(stmt)) == SQLITE_BUSY || result == SQLITE_LOCKED) && counter < 2;\ | |||||
+ counter++) {\ | |||||
+ /* While SQLITE_BUSY has a built in timeout,\ | |||||
+ * SQLITE_LOCKED does not, so sleep */\ | |||||
+ if (result == SQLITE_LOCKED)\ | |||||
+ sleep(1);\ | |||||
+ }\ | |||||
+\ | |||||
+ switch (result)\ | |||||
+ {\ | |||||
+ case SQLITE_DONE:\ | |||||
+ /* no rows returned */\ | |||||
+ ret = 0;\ | |||||
+ break;\ | |||||
+ case SQLITE_ROW:\ | |||||
+ if (sqlite3_column_type(stmt, 0) == SQLITE_NULL)\ | |||||
+ {\ | |||||
+ ret = 0;\ | |||||
+ break;\ | |||||
+ }\ | |||||
+ ret = column_get_fn(stmt, 0);\ | |||||
+ break;\ | |||||
+ default:\ | |||||
+ DPRINTF(E_WARN, L_DB_SQL, "%s: step failed: %s\n%s\n", __func__, sqlite3_errmsg(db), sql);\ | |||||
+ ret = -1;\ | |||||
+ break;\ | |||||
+ }\ | |||||
+ sqlite3_free(sql);\ | |||||
+ sqlite3_finalize(stmt);\ | |||||
+\ | |||||
+ return ret; | |||||
+ | |||||
int | |||||
sql_get_int_field(sqlite3 *db, const char *fmt, ...) | |||||
{ | |||||
- va_list ap; | |||||
- int counter, result; | |||||
- char *sql; | |||||
- int ret; | |||||
- sqlite3_stmt *stmt; | |||||
- | |||||
- va_start(ap, fmt); | |||||
- sql = sqlite3_vmprintf(fmt, ap); | |||||
- va_end(ap); | |||||
- | |||||
- //DPRINTF(E_DEBUG, L_DB_SQL, "sql: %s\n", sql); | |||||
- | |||||
- switch (sqlite3_prepare_v2(db, sql, -1, &stmt, NULL)) | |||||
- { | |||||
- case SQLITE_OK: | |||||
- break; | |||||
- default: | |||||
- DPRINTF(E_ERROR, L_DB_SQL, "prepare failed: %s\n%s\n", sqlite3_errmsg(db), sql); | |||||
- sqlite3_free(sql); | |||||
- return -1; | |||||
- } | |||||
- | |||||
- for (counter = 0; | |||||
- ((result = sqlite3_step(stmt)) == SQLITE_BUSY || result == SQLITE_LOCKED) && counter < 2; | |||||
- counter++) { | |||||
- /* While SQLITE_BUSY has a built in timeout, | |||||
- * SQLITE_LOCKED does not, so sleep */ | |||||
- if (result == SQLITE_LOCKED) | |||||
- sleep(1); | |||||
- } | |||||
- | |||||
- switch (result) | |||||
- { | |||||
- case SQLITE_DONE: | |||||
- /* no rows returned */ | |||||
- ret = 0; | |||||
- break; | |||||
- case SQLITE_ROW: | |||||
- if (sqlite3_column_type(stmt, 0) == SQLITE_NULL) | |||||
- { | |||||
- ret = 0; | |||||
- break; | |||||
- } | |||||
- ret = sqlite3_column_int(stmt, 0); | |||||
- break; | |||||
- default: | |||||
- DPRINTF(E_WARN, L_DB_SQL, "%s: step failed: %s\n%s\n", __func__, sqlite3_errmsg(db), sql); | |||||
- ret = -1; | |||||
- break; | |||||
- } | |||||
- sqlite3_free(sql); | |||||
- sqlite3_finalize(stmt); | |||||
- | |||||
- return ret; | |||||
+ sql_get_field(int, sqlite3_column_int) | |||||
} | |||||
int64_t | |||||
sql_get_int64_field(sqlite3 *db, const char *fmt, ...) | |||||
{ | |||||
- va_list ap; | |||||
- int counter, result; | |||||
- char *sql; | |||||
- int64_t ret; | |||||
- sqlite3_stmt *stmt; | |||||
- | |||||
- va_start(ap, fmt); | |||||
- sql = sqlite3_vmprintf(fmt, ap); | |||||
- va_end(ap); | |||||
- | |||||
- //DPRINTF(E_DEBUG, L_DB_SQL, "sql: %s\n", sql); | |||||
- | |||||
- switch (sqlite3_prepare_v2(db, sql, -1, &stmt, NULL)) | |||||
- { | |||||
- case SQLITE_OK: | |||||
- break; | |||||
- default: | |||||
- DPRINTF(E_ERROR, L_DB_SQL, "prepare failed: %s\n%s\n", sqlite3_errmsg(db), sql); | |||||
- sqlite3_free(sql); | |||||
- return -1; | |||||
- } | |||||
- | |||||
- for (counter = 0; | |||||
- ((result = sqlite3_step(stmt)) == SQLITE_BUSY || result == SQLITE_LOCKED) && counter < 2; | |||||
- counter++) { | |||||
- /* While SQLITE_BUSY has a built in timeout, | |||||
- * SQLITE_LOCKED does not, so sleep */ | |||||
- if (result == SQLITE_LOCKED) | |||||
- sleep(1); | |||||
- } | |||||
- | |||||
- switch (result) | |||||
- { | |||||
- case SQLITE_DONE: | |||||
- /* no rows returned */ | |||||
- ret = 0; | |||||
- break; | |||||
- case SQLITE_ROW: | |||||
- if (sqlite3_column_type(stmt, 0) == SQLITE_NULL) | |||||
- { | |||||
- ret = 0; | |||||
- break; | |||||
- } | |||||
- ret = sqlite3_column_int64(stmt, 0); | |||||
- break; | |||||
- default: | |||||
- DPRINTF(E_WARN, L_DB_SQL, "%s: step failed: %s\n%s\n", __func__, sqlite3_errmsg(db), sql); | |||||
- ret = -1; | |||||
- break; | |||||
- } | |||||
- sqlite3_free(sql); | |||||
- sqlite3_finalize(stmt); | |||||
- | |||||
- return ret; | |||||
+ sql_get_field(int64_t, sqlite3_column_int64) | |||||
} | |||||
char * |