db: create cache index with non-repository packages
this enables virtual packages and files specified from command line to work on non-harddisk installs.cute-signatures
parent
8806ce875e
commit
e5be34335c
27
src/add.c
27
src/add.c
|
@ -77,6 +77,22 @@ static int cup(void)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int non_repository_check(struct apk_database *db)
|
||||
{
|
||||
if (apk_flags & APK_FORCE)
|
||||
return 0;
|
||||
if (apk_db_cache_active(db))
|
||||
return 0;
|
||||
if (apk_db_permanent(db))
|
||||
return 0;
|
||||
|
||||
apk_error("You tried to add a non-repository package to system, "
|
||||
"but it would be lost on next reboot. Enable package caching "
|
||||
"(apk cache --help) or use --force if you know what you are "
|
||||
"doing.");
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int add_main(void *ctx, int argc, char **argv)
|
||||
{
|
||||
|
@ -97,6 +113,9 @@ static int add_main(void *ctx, int argc, char **argv)
|
|||
return r;
|
||||
|
||||
if (actx->virtpkg) {
|
||||
if (non_repository_check(&db))
|
||||
goto err;
|
||||
|
||||
virtpkg = apk_pkg_new();
|
||||
if (virtpkg == NULL) {
|
||||
apk_error("Failed to allocate virtual meta package");
|
||||
|
@ -119,14 +138,8 @@ static int add_main(void *ctx, int argc, char **argv)
|
|||
struct apk_package *pkg = NULL;
|
||||
struct apk_sign_ctx sctx;
|
||||
|
||||
if (!apk_db_cache_active(&db) &&
|
||||
!apk_db_permanent(&db) &&
|
||||
!(apk_flags & APK_FORCE)) {
|
||||
apk_error("Use --force or enable package "
|
||||
"caching to install non-repository "
|
||||
"packages.");
|
||||
if (non_repository_check(&db))
|
||||
goto err;
|
||||
}
|
||||
|
||||
apk_sign_ctx_init(&sctx, APK_SIGN_VERIFY_AND_GENERATE,
|
||||
NULL);
|
||||
|
|
|
@ -83,6 +83,7 @@ struct apk_database {
|
|||
int root_fd, lock_fd;
|
||||
unsigned name_id, num_repos;
|
||||
const char *cache_dir;
|
||||
int permanent;
|
||||
|
||||
struct apk_dependency_array *world;
|
||||
struct apk_string_array *protected_paths;
|
||||
|
|
161
src/database.c
161
src/database.c
|
@ -1,7 +1,7 @@
|
|||
/* database.c - Alpine Package Keeper (APK)
|
||||
*
|
||||
* Copyright (C) 2005-2008 Natanael Copa <n@tanael.org>
|
||||
* Copyright (C) 2008 Timo Teräs <timo.teras@iki.fi>
|
||||
* Copyright (C) 2008-2009 Timo Teräs <timo.teras@iki.fi>
|
||||
* All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
|
@ -395,6 +395,23 @@ struct apk_package *apk_db_pkg_add(struct apk_database *db, struct apk_package *
|
|||
return idb;
|
||||
}
|
||||
|
||||
static void apk_db_cache_get_name(char *buf, size_t bufsz,
|
||||
struct apk_database *db,
|
||||
struct apk_checksum *csum,
|
||||
const char *file, int temp)
|
||||
{
|
||||
char csumstr[APK_CACHE_CSUM_BYTES*2+1];
|
||||
apk_blob_t bbuf = APK_BLOB_BUF(csumstr);
|
||||
|
||||
apk_blob_push_hexdump(&bbuf,
|
||||
APK_BLOB_PTR_LEN((char *) csum->data,
|
||||
APK_CACHE_CSUM_BYTES));
|
||||
apk_blob_push_blob(&bbuf, APK_BLOB_PTR_LEN("", 1));
|
||||
|
||||
snprintf(buf, bufsz, "%s/%s/%s.%s%s",
|
||||
db->root, db->cache_dir, csumstr, file, temp ? ".new" : "");
|
||||
}
|
||||
|
||||
int apk_db_index_read(struct apk_database *db, struct apk_bstream *bs, int repo)
|
||||
{
|
||||
struct apk_package *pkg = NULL;
|
||||
|
@ -410,9 +427,9 @@ int apk_db_index_read(struct apk_database *db, struct apk_bstream *bs, int repo)
|
|||
if (pkg == NULL)
|
||||
continue;
|
||||
|
||||
if (repo != -1)
|
||||
if (repo >= 0)
|
||||
pkg->repos |= BIT(repo);
|
||||
else
|
||||
else if (repo == -1)
|
||||
apk_pkg_set_state(db, pkg, APK_PKG_INSTALLED);
|
||||
|
||||
if (apk_db_pkg_add(db, pkg) != pkg && repo == -1) {
|
||||
|
@ -678,6 +695,12 @@ static int apk_db_read_state(struct apk_database *db, int flags)
|
|||
apk_db_index_read(db, bs, -1);
|
||||
bs->close(bs, NULL);
|
||||
}
|
||||
|
||||
bs = apk_bstream_from_file("etc/apk/cache/installed");
|
||||
if (bs != NULL) {
|
||||
apk_db_index_read(db, bs, -2);
|
||||
bs->close(bs, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
if (!(flags & APK_OPENF_NO_SCRIPTS)) {
|
||||
|
@ -696,6 +719,73 @@ static int apk_db_read_state(struct apk_database *db, int flags)
|
|||
return 0;
|
||||
}
|
||||
|
||||
struct index_write_ctx {
|
||||
struct apk_ostream *os;
|
||||
int count;
|
||||
int force;
|
||||
};
|
||||
|
||||
static int write_index_entry(apk_hash_item item, void *ctx)
|
||||
{
|
||||
struct index_write_ctx *iwctx = (struct index_write_ctx *) ctx;
|
||||
struct apk_package *pkg = (struct apk_package *) item;
|
||||
int r;
|
||||
|
||||
if (!iwctx->force && pkg->filename == NULL)
|
||||
return 0;
|
||||
|
||||
r = apk_pkg_write_index_entry(pkg, iwctx->os);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (iwctx->os->write(iwctx->os, "\n", 1) != 1)
|
||||
return -1;
|
||||
|
||||
iwctx->count++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int apk_db_index_write_nr_cache(struct apk_database *db)
|
||||
{
|
||||
struct index_write_ctx ctx = { NULL, 0, TRUE };
|
||||
struct apk_package *pkg;
|
||||
struct apk_ostream *os;
|
||||
int r;
|
||||
|
||||
if (!apk_db_cache_active(db))
|
||||
return 0;
|
||||
|
||||
/* Write list of installed non-repository packages to
|
||||
* cached index file */
|
||||
ctx.os = os = apk_ostream_to_file("etc/apk/cache/installed.new", 0644);
|
||||
if (os == NULL)
|
||||
return -1;
|
||||
|
||||
list_for_each_entry(pkg, &db->installed.packages, installed_pkgs_list) {
|
||||
if (pkg->repos != 0)
|
||||
continue;
|
||||
r = write_index_entry(pkg, &ctx);
|
||||
if (r != 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
os->close(os);
|
||||
if (rename("etc/apk/cache/installed.new",
|
||||
"etc/apk/cache/installed") < 0)
|
||||
return -errno;
|
||||
|
||||
return ctx.count;
|
||||
}
|
||||
|
||||
int apk_db_index_write(struct apk_database *db, struct apk_ostream *os)
|
||||
{
|
||||
struct index_write_ctx ctx = { os, 0, FALSE };
|
||||
|
||||
apk_hash_foreach(&db->available.packages, write_index_entry, &ctx);
|
||||
|
||||
return ctx.count;
|
||||
}
|
||||
|
||||
static int add_protected_path(void *ctx, apk_blob_t blob)
|
||||
{
|
||||
struct apk_database *db = (struct apk_database *) ctx;
|
||||
|
@ -746,6 +836,7 @@ int apk_db_open(struct apk_database *db, const char *root, unsigned int flags)
|
|||
apk_hash_init(&db->installed.files, &file_hash_ops, 10000);
|
||||
list_init(&db->installed.packages);
|
||||
db->cache_dir = apk_static_cache_dir;
|
||||
db->permanent = 1;
|
||||
|
||||
if (root != NULL) {
|
||||
fchdir(apk_cwd_fd);
|
||||
|
@ -759,6 +850,8 @@ int apk_db_open(struct apk_database *db, const char *root, unsigned int flags)
|
|||
msg = "Unable to open root";
|
||||
goto ret_errno;
|
||||
}
|
||||
if (fstat(db->root_fd, &st) != 0 || major(st.st_dev) == 0)
|
||||
db->permanent = 0;
|
||||
|
||||
fchdir(db->root_fd);
|
||||
if (stat(apk_linked_cache_dir, &st) == 0 && S_ISDIR(st.st_mode))
|
||||
|
@ -834,6 +927,9 @@ int apk_db_open(struct apk_database *db, const char *root, unsigned int flags)
|
|||
if (!(flags & APK_OPENF_NO_REPOS)) {
|
||||
list_for_each_entry(repo, &apk_repository_list.list, list)
|
||||
apk_db_add_repository(db, APK_BLOB_STR(repo->url));
|
||||
|
||||
if (apk_flags & APK_UPDATE_CACHE)
|
||||
apk_db_index_write_nr_cache(db);
|
||||
}
|
||||
|
||||
fchdir(apk_cwd_fd);
|
||||
|
@ -895,6 +991,7 @@ int apk_db_write_config(struct apk_database *db)
|
|||
return -errno;
|
||||
|
||||
unlink("var/lib/apk/scripts");
|
||||
apk_db_index_write_nr_cache(db);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -943,13 +1040,7 @@ int apk_db_cache_active(struct apk_database *db)
|
|||
|
||||
int apk_db_permanent(struct apk_database *db)
|
||||
{
|
||||
struct stat st;
|
||||
|
||||
if (fstat(db->root_fd, &st) != 0)
|
||||
return 0;
|
||||
if (major(st.st_dev) == 0)
|
||||
return 0;
|
||||
return 1;
|
||||
return db->permanent;
|
||||
}
|
||||
|
||||
struct apk_package *apk_db_get_pkg(struct apk_database *db,
|
||||
|
@ -978,56 +1069,6 @@ struct apk_package *apk_db_get_file_owner(struct apk_database *db,
|
|||
return dbf->diri->pkg;
|
||||
}
|
||||
|
||||
struct index_write_ctx {
|
||||
struct apk_ostream *os;
|
||||
int count;
|
||||
};
|
||||
|
||||
static int write_index_entry(apk_hash_item item, void *ctx)
|
||||
{
|
||||
struct index_write_ctx *iwctx = (struct index_write_ctx *) ctx;
|
||||
struct apk_package *pkg = (struct apk_package *) item;
|
||||
int r;
|
||||
|
||||
if (pkg->filename == NULL)
|
||||
return 0;
|
||||
|
||||
r = apk_pkg_write_index_entry(pkg, iwctx->os);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (iwctx->os->write(iwctx->os, "\n", 1) != 1)
|
||||
return -1;
|
||||
|
||||
iwctx->count++;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int apk_db_index_write(struct apk_database *db, struct apk_ostream *os)
|
||||
{
|
||||
struct index_write_ctx ctx = { os, 0 };
|
||||
|
||||
apk_hash_foreach(&db->available.packages, write_index_entry, &ctx);
|
||||
|
||||
return ctx.count;
|
||||
}
|
||||
|
||||
static void apk_db_cache_get_name(char *buf, size_t bufsz,
|
||||
struct apk_database *db,
|
||||
struct apk_checksum *csum,
|
||||
const char *file, int temp)
|
||||
{
|
||||
char csumstr[APK_CACHE_CSUM_BYTES*2+1];
|
||||
apk_blob_t bbuf = APK_BLOB_BUF(csumstr);
|
||||
|
||||
apk_blob_push_hexdump(&bbuf,
|
||||
APK_BLOB_PTR_LEN((char *) csum->data, APK_CACHE_CSUM_BYTES));
|
||||
apk_blob_push_blob(&bbuf, APK_BLOB_PTR_LEN("", 1));
|
||||
|
||||
snprintf(buf, bufsz, "%s/%s/%s.%s%s",
|
||||
db->root, db->cache_dir, csumstr, file, temp ? ".new" : "");
|
||||
}
|
||||
|
||||
static struct apk_bstream *apk_db_cache_open(struct apk_database *db,
|
||||
struct apk_checksum *csum,
|
||||
const char *file)
|
||||
|
|
Loading…
Reference in New Issue