From: Michael Tremer Date: Mon, 16 Oct 2023 17:09:08 +0000 (+0000) Subject: downloader: Anchor the downloader to the context X-Git-Tag: 0.9.30~1481 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=88b4d102c607c425f23d999178033f3d694f715c;p=pakfire.git downloader: Anchor the downloader to the context Signed-off-by: Michael Tremer --- diff --git a/src/libpakfire/downloader.c b/src/libpakfire/downloader.c index d5862b41c..5daaac568 100644 --- a/src/libpakfire/downloader.c +++ b/src/libpakfire/downloader.c @@ -43,7 +43,7 @@ #define MAX_PARALLEL 4 struct pakfire_transfer { - struct pakfire* pakfire; + struct pakfire_ctx* ctx; int nrefs; // Reference to the downloader @@ -86,7 +86,7 @@ struct pakfire_transfer { }; struct pakfire_downloader { - struct pakfire* pakfire; + struct pakfire_ctx* ctx; int nrefs; unsigned int parallel; @@ -113,14 +113,14 @@ static int pakfire_downloader_setup_curl(struct pakfire_downloader* downloader) // Initialize cURL r = curl_global_init(CURL_GLOBAL_DEFAULT); if (r) { - ERROR(downloader->pakfire, "Could not initialize cURL: %d\n", r); + CTX_ERROR(downloader->ctx, "Could not initialize cURL: %d\n", r); return r; } // Create a new multi handle downloader->curl = curl_multi_init(); if (!downloader->curl) { - ERROR(downloader->pakfire, "Could not create cURL multi handle\n"); + CTX_ERROR(downloader->ctx, "Could not create cURL multi handle\n"); return 1; } @@ -152,8 +152,8 @@ static void pakfire_downloader_transfer_free(struct pakfire_transfer* transfer) pakfire_mirrorlist_unref(transfer->mirrors); if (transfer->progress) pakfire_progress_unref(transfer->progress); - if (transfer->pakfire) - pakfire_unref(transfer->pakfire); + if (transfer->ctx) + pakfire_ctx_unref(transfer->ctx); free(transfer); } @@ -187,28 +187,32 @@ static void pakfire_downloader_free(struct pakfire_downloader* downloader) { if (downloader->curl) curl_multi_cleanup(downloader->curl); - - pakfire_unref(downloader->pakfire); + if (downloader->ctx) + pakfire_ctx_unref(downloader->ctx); free(downloader); } -int pakfire_downloader_create(struct pakfire_downloader** downloader, struct pakfire* pakfire) { +int pakfire_downloader_create( + struct pakfire_downloader** downloader, struct pakfire_ctx* ctx) { struct pakfire_downloader* d = NULL; int r; +#warning The OFFLINE flag must be moved into the context +#if 0 // Fail if pakfire is running in offline mode if (pakfire_has_flag(pakfire, PAKFIRE_FLAGS_OFFLINE)) { ERROR(pakfire, "Cannot initialize downloader in offline mode\n"); return -ENOTSUP; } +#endif // Allocate a new object d = calloc(1, sizeof(*d)); if (!d) return -ENOMEM; - // Store reference to Pakfire - d->pakfire = pakfire_ref(pakfire); + // Store reference to the context + d->ctx = pakfire_ctx_ref(ctx); // Initialize reference counting d->nrefs = 1; @@ -254,20 +258,20 @@ struct pakfire_downloader* pakfire_downloader_unref(struct pakfire_downloader* d #ifdef ENABLE_DEBUG static int debug_callback(CURL *handle, curl_infotype type, char* data, size_t size, void* private) { - struct pakfire* pakfire = (struct pakfire*)private; + struct pakfire_ctx* ctx = private; switch (type) { case CURLINFO_TEXT: - DEBUG(pakfire, "cURL: %.*s", (int)size, data); + CTX_DEBUG(ctx, "cURL: %.*s", (int)size, data); break; // Log headers case CURLINFO_HEADER_IN: - DEBUG(pakfire, "cURL: < %.*s", (int)size, data); + CTX_DEBUG(ctx, "cURL: < %.*s", (int)size, data); break; case CURLINFO_HEADER_OUT: - DEBUG(pakfire, "cURL: > %.*s", (int)size, data); + CTX_DEBUG(ctx, "cURL: > %.*s", (int)size, data); break; // Ignore everything else @@ -282,6 +286,7 @@ static int debug_callback(CURL *handle, curl_infotype type, static size_t pakfire_downloader_transfer_write( char* data, size_t size, size_t nmemb, void* p) { struct pakfire_transfer* transfer = p; + struct pakfire_ctx* ctx = transfer->ctx; int r; // Do not write empty blocks @@ -292,7 +297,7 @@ static size_t pakfire_downloader_transfer_write( if (transfer->evp) { r = EVP_DigestUpdate(transfer->evp, data, nmemb); if (r != 1) { - ERROR(transfer->downloader->pakfire, "EVP_DigestUpdate failed: %s\n", + CTX_ERROR(ctx, "EVP_DigestUpdate failed: %s\n", ERR_error_string(ERR_get_error(), NULL)); return 0; } @@ -309,7 +314,7 @@ static int pakfire_downloader_transfer_setup( int r; // Fetch global configuration - config = pakfire_get_config(downloader->pakfire); + config = pakfire_ctx_get_config(downloader->ctx); // Set global configuration if (config) { @@ -326,7 +331,7 @@ static int pakfire_downloader_transfer_setup( curl_easy_setopt(transfer->handle, CURLOPT_VERBOSE, 1L); curl_easy_setopt(transfer->handle, CURLOPT_DEBUGFUNCTION, debug_callback); - curl_easy_setopt(transfer->handle, CURLOPT_DEBUGDATA, downloader->pakfire); + curl_easy_setopt(transfer->handle, CURLOPT_DEBUGDATA, downloader->ctx); #endif // Limit protocols to HTTPS, HTTP, FTP and FILE @@ -363,8 +368,8 @@ int pakfire_downloader_transfer_create(struct pakfire_transfer** transfer, if (!t) return -errno; - // Store a reference to Pakfire - t->pakfire = pakfire_ref(downloader->pakfire); + // Store a reference to the context + t->ctx = pakfire_ctx_ref(downloader->ctx); // Initialize the reference counter t->nrefs = 1; @@ -546,13 +551,13 @@ static int pakfire_transfer_select_mirror(struct pakfire_downloader* downloader, // No mirror found if (!transfer->mirror) { - ERROR(downloader->pakfire, "No mirrors left to try\n"); + CTX_ERROR(downloader->ctx, "No mirrors left to try\n"); // No mirrors left return ENOENT; } - DEBUG(downloader->pakfire, "Selected mirror %s\n", pakfire_mirror_get_url(transfer->mirror)); + CTX_DEBUG(downloader->ctx, "Selected mirror %s\n", pakfire_mirror_get_url(transfer->mirror)); return 0; } @@ -589,7 +594,7 @@ static int pakfire_transfer_save(struct pakfire_downloader* downloader, if (!*transfer->path) return 0; - DEBUG(downloader->pakfire, + CTX_DEBUG(downloader->ctx, "Download successful. Storing result in %s\n", transfer->path); // Flush any buffered data out to disk @@ -606,7 +611,7 @@ static int pakfire_transfer_save(struct pakfire_downloader* downloader, // Move the temporary file to its destination r = link(transfer->tempfile, transfer->path); if (r) { - ERROR(downloader->pakfire, "Could not link destination file %s: %m\n", + CTX_ERROR(downloader->ctx, "Could not link destination file %s: %m\n", transfer->path); return r; } @@ -617,7 +622,7 @@ static int pakfire_transfer_save(struct pakfire_downloader* downloader, if (times.modtime) { r = utime(transfer->path, ×); if (r) - ERROR(downloader->pakfire, "Could not set mtime of %s: %m\n", transfer->path); + CTX_ERROR(downloader->ctx, "Could not set mtime of %s: %m\n", transfer->path); } return 0; @@ -627,7 +632,7 @@ static int pakfire_transfer_fail(struct pakfire_downloader* downloader, struct pakfire_transfer* transfer, int code) { int r; - DEBUG(downloader->pakfire, "Transfer failed\n"); + CTX_DEBUG(downloader->ctx, "Transfer failed\n"); // Get file descriptor int fd = fileno(transfer->f); @@ -665,14 +670,14 @@ static int pakfire_transfer_done(struct pakfire_downloader* downloader, if (r) return r; - DEBUG(downloader->pakfire, "cURL transfer done: %d - %s\n", + CTX_DEBUG(downloader->ctx, "cURL transfer done: %d - %s\n", code, curl_easy_strerror(code)); // Finish message digest computation if (transfer->evp) { r = EVP_DigestFinal_ex(transfer->evp, transfer->computed_digest, &transfer->computed_digest_length); if (r != 1) { - ERROR(downloader->pakfire, "Could not finish message digest computation: %s\n", + CTX_ERROR(downloader->ctx, "Could not finish message digest computation: %s\n", ERR_error_string(ERR_get_error(), NULL)); return 1; } @@ -684,36 +689,36 @@ static int pakfire_transfer_done(struct pakfire_downloader* downloader, // Effective URL curl_easy_getinfo(h, CURLINFO_EFFECTIVE_URL, &url); if (url) - DEBUG(downloader->pakfire, " Effective URL: %s\n", url); + CTX_DEBUG(downloader->ctx, " Effective URL: %s\n", url); // Response code curl_easy_getinfo(h, CURLINFO_RESPONSE_CODE, &response_code); if (response_code) - DEBUG(downloader->pakfire, " Response code: %ld\n", response_code); + CTX_DEBUG(downloader->ctx, " Response code: %ld\n", response_code); // HTTP Version curl_easy_getinfo(h, CURLINFO_HTTP_VERSION, &http_version); if (http_version) - DEBUG(downloader->pakfire, " HTTP Version: %s\n", curl_http_version(http_version)); + CTX_DEBUG(downloader->ctx, " HTTP Version: %s\n", curl_http_version(http_version)); // Total Times curl_easy_getinfo(h, CURLINFO_TOTAL_TIME, &total_time); - DEBUG(downloader->pakfire, " Total Time: %.2fs\n", total_time); + CTX_DEBUG(downloader->ctx, " Total Time: %.2fs\n", total_time); // Download Size curl_easy_getinfo(h, CURLINFO_SIZE_DOWNLOAD_T, &download_size); if (download_size) - DEBUG(downloader->pakfire, " Download Size: %ld bytes\n", download_size); + CTX_DEBUG(downloader->ctx, " Download Size: %ld bytes\n", download_size); // Download Speed curl_easy_getinfo(h, CURLINFO_SPEED_DOWNLOAD_T, &speed); if (speed) - DEBUG(downloader->pakfire, " Download Speed: %ld bps\n", speed); + CTX_DEBUG(downloader->ctx, " Download Speed: %ld bps\n", speed); // Message Digest char* hexdigest = __pakfire_hexlify(transfer->computed_digest, transfer->computed_digest_length); if (hexdigest) { - DEBUG(downloader->pakfire, " Message Digest: %s\n", hexdigest); + CTX_DEBUG(downloader->ctx, " Message Digest: %s\n", hexdigest); free(hexdigest); } @@ -729,9 +734,9 @@ static int pakfire_transfer_done(struct pakfire_downloader* downloader, char* expected_hexdigest = __pakfire_hexlify(transfer->expected_digest, transfer->expected_digest_length); - ERROR(downloader->pakfire, "Download checksum for %s didn't match:\n", transfer->url); - ERROR(downloader->pakfire, " Expected: %s\n", expected_hexdigest); - ERROR(downloader->pakfire, " Computed: %s\n", computed_hexdigest); + CTX_ERROR(downloader->ctx, "Download checksum for %s didn't match:\n", transfer->url); + CTX_ERROR(downloader->ctx, " Expected: %s\n", expected_hexdigest); + CTX_ERROR(downloader->ctx, " Computed: %s\n", computed_hexdigest); if (computed_hexdigest) free(computed_hexdigest); @@ -839,7 +844,7 @@ static int pakfire_downloader_transfer_prepare_progress(struct pakfire_downloade progress_flags |= PAKFIRE_PROGRESS_NO_PROGRESS; // Make a new progress meter - r = pakfire_progress_create(&transfer->progress, transfer->pakfire, progress_flags, parent); + r = pakfire_progress_create(&transfer->progress, transfer->ctx, progress_flags, parent); if (r) return r; @@ -918,7 +923,7 @@ static int pakfire_downloader_transfer_prepare(struct pakfire_downloader* downlo // Fail if we could not set the URL } else { - ERROR(downloader->pakfire, "Invalid transfer %s\n", transfer->url); + CTX_ERROR(downloader->ctx, "Invalid transfer %s\n", transfer->url); return -EINVAL; } @@ -926,7 +931,7 @@ static int pakfire_downloader_transfer_prepare(struct pakfire_downloader* downlo if (!transfer->f) { r = pakfire_downloader_transfer_prepare_tmpfile(transfer); if (r) { - ERROR_ERRNO(transfer->pakfire, r, "Could not open a temporary file: %m\n"); + CTX_ERROR(downloader->ctx, "Could not open a temporary file: %s\n", strerror(-r)); return r; } } @@ -941,14 +946,14 @@ static int pakfire_downloader_transfer_prepare(struct pakfire_downloader* downlo if (transfer->md) { transfer->evp = EVP_MD_CTX_new(); if (!transfer->evp) { - ERROR(downloader->pakfire, "Could not create EVP context: %m\n"); + CTX_ERROR(downloader->ctx, "Could not create EVP context: %m\n"); return 1; } // Initialize the EVP context r = EVP_DigestInit_ex(transfer->evp, transfer->md, NULL); if (r != 1) { - ERROR(downloader->pakfire, "Could not initialize EVP context: %s\n", + CTX_ERROR(downloader->ctx, "Could not initialize EVP context: %s\n", ERR_error_string(ERR_get_error(), NULL)); return 1; } @@ -1023,7 +1028,7 @@ static int pakfire_downloader_transfer_start(struct pakfire_downloader* download struct pakfire_transfer* transfer, struct pakfire_progress* progress) { int r; - DEBUG(downloader->pakfire, "Starting transfer %p...\n", transfer); + CTX_DEBUG(downloader->ctx, "Starting transfer %p...\n", transfer); // Prepare the transfer r = pakfire_downloader_transfer_prepare(downloader, transfer, progress, 0); @@ -1033,7 +1038,7 @@ static int pakfire_downloader_transfer_start(struct pakfire_downloader* download // Add the handle to cURL r = curl_multi_add_handle(downloader->curl, transfer->handle); if (r) { - ERROR(downloader->pakfire, "Adding handle failed: %s\n", curl_multi_strerror(r)); + CTX_ERROR(downloader->ctx, "Adding handle failed: %s\n", curl_multi_strerror(r)); return r; } @@ -1099,7 +1104,7 @@ int pakfire_downloader_run(struct pakfire_downloader* downloader, const char* ti const unsigned int num_queued_transfers = pakfire_downloader_total_queued_transfers(downloader); // Create a new progress indicator - r = pakfire_progress_create(&progress, downloader->pakfire, progress_flags, NULL); + r = pakfire_progress_create(&progress, downloader->ctx, progress_flags, NULL); if (r) goto ERROR; @@ -1126,7 +1131,7 @@ int pakfire_downloader_run(struct pakfire_downloader* downloader, const char* ti // Run cURL r = curl_multi_perform(downloader->curl, &still_running); if (r) { - ERROR(downloader->pakfire, "cURL error: %s\n", curl_easy_strerror(r)); + CTX_ERROR(downloader->ctx, "cURL error: %s\n", curl_easy_strerror(r)); goto ERROR; } @@ -1169,7 +1174,7 @@ int pakfire_downloader_run(struct pakfire_downloader* downloader, const char* ti break; default: - ERROR(downloader->pakfire, "Received unhandled cURL message %u\n", msg->msg); + CTX_ERROR(downloader->ctx, "Received unhandled cURL message %u\n", msg->msg); break; } } diff --git a/src/libpakfire/filelist.c b/src/libpakfire/filelist.c index 08738a656..5f9f1573e 100644 --- a/src/libpakfire/filelist.c +++ b/src/libpakfire/filelist.c @@ -41,6 +41,7 @@ struct pakfire_filelist_element { }; struct pakfire_filelist { + struct pakfire_ctx* ctx; struct pakfire* pakfire; int nrefs; @@ -52,6 +53,9 @@ PAKFIRE_EXPORT int pakfire_filelist_create(struct pakfire_filelist** list, struc if (!l) return -ENOMEM; + // Store a reference to the context + l->ctx = pakfire_ctx(pakfire); + l->pakfire = pakfire_ref(pakfire); l->nrefs = 1; @@ -65,6 +69,8 @@ PAKFIRE_EXPORT int pakfire_filelist_create(struct pakfire_filelist** list, struc static void pakfire_filelist_free(struct pakfire_filelist* list) { pakfire_filelist_clear(list); pakfire_unref(list->pakfire); + if (list->ctx) + pakfire_ctx_unref(list->ctx); free(list); } @@ -425,7 +431,7 @@ int pakfire_filelist_walk(struct pakfire_filelist* list, // Show progress when iterating over the filelist if (flags & PAKFIRE_FILELIST_SHOW_PROGRESS) { - r = pakfire_progress_create(&progress, list->pakfire, + r = pakfire_progress_create(&progress, list->ctx, PAKFIRE_PROGRESS_SHOW_PERCENTAGE|PAKFIRE_PROGRESS_SHOW_ETA, NULL); if (r) goto ERROR; @@ -501,7 +507,7 @@ int pakfire_filelist_verify(struct pakfire_filelist* list, struct pakfire_fileli DEBUG(list->pakfire, "Verifying filelist (%zu file(s))...\n", length); // Setup progress - r = pakfire_progress_create(&progress, list->pakfire, + r = pakfire_progress_create(&progress, list->ctx, PAKFIRE_PROGRESS_SHOW_PERCENTAGE|PAKFIRE_PROGRESS_SHOW_ETA, NULL); if (r) goto ERROR; diff --git a/src/libpakfire/include/pakfire/downloader.h b/src/libpakfire/include/pakfire/downloader.h index 0f36f95a5..fdec8ecd2 100644 --- a/src/libpakfire/include/pakfire/downloader.h +++ b/src/libpakfire/include/pakfire/downloader.h @@ -25,16 +25,16 @@ struct pakfire_downloader; +#include #include #include -#include enum pakfire_transfer_flags { PAKFIRE_TRANSFER_NO_PROGRESS = (1 << 0), PAKFIRE_TRANSFER_NOTEMP = (1 << 1), }; -int pakfire_downloader_create(struct pakfire_downloader** downloader, struct pakfire* pakfire); +int pakfire_downloader_create(struct pakfire_downloader** downloader, struct pakfire_ctx* ctx); struct pakfire_downloader* pakfire_downloader_ref(struct pakfire_downloader* downloader); struct pakfire_downloader* pakfire_downloader_unref(struct pakfire_downloader* downloader); diff --git a/src/libpakfire/repo.c b/src/libpakfire/repo.c index e4462aa96..43189287d 100644 --- a/src/libpakfire/repo.c +++ b/src/libpakfire/repo.c @@ -455,7 +455,7 @@ static int pakfire_repo_download_database(struct pakfire_repo* repo, return r; // Create a downloader - r = pakfire_downloader_create(&downloader, repo->pakfire); + r = pakfire_downloader_create(&downloader, repo->ctx); if (r) goto ERROR; @@ -622,7 +622,7 @@ static int pakfire_repo_refresh_mirrorlist(struct pakfire_repo* repo, const int } // Create a new downloader - r = pakfire_downloader_create(&downloader, repo->pakfire); + r = pakfire_downloader_create(&downloader, repo->ctx); if (r) goto ERROR; @@ -682,7 +682,7 @@ static int pakfire_repo_download_metadata(struct pakfire_repo* repo, const char* } // Create a downloader - r = pakfire_downloader_create(&downloader, repo->pakfire); + r = pakfire_downloader_create(&downloader, repo->ctx); if (r) goto ERROR; @@ -1274,7 +1274,7 @@ static int pakfire_repo_download(struct pakfire_repo* repo, const char* url, } // Create the downloader - r = pakfire_downloader_create(&downloader, repo->pakfire); + r = pakfire_downloader_create(&downloader, repo->ctx); if (r) goto ERROR; @@ -1588,7 +1588,7 @@ PAKFIRE_EXPORT int pakfire_repo_scan(struct pakfire_repo* repo, int flags) { const size_t num_files = pakfire_filelist_length(filelist); // Create progress indicator - r = pakfire_progress_create(&progress, repo->pakfire, + r = pakfire_progress_create(&progress, repo->ctx, PAKFIRE_PROGRESS_SHOW_COUNTER|PAKFIRE_PROGRESS_SHOW_ELAPSED_TIME, NULL); if (r) goto ERROR; diff --git a/src/libpakfire/transaction.c b/src/libpakfire/transaction.c index 0862747d7..fcf1b3d66 100644 --- a/src/libpakfire/transaction.c +++ b/src/libpakfire/transaction.c @@ -1895,7 +1895,7 @@ PAKFIRE_EXPORT int pakfire_transaction_download(struct pakfire_transaction* tran int r; // Initialize the downloader - r = pakfire_downloader_create(&downloader, transaction->pakfire); + r = pakfire_downloader_create(&downloader, transaction->ctx); if (r) { ERROR(transaction->pakfire, "Could not initialize downloader: %m\n"); return 1;