diff --git a/src/db.c b/src/db.c index fd5fe692..b1903965 100644 --- a/src/db.c +++ b/src/db.c @@ -917,14 +917,14 @@ db_file_inc_playcount(int id) } void -db_file_ping(int id) +db_file_ping(char *path) { -#define Q_TMPL "UPDATE songs SET db_timestamp = %" PRIi64 ", disabled = 0 WHERE id = %d;" +#define Q_TMPL "UPDATE songs SET db_timestamp = %" PRIi64 ", disabled = 0 WHERE path = '%q';" char *query; char *errmsg; int ret; - query = sqlite3_mprintf(Q_TMPL, (int64_t)time(NULL), id); + query = sqlite3_mprintf(Q_TMPL, (int64_t)time(NULL), path); if (!query) { DPRINTF(E_LOG, L_DB, "Out of memory for query string\n"); @@ -937,7 +937,7 @@ db_file_ping(int id) errmsg = NULL; ret = sqlite3_exec(hdl, query, NULL, NULL, &errmsg); if (ret != SQLITE_OK) - DPRINTF(E_LOG, L_DB, "Error pinging file %d: %s\n", id, errmsg); + DPRINTF(E_LOG, L_DB, "Error pinging file '%s': %s\n", path, errmsg); sqlite3_free(errmsg); sqlite3_free(query); @@ -946,9 +946,9 @@ db_file_ping(int id) } int -db_file_id_bypath(char *path, int *id) +db_file_id_bypath(char *path) { -#define Q_TMPL "SELECT id FROM songs WHERE disabled = 0 AND path = '%q';" +#define Q_TMPL "SELECT id FROM songs WHERE path = '%q';" char *query; sqlite3_stmt *stmt; int ret; @@ -958,7 +958,7 @@ db_file_id_bypath(char *path, int *id) { DPRINTF(E_LOG, L_DB, "Out of memory for query string\n"); - return -1; + return 0; } DPRINTF(E_DBG, L_DB, "Running query '%s'\n", query); @@ -969,7 +969,7 @@ db_file_id_bypath(char *path, int *id) DPRINTF(E_LOG, L_DB, "Could not prepare statement: %s\n", sqlite3_errmsg(hdl)); sqlite3_free(query); - return -1; + return 0; } ret = sqlite3_step(stmt); @@ -982,15 +982,66 @@ db_file_id_bypath(char *path, int *id) sqlite3_finalize(stmt); sqlite3_free(query); - return -1; + return 0; } - *id = sqlite3_column_int(stmt, 0); + ret = sqlite3_column_int(stmt, 0); sqlite3_finalize(stmt); sqlite3_free(query); - return 0; + return ret; + +#undef Q_TMPL +} + +time_t +db_file_stamp_bypath(char *path) +{ +#define Q_TMPL "SELECT db_timestamp FROM songs WHERE path = '%q';" + char *query; + sqlite3_stmt *stmt; + time_t stamp; + int ret; + + query = sqlite3_mprintf(Q_TMPL, path); + if (!query) + { + DPRINTF(E_LOG, L_DB, "Out of memory for query string\n"); + + return 0; + } + + DPRINTF(E_DBG, L_DB, "Running query '%s'\n", query); + + ret = sqlite3_prepare_v2(hdl, query, strlen(query) + 1, &stmt, NULL); + if (ret != SQLITE_OK) + { + DPRINTF(E_LOG, L_DB, "Could not prepare statement: %s\n", sqlite3_errmsg(hdl)); + + sqlite3_free(query); + return 0; + } + + ret = sqlite3_step(stmt); + if (ret != SQLITE_ROW) + { + if (ret == SQLITE_DONE) + DPRINTF(E_INFO, L_DB, "No results\n"); + else + DPRINTF(E_LOG, L_DB, "Could not step: %s\n", sqlite3_errmsg(hdl)); + + sqlite3_finalize(stmt); + sqlite3_free(query); + return 0; + } + + stamp = (time_t)sqlite3_column_int64(stmt, 0); + + sqlite3_finalize(stmt); + sqlite3_free(query); + + return stamp; #undef Q_TMPL } diff --git a/src/db.h b/src/db.h index 8023fc06..af325aa1 100644 --- a/src/db.h +++ b/src/db.h @@ -226,10 +226,13 @@ void db_file_inc_playcount(int id); void -db_file_ping(int id); +db_file_ping(char *path); int -db_file_id_bypath(char *path, int *id); +db_file_id_bypath(char *path); + +time_t +db_file_stamp_bypath(char *path); struct media_file_info * db_file_fetch_byid(int id); diff --git a/src/filescanner.c b/src/filescanner.c index 422b1421..57a24869 100644 --- a/src/filescanner.c +++ b/src/filescanner.c @@ -177,73 +177,52 @@ fixup_tags(struct media_file_info *mfi) static void process_media_file(char *file, time_t mtime, off_t size, int compilation) { - struct media_file_info *mfi; + struct media_file_info mfi; char *filename; char *ext; - int need_update; + time_t stamp; int ret; - mfi = db_file_fetch_bypath(file); + stamp = db_file_stamp_bypath(file); - need_update = (!mfi || (mfi->db_timestamp < mtime)); - - if (!need_update) + if (stamp >= mtime) { - db_file_ping(mfi->id); - - free_mfi(mfi, 0); + db_file_ping(file); return; } - if (mfi) - { - ret = mfi->id; - free_mfi(mfi, 1); - } - else - { - ret = 0; - mfi = (struct media_file_info *)malloc(sizeof(struct media_file_info)); - if (!mfi) - { - DPRINTF(E_WARN, L_SCAN, "Out of memory for media_file_info\n"); - return; - } - } + memset(&mfi, 0, sizeof(struct media_file_info)); - memset(mfi, 0, sizeof(struct media_file_info)); - mfi->id = ret; + if (stamp) + mfi.id = db_file_id_bypath(file); filename = strrchr(file, '/'); if (!filename) { DPRINTF(E_LOG, L_SCAN, "Could not determine filename for %s\n", file); - free(mfi); return; } - mfi->fname = strdup(filename + 1); - if (!mfi->fname) + mfi.fname = strdup(filename + 1); + if (!mfi.fname) { DPRINTF(E_WARN, L_SCAN, "Out of memory for fname\n"); - free(mfi); return; } - mfi->path = strdup(file); - if (!mfi->path) + mfi.path = strdup(file); + if (!mfi.path) { DPRINTF(E_WARN, L_SCAN, "Out of memory for path\n"); - free(mfi->fname); - free(mfi); + free(mfi.fname); return; } - mfi->time_modified = mtime; - mfi->file_size = size; + mfi.time_modified = mtime; + mfi.file_size = size; ret = -1; @@ -254,38 +233,38 @@ process_media_file(char *file, time_t mtime, off_t size, int compilation) if ((strcmp(ext, ".pls") == 0) || (strcmp(ext, ".url") == 0)) { - ret = scan_url_file(file, mfi); + ret = scan_url_file(file, &mfi); if (ret == 0) - mfi->data_kind = 1; /* url/stream */ + mfi.data_kind = 1; /* url/stream */ } } /* General case */ if (ret < 0) { - ret = scan_metadata_ffmpeg(file, mfi); - mfi->data_kind = 0; /* real file */ + ret = scan_metadata_ffmpeg(file, &mfi); + mfi.data_kind = 0; /* real file */ } if (ret < 0) { DPRINTF(E_LOG, L_SCAN, "Could not extract metadata for %s\n", file); - free_mfi(mfi, 0); + free_mfi(&mfi, 1); return; } - mfi->compilation = compilation; - mfi->item_kind = 2; /* music */ + mfi.compilation = compilation; + mfi.item_kind = 2; /* music */ - fixup_tags(mfi); + fixup_tags(&mfi); - if (mfi->id == 0) - db_file_add(mfi); + if (mfi.id == 0) + db_file_add(&mfi); else - db_file_update(mfi); + db_file_update(&mfi); - free_mfi(mfi, 0); + free_mfi(&mfi, 1); } static void