diff --git a/src/apk.c b/src/apk.c index 80123ca..266886f 100644 --- a/src/apk.c +++ b/src/apk.c @@ -133,27 +133,27 @@ static int option_parse_global(void *ctx, struct apk_db_options *dbopts, int opt version(); return -ESHUTDOWN; case OPT_GLOBAL_force: - apk_force |= APK_FORCE_OVERWRITE | APK_FORCE_OLD_APK - | APK_FORCE_BROKEN_WORLD | APK_FORCE_NON_REPOSITORY - | APK_FORCE_BINARY_STDOUT; + dbopts->force |= APK_FORCE_OVERWRITE | APK_FORCE_OLD_APK + | APK_FORCE_BROKEN_WORLD | APK_FORCE_NON_REPOSITORY + | APK_FORCE_BINARY_STDOUT; break; case OPT_GLOBAL_force_overwrite: - apk_force |= APK_FORCE_OVERWRITE; + dbopts->force |= APK_FORCE_OVERWRITE; break; case OPT_GLOBAL_force_old_apk: - apk_force |= APK_FORCE_OLD_APK; + dbopts->force |= APK_FORCE_OLD_APK; break; case OPT_GLOBAL_force_broken_world: - apk_force |= APK_FORCE_BROKEN_WORLD; + dbopts->force |= APK_FORCE_BROKEN_WORLD; break; case OPT_GLOBAL_force_refresh: - apk_force |= APK_FORCE_REFRESH; + dbopts->force |= APK_FORCE_REFRESH; break; case OPT_GLOBAL_force_non_repository: - apk_force |= APK_FORCE_NON_REPOSITORY; + dbopts->force |= APK_FORCE_NON_REPOSITORY; break; case OPT_GLOBAL_force_binary_stdout: - apk_force |= APK_FORCE_BINARY_STDOUT; + dbopts->force |= APK_FORCE_BINARY_STDOUT; break; case OPT_GLOBAL_interactive: apk_flags |= APK_INTERACTIVE; @@ -252,8 +252,8 @@ static int option_parse_commit(void *ctx, struct apk_db_options *dbopts, int opt case OPT_COMMIT_initramfs_diskless_boot: dbopts->open_flags |= APK_OPENF_CREATE; apk_flags |= APK_NO_COMMIT_HOOKS; - apk_force |= APK_FORCE_OVERWRITE | APK_FORCE_OLD_APK - | APK_FORCE_BROKEN_WORLD | APK_FORCE_NON_REPOSITORY; + dbopts->force |= APK_FORCE_OVERWRITE | APK_FORCE_OLD_APK + | APK_FORCE_BROKEN_WORLD | APK_FORCE_NON_REPOSITORY; break; default: return -ENOTSUP; @@ -469,7 +469,7 @@ int main(int argc, char **argv) ctx = calloc(1, applet->context_size); dbopts.open_flags = applet->open_flags; apk_flags |= applet->forced_flags; - apk_force |= applet->forced_force; + dbopts.force |= applet->forced_force; } init_openssl(); diff --git a/src/apk_database.h b/src/apk_database.h index 83388ec..b69e3b5 100644 --- a/src/apk_database.h +++ b/src/apk_database.h @@ -22,6 +22,13 @@ #include "adb.h" +#define APK_FORCE_OVERWRITE BIT(0) +#define APK_FORCE_OLD_APK BIT(1) +#define APK_FORCE_BROKEN_WORLD BIT(2) +#define APK_FORCE_REFRESH BIT(3) +#define APK_FORCE_NON_REPOSITORY BIT(4) +#define APK_FORCE_BINARY_STDOUT BIT(5) + struct apk_name; APK_ARRAY(apk_name_array, struct apk_name *); @@ -118,7 +125,7 @@ struct apk_repository { }; struct apk_db_options { - int lock_wait; + unsigned int force, lock_wait; unsigned int cache_max_age; unsigned long open_flags; const char *root; @@ -142,6 +149,7 @@ struct apk_repository_tag { }; struct apk_database { + unsigned int force; char *root; int root_fd, lock_fd, cache_fd, keys_fd; unsigned num_repos, num_repo_tags; @@ -230,6 +238,9 @@ int apk_db_check_world(struct apk_database *db, struct apk_dependency_array *wor int apk_db_fire_triggers(struct apk_database *db); int apk_db_run_script(struct apk_database *db, char *fn, char **argv); void apk_db_update_directory_permissions(struct apk_database *db); +static inline time_t apk_db_url_since(struct apk_database *db, time_t since) { + return (db->force & APK_FORCE_REFRESH) ? APK_ISTREAM_FORCE_REFRESH : since; +} struct apk_package *apk_db_pkg_add(struct apk_database *db, struct apk_package *pkg); struct apk_package *apk_db_get_pkg(struct apk_database *db, struct apk_checksum *csum); diff --git a/src/apk_defines.h b/src/apk_defines.h index dc38a0e..187b455 100644 --- a/src/apk_defines.h +++ b/src/apk_defines.h @@ -69,8 +69,7 @@ static inline int IS_ERR_OR_NULL(const void *ptr) { return IS_ERR(ptr) || !ptr; #define ROUND_UP(x,a) (((x)+(a)-1) & ~((a)-1)) extern int apk_verbosity; -extern unsigned int apk_flags, apk_force; -extern const char *apk_arch; +extern unsigned int apk_flags; extern char **apk_argv; #define APK_SIMULATE 0x0002 @@ -86,13 +85,6 @@ extern char **apk_argv; #define APK_NO_CACHE 0x8000 #define APK_NO_COMMIT_HOOKS 0x00010000 -#define APK_FORCE_OVERWRITE BIT(0) -#define APK_FORCE_OLD_APK BIT(1) -#define APK_FORCE_BROKEN_WORLD BIT(2) -#define APK_FORCE_REFRESH BIT(3) -#define APK_FORCE_NON_REPOSITORY BIT(4) -#define APK_FORCE_BINARY_STDOUT BIT(5) - /* default architecture for APK packages. */ #if defined(__x86_64__) #define APK_DEFAULT_ARCH "x86_64" diff --git a/src/apk_io.h b/src/apk_io.h index 02edf1d..2e70b53 100644 --- a/src/apk_io.h +++ b/src/apk_io.h @@ -75,11 +75,12 @@ struct apk_istream { #define APK_IO_ALL ((size_t)-1) +#define APK_ISTREAM_FORCE_REFRESH ((time_t) -1) + struct apk_istream *apk_istream_from_file(int atfd, const char *file); struct apk_istream *apk_istream_from_file_gz(int atfd, const char *file); struct apk_istream *apk_istream_from_fd(int fd); struct apk_istream *apk_istream_from_fd_url_if_modified(int atfd, const char *url, time_t since); -struct apk_istream *apk_istream_from_url_gz(const char *url); ssize_t apk_istream_read(struct apk_istream *is, void *ptr, size_t size); apk_blob_t apk_istream_get(struct apk_istream *is, size_t len); apk_blob_t apk_istream_get_max(struct apk_istream *is, size_t size); @@ -90,18 +91,14 @@ ssize_t apk_istream_splice(struct apk_istream *is, int fd, size_t size, ssize_t apk_stream_copy(struct apk_istream *is, struct apk_ostream *os, size_t size, apk_progress_cb cb, void *cb_ctx, EVP_MD_CTX *mdctx); -static inline struct apk_istream *apk_istream_from_url(const char *url) -{ - return apk_istream_from_fd_url_if_modified(AT_FDCWD, url, 0); -} -static inline struct apk_istream *apk_istream_from_fd_url(int atfd, const char *url) -{ - return apk_istream_from_fd_url_if_modified(atfd, url, 0); -} -static inline struct apk_istream *apk_istream_from_url_if_modified(const char *url, time_t since) +static inline struct apk_istream *apk_istream_from_url(const char *url, time_t since) { return apk_istream_from_fd_url_if_modified(AT_FDCWD, url, since); } +static inline struct apk_istream *apk_istream_from_fd_url(int atfd, const char *url, time_t since) +{ + return apk_istream_from_fd_url_if_modified(atfd, url, since); +} static inline void apk_istream_get_meta(struct apk_istream *is, struct apk_file_meta *meta) { is->ops->get_meta(is, meta); diff --git a/src/app_add.c b/src/app_add.c index f4acd22..4f2a9a6 100644 --- a/src/app_add.c +++ b/src/app_add.c @@ -63,7 +63,7 @@ static const struct apk_option_group optgroup_applet = { static int non_repository_check(struct apk_database *db) { - if (apk_force & APK_FORCE_NON_REPOSITORY) + if (db->force & APK_FORCE_NON_REPOSITORY) return 0; if (apk_db_cache_active(db)) return 0; diff --git a/src/app_convdb.c b/src/app_convdb.c index f77bbf8..fb89402 100644 --- a/src/app_convdb.c +++ b/src/app_convdb.c @@ -209,7 +209,7 @@ static int conv_main(void *pctx, struct apk_database *db, struct apk_string_arra read_triggers(ctx, apk_istream_from_file(db->root_fd, "lib/apk/db/triggers")); - convert_idb(ctx, apk_istream_from_fd_url(db->root_fd, "lib/apk/db/installed")); + convert_idb(ctx, apk_istream_from_file(db->root_fd, "lib/apk/db/installed")); adb_wo_obj(&idb, ADBI_IDB_PACKAGES, &ctx->pkgs); adb_w_rootobj(&idb); diff --git a/src/app_convndx.c b/src/app_convndx.c index a19b322..e20f673 100644 --- a/src/app_convndx.c +++ b/src/app_convndx.c @@ -80,7 +80,7 @@ static int conv_main(void *pctx, struct apk_database *db, struct apk_string_arra adb_wo_alloca(&ctx->pkgs, &schema_pkginfo_array, &ctx->dbi); foreach_array_item(arg, args) { - r = load_index(ctx, apk_istream_from_url(*arg)); + r = load_index(ctx, apk_istream_from_url(*arg, apk_db_url_since(db, 0))); if (r) goto err; fprintf(stderr, "%s: %u packages\n", *arg, adb_ra_num(&ctx->pkgs)); } diff --git a/src/app_fetch.c b/src/app_fetch.c index 4704b0b..7b32ab4 100644 --- a/src/app_fetch.c +++ b/src/app_fetch.c @@ -168,7 +168,7 @@ static int fetch_package(apk_hash_item item, void *pctx) } } - is = apk_istream_from_fd_url(urlfd, url); + is = apk_istream_from_fd_url(urlfd, url, apk_db_url_since(db, 0)); if (IS_ERR_OR_NULL(is)) { r = PTR_ERR(is) ?: -EIO; goto err; @@ -314,7 +314,7 @@ static int fetch_main(void *pctx, struct apk_database *db, struct apk_string_arr ctx->outdir_fd = AT_FDCWD; if ((args->num == 1) && (strcmp(args->item[0], "coffee") == 0)) { - if (apk_force) return cup(); + if (db->force) return cup(); apk_message("Go and fetch your own coffee."); return 0; } diff --git a/src/app_index.c b/src/app_index.c index 25ca3b4..b8c3461 100644 --- a/src/app_index.c +++ b/src/app_index.c @@ -117,7 +117,7 @@ static int index_main(void *ctx, struct apk_database *db, struct apk_string_arra apk_blob_t *rewrite_arch = NULL; if (isatty(STDOUT_FILENO) && ictx->output == NULL && - !(apk_force & APK_FORCE_BINARY_STDOUT)) { + !(db->force & APK_FORCE_BINARY_STDOUT)) { apk_error("Will not write binary index to console. " "Use --force-binary-stdout to override."); return -1; diff --git a/src/database.c b/src/database.c index 806f873..045d6c7 100644 --- a/src/database.c +++ b/src/database.c @@ -48,7 +48,7 @@ enum { }; int apk_verbosity = 1; -unsigned int apk_flags = 0, apk_force = 0; +unsigned int apk_flags = 0; static apk_blob_t tmpprefix = { .len=8, .ptr = ".apknew." }; @@ -630,7 +630,7 @@ int apk_cache_download(struct apk_database *db, struct apk_repository *repo, r = apk_repo_format_real_url(db->arch, repo, pkg, url, sizeof(url), &urlp); if (r < 0) return r; - if (autoupdate && !(apk_force & APK_FORCE_REFRESH)) { + if (autoupdate && !(db->force & APK_FORCE_REFRESH)) { if (fstatat(db->cache_fd, cacheitem, &st, 0) == 0 && now - st.st_mtime <= db->cache_max_age) return -EALREADY; @@ -642,13 +642,13 @@ int apk_cache_download(struct apk_database *db, struct apk_repository *repo, if (verify != APK_SIGN_NONE) { apk_sign_ctx_init(&sctx, APK_SIGN_VERIFY, NULL, db->keys_fd); - is = apk_istream_from_url_if_modified(url, st.st_mtime); + is = apk_istream_from_url(url, apk_db_url_since(db, st.st_mtime)); is = apk_istream_tee(is, db->cache_fd, tmpcacheitem, !autoupdate, cb, cb_ctx); is = apk_istream_gunzip_mpart(is, apk_sign_ctx_mpart_cb, &sctx); r = apk_tar_parse(is, apk_sign_ctx_verify_tar, &sctx, &db->id_cache); apk_sign_ctx_free(&sctx); } else { - is = apk_istream_from_url_if_modified(url, st.st_mtime); + is = apk_istream_from_url(url, apk_db_url_since(db, st.st_mtime)); if (!IS_ERR_OR_NULL(is)) { fd = openat(db->cache_fd, tmpcacheitem, O_RDWR | O_CREAT | O_TRUNC | O_CLOEXEC, 0644); if (fd < 0) r = -errno; @@ -871,13 +871,13 @@ int apk_db_index_read(struct apk_database *db, struct apk_istream *is, int repo) case 's': ipkg->broken_script = 1; break; case 'x': ipkg->broken_xattr = 1; break; default: - if (!(apk_force & APK_FORCE_OLD_APK)) + if (!(db->force & APK_FORCE_OLD_APK)) goto old_apk_tools; } } break; default: - if (r != 0 && !(apk_force & APK_FORCE_OLD_APK)) + if (r != 0 && !(db->force & APK_FORCE_OLD_APK)) goto old_apk_tools; /* Installed. So mark the package as installable. */ pkg->filename = NULL; @@ -1527,6 +1527,7 @@ int apk_db_open(struct apk_database *db, struct apk_db_options *dbopts) r = -1; goto ret_r; } + db->force = dbopts->force; if ((dbopts->open_flags & APK_OPENF_WRITE) && !(dbopts->open_flags & APK_OPENF_NO_AUTOUPDATE) && !(apk_flags & APK_NO_NETWORK)) @@ -2054,7 +2055,7 @@ int apk_db_check_world(struct apk_database *db, struct apk_dependency_array *wor struct apk_dependency *dep; int bad = 0, tag; - if (apk_force & APK_FORCE_BROKEN_WORLD) + if (db->force & APK_FORCE_BROKEN_WORLD) return 0; foreach_array_item(dep, world) { @@ -2276,7 +2277,7 @@ int apk_db_add_repository(apk_database_t _db, apk_blob_t _repository) r = apk_repo_format_real_url(db->arch, repo, NULL, buf, sizeof(buf), &urlp); } if (r == 0) { - r = load_index(db, apk_istream_from_fd_url(db->cache_fd, buf), targz, repo_num); + r = load_index(db, apk_istream_from_fd_url(db->cache_fd, buf, apk_db_url_since(db, 0)), targz, repo_num); } if (r != 0) { @@ -2538,7 +2539,7 @@ static int apk_db_install_archive_entry(void *_ctx, if (pkg_prio >= 0) break; - if (!(apk_force & APK_FORCE_OVERWRITE)) { + if (!(db->force & APK_FORCE_OVERWRITE)) { apk_error(PKG_VER_FMT": trying to overwrite %s owned by "PKG_VER_FMT".", PKG_VER_PRINTF(pkg), ae->name, PKG_VER_PRINTF(opkg)); ipkg->broken_files = 1; @@ -2791,7 +2792,7 @@ static int apk_db_unpack_pkg(struct apk_database *db, if (!apk_db_cache_active(db)) need_copy = FALSE; - is = apk_istream_from_fd_url(filefd, file); + is = apk_istream_from_fd_url(filefd, file, apk_db_url_since(db, 0)); if (IS_ERR_OR_NULL(is)) { r = PTR_ERR(is); if (r == -ENOENT && pkg->filename == NULL) diff --git a/src/io_url.c b/src/io_url.c index 93728aa..d61dd52 100644 --- a/src/io_url.c +++ b/src/io_url.c @@ -103,6 +103,7 @@ static struct apk_istream *apk_istream_fetch(const char *url, time_t since) { struct apk_fetch_istream *fis = NULL; struct url *u; + char *flags = "Ci"; fetchIO *io = NULL; int rc = -EIO; @@ -117,8 +118,12 @@ static struct apk_istream *apk_istream_fetch(const char *url, time_t since) goto err; } - u->last_modified = since; - io = fetchXGet(u, &fis->urlstat, (apk_force & APK_FORCE_REFRESH) ? "Ci" : "i"); + if (since != APK_ISTREAM_FORCE_REFRESH) { + u->last_modified = since; + flags = "i"; + } + + io = fetchXGet(u, &fis->urlstat, flags); if (!io) { rc = fetch_maperror(fetchLastErrCode); goto err; @@ -147,8 +152,3 @@ struct apk_istream *apk_istream_from_fd_url_if_modified(int atfd, const char *ur return apk_istream_from_file(atfd, apk_url_local_file(url)); return apk_istream_fetch(url, since); } - -struct apk_istream *apk_istream_from_url_gz(const char *file) -{ - return apk_istream_gunzip(apk_istream_from_url(file)); -} diff --git a/src/solver.c b/src/solver.c index df63060..be9240a 100644 --- a/src/solver.c +++ b/src/solver.c @@ -1097,7 +1097,7 @@ restart: generate_changeset(ss, world); - if (ss->errors && (apk_force & APK_FORCE_BROKEN_WORLD)) { + if (ss->errors && (db->force & APK_FORCE_BROKEN_WORLD)) { foreach_array_item(d, world) { name = d->name; pkg = name->ss.chosen.pkg;