Как показано в вашем депо github, oprations
(операции!?) - локальная переменная, которая будет освобождена в конце функции readHeader.Чтобы обработать функцию readHeader и получить правильный размер файла для данного экземпляра Erza, нужно передать указатель на значение userdata
.Класс Erza может быть переписан как:
class Erza : public Endeavour {
//... your class body
public:
bool download (const char *url,const char* path){
curl = curl_easy_init();
if (curl) {
fp = fopen(path, "wb");
curl_easy_setopt(curl, CURLOPT_URL, url);
curl_easy_setopt(curl, CURLOPT_CAINFO, "./ca-bundle.crt");
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, false);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, false);
curl_easy_setopt(curl, CURLOPT_HEADERFUNCTION, readHeader);
curl_easy_setopt(curl, CURLOPT_HEADERDATA, this ); //<-- set this pointer to userdata value used in the callback.
curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);
res = curl_easy_perform(curl);
curl_easy_cleanup(curl);
fclose(fp);
return false;
}else
return true;
}
size_t analyseHeader( char* header, size_t size, size_t nitems ){
if (startsWith(header, "Content-Length:")) {
std::string header_in_string = replaceAll(header, "Content-Length:", "");
long size = atol(header_in_string.c_str());
file_size = size; // file_size is a member variable
std::cout << size; // here it is showing correct file size
}
else if (startsWith(header, "Content-Type:")) {
// do something
}else
// do something
return size * nitems;
}
}//Eof class Erza
size_t readHeader(char* header, size_t size, size_t nitems, void *userdata) {
//get the called context (Erza instance pointer set in userdata)
Erza * oprations = (Erza *)userdata;
return oprations->analyseHeader( header, size, nitems );
}