curl_easy_perform 导致应用程序意外终止,服务器需要很长时间才能回复
Posted
技术标签:
【中文标题】curl_easy_perform 导致应用程序意外终止,服务器需要很长时间才能回复【英文标题】:curl_easy_perform causes app to terminate unexpectedly with server that takes long to reply 【发布时间】:2017-10-28 17:38:41 【问题描述】:我正在使用 libcurl 向服务器发送 POST 请求。一切正常,直到我注意到有时应用程序意外终止(不是超时,它甚至没有错误消息就结束了)。我已将其缩小到 curl_esy_perform。服务器回复该请求的时间很长(使用 Postman 测试,需要 20 分钟以上,但最终会回复),我的应用程序在大约 12 分钟后崩溃,没有任何错误消息。超时设置为 3600 秒。写入内存回调根本没有被调用(它不应该因为服务器不返回部分数据)这就是我使用 curl 的方式:
curl_global_init(CURL_GLOBAL_ALL);
CURL* curl;
CURLcode res;
struct MemoryStruct chunk;
int err = -1;
chunk.memory = (PCHAR)malloc(1);
chunk.size = 0;
if (!(curl = curl_easy_init()))
cout << "Error initializing cURL" << endl;
return 1;
curl_easy_setopt(curl, CURLOPT_URL, url);
curl_easy_setopt(curl, CURLOPT_PORT, port);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, CurlWriteMemCallback);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, (PVOID)&chunk);
curl_easy_setopt(curl, CURLOPT_USERAGENT, "libcurl-agent/1.0");
curl_easy_setopt(curl, CURLOPT_TIMEOUT, 3600);
struct curl_slist* headers = NULL;
headers = curl_slist_append(headers, "Accept: application/json");
headers = curl_slist_append(headers, "Content-Type: application/json");
headers = curl_slist_append(headers, "charsets: utf-8");
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
curl_easy_setopt(curl, CURLOPT_POSTFIELDS, body);
curl_easy_setopt(curl, CURLOPT_POSTFIELDSIZE, (long)strlen(body));
// It crashes during curl_easy_perform, after it hangs for ~12 minutes
res = curl_easy_perform(curl);
.
.
.
size_t CurlWriteMemCallback(PVOID contents, size_t size, size_t nmemb, PVOID userp)
size_t realsize = size * nmemb;
struct MemoryStruct *mem = (struct MemoryStruct *)userp;
mem->memory = (PCHAR)realloc(mem->memory, mem->size + realsize + 1);
if (!mem->memory)
FATAL() << "Not enough memory in cURL write memory callback";
return 0;
memcpy(&(mem->memory[mem->size]), contents, realsize);
mem->size += realsize;
mem->memory[mem->size] = 0;
return realsize;
【问题讨论】:
告诉我们更多关于“崩溃”的细节! 没有什么需要添加的:就好像调用了 exit() 一样。也看到这个问题(当我使用 WinHTTP 而不是 libcurl 时,该请求会发生完全相同的事情):***.com/questions/44255828/… 【参考方案1】:是否由于 curl 手册页中描述的有关超时信号的行为而退出进程? https://curl.haxx.se/libcurl/c/CURLOPT_TIMEOUT.html
即 "这个选项可能会导致 libcurl 使用 SIGALRM 信号来超时系统调用。"
如果您的应用程序不处理该信号,那么它将退出。
有一个选项可以在超时的情况下禁用生成此信号: “在类 unix 系统中,除非设置了 CURLOPT_NOSIGNAL,否则这可能会导致使用信号。”
希望这还不算太晚,至少可以帮助其他人。
【讨论】:
对不起哥们,这种行为发生在以前工作的一个项目中。我不记得细节了。不知何故,我设法通过了它,但我不知道如何。以上是关于curl_easy_perform 导致应用程序意外终止,服务器需要很长时间才能回复的主要内容,如果未能解决你的问题,请参考以下文章
Libcurl 挂在 curl_easy_perform 或 curl_multi_perform 从不减少第二个参数