43 if (!file || fseek(file, 0, SEEK_END) != 0)
46 const long fileSize = ftell(file);
53 void *buffer = malloc(fileSize);
54 const size_t read = fread(buffer, 1, fileSize, file);
55 unsigned long adler = adler32_z(0L, Z_NULL, 0);
56 adler = adler32_z(adler, (Bytef*) buffer, read);
176 auto *d =
reinterpret_cast<Download*
>(ptr);
177 bool complete =
false;
178 std::string outFilename;
180 if (!d->mMemoryWrite)
183 for (
int attempts = 0; attempts < 3 && !complete && !d->mCancel; ++attempts)
185 CURL *curl = curl_easy_init();
189 Log::info(
"Downloading: %s", d->mUrl.c_str());
191 curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1);
192 curl_easy_setopt(curl, CURLOPT_HTTPHEADER, d->mHeaders);
194 FILE *file =
nullptr;
198 curl_easy_setopt(curl, CURLOPT_FAILONERROR, 1);
200 curl_easy_setopt(curl, CURLOPT_WRITEDATA, ptr);
204 file = fopen(outFilename.c_str(),
"w+b");
205 curl_easy_setopt(curl, CURLOPT_WRITEDATA, file);
209 const std::string userAgent =
212 curl_easy_setopt(curl, CURLOPT_USERAGENT, userAgent.c_str());
213 curl_easy_setopt(curl, CURLOPT_ERRORBUFFER, d->mError);
214 curl_easy_setopt(curl, CURLOPT_URL, d->mUrl.c_str());
215 curl_easy_setopt(curl, CURLOPT_NOPROGRESS, 0);
217 curl_easy_setopt(curl, CURLOPT_XFERINFODATA, ptr);
218 curl_easy_setopt(curl, CURLOPT_NOSIGNAL, 1);
219 curl_easy_setopt(curl, CURLOPT_CONNECTTIMEOUT, 15);
221 const CURLcode res = curl_easy_perform(curl);
222 curl_easy_cleanup(curl);
224 if (res == CURLE_ABORTED_BY_CALLBACK)
231 ::remove(outFilename.c_str());
240 res, d->mError, d->mUrl.c_str());
245 ::remove(outFilename.c_str());
251 if (!d->mMemoryWrite)
256 unsigned long adler =
fadler32(file);
258 if (d->mAdler != adler)
264 ::remove(outFilename.c_str());
265 Log::info(
"Checksum for file %s failed: (%lx/%lx)",
266 d->mFileName.c_str(),
278 ::remove(d->mFileName.c_str());
279 ::rename(outFilename.c_str(), d->mFileName.c_str());
283 file = fopen(d->mFileName.c_str(),
"rb");
301 auto state = d->mState.lock();
static int downloadProgress(void *clientp, curl_off_t dltotal, curl_off_t dlnow, curl_off_t ultotal, curl_off_t ulnow)
A libcurl callback for reporting progress.
#define PACKAGE_EXTENDED_VERSION