C语言 pthread_create使用85MB的VIRT而不是8MB的VIRT



好的,所以我理解VIRT !=物理内存,并且通常建议不要担心它等。

但是我很困惑,为什么我的每个pthread_create导致VIRT增加85MB,而不是按照我的ulimit堆栈设置为8192 kb通常的8MB。

我怀疑它与堆有关,但我是C的新手,对这方面不确定。

我的代码片段是:
if (tcount == gset_vars->global_threads_max)
{
for (j = 0; j< tcount; j++)
{
pthread_join(tid[j], NULL); // close threads
}
tcount=0;
}
pthread_create(&tid[tcount],NULL,HTTP_Multi_Thread,(void *)&args[i]);
tcount++;

代码注释:

它在一个for循环中有15次迭代,结果VIRT是1275MB(即15*85)

内部for循环只在gset_vars->global_threads_max var设置为小于15时运行(无论如何,这不会影响生成的VIRT大小)。

函数调用(HTTP_Multi_Thread)只是运行一些基本的libcurl来下载单个文件并将其写入磁盘。参数只是url和本地文件名。

注意:为了保持代码片段简短,它没有显示在主循环之后我确实在所有线程(tcount)上运行pthread_join。

编辑:根据@johnbollinger的建议,这里是一个基本的,可复制的例子:

#include <stdio.h>
#include <pthread.h>
#include <curl/curl.h>
#include <string.h>
#include <unistd.h>
#define NUMT 8
char *urls[NUMT] = {
"http://example.com",
"http://example.com",
"http://example.com",
"http://example.com",
"http://example.com",
"http://example.com",
"http://example.com",
"http://example.com"};
char *filenames[NUMT] = {
"ex1.txt",
"ex2.txt",
"ex3.txt",
"ex4.txt",
"ex5.txt",
"ex6.txt",
"ex7.txt",
"ex8.txt"};
struct arg_struct
{
char url[128];
char filename[128];
};
size_t write_data(void *ptr, size_t size, size_t nmemb, FILE *stream)
{
size_t written = fwrite(ptr, size, nmemb, stream);
return written;
}
static void *pull_one_url(void *arguments)
{
struct arg_struct *myargs = arguments;
char url[128];
char filename[128];
strcpy(url, myargs->url);
strcpy(filename, myargs->filename);
FILE *fp;
fp = fopen(filename, "wb");
CURL *curl;
curl = curl_easy_init();
curl_easy_setopt(curl, CURLOPT_URL, url);
//curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_data);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);
curl_easy_perform(curl);
curl_easy_cleanup(curl);
fclose(fp);
return NULL;
}
int main(int argc, char **argv)
{
pthread_t tid[NUMT];
int i;
struct arg_struct args[NUMT];
curl_global_init(CURL_GLOBAL_ALL);
for (i = 0; i < NUMT; i++)
{
strcpy(args[i].filename, filenames[i]);
strcpy(args[i].url, urls[i]);
pthread_create(&tid[i],
NULL,
pull_one_url,
(void *)&args[i]);
}
for (i = 0; i < NUMT; i++)
{
pthread_join(tid[i], NULL);
fprintf(stderr, "Thread %d terminatedn", i);
}
curl_global_cleanup();
sleep(60);
}

休眠(60)的唯一目的是在运行时允许一些分析时间。对于Windows用户,可能需要启用WRITEFUNCTION选项。

您的ulimit堆栈设置仅影响进程的启动堆栈。它对新创建线程的堆栈大小没有任何影响。为此,您需要使用pthread_attr_setstacksize

最新更新