mirror of
https://github.com/morgan9e/systemd
synced 2026-04-14 08:25:20 +09:00
pull-job: optionally take expected content length and compare it with what we are downloading
This commit is contained in:
@@ -93,6 +93,7 @@ static int pull_job_restart(PullJob *j, const char *new_url) {
|
||||
j->etag_exists = false;
|
||||
j->mtime = 0;
|
||||
j->checksum = mfree(j->checksum);
|
||||
j->expected_content_length = UINT64_MAX;
|
||||
|
||||
curl_glue_remove_and_free(j->glue, j->curl);
|
||||
j->curl = NULL;
|
||||
@@ -114,6 +115,15 @@ static int pull_job_restart(PullJob *j, const char *new_url) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static uint64_t pull_job_content_length_effective(PullJob *j) {
|
||||
assert(j);
|
||||
|
||||
if (j->expected_content_length != UINT64_MAX)
|
||||
return j->expected_content_length;
|
||||
|
||||
return j->content_length;
|
||||
}
|
||||
|
||||
void pull_job_curl_on_finished(CurlGlue *g, CURL *curl, CURLcode result) {
|
||||
PullJob *j = NULL;
|
||||
char *scheme = NULL;
|
||||
@@ -214,8 +224,9 @@ void pull_job_curl_on_finished(CurlGlue *g, CURL *curl, CURLcode result) {
|
||||
goto finish;
|
||||
}
|
||||
|
||||
if (j->content_length != UINT64_MAX &&
|
||||
j->content_length != j->written_compressed) {
|
||||
uint64_t cl = pull_job_content_length_effective(j);
|
||||
if (cl != UINT64_MAX &&
|
||||
cl != j->written_compressed) {
|
||||
r = log_error_errno(SYNTHETIC_ERRNO(EIO), "Download truncated.");
|
||||
goto finish;
|
||||
}
|
||||
@@ -374,8 +385,9 @@ static int pull_job_write_compressed(PullJob *j, void *p, size_t sz) {
|
||||
if (j->written_compressed + sz > j->compressed_max)
|
||||
return log_error_errno(SYNTHETIC_ERRNO(EFBIG), "File overly large, refusing.");
|
||||
|
||||
if (j->content_length != UINT64_MAX &&
|
||||
j->written_compressed + sz > j->content_length)
|
||||
uint64_t cl = pull_job_content_length_effective(j);
|
||||
if (cl != UINT64_MAX &&
|
||||
j->written_compressed + sz > cl)
|
||||
return log_error_errno(SYNTHETIC_ERRNO(EFBIG),
|
||||
"Content length incorrect.");
|
||||
|
||||
@@ -589,6 +601,12 @@ static size_t pull_job_header_callback(void *contents, size_t size, size_t nmemb
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (j->expected_content_length != UINT64_MAX &&
|
||||
j->expected_content_length != j->content_length) {
|
||||
r = log_error_errno(SYNTHETIC_ERRNO(EPROTO), "Content does not have expected size.");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
log_info("Downloading %s for %s.", FORMAT_BYTES(j->content_length), j->url);
|
||||
}
|
||||
|
||||
@@ -691,6 +709,7 @@ int pull_job_new(
|
||||
.url = TAKE_PTR(u),
|
||||
.offset = UINT64_MAX,
|
||||
.sync = true,
|
||||
.expected_content_length = UINT64_MAX,
|
||||
};
|
||||
|
||||
*ret = TAKE_PTR(j);
|
||||
|
||||
@@ -58,6 +58,8 @@ typedef struct PullJob {
|
||||
uint64_t uncompressed_max;
|
||||
uint64_t compressed_max;
|
||||
|
||||
uint64_t expected_content_length;
|
||||
|
||||
uint8_t *payload;
|
||||
size_t payload_size;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user