00001
00021 #include "lightmediascanner_db_private.h"
00022 #include <stdlib.h>
00023 #include <stdio.h>
00024 #include <string.h>
00025
00026 #if SQLITE_VERSION_NUMBER < 3003009
00027 int
00028 sqlite3_prepare_v2(sqlite3 *db, const char *sql, int len, sqlite3_stmt **stmt, const char **tail)
00029 {
00030 return sqlite3_prepare(db, sql, len, stmt, tail);
00031 }
00032 #endif
00033
00034 #if SQLITE_VERSION_NUMBER < 3003007
00035 int
00036 sqlite3_clear_bindings(sqlite3_stmt *stmt)
00037 {
00038 int i, last;
00039 int rc;
00040
00041 rc = SQLITE_OK;
00042 last = sqlite3_bind_parameter_count(stmt);
00043 for(i = 1; rc == SQLITE_OK && i <= last; i++) {
00044 rc = sqlite3_bind_null(stmt, i);
00045 }
00046 return rc;
00047 }
00048 #endif
00049
00050 #if SQLITE_VERSION_NUMBER < 3003008
00051
00052
00053
00054 int
00055 lms_db_create_trigger_if_not_exists(sqlite3 *db, const char *sql)
00056 {
00057 char *errmsg, *query;
00058 int r, sql_len, prefix_len;
00059
00060 prefix_len = sizeof("CREATE TRIGGER ") - 1;
00061 sql_len = strlen(sql);
00062 query = malloc((prefix_len + sql_len + 1) * sizeof(char));
00063 if (!query)
00064 return -1;
00065
00066 memcpy(query, "CREATE TRIGGER ", prefix_len);
00067 memcpy(query + prefix_len, sql, sql_len + 1);
00068 r = sqlite3_exec(db, query, NULL, NULL, &errmsg);
00069 free(query);
00070 if (r != SQLITE_OK)
00071 sqlite3_free(errmsg);
00072 return 0;
00073 }
00074 #else
00075 int
00076 lms_db_create_trigger_if_not_exists(sqlite3 *db, const char *sql)
00077 {
00078 char *errmsg, *query;
00079 int r, sql_len, prefix_len;
00080
00081 prefix_len = sizeof("CREATE TRIGGER IF NOT EXISTS ") - 1;
00082 sql_len = strlen(sql);
00083 query = malloc((prefix_len + sql_len + 1) * sizeof(char));
00084 if (!query)
00085 return -1;
00086
00087 memcpy(query, "CREATE TRIGGER IF NOT EXISTS ", prefix_len);
00088 memcpy(query + prefix_len, sql, sql_len + 1);
00089 r = sqlite3_exec(db, query, NULL, NULL, &errmsg);
00090 free(query);
00091 if (r != SQLITE_OK) {
00092 fprintf(stderr, "ERROR: could not create trigger: %s\n", errmsg);
00093 sqlite3_free(errmsg);
00094 return -2;
00095 }
00096 return 0;
00097 }
00098 #endif
00099
00100 sqlite3_stmt *
00101 lms_db_compile_stmt(sqlite3 *db, const char *sql)
00102 {
00103 sqlite3_stmt *stmt;
00104
00105 if (sqlite3_prepare_v2(db, sql, -1, &stmt, NULL) != SQLITE_OK)
00106 fprintf(stderr, "ERROR: could not prepare \"%s\": %s\n", sql,
00107 sqlite3_errmsg(db));
00108
00109 return stmt;
00110 }
00111
00112 int
00113 lms_db_finalize_stmt(sqlite3_stmt *stmt, const char *name)
00114 {
00115 int r;
00116
00117 r = sqlite3_finalize(stmt);
00118 if (r != SQLITE_OK) {
00119 fprintf(stderr, "ERROR: could not finalize %s statement: #%d\n",
00120 name, r);
00121 return -1;
00122 }
00123
00124 return 0;
00125 }
00126
00127 int
00128 lms_db_reset_stmt(sqlite3_stmt *stmt)
00129 {
00130 int r, ret;
00131
00132 ret = r = sqlite3_reset(stmt);
00133 if (r != SQLITE_OK)
00134 fprintf(stderr, "ERROR: could not reset SQL statement: #%d\n", r);
00135
00136 r = sqlite3_clear_bindings(stmt);
00137 ret += r;
00138 if (r != SQLITE_OK)
00139 fprintf(stderr, "ERROR: could not clear SQL: #%d\n", r);
00140
00141 return ret;
00142 }
00143
00144 int
00145 lms_db_bind_text(sqlite3_stmt *stmt, int col, const char *text, int len)
00146 {
00147 int r;
00148
00149 if (text)
00150 r = sqlite3_bind_text(stmt, col, text, len, SQLITE_STATIC);
00151 else
00152 r = sqlite3_bind_null(stmt, col);
00153
00154 if (r == SQLITE_OK)
00155 return 0;
00156 else {
00157 sqlite3 *db;
00158 const char *err;
00159
00160 db = sqlite3_db_handle(stmt);
00161 err = sqlite3_errmsg(db);
00162 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00163 return -col;
00164 }
00165 }
00166
00167 int
00168 lms_db_bind_blob(sqlite3_stmt *stmt, int col, const void *blob, int len)
00169 {
00170 int r;
00171
00172 if (blob)
00173 r = sqlite3_bind_blob(stmt, col, blob, len, SQLITE_STATIC);
00174 else
00175 r = sqlite3_bind_null(stmt, col);
00176
00177 if (r == SQLITE_OK)
00178 return 0;
00179 else {
00180 sqlite3 *db;
00181 const char *err;
00182
00183 db = sqlite3_db_handle(stmt);
00184 err = sqlite3_errmsg(db);
00185 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00186 return -col;
00187 }
00188 }
00189
00190 int
00191 lms_db_bind_int64(sqlite3_stmt *stmt, int col, int64_t value)
00192 {
00193 int r;
00194
00195 r = sqlite3_bind_int64(stmt, col, value);
00196 if (r == SQLITE_OK)
00197 return 0;
00198 else {
00199 sqlite3 *db;
00200 const char *err;
00201
00202 db = sqlite3_db_handle(stmt);
00203 err = sqlite3_errmsg(db);
00204 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00205 return -col;
00206 }
00207 }
00208
00209 int
00210 lms_db_bind_int64_or_null(sqlite3_stmt *stmt, int col, int64_t *p_value)
00211 {
00212 int r;
00213
00214 if (p_value)
00215 r = sqlite3_bind_int64(stmt, col, *p_value);
00216 else
00217 r = sqlite3_bind_null(stmt, col);
00218 if (r == SQLITE_OK)
00219 return 0;
00220 else {
00221 sqlite3 *db;
00222 const char *err;
00223
00224 db = sqlite3_db_handle(stmt);
00225 err = sqlite3_errmsg(db);
00226 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00227 return -col;
00228 }
00229 }
00230
00231 int
00232 lms_db_bind_int(sqlite3_stmt *stmt, int col, int value)
00233 {
00234 int r;
00235
00236 r = sqlite3_bind_int(stmt, col, value);
00237 if (r == SQLITE_OK)
00238 return 0;
00239 else {
00240 sqlite3 *db;
00241 const char *err;
00242
00243 db = sqlite3_db_handle(stmt);
00244 err = sqlite3_errmsg(db);
00245 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00246 return -col;
00247 }
00248 }
00249
00250 int
00251 lms_db_bind_double(sqlite3_stmt *stmt, int col, double value)
00252 {
00253 int r;
00254
00255 r = sqlite3_bind_double(stmt, col, value);
00256 if (r == SQLITE_OK)
00257 return 0;
00258 else {
00259 sqlite3 *db;
00260 const char *err;
00261
00262 db = sqlite3_db_handle(stmt);
00263 err = sqlite3_errmsg(db);
00264 fprintf(stderr, "ERROR: could not bind SQL value %d: %s\n", col, err);
00265 return -col;
00266 }
00267 }
00268
00269 int
00270 lms_db_table_version_get(sqlite3 *db, const char *table)
00271 {
00272 int r, version;
00273 sqlite3_stmt *stmt;
00274
00275 stmt = lms_db_compile_stmt(db,
00276 "SELECT version FROM lms_internal WHERE tab = ?");
00277 if (!stmt)
00278 return -1;
00279
00280 if (lms_db_bind_text(stmt, 1, table, -1) != 0) {
00281 version = -1;
00282 goto done;
00283 }
00284
00285 r = sqlite3_step(stmt);
00286 if (r == SQLITE_DONE)
00287 version = 0;
00288 else if (r == SQLITE_ROW)
00289 version = sqlite3_column_int(stmt, 0);
00290 else {
00291 version = -1;
00292 fprintf(stderr, "ERROR: could not get table '%s' version: %s\n",
00293 table, sqlite3_errmsg(db));
00294 }
00295
00296 done:
00297 lms_db_reset_stmt(stmt);
00298 lms_db_finalize_stmt(stmt, "table_version_get");
00299
00300 return version;
00301 }
00302
00303 int
00304 lms_db_table_version_set(sqlite3 *db, const char *table, unsigned int version)
00305 {
00306 int r, ret;
00307 sqlite3_stmt *stmt;
00308
00309 stmt = lms_db_compile_stmt(db,
00310 "INSERT OR REPLACE INTO lms_internal (tab, version) VALUES (?, ?)");
00311 if (!stmt)
00312 return -1;
00313
00314 ret = lms_db_bind_text(stmt, 1, table, -1);
00315 if (ret != 0)
00316 goto done;
00317
00318 ret = lms_db_bind_int(stmt, 2, version);
00319 if (ret != 0)
00320 goto done;
00321
00322 r = sqlite3_step(stmt);
00323 if (r != SQLITE_DONE) {
00324 ret = -1;
00325 fprintf(stderr, "ERROR: could not set table '%s' version: %s\n",
00326 table, sqlite3_errmsg(db));
00327 }
00328
00329 done:
00330 lms_db_reset_stmt(stmt);
00331 lms_db_finalize_stmt(stmt, "table_version_set");
00332
00333 return ret;
00334 }
00335
00336 int
00337 lms_db_table_update(sqlite3 *db, const char *table, unsigned int current_version, unsigned int last_version, const lms_db_table_updater_t *updaters)
00338 {
00339 if (current_version == last_version)
00340 return 0;
00341 else if (current_version > last_version) {
00342 fprintf(stderr,
00343 "WARNING: current version (%d) of table '%s' is greater than "
00344 "last known version (%d), no updates will be made.\n",
00345 current_version, table, last_version);
00346 return 0;
00347 }
00348
00349 for (; current_version < last_version; current_version++) {
00350 int r, is_last_run;
00351
00352 is_last_run = current_version == (last_version - 1);
00353 r = updaters[current_version](db, table, current_version, is_last_run);
00354 if (r != 0) {
00355 fprintf(stderr,
00356 "ERROR: could not update table '%s' from version %d->%d\n",
00357 table, current_version, current_version + 1);
00358 return r;
00359 }
00360 lms_db_table_version_set(db, table, current_version + 1);
00361 }
00362
00363 return 0;
00364 }
00365
00366 int
00367 lms_db_table_update_if_required(sqlite3 *db, const char *table, unsigned int last_version, lms_db_table_updater_t *updaters)
00368 {
00369 int current_version;
00370
00371 current_version = lms_db_table_version_get(db, table);
00372 if (current_version < 0)
00373 return -1;
00374 else
00375 return lms_db_table_update(db, table, current_version, last_version,
00376 updaters);
00377 }
00378
00379 static int
00380 lms_db_cache_find_db(const struct lms_db_cache *cache, const sqlite3 *db)
00381 {
00382 int i;
00383
00384 for (i = 0; i < cache->size; i++)
00385 if (cache->entries[i].db == db)
00386 return i;
00387
00388 return -1;
00389 }
00390
00391 static int
00392 lms_db_cache_resize(struct lms_db_cache *cache, int new_size)
00393 {
00394 cache->size = new_size;
00395 cache->entries = realloc(cache->entries,
00396 cache->size * sizeof(*cache->entries));
00397 if (cache->size && !cache->entries) {
00398 perror("realloc");
00399 cache->size = 0;
00400 return -1;
00401 }
00402
00403 return 0;
00404 }
00405
00406 int
00407 lms_db_cache_add(struct lms_db_cache *cache, const sqlite3 *db, void *data)
00408 {
00409 struct lms_db_cache_entry *e;
00410 int idx;
00411
00412 idx = lms_db_cache_find_db(cache, db);
00413 if (idx >= 0) {
00414 e = cache->entries + idx;
00415 if (e->data == data)
00416 return 0;
00417 else {
00418 fprintf(stderr,
00419 "ERROR: cache %p for db %p has another data registered"
00420 ": %p (current is %p)\n", cache, db, e->data, data);
00421 return -1;
00422 }
00423 }
00424
00425 idx = cache->size;
00426 if (lms_db_cache_resize(cache, cache->size + 1) != 0) {
00427 return -2;
00428 }
00429
00430 e = cache->entries + idx;
00431 e->db = db;
00432 e->data = data;
00433 return 0;
00434 }
00435
00436 int
00437 lms_db_cache_del(struct lms_db_cache *cache, const sqlite3 *db, void *data)
00438 {
00439 int idx;
00440 struct lms_db_cache_entry *e;
00441
00442 idx = lms_db_cache_find_db(cache, db);
00443 if (idx < 0) {
00444 fprintf(stderr, "ERROR: no db %p found in cache %p\n", db, cache);
00445 return -1;
00446 }
00447
00448 e = cache->entries + idx;
00449 if (e->data != data) {
00450 fprintf(stderr, "ERROR: data mismatch in request to delete from cache: "
00451 "want %p, has %p, cache %p, db %p\n", data, e->data, cache, db);
00452 return -2;
00453 }
00454
00455 for (; idx < cache->size - 1; idx++)
00456 cache->entries[idx] = cache->entries[idx + 1];
00457
00458 return lms_db_cache_resize(cache, cache->size - 1);
00459 }
00460
00461 int
00462 lms_db_cache_get(struct lms_db_cache *cache, const sqlite3 *db, void **pdata)
00463 {
00464 int idx;
00465
00466 idx = lms_db_cache_find_db(cache, db);
00467 if (idx < 0)
00468 return -1;
00469
00470 *pdata = cache->entries[idx].data;
00471 return 0;
00472 }
00473
00474 int
00475 lms_db_create_core_tables_if_required(sqlite3 *db)
00476 {
00477 char *errmsg;
00478 int r;
00479
00480 errmsg = NULL;
00481 r = sqlite3_exec(db,
00482 "CREATE TABLE IF NOT EXISTS lms_internal ("
00483 "tab TEXT NOT NULL UNIQUE, "
00484 "version INTEGER NOT NULL"
00485 ")",
00486 NULL, NULL, &errmsg);
00487 if (r != SQLITE_OK) {
00488 fprintf(stderr, "ERROR: could not create 'lms_internal' table: %s\n",
00489 errmsg);
00490 sqlite3_free(errmsg);
00491 return -1;
00492 }
00493
00494 r = sqlite3_exec(db,
00495 "CREATE TABLE IF NOT EXISTS files ("
00496 "id INTEGER PRIMARY KEY AUTOINCREMENT, "
00497 "path BLOB NOT NULL UNIQUE, "
00498 "mtime INTEGER NOT NULL, "
00499 "dtime INTEGER NOT NULL, "
00500 "size INTEGER NOT NULL"
00501 ")",
00502 NULL, NULL, &errmsg);
00503 if (r != SQLITE_OK) {
00504 fprintf(stderr, "ERROR: could not create 'files' table: %s\n", errmsg);
00505 sqlite3_free(errmsg);
00506 return -2;
00507 }
00508
00509 r = sqlite3_exec(db,
00510 "CREATE INDEX IF NOT EXISTS files_path_idx ON files ("
00511 "path"
00512 ")",
00513 NULL, NULL, &errmsg);
00514 if (r != SQLITE_OK) {
00515 fprintf(stderr, "ERROR: could not create 'files_path_idx' index: %s\n",
00516 errmsg);
00517 sqlite3_free(errmsg);
00518 return -3;
00519 }
00520
00521 return 0;
00522 }
00523
00524
00525 sqlite3_stmt *
00526 lms_db_compile_stmt_begin_transaction(sqlite3 *db)
00527 {
00528 return lms_db_compile_stmt(db, "BEGIN TRANSACTION");
00529 }
00530
00531 int
00532 lms_db_begin_transaction(sqlite3_stmt *stmt)
00533 {
00534 int r, ret;
00535
00536 ret = 0;
00537 r = sqlite3_step(stmt);
00538 if (r != SQLITE_DONE) {
00539 fprintf(stderr, "ERROR: could not begin transaction: %s\n",
00540 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00541 ret = -1;
00542 }
00543
00544 r = sqlite3_reset(stmt);
00545 if (r != SQLITE_OK)
00546 fprintf(stderr, "ERROR: could not reset SQL statement: %s\n",
00547 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00548
00549 return ret;
00550 }
00551
00552 sqlite3_stmt *
00553 lms_db_compile_stmt_end_transaction(sqlite3 *db)
00554 {
00555 return lms_db_compile_stmt(db, "COMMIT");
00556 }
00557
00558 int
00559 lms_db_end_transaction(sqlite3_stmt *stmt)
00560 {
00561 int r, ret;
00562
00563 ret = 0;
00564 r = sqlite3_step(stmt);
00565 if (r != SQLITE_DONE) {
00566 fprintf(stderr, "ERROR: could not end transaction: %s\n",
00567 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00568 ret = -1;
00569 }
00570
00571 r = sqlite3_reset(stmt);
00572 if (r != SQLITE_OK)
00573 fprintf(stderr, "ERROR: could not reset SQL statement: %s\n",
00574 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00575
00576 return ret;
00577 }
00578
00579 sqlite3_stmt *
00580 lms_db_compile_stmt_get_file_info(sqlite3 *db)
00581 {
00582 return lms_db_compile_stmt(db,
00583 "SELECT id, mtime, dtime, size FROM files WHERE path = ?");
00584 }
00585
00586 int
00587 lms_db_get_file_info(sqlite3_stmt *stmt, struct lms_file_info *finfo)
00588 {
00589 int r, ret;
00590
00591 ret = lms_db_bind_blob(stmt, 1, finfo->path, finfo->path_len);
00592 if (ret != 0)
00593 goto done;
00594
00595 r = sqlite3_step(stmt);
00596 if (r == SQLITE_DONE) {
00597 ret = 1;
00598 finfo->id = -1;
00599 goto done;
00600 }
00601
00602 if (r != SQLITE_ROW) {
00603 fprintf(stderr, "ERROR: could not get file info from table: %s\n",
00604 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00605 ret = -2;
00606 goto done;
00607 }
00608
00609 finfo->id = sqlite3_column_int64(stmt, 0);
00610 finfo->mtime = sqlite3_column_int(stmt, 1);
00611 finfo->dtime = sqlite3_column_int(stmt, 2);
00612 finfo->size = sqlite3_column_int(stmt, 3);
00613 ret = 0;
00614
00615 done:
00616 lms_db_reset_stmt(stmt);
00617
00618 return ret;
00619 }
00620
00621 sqlite3_stmt *
00622 lms_db_compile_stmt_update_file_info(sqlite3 *db)
00623 {
00624 return lms_db_compile_stmt(db,
00625 "UPDATE files SET mtime = ?, dtime = ?, size = ? WHERE id = ?");
00626 }
00627
00628 int
00629 lms_db_update_file_info(sqlite3_stmt *stmt, const struct lms_file_info *finfo)
00630 {
00631 int r, ret;
00632
00633 ret = lms_db_bind_int(stmt, 1, finfo->mtime);
00634 if (ret != 0)
00635 goto done;
00636
00637 ret = lms_db_bind_int(stmt, 2, finfo->dtime);
00638 if (ret != 0)
00639 goto done;
00640
00641 ret = lms_db_bind_int(stmt, 3, finfo->size);
00642 if (ret != 0)
00643 goto done;
00644
00645 ret = lms_db_bind_int(stmt, 4, finfo->id);
00646 if (ret != 0)
00647 goto done;
00648
00649 r = sqlite3_step(stmt);
00650 if (r != SQLITE_DONE) {
00651 fprintf(stderr, "ERROR: could not update file info: %s\n",
00652 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00653 ret = -5;
00654 goto done;
00655 }
00656
00657 ret = 0;
00658
00659 done:
00660 lms_db_reset_stmt(stmt);
00661
00662 return ret;
00663 }
00664
00665 sqlite3_stmt *
00666 lms_db_compile_stmt_insert_file_info(sqlite3 *db)
00667 {
00668 return lms_db_compile_stmt(db,
00669 "INSERT INTO files (path, mtime, dtime, size) VALUES(?, ?, ?, ?)");
00670 }
00671
00672 int
00673 lms_db_insert_file_info(sqlite3_stmt *stmt, struct lms_file_info *finfo)
00674 {
00675 int r, ret;
00676
00677 ret = lms_db_bind_blob(stmt, 1, finfo->path, finfo->path_len);
00678 if (ret != 0)
00679 goto done;
00680
00681 ret = lms_db_bind_int(stmt, 2, finfo->mtime);
00682 if (ret != 0)
00683 goto done;
00684
00685 ret = lms_db_bind_int(stmt, 3, finfo->dtime);
00686 if (ret != 0)
00687 goto done;
00688
00689 ret = lms_db_bind_int(stmt, 4, finfo->size);
00690 if (ret != 0)
00691 goto done;
00692
00693 r = sqlite3_step(stmt);
00694 if (r != SQLITE_DONE) {
00695 fprintf(stderr, "ERROR: could not insert file info: %s\n",
00696 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00697 ret = -5;
00698 goto done;
00699 }
00700
00701 finfo->id = sqlite3_last_insert_rowid(sqlite3_db_handle(stmt));
00702 ret = 0;
00703
00704 done:
00705 lms_db_reset_stmt(stmt);
00706
00707 return ret;
00708 }
00709
00710 sqlite3_stmt *
00711 lms_db_compile_stmt_delete_file_info(sqlite3 *db)
00712 {
00713 return lms_db_compile_stmt(db, "DELETE FROM files WHERE id = ?");
00714 }
00715
00716 int
00717 lms_db_delete_file_info(sqlite3_stmt *stmt, const struct lms_file_info *finfo)
00718 {
00719 int r, ret;
00720
00721 ret = lms_db_bind_int64(stmt, 1, finfo->id);
00722 if (ret != 0)
00723 goto done;
00724
00725 r = sqlite3_step(stmt);
00726 if (r != SQLITE_DONE) {
00727 fprintf(stderr, "ERROR: could not delete file info: %s\n",
00728 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00729 ret = -2;
00730 goto done;
00731 }
00732 ret = 0;
00733
00734 done:
00735 lms_db_reset_stmt(stmt);
00736
00737 return ret;
00738 }
00739
00740 sqlite3_stmt *
00741 lms_db_compile_stmt_set_file_dtime(sqlite3 *db)
00742 {
00743 return lms_db_compile_stmt(db, "UPDATE files SET dtime = ? WHERE id = ?");
00744 }
00745
00746 int
00747 lms_db_set_file_dtime(sqlite3_stmt *stmt, const struct lms_file_info *finfo)
00748 {
00749 int r, ret;
00750
00751 ret = lms_db_bind_int(stmt, 1, finfo->dtime);
00752 if (ret != 0)
00753 goto done;
00754
00755 ret = lms_db_bind_int64(stmt, 1, finfo->id);
00756 if (ret != 0)
00757 goto done;
00758
00759 r = sqlite3_step(stmt);
00760 if (r != SQLITE_DONE) {
00761 fprintf(stderr, "ERROR: could not set file dtime: %s\n",
00762 sqlite3_errmsg(sqlite3_db_handle(stmt)));
00763 ret = -3;
00764 goto done;
00765 }
00766
00767 ret = 0;
00768
00769 done:
00770 lms_db_reset_stmt(stmt);
00771
00772 return ret;
00773 }
00774
00775 sqlite3_stmt *
00776 lms_db_compile_stmt_get_files(sqlite3 *db)
00777 {
00778 return lms_db_compile_stmt(db,
00779 "SELECT id, path, mtime, dtime, size FROM files WHERE path LIKE ?");
00780 }
00781
00782 int
00783 lms_db_get_files(sqlite3_stmt *stmt, const char *path, int len)
00784 {
00785 int ret;
00786
00787 ret = lms_db_bind_blob(stmt, 1, path, len);
00788 return ret;
00789 }