pthread堆栈的一部分似乎已被使用

问题描述

| 我已将Linux中pthread的堆栈大小设置为16 KB。如果然后将一个大于8 KB的数组压入堆栈,则应用程序会因分段错误而停止。在我看来,我正在尝试访问堆栈底部下方的内存,这可能是未映射的内存,因此是段错误。 这是示例代码
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
#include <string.h>

void *start_routine(void *arg)
{
  size_t size = 9*1024;
  unsigned char arr[size];

  memset(arr,size);
}

int main()
{
  int err;
  pthread_attr_t threadAttr;
  size_t stacksize;
  void *stackAddr;
  pthread_t thread;

  pthread_attr_init(&threadAttr);
  pthread_attr_setstacksize(&threadAttr,16*1024);
  pthread_attr_getstacksize(&threadAttr,&stacksize);
  printf(\"stacksize: %d\\n\",stacksize);

  pthread_create(&thread,&threadAttr,start_routine,NULL );
  pthread_join(thread,NULL);

  return 0;
}  
我松散了大约8 KB的堆栈,这似乎很奇怪。我也尝试使用更大的堆栈大小。它似乎以某种方式改变了我可以使用的堆栈数量。 我知道对于当今的系统(某些嵌入式系统除外),这几个字节并不是很重要,但是我很好奇为什么我不能使用大部分已定义的堆栈。我不希望我可以使用整个堆栈,但是丢失大约8 KB似乎是很多的。 在调用入口例程之前,在线程的堆栈上放置了哪些信息? 谢谢 菲利普     

解决方法

在对glibc nptl源代码进行了一些研究之后,我得出的结论是,在堆栈的底部放置了拥有堆栈的线程的pthread-struct,并可能根据glibc的配置提供了一些其他变量。他们一起使用大约3K。堆栈的顶部装有保护页,通常为4K大。因此大约已经使用了7-8K。至少对于保护页面的内存没有单独分配,我感到有些惊讶。我想着要记住那是事实,但事实并非如此。