#include <sqlite3.h>
#include <pakfire/archive.h>
+#include <pakfire/ctx.h>
#include <pakfire/db.h>
#include <pakfire/dependencies.h>
#include <pakfire/digest.h>
#define SCHEMA_MIN_SUP 7
struct pakfire_db {
+ struct pakfire_ctx* ctx;
struct pakfire* pakfire;
int nrefs;
};
static void logging_callback(void* data, int r, const char* msg) {
- struct pakfire* pakfire = (struct pakfire*)data;
+ struct pakfire_ctx* ctx = data;
- ERROR(pakfire, "Database Error: %s: %s\n",
+ CTX_ERROR(ctx, "Database Error: %s: %s\n",
sqlite3_errstr(r), msg);
}
+static int pakfire_db_check_table(struct pakfire_db* db, const char* table) {
+ sqlite3_stmt* stmt = NULL;
+ int r;
+
+ const char* sql = "SELECT * FROM sqlite_master WHERE type = ? AND name = ?";
+
+ // Prepare the statement
+ r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
+ if (r != SQLITE_OK) {
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
+ sql, sqlite3_errmsg(db->handle));
+ goto ERROR;
+ }
+
+ // Bind type
+ r = sqlite3_bind_text(stmt, 1, "table", -1, NULL);
+ if (r != SQLITE_OK) {
+ CTX_ERROR(db->ctx, "Could not bind type: %s\n", sqlite3_errmsg(db->handle));
+ goto ERROR;
+ }
+
+ // Bind name
+ r = sqlite3_bind_text(stmt, 2, table, -1, NULL);
+ if (r != SQLITE_OK) {
+ CTX_ERROR(db->ctx, "Could not bind name: %s\n", sqlite3_errmsg(db->handle));
+ goto ERROR;
+ }
+
+ // Execute the statement
+ do {
+ r = sqlite3_step(stmt);
+ } while (r == SQLITE_BUSY);
+
+ // We should have read a row
+ if (r != SQLITE_ROW)
+ goto ERROR;
+
+ // If we get here, the table exists.
+ r = 0;
+
+ERROR:
+ if (stmt)
+ sqlite3_finalize(stmt);
+
+ return r;
+}
+
static sqlite3_value* pakfire_db_get(struct pakfire_db* db, const char* key) {
sqlite3_stmt* stmt = NULL;
sqlite3_value* val = NULL;
int r;
+ // If the schema has not been initialized, yet, check if the settings table exist, at all
+ if (!db->schema) {
+ r = pakfire_db_check_table(db, "settings");
+ if (r)
+ return NULL;
+ }
+
const char* sql = "SELECT val FROM settings WHERE key = ?";
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r != SQLITE_OK) {
- //ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ //CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
// sql, sqlite3_errmsg(db->handle));
return NULL;
}
// Bind key
r = sqlite3_bind_text(stmt, 1, key, strlen(key), NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Read value
val = sqlite3_column_value(stmt, 0);
if (!val) {
- ERROR(db->pakfire, "Could not read value\n");
+ CTX_ERROR(db->ctx, "Could not read value\n");
goto ERROR;
}
sqlite3_stmt* stmt = NULL;
int r;
- DEBUG(db->pakfire, "Setting %s to '%s'\n", key, val);
+ CTX_DEBUG(db->ctx, "Setting %s to '%s'\n", key, val);
const char* sql = "INSERT INTO settings(key, val) VALUES(?, ?) \
ON CONFLICT (key) DO UPDATE SET val = excluded.val";
// Prepare statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
return 1;
}
// Bind key
r = sqlite3_bind_text(stmt, 1, key, strlen(key), NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind val
r = sqlite3_bind_text(stmt, 2, val, strlen(val), NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not bind val: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind val: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
sqlite3_stmt* stmt = NULL;
int r;
- DEBUG(db->pakfire, "Setting %s to '%d'\n", key, val);
+ CTX_DEBUG(db->ctx, "Setting %s to '%d'\n", key, val);
const char* sql = "INSERT INTO settings(key, val) VALUES(?, ?) \
ON CONFLICT (key) DO UPDATE SET val = excluded.val";
// Prepare statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
return 1;
}
// Bind key
r = sqlite3_bind_text(stmt, 1, key, strlen(key), NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind key: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind val
r = sqlite3_bind_int64(stmt, 2, val);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not bind val: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind val: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
t = sqlite3_value_int64(value);
sqlite3_value_free(value);
} else {
- DEBUG(db->pakfire, "Could not find last modification timestamp\n");
+ CTX_DEBUG(db->ctx, "Could not find last modification timestamp\n");
}
return t;
static int pakfire_db_execute(struct pakfire_db* db, const char* stmt) {
int r;
- DEBUG(db->pakfire, "Executing database query: %s\n", stmt);
+ CTX_DEBUG(db->ctx, "Executing database query: %s\n", stmt);
do {
r = sqlite3_exec(db->handle, stmt, NULL, NULL, NULL);
// Log any errors
if (r) {
- ERROR(db->pakfire, "Database query failed: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Database query failed: %s\n", sqlite3_errmsg(db->handle));
}
return r;
// Close database handle
int r = sqlite3_close(db->handle);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not close database handle: %s\n",
+ CTX_ERROR(db->ctx, "Could not close database handle: %s\n",
sqlite3_errmsg(db->handle));
}
}
- pakfire_unref(db->pakfire);
-
+ if (db->pakfire)
+ pakfire_unref(db->pakfire);
+ if (db->ctx)
+ pakfire_ctx_unref(db->ctx);
free(db);
}
static int pakfire_db_get_schema(struct pakfire_db* db) {
+ // Fetch the schema version
sqlite3_value* value = pakfire_db_get(db, "schema");
if (!value)
- return -1;
+ return 0;
int schema = sqlite3_value_int64(value);
sqlite3_value_free(value);
- DEBUG(db->pakfire, "Database has schema version %d\n", schema);
+ CTX_DEBUG(db->ctx, "Database has schema version %d\n", schema);
return schema;
}
// Set architecture
r = pakfire_db_set_string(db, "arch", arch);
if (r) {
- ERROR(db->pakfire, "Could not set architecture\n");
+ CTX_ERROR(db->ctx, "Could not set architecture\n");
return r;
}
switch (db->schema) {
// No schema exists
- case -1:
+ case 0:
r = pakfire_db_create_schema(db);
if (r)
goto ROLLBACK;
break;
default:
- ERROR(db->pakfire, "Cannot migrate database from schema %d\n", db->schema);
+ CTX_ERROR(db->ctx, "Cannot migrate database from schema %d\n", db->schema);
goto ROLLBACK;
}
// Fetch database architecture
char* db_arch = pakfire_db_get_string(db, "arch");
if (!db_arch) {
- ERROR(db->pakfire, "Database is of an unknown architecture\n");
+ CTX_ERROR(db->ctx, "Database is of an unknown architecture\n");
goto ERROR;
}
int r;
// Setup logging
- sqlite3_config(SQLITE_CONFIG_LOG, logging_callback, db->pakfire);
+ sqlite3_config(SQLITE_CONFIG_LOG, logging_callback, db->ctx);
// Enable foreign keys
pakfire_db_execute(db, "PRAGMA foreign_keys = ON");
db->schema = pakfire_db_get_schema(db);
// Check if the schema is recent enough
- if (db->schema > 0 && db->schema < SCHEMA_MIN_SUP) {
- ERROR(db->pakfire, "Database schema %d is not supported by this version of Pakfire\n",
+ if (db->schema && db->schema < SCHEMA_MIN_SUP) {
+ CTX_ERROR(db->ctx, "Database schema %d is not supported by this version of Pakfire\n",
db->schema);
return 1;
}
// Read modification timestamp
db->last_modified_at = pakfire_read_modification_time(db);
- DEBUG(db->pakfire, "The database was last modified at %ld\n", db->last_modified_at);
+ CTX_DEBUG(db->ctx, "The database was last modified at %ld\n", db->last_modified_at);
// Done when not in read-write mode
if (db->mode != PAKFIRE_DB_READWRITE)
// Set database journal to WAL
r = pakfire_db_execute(db, "PRAGMA journal_mode = WAL");
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not set journal mode to WAL: %s\n",
+ CTX_ERROR(db->ctx, "Could not set journal mode to WAL: %s\n",
sqlite3_errmsg(db->handle));
return 1;
}
// Disable autocheckpoint
r = sqlite3_wal_autocheckpoint(db->handle, 0);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not disable autocheckpoint: %s\n",
+ CTX_ERROR(db->ctx, "Could not disable autocheckpoint: %s\n",
sqlite3_errmsg(db->handle));
return 1;
}
if (!o)
return -ENOMEM;
+ // Store a reference to the context
+ o->ctx = pakfire_ctx(pakfire);
+
o->pakfire = pakfire_ref(pakfire);
o->nrefs = 1;
// Try to open the sqlite3 database file
r = sqlite3_open_v2(o->path, &o->handle, sqlite3_flags, NULL);
if (r != SQLITE_OK) {
- ERROR(pakfire, "Could not open database %s: %s\n",
+ CTX_ERROR(o->ctx, "Could not open database %s: %s\n",
o->path, sqlite3_errmsg(o->handle));
r = 1;
r = sqlite3_prepare_v2(db->handle, "PRAGMA integrity_check", -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare integrity check: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare integrity check: %s\n",
sqlite3_errmsg(db->handle));
return 1;
}
errors++;
// Log the message
- ERROR(db->pakfire, "%s\n", error);
+ CTX_ERROR(db->ctx, "%s\n", error);
// Break on anything else
} else
sqlite3_finalize(stmt);
if (errors)
- ERROR(db->pakfire, "Database integrity check failed\n");
+ CTX_ERROR(db->ctx, "Database integrity check failed\n");
else
- INFO(db->pakfire, "Database integrity check passed\n");
+ CTX_INFO(db->ctx, "Database integrity check passed\n");
return errors;
}
r = sqlite3_prepare_v2(db->handle, "PRAGMA foreign_key_check", -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare foreign key check: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare foreign key check: %s\n",
sqlite3_errmsg(db->handle));
return 1;
}
errors++;
// Log the message
- ERROR(db->pakfire, "Foreign key violation found in %s, row %lu: "
+ CTX_ERROR(db->ctx, "Foreign key violation found in %s, row %lu: "
"%lu does not exist in table %s\n", table, rowid, foreign_rowid, foreign_table);
// Break on anything else
sqlite3_finalize(stmt);
if (errors)
- ERROR(db->pakfire, "Foreign key check failed\n");
+ CTX_ERROR(db->ctx, "Foreign key check failed\n");
else
- INFO(db->pakfire, "Foreign key check passed\n");
+ CTX_INFO(db->ctx, "Foreign key check passed\n");
return errors;
}
int r = sqlite3_prepare_v2(db->handle, "SELECT COUNT(*) FROM packages", -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s\n",
sqlite3_errmsg(db->handle));
return -1;
}
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
goto END;
}
// Bind package ID
r = sqlite3_bind_int64(stmt, 1, id);
if (r) {
- ERROR(db->pakfire, "Could not bind id: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind id: %s\n",
sqlite3_errmsg(db->handle));
goto END;
}
// Bind type
r = sqlite3_bind_text(stmt, 2, dep->name, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind type: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind type: %s\n",
sqlite3_errmsg(db->handle));
goto END;
}
// Bind dependency
r = sqlite3_bind_text(stmt, 3, *d, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind dependency: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind dependency: %s\n",
sqlite3_errmsg(db->handle));
goto END;
}
// Get the filelist from the archive
struct pakfire_filelist* filelist = pakfire_archive_get_filelist(archive);
if (!filelist) {
- ERROR(db->pakfire, "Could not fetch filelist from archive\n");
+ CTX_ERROR(db->ctx, "Could not fetch filelist from archive\n");
return 1;
}
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
goto END;
}
// Bind package ID
r = sqlite3_bind_int64(stmt, 1, id);
if (r) {
- ERROR(db->pakfire, "Could not bind id: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind id: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_text(stmt, 2, path, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind path: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind path: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_int64(stmt, 3, size);
if (r) {
- ERROR(db->pakfire, "Could not bind size: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind size: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
// Bind config - XXX TODO
r = sqlite3_bind_null(stmt, 4);
if (r) {
- ERROR(db->pakfire, "Could not bind config: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind config: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
// Bind datafile - XXX TODO
r = sqlite3_bind_null(stmt, 5);
if (r) {
- ERROR(db->pakfire, "Could not bind datafile: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind datafile: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_int64(stmt, 6, mode);
if (r) {
- ERROR(db->pakfire, "Could not bind mode: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind mode: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_text(stmt, 7, uname, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind uname: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind uname: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_text(stmt, 8, gname, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind gname: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind gname: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_int64(stmt, 9, ctime);
if (r) {
- ERROR(db->pakfire, "Could not bind ctime: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind ctime: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
r = sqlite3_bind_int64(stmt, 10, mtime);
if (r) {
- ERROR(db->pakfire, "Could not bind mtime: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind mtime: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
if (mimetype) {
r = sqlite3_bind_text(stmt, 11, mimetype, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind MIME type: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind MIME type: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
} else {
r = sqlite3_bind_null(stmt, 11);
if (r) {
- ERROR(db->pakfire, "Could not bind an empty MIME type: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind an empty MIME type: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// Bind capabilities - XXX TODO
r = sqlite3_bind_null(stmt, 12);
if (r) {
- ERROR(db->pakfire, "Could not bind capabilities: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind capabilities: %s\n", sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
}
// SHA2-512 Digest
r = pakfire_db_bind_digest(db, stmt, 13, file, PAKFIRE_DIGEST_SHA2_512);
if (r) {
- ERROR(db->pakfire, "Could not bind SHA2-512 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind SHA2-512 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// SHA2-256 Digest
r = pakfire_db_bind_digest(db, stmt, 14, file, PAKFIRE_DIGEST_SHA2_256);
if (r) {
- ERROR(db->pakfire, "Could not bind SHA2-256 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind SHA2-256 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// BLAKE2b512 Digest
r = pakfire_db_bind_digest(db, stmt, 15, file, PAKFIRE_DIGEST_BLAKE2B512);
if (r) {
- ERROR(db->pakfire, "Could not bind BLAKE2b512 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind BLAKE2b512 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// BLAKE2s256 Digest
r = pakfire_db_bind_digest(db, stmt, 16, file, PAKFIRE_DIGEST_BLAKE2S256);
if (r) {
- ERROR(db->pakfire, "Could not bind BLAKE2s256 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind BLAKE2s256 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// SHA3-512 Digest
r = pakfire_db_bind_digest(db, stmt, 17, file, PAKFIRE_DIGEST_SHA3_512);
if (r) {
- ERROR(db->pakfire, "Could not bind SHA3-512 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind SHA3-512 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// SHA3-256 Digest
r = pakfire_db_bind_digest(db, stmt, 18, file, PAKFIRE_DIGEST_SHA3_256);
if (r) {
- ERROR(db->pakfire, "Could not bind SHA3-256 digest: %s\n",
+ CTX_ERROR(db->ctx, "Could not bind SHA3-256 digest: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// Check for errors
if (r != SQLITE_DONE) {
- ERROR(db->pakfire, "Could not add file to database: %s\n",
+ CTX_ERROR(db->ctx, "Could not add file to database: %s\n",
sqlite3_errmsg(db->handle));
pakfire_file_unref(file);
goto END;
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
goto END;
}
// Bind package ID
r = sqlite3_bind_int64(stmt, 1, id);
if (r) {
- ERROR(db->pakfire, "Could not bind id: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind id: %s\n", sqlite3_errmsg(db->handle));
pakfire_scriptlet_unref(scriptlet);
goto END;
}
// Bind handle
r = sqlite3_bind_text(stmt, 2, *type, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind type: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind type: %s\n", sqlite3_errmsg(db->handle));
pakfire_scriptlet_unref(scriptlet);
goto END;
}
// Bind scriptlet
r = sqlite3_bind_text(stmt, 3, data, size, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind scriptlet: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind scriptlet: %s\n", sqlite3_errmsg(db->handle));
pakfire_scriptlet_unref(scriptlet);
goto END;
}
// Check for errors
if (r != SQLITE_DONE) {
- ERROR(db->pakfire, "Could not add scriptlet to database: %s\n",
+ CTX_ERROR(db->ctx, "Could not add scriptlet to database: %s\n",
sqlite3_errmsg(db->handle));
pakfire_scriptlet_unref(scriptlet);
goto END;
sqlite3_stmt* stmt = NULL;
int r;
+ char** groups = NULL;
+ char* __groups = NULL;
+
// Begin a new transaction
r = pakfire_db_begin_transaction(db);
if (r)
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r != SQLITE_OK) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s: %s\n",
sql, sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 1, name, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind name: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind name: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 2, evr, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind evr: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind evr: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 3, arch, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind arch: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind arch: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind groups
- const char* groups = pakfire_package_get_string(pkg, PAKFIRE_PKG_GROUPS);
-
+ groups = pakfire_package_get_strings(pkg, PAKFIRE_PKG_GROUPS);
if (groups) {
- r = sqlite3_bind_text(stmt, 4, groups, -1, NULL);
+ // Join everything together as SQLite doesn't support arrays
+ __groups = pakfire_string_join(groups, " ");
+ if (!__groups) {
+ r = 1;
+ goto ERROR;
+ }
+
+ r = sqlite3_bind_text(stmt, 4, __groups, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind groups: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind groups: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 5, filename, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind filename: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind filename: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_int64(stmt, 6, size);
if (r) {
- ERROR(db->pakfire, "Could not bind size: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind size: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_int64(stmt, 7, inst_size);
if (r) {
- ERROR(db->pakfire, "Could not bind inst_size: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind inst_size: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Fetch the digest
digest = pakfire_package_get_digest(pkg, &digest_type, &digest_length);
if (!digest) {
- ERROR(db->pakfire, "Could not fetch the package's digest: %m\n");
+ CTX_ERROR(db->ctx, "Could not fetch the package's digest: %m\n");
r = 1;
goto ERROR;
}
// Set the digest type
r = sqlite3_bind_int64(stmt, 8, digest_type);
if (r) {
- ERROR(db->pakfire, "Could not bind digest type: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind digest type: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Set the digest
r = sqlite3_bind_blob(stmt, 9, digest, digest_length, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind digest: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind digest: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 10, license, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind license: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind license: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 11, summary, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind summary: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind summary: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 12, description, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind description: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind description: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 13, uuid, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 14, vendor, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind vendor: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind vendor: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 15, build_host, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind build_host: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind build_host: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_int64(stmt, 16, build_time);
if (r) {
- ERROR(db->pakfire, "Could not bind build_time: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind build_time: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// installed by the user?
r = sqlite3_bind_int(stmt, 18, userinstalled);
if (r) {
- ERROR(db->pakfire, "Could not bind userinstalled: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind userinstalled: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
} while (r == SQLITE_BUSY);
if (r != SQLITE_DONE) {
- ERROR(db->pakfire, "Could not add package to database: %s\n",
+ CTX_ERROR(db->ctx, "Could not add package to database: %s\n",
sqlite3_errmsg(db->handle));
r = 1;
goto ERROR;
goto ERROR;
ERROR:
+ if (groups)
+ pakfire_strings_free(groups);
+ if (__groups)
+ free(__groups);
if (stmt)
sqlite3_finalize(stmt);
// Fetch the package's UUID
const char* uuid = pakfire_package_get_string(pkg, PAKFIRE_PKG_UUID);
if (!uuid) {
- ERROR(db->pakfire, "Package has no UUID\n");
+ CTX_ERROR(db->ctx, "Package has no UUID\n");
r = 1;
goto ERROR;
}
r = sqlite3_prepare_v2(db->handle,
"DELETE FROM packages WHERE uuid = ?", -1, &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s\n",
sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind UUID
r = sqlite3_bind_text(stmt, 1, uuid, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Check if we have been successful
if (r != SQLITE_DONE) {
- ERROR(db->pakfire, "Could not delete package %s\n", uuid);
+ CTX_ERROR(db->ctx, "Could not delete package %s\n", uuid);
r = 1;
goto ERROR;
}
// Fetch the package's UUID
const char* uuid = pakfire_package_get_string(pkg, PAKFIRE_PKG_UUID);
if (!uuid) {
- ERROR(db->pakfire, "Package has no UUID\n");
+ CTX_ERROR(db->ctx, "Package has no UUID\n");
goto ERROR;
}
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s %s\n",
sql, sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind UUID
r = sqlite3_bind_text(stmt, 1, uuid, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind uuid: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
r = sqlite3_bind_text(stmt, 2, type, -1, NULL);
if (r) {
- ERROR(db->pakfire, "Could not bind type: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind type: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
- DEBUG(db->pakfire, "Searching for scriptlet for package %s of type %s\n", uuid, type);
+ CTX_DEBUG(db->ctx, "Searching for scriptlet for package %s of type %s\n", uuid, type);
// Execute query
do {
ssize_t size = sqlite3_column_bytes(stmt, 1);
// Create a scriptlet object
- r = pakfire_scriptlet_create(&scriptlet, db->pakfire, type, data, size);
+ r = pakfire_scriptlet_create(&scriptlet, db->ctx, type, data, size);
if (r)
goto ERROR;
}
// Name
const char* name = (const char*)sqlite3_column_text(stmt, 0);
if (!name) {
- ERROR(db->pakfire, "Could not read name: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not read name: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// EVR
const char* evr = (const char*)sqlite3_column_text(stmt, 1);
if (!evr) {
- ERROR(db->pakfire, "Could not read evr: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not read evr: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Arch
const char* arch = (const char*)sqlite3_column_text(stmt, 2);
if (!arch) {
- ERROR(db->pakfire, "Could not read arch: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not read arch: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}
// Create package
r = pakfire_package_create(&pkg, db->pakfire, repo, name, evr, arch);
if (r) {
- ERROR(db->pakfire, "Could not create package '%s-%s.%s': %m\n", name, evr, arch);
+ CTX_ERROR(db->ctx, "Could not create package '%s-%s.%s': %m\n", name, evr, arch);
goto ERROR;
}
for (const struct dependency* deps = dependencies; deps->field; deps++) {
const char* relations = (const char*)sqlite3_column_text(stmt, deps->field);
if (relations) {
- r = pakfire_str2deps(db->pakfire, pkg, deps->key, relations);
+ r = pakfire_str2deps(db->ctx, pkg, deps->key, relations);
if (r)
goto ERROR;
}
sqlite3_stmt* stmt = NULL;
int r = 1;
- DEBUG(db->pakfire, "Loading package database...\n");
+ CTX_DEBUG(db->ctx, "Loading package database...\n");
// Drop contents of the repository
pakfire_repo_clear(repo);
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s %s\n",
sql, sqlite3_errmsg(db->handle));
goto ERROR;
}
// Save time when we finished
t_end = clock();
- DEBUG(db->pakfire, "Loading package database completed in %.4fms\n",
+ CTX_DEBUG(db->ctx, "Loading package database completed in %.4fms\n",
(double)(t_end - t_start) * 1000 / CLOCKS_PER_SEC);
// Mark repository as changed
ERROR:
if (r) {
- ERROR(db->pakfire, "Failed reading package database: %m\n");
+ CTX_ERROR(db->ctx, "Failed reading package database: %m\n");
pakfire_repo_clear(repo);
}
// Abort if no path is set
if (!path) {
- ERROR(db->pakfire, "File has no path\n");
+ CTX_ERROR(db->ctx, "File has no path\n");
r = 1;
goto ERROR;
}
// Set path
r = pakfire_file_set_path(file, path);
if (r) {
- ERROR(db->pakfire, "%s: Could not set path '%s': %m\n", path, path);
+ CTX_ERROR(db->ctx, "%s: Could not set path '%s': %m\n", path, path);
goto ERROR;
}
// Make the absolute path
r = pakfire_path(db->pakfire, abspath, "%s", path);
if (r) {
- ERROR(db->pakfire, "%s: Could not make absolute path: %m\n", path);
+ CTX_ERROR(db->ctx, "%s: Could not make absolute path: %m\n", path);
goto ERROR;
}
// Set the absolute path
r = pakfire_file_set_abspath(file, abspath);
if (r) {
- ERROR(db->pakfire, "%s: Could not set absolute path %s: %m\n", path, abspath);
+ CTX_ERROR(db->ctx, "%s: Could not set absolute path %s: %m\n", path, abspath);
goto ERROR;
}
// Abort if no user is set
if (!uname) {
- ERROR(db->pakfire, "%s: No user\n", path);
+ CTX_ERROR(db->ctx, "%s: No user\n", path);
r = 1;
goto ERROR;
}
// Set uname
r = pakfire_file_set_uname(file, uname);
if (r) {
- ERROR(db->pakfire, "%s: Could not set user '%s': %m\n", path, uname);
+ CTX_ERROR(db->ctx, "%s: Could not set user '%s': %m\n", path, uname);
goto ERROR;
}
// Abort if no group is set
if (!gname) {
- ERROR(db->pakfire, "%s: No group\n", path);
+ CTX_ERROR(db->ctx, "%s: No group\n", path);
r = 1;
goto ERROR;
}
// Set gname
r = pakfire_file_set_gname(file, gname);
if (r) {
- ERROR(db->pakfire, "%s: Could not set group '%s': %m\n", path, gname);
+ CTX_ERROR(db->ctx, "%s: Could not set group '%s': %m\n", path, gname);
goto ERROR;
}
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s %s\n",
sql, sqlite3_errmsg(db->handle));
goto ERROR;
}
ERROR:
if (r)
- ERROR(db->pakfire, "Could not fetch filelist: %m\n");
+ CTX_ERROR(db->ctx, "Could not fetch filelist: %m\n");
if (stmt)
sqlite3_finalize(stmt);
// Fetch the package ID
uint64_t id = pakfire_package_get_num(pkg, PAKFIRE_PKG_DBID, 0);
if (!id) {
- ERROR(db->pakfire, "Package did not have an ID\n");
+ CTX_ERROR(db->ctx, "Package did not have an ID\n");
return 1;
}
// Create a new filelist
r = pakfire_filelist_create(&fl, db->pakfire);
if (r) {
- ERROR(db->pakfire, "Could not create filelist: %m\n");
+ CTX_ERROR(db->ctx, "Could not create filelist: %m\n");
goto ERROR;
}
// Prepare the statement
r = sqlite3_prepare_v2(db->handle, sql, strlen(sql), &stmt, NULL);
if (r) {
- ERROR(db->pakfire, "Could not prepare SQL statement: %s %s\n",
+ CTX_ERROR(db->ctx, "Could not prepare SQL statement: %s %s\n",
sql, sqlite3_errmsg(db->handle));
goto ERROR;
}
// Bind package ID
r = sqlite3_bind_int64(stmt, 1, id);
if (r) {
- ERROR(db->pakfire, "Could not bind package ID: %s\n", sqlite3_errmsg(db->handle));
+ CTX_ERROR(db->ctx, "Could not bind package ID: %s\n", sqlite3_errmsg(db->handle));
goto ERROR;
}