精华内容
下载资源
问答
  • 每个线程都有一个堆栈那么,这个堆栈多大呢?HANDLE CreateThread(LPSECURITY_ATTRIBUTES-那默认大小又是多少?写个小程序算一下~#include #include #define STACK_SIZE 0.5*1024*1024DWORD WINAPI ThreadFunc(PVOID ...

    每个线程都有一个堆栈那么,这个堆栈多大呢?

    HANDLE CreateThread(

    LPSECURITY_ATTRIBUTES

    -那默认大小又是多少?

    写个小程序算一下~

    #include

    #include

    #define STACK_SIZE 0.5*1024*1024

    DWORD WINAPI ThreadFunc(PVOID pvParam)

    {

    DWORD dwRet = 0;

    printf("%-3d:0x%x\n",pvParam,&dwRet);

    return dwRet;

    }

    int

    main(int,char**)

    {

    DWORD dwTid;

    printf("Main:0x%x\n",&dwTid);

    for(int i=0;i<50;i++)

    CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,0,&dwTid); // 莫小注:原作者这处代码有错,这不能修改线程栈大小

    Sleep(2000);

    return 0;

    }

    输出:

    Main:0x12ff78

    0       :0x50ffb0

    1       :0x60ffb0

    2       :0x70ffb0

    3       :0x80ffb0

    4       :0x90ffb0

    0x60ffb0 - 0x50ffb0 = 0x100000 byte = 1MB

    那么这个小程序中线程最小堆栈大小为1MB. (对么?为什么呢?后面有验证)

    将STACK_SIZE换成0, 结果和上面一样

    将STACK_SIZE换成2, 结果变成2MB

    以下是从MSDN中查到的

    Generally, the reserve size is the default reserve size specified in theexecutable header. However, if the initially committed size specified by dwStackSize is larger than the default reserve size, the reserve size is this new commit size rounded up to the nearest multiple of 1 MB.

    根据winnt.h中的      IMAGE_OPTIONAL_HEADER结构体

    typedef struct _IMAGE_OPTIONAL_HEADER {

    //

    // Standard fields.

    //

    WORD        Magic;

    BYTE        MajorLinkerVersion;

    BYTE        MinorLinkerVersion;

    DWORD       SizeOfCode;

    DWORD       SizeOfInitializedData;

    DWORD       SizeOfUninitializedData;

    DWORD       AddressOfEntryPoint;

    DWORD       BaseOfCode;

    DWORD       BaseOfData;

    //

    // NT additional fields.

    //

    DWORD       ImageBase;

    DWORD       SectionAlignment;

    DWORD       FileAlignment;

    WORD        MajorOperatingSystemVersion;

    WORD        MinorOperatingSystemVersion;

    WORD        MajorImageVersion;

    WORD        MinorImageVersion;

    WORD        MajorSubsystemVersion;

    WORD        MinorSubsystemVersion;

    DWORD       Win32VersionValue;

    DWORD       SizeOfImage;

    DWORD       SizeOfHeaders;

    DWORD       CheckSum;

    WORD        Subsystem;

    WORD        DllCharacteristics;

    DWORD       SizeOfStackReserve;

    DWORD       SizeOfStackCommit;

    DWORD       SizeOfHeapReserve;

    DWORD       SizeOfHeapCommit;

    DWORD       LoaderFlags;

    DWORD       NumberOfRvaAndSizes;

    IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES];

    } IMAGE_OPTIONAL_HEADER32, *PIMAGE_OPTIONAL_HEADER32;

    我推测,应该可以在链接期间指定栈大小

    查看link.exe的参数

    /STACK:reserve[,commit]

    果然如此~~

    看到网上有人问如何改变默认的线程堆栈大小,在MSDN中有答案:

    The default size for the reserved and initially committed stack memory is specified in the executable file header. Thread or fiber creation fails if there is not enough memory to reserve or commit the number of bytes requested. To specify a different default stack size for all threads and fibers,use the STACKSIZE statement in the module definition (.def) file. For more information on these default sizes and how to change them, see the documentation included with your linker.

    (模块定义 (.def) 文件为链接器提供有关被链接程序的导出、属性及其他方面的信息)

    可见,默认线程堆栈大小在链接阶段可以由程序员指定

    以上部分载自他人空间.

    MSDN中有段话很重要:

    To change the reserved stack size, set thedwCreationFlagsparameter ofCreateThreadorCreateRemoteThreadtoSTACK_SIZE_PARAM_IS_A_RESERVATIONand use thedwStackSizeparameter.

    我用MSDN2001版查看的时候,它有注明STACK_SIZE_PARAM_IS_A_RESERVATION 适用于XP系统, 在MSDN2008版没注明了,我是在XP下测试的

    下面是我改的测试代码:

    8f900a89c6347c561fdf2122f13be562.png

    961ddebeb323a10fe0623af514929fc1.png代码

    1 #include"stdafx.h"2 #include3 #include4 5 #defineSTACK_SIZE 64*1024//设置线程栈为64K6 7 DWORD WINAPI ThreadFunc(PVOID pvParam)8 {9 DWORD dwRet=0;10 printf("%-3d:0x%x\n",pvParam,&dwRet);11 Sleep(2000);//避免线程退出,这个线程栈地址又被分配给其它新创建的线程12 returndwRet;13 }14 15 intmain(int,char**)16 {17 DWORD dwTid;18 printf("Main:0x%x\n",&dwTid);19 20 HANDLE handles[10];21 22 for(inti=0;i<10;i++)23 {24 handles[i]=CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,STACK_SIZE_PARAM_IS_A_RESERVATION ,&dwTid);25 Sleep(100);//保证每次Create后得到的线程栈地址是递增的26 }27 for(inti=0; i<10; i++)28 {29 CloseHandle(handles[i]);30 }31 32 getchar();33 return0;34 }

    -----CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,STACK_SIZE_PARAM_IS_A_RESERVATION,&dwTid);

    运行结果:

    685e4174160eae74d0c43b43b98d443e.png

    每次相差(10000)x = (655366)d = 64*1024, 设置成功,64K.

    另外, Linux平台的栈默认大小应该是8192KB, Windows平台的栈默认大小应该是1024KB, 项目移植的时候要注意设置, 免得空间不足, 分配失败

    展开全文
  • 设置线程堆栈大小

    2010-08-06 23:45:00
    每个线程都有一个堆栈那么,这个堆栈多大呢? HANDLE CreateThread( LPSECURITY_ATTRIBUTES lpThreadAttributes, SIZE_T dwStackSize, LPTHREAD_START_ROUTINE lpStartAddress, LPVOID lpParameter, ...

    每个线程都有一个堆栈那么,这个堆栈多大呢?

    HANDLE CreateThread(
           LPSECURITY_ATTRIBUTES lpThreadAttributes,
           SIZE_T dwStackSize,
           LPTHREAD_START_ROUTINE lpStartAddress,
           LPVOID lpParameter,
           DWORD dwCreationFlags,
           LPDWORD lpThreadId
    );

    在创建线程的时候可以指定堆栈大 小,dwStackSize=0则使用默认大小


    -那默认大小又是多少?

          写个小程序算一下~

    #include <stdio.h>
    #include <windows.h>

    #define STACK_SIZE 0.5*1024*1024

    DWORD WINAPI ThreadFunc(PVOID pvParam)
    {
          DWORD dwRet = 0;
          printf("%-3d:0x%x\n",pvParam,&dwRet);
          return dwRet;
    }

    int
    main(int,char**)
    {
          DWORD dwTid;
          printf("Main:0x%x\n",&dwTid);
          for(int i=0;i<50;i++)
            CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,0,&dwTid); // 莫小注:原作者这处代码有错,这不能修改线程栈大小

          Sleep(2000);
        return 0;
    }

    输出:

    Main:0x12ff78
    0       :0x50ffb0
    1       :0x60ffb0
    2       :0x70ffb0
    3       :0x80ffb0
    4       :0x90ffb0

    0x60ffb0 - 0x50ffb0 = 0x100000 byte = 1MB

    那么这个小程序中线程最小堆栈大小为1MB. (对么?为什么呢?后面有验证)
    将STACK_SIZE换成0, 结果和上面一样
    将STACK_SIZE换成2, 结果变成2MB

    以下是从MSDN中查到的

    Generally, the reserve size is the default reserve size specified in the executable header. However, if the initially committed size specified by dwStackSize is larger than the default reserve size, the reserve size is this new commit size rounded up to the nearest multiple of 1 MB.

    根据winnt.h中的      IMAGE_OPTIONAL_HEADER结构体
    typedef struct _IMAGE_OPTIONAL_HEADER {
           //
            // Standard fields.
            //

            WORD        Magic;
            BYTE        MajorLinkerVersion;
            BYTE        MinorLinkerVersion;
            DWORD       SizeOfCode;
            DWORD       SizeOfInitializedData;
            DWORD       SizeOfUninitializedData;
            DWORD       AddressOfEntryPoint;
            DWORD       BaseOfCode;
            DWORD       BaseOfData;

            //
            // NT additional fields.
            //

            DWORD       ImageBase;
            DWORD       SectionAlignment;
            DWORD       FileAlignment;
            WORD        MajorOperatingSystemVersion;
            WORD        MinorOperatingSystemVersion;
            WORD        MajorImageVersion;
            WORD        MinorImageVersion;
            WORD        MajorSubsystemVersion;
            WORD        MinorSubsystemVersion;
            DWORD       Win32VersionValue;
            DWORD       SizeOfImage;
            DWORD       SizeOfHeaders;
            DWORD       CheckSum;
            WORD        Subsystem;
            WORD        DllCharacteristics;
            DWORD       SizeOfStackReserve;
            DWORD       SizeOfStackCommit;
            DWORD       SizeOfHeapReserve;
            DWORD       SizeOfHeapCommit;
            DWORD       LoaderFlags;
            DWORD       NumberOfRvaAndSizes;
            IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES];
    } IMAGE_OPTIONAL_HEADER32, *PIMAGE_OPTIONAL_HEADER32;

    我推测,应该可以在链接期间指定栈大小
    查看link.exe的参数

    /STACK:reserve[,commit]
    果然如此~~

    看到网上有人问如何改变默认的线程堆栈大小,在MSDN中有答案:

    The default size for the reserved and initially committed stack memory is specified in the executable file header. Thread or fiber creation fails if there is not enough memory to reserve or commit the number of bytes requested. To specify a different default stack size for all threads and fibers, use the STACKSIZE statement in the module definition (.def) file. For more information on these default sizes and how to change them, see the documentation included with your linker.

    (模块定义 (.def) 文件为链接器提供有关被链接程序的导出、属性及其他方面的信息)

    可见,默认线程堆栈大小在链接阶段可以由程序员指定

     

     

    以上部分载自他人空间.

    MSDN中有段话很重要:

    To change the reserved stack size, set the dwCreationFlags parameter of CreateThread or CreateRemoteThread to STACK_SIZE_PARAM_IS_A_RESERVATION and use the dwStackSize parameter. 

    我用MSDN2001版查看的时候,它有注明STACK_SIZE_PARAM_IS_A_RESERVATION 适用于XP系统, 在MSDN2008版没注明了,我是在XP下测试的

    下面是我改的测试代码:

     

    代码
     1 #include "stdafx.h"
     2 #include <stdio.h>
     3 #include <windows.h>
     4 
     5 #define STACK_SIZE 64*1024 // 设置线程栈为64K
     6 
     7 DWORD WINAPI ThreadFunc(PVOID pvParam)
     8 {
     9     DWORD dwRet = 0;
    10     printf("%-3d:0x%x\n",pvParam,&dwRet);
    11     Sleep(2000);  // 避免线程退出,这个线程栈地址又被分配给其它新创建的线程
    12     return dwRet;
    13 }
    14 
    15 int main(int,char**)
    16 {
    17     DWORD dwTid;
    18     printf("Main:0x%x\n",&dwTid);
    19 
    20     HANDLE handles[10];
    21 
    22     for(int i=0;i<10;i++)
    23     {
    24         handles[i] = CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,STACK_SIZE_PARAM_IS_A_RESERVATION ,&dwTid);
    25         Sleep(100); // 保证每次Create后得到的线程栈地址是递增的
    26     }
    27     for(int i=0; i<10; i++)
    28     {
    29         CloseHandle(handles[i]);
    30     }
    31 
    32     getchar();
    33     return 0;
    34 }

       -----CreateThread(NULL,STACK_SIZE,ThreadFunc,(PVOID)i,STACK_SIZE_PARAM_IS_A_RESERVATION ,&dwTid);

    运行结果:

     

     每次相差(10000)x = (655366)d = 64*1024, 设置成功,64K.

    另外, Linux平台的栈默认大小应该是8192KB, Windows平台的栈默认大小应该是1024KB, 项目移植的时候要注意设置, 免得空间不足, 分配失败

    转载于:https://www.cnblogs.com/nsnow/archive/2010/08/06/1794490.html

    展开全文
  • pthread_attr_setstacksize可以设置线程堆栈大小,用法: pthread_t thread; int ret; pthread_attr_t thread_attr; pthread_attr_init(&thread_attr); pthread_attr_setstacksize(&thread_...

    pthread_attr_setstacksize可以设置线程堆栈大小,用法:

    	pthread_t thread;
    
        int ret;
        pthread_attr_t thread_attr;
    
        pthread_attr_init(&thread_attr);
        pthread_attr_setstacksize(&thread_attr, 256*1024);
    
        ret = pthread_create(&thread, &thread_attr, threadProc, param);
        pthread_attr_destroy(&thread_attr);
    

    通过ulimit -s 命令查看出的,默认的线程堆栈大小为8192

    root@ubuntu:~# ulimit -s
    8192
    root@ubuntu:~# 
    

    在上面的程序中,我们修改为了256*1024。

    展开全文
  • 设置线程堆栈大小-----一台电脑最多能开启多少个线程
                    //http://www.cnblogs.com/nsnow/archive/2010/08/06/1794490.html
    //http://blog.csdn.net/nokianasty/article/details/7600322


    // Linux平台的栈默认大小应该是8192KB, Windows平台的栈默认大小应该是1024KB, 项目移植的时候要注意设置, 免得空间不足, 分配失败


    #include <process.h>
    #include <Windows.h>
    #include <iostream>
    using namespace std;


    class CTest
    {
    private:
    int *m_a;
    public:
    CTest(){m_a=new int;cout<<"CTest()"<<endl;}
    ~CTest(){if(m_a!=NULL){delete m_a;m_a=NULL;cout<<"~CTest()"<<endl;}}
    };
    //以下是_beginthreadex的函数原型
    /*_CRTIMP uintptr_t __cdecl _beginthreadex
    (_In_opt_ void * _Security, 
    _In_ unsigned _StackSize,
    _In_ unsigned (__stdcall * _StartAddress) (void *), 
    _In_opt_ void * _ArgList, 
    _In_ unsigned _InitFlag, 
    _Out_opt_ unsigned * _ThrdAddr);
    */
    //1--------当_StackSize为0时(_InitFlag=0),即默认时,线程栈大小为1M(1024*1024)
    //2--------当_StackSize>1M时(_InitFlag=0或_InitFlag=STACK_SIZE_PARAM_IS_A_RESERVATION),线程栈大小都为设定堆栈大小
    //3--------当_StackSize<1M时(_InitFlag=0),线程栈大小为1M
    //4--------当_StackSize<1M时(_InitFlag=STACK_SIZE_PARAM_IS_A_RESERVATION),线程栈大小为设定堆栈大小
    //5--------当设定栈大小为20M时,总共内存使用应该是20*5+进程内存>100M,但用任务管理器查看此程序内存使用情况为:1964K,即不到2M,
    //---------后来知道,栈内存是线程自己管理的,不会计入进程所占内存------堆属于进程这个容器!栈属于线程这个运行单元!
    #define STACK_SIZE   1024*1024*20     


    UINT threadProc(void *data)
    {
    CTest test;
    //while(true)
    {
    int a=1;
    cout<<"线程--------"<<(int)data<<":"<<&a<<endl;
    Sleep(3000);  // 避免线程退出,这个线程栈地址又被分配给其它新创建的线程(不用此句,&a地址一样,因为下一个线程使用了上一个退出线程的堆栈...)
    }
    _endthreadex(0);    //测试调用提前退出时是否未调用test的析构函数,等待3秒查看结果!!结果表明,_endthreadex强制提前退出线程时未调用析构函数,导致内存泄露!!!
    return 0;
    }


    int main()
    {
    HANDLE handle[5]={0};
    for(int i=0;i<5;i++)
    {
    handle[i]=(HANDLE)_beginthreadex(NULL,STACK_SIZE,(UINT(__stdcall*)(void*))threadProc,(void*)(i+1),STACK_SIZE_PARAM_IS_A_RESERVATION/*0*/,NULL);
    Sleep(200);         //没有用锁,所以暂时用sleep的方式保证线程是以i依次递增的
    }


    for(int i=0;i<5;i++)
    {
    if(handle[i]!=NULL)
    CloseHandle(handle[i]);
    }
    system("pause");
    return 0;
    }




    02C1FF4C-0181FF4C=01400000=20M

    当然这么小的程序没必要设这么大的栈,浪费大量内存资源...

    同时附加测试可以看到3秒过后,只调用了构造函数,未调用析构函数,导致内存泄露,而屏蔽掉_endthreadex(0); 后则可成功调用析构函数,因此

    使用_endthreadex等类似函数时应注意



    依据以上结果,我们可以推断:

    当默认情况时,栈大小为1M,若一台2G内存的电脑,则最多可以分配线程数应 小于  2G/1M=2048

    不同内存,不同栈大小则以此类推

               
    展开全文
  • 线程线程 被定义为程序的执行流。每个线程都定义了一个单独的控制流。如果应用程序涉及到复杂的和耗时的操作,那么将程序分成多个线程执行流往往是有益的,每个线程执行特定的工作。线程是轻量级进程。一个使用...
  • 案发现场 因业务所需在多线程环境下使用HttpClient组件对某个HTTP服务发起请求...然后再用jvisualvm工具查看发现服务器主机CPU使用率在90%之上并未呈现出下降趋势,查看实时线程有一批线程是一直处于运行状态且运行...
  • stack overflow堆栈溢出和快速排序这两个概念对开发人员来说并不陌生,但是通知都只是听说过,真正开发过程中却很少会遇到。我也是敲代码好些行后非常有幸撞上了,而且还是两个一起出现的,这其中过程的滋味还是相当...
  • 如果你学过数据结构,就一定会遇到“堆”,"栈","堆栈",这些对于小白来说有些头大,下面就来科普一下何谓堆栈?按照WIKI的定义:堆栈(英语:stack),是计算机科学中一种特殊的串列形式的抽象数据类型,其特殊之处在于...
  • 点击上方“布衣码农”,免费订阅~选择“设为星标”,第一时间免费获得更新~「布衣码农」肢解ThreadThread作为线程的抽象,Thread的实例用于描述线程,对线程的操纵,就是对Thread实例对象的管理与控制。创建一个线程...
  • 每个线程都有一个堆栈那么,这个堆栈多大呢? HANDLE CreateThread(  LPSECURITY_ATTRIBUTES lpThreadAttributes,  SIZE_T dwStackSize,  LPTHREAD_START_ROUTINE lpStartAddress,  LPVOID lpParameter,
  • 这个构造方法怎么用publicThread(ThreadGroupgroup,Runnabletarget,Stringname,longstackSize//设置线程堆栈大小)我没有接触过java,但是要做一个程序,我是这样写的,但是不对,高手帮帮...这个构造方法怎么用public ...
  • 目录1. SylixOS线程、线程栈介绍11.1线程的介绍11.2线程栈的介绍12. SylixOS线程栈大小的分配12.1线程、线程栈相关属性的设置22.2线程栈大小22.3线程堆栈警戒区33. 总结54. 参考资料5 SylixOS线程、线程栈介...
  • 我是如何得到这个64k限制的,当我试图在IntelliJ iDE上配置运行时vm选项时,我试图给出一些像10k这样的东西,它弹出这个错误,说它需要至少64k的线程堆栈大小.另一个问题是,如何从java程序中找到我的嵌入式设备中运行...
  • 在单元测试时,发现了比较多的线程堆栈空间不够导致 COREDUMP ...目前基础平台子系统通过配置环境变量,将默认堆栈大小设置为128K,可以减少这个问题的出现,但业务系统在编码时仍然 需要注意栈的使用,避免出现问题。
  • 在单元测试时,发现了比较多的线程堆栈空间不够导致 CORE...目前基础平台子系统通过配置环境变量,将默认堆栈大小设置为128K,可以减少这个问题的出现,但业务系统在编码时仍然 需要注意栈的使用,避免出现问题。
  • pthread_create 创建线程时,若不指定分配堆栈大小,系统会分配默认值,查看默认值方法如下: # ulimit -s8192# 上述表示为8M;单位为KB。 也可以通过# ulimit -a其中 stack size 项也表示堆栈大小。ulimit -s value...
  • pthread_create 创建线程时,若不指定分配堆栈大小,系统会分配默认值,查看默认值方法如下: # ulimit -s8192# 上述表示为8M;单位为KB。 也可以通过# ulimit -a其中 stack size 项也表示堆栈大小。ulimit -s ...
  • author: 张继飞 pthread_create 创建线程时,若不指定分配堆栈大小,系统会分配默认值,查看默认值方法如下: # ulimit -s8192# 上述表示为8M;单位为KB。 也可以通过# ulimit -a 其中 stack size 项也表示堆栈...
  • 线程堆栈

    千次阅读 2012-05-24 23:47:11
    线程堆栈! 2008-06-25 10:39  一个线程的开销包括:  内核模式下的开销(内核堆栈,对象管理所需内存)  用户模式下的开销...Visual C++编译器默认设置是每个线程的堆栈大小是1MB。当然,如果你
  • API pthread_attr_setstacksize(pthread_attr_t * attr,size_t stacksize)是设置为创建的线程堆栈分配的最小堆栈大小(以字节为单位).但是如何设置最大堆栈大小?谢谢解决方法:如果使用pthread_attr_setstack自行管理...
  • 学习ucosii,网上找了个demo,移植到stm32f030R8,SRAM20k我的板子是stm32f030k6,SRAM4K就是电量LED,把io口配置改下,直接编译,报出很多内存不足的错误,不知怎么解决了,原子哥,指点下吧.\obj\Ucosii_Demo.axf:...
  • 线程堆栈

    2012-03-30 15:55:12
    一个线程的开销包括:  内核模式下的开销(内核堆栈,对象管理所需...Visual C++编译器默认设置是每个线程堆栈大小是1MB。当然,如果你在创建线程时指定较小的堆栈大小,你应该可以创建较多的线程。  但是创

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 453
精华内容 181
关键字:

设置线程堆栈大小