C语言中的内存模型
2015-07-30 19:19
148 查看
写了好几年的程序了,大部分时候都是在用C++,剩下用了点java。用java的时候基本上没有考虑过内在模型的问题,因为使用频率并不高,也没有碰到过什么大的问题。用C++这么多年了,但是对内存模型其实还是说不了太清楚,好像很懂,但说的很清楚明白,能够通过代码证明我的方法,其实还是搞不定。说起来有点搞笑加心酸,但是是这样,整天写代码也未必是高手,就像整天开车也没能成赛车手一样。所以一直不停的努力,才可能成为高手,天天在那里写烂代码,不会提高什么水平的,只能腐朽下去。
先看一下APUE中的C内存空间分布图
其中low address在64位下的开始地址是0x0000000000400000,32位的程序,我现在基本上没有写了。
那么从低地址到高地址依次的段为:
1 第一部分是只读区,存放程序(.text)和文字常量(.rodata)。二进制代码和文字常量在内存中具体怎么个分布法,我不清楚。也有可能本身就是混着放的,需要一个证明的方法。代码区用来存放程序的二进制代码。常量字符串就是放在文字常量区,程序结束后由系统释放。
2 第二部分是可读写区,存放全局变量和静态变量。可读写区从低地址到高地址分成两个部分,第一部分是已经初始化的(.data),第二部分是未初始化的(.bss)。已经初始化的区域,从低地址到高地址,先是全局初始化的,后面是局部静态初始化的。未初始化区域,从低地址到高地址,先是局部静态未初始化的,后是全局未初始化的。
3 第三部分是堆区域,从低地址向高地址增加。
4 第四部分是栈区域,从高地址向低地址增加。
5 第五部分是命令行参数和环境变量。
6 第六部分是操作系统使用的区域。
以上的部分内容,是我从网上看到的,加上自己代码验证的,有不对的地方,请指正。详细的验证过程代码太多,就不在这里贴了。所以内存从低地址到高地址,各段分别是.text,.rodata,.data,.bss,heap,stack。以上的内存的分布情况,而C语言中那些东西放到什么地方,我们需要代码来看一下。
注意的是:全局未初始化区的变量都被初始化为0
先看一下APUE中的C内存空间分布图
其中low address在64位下的开始地址是0x0000000000400000,32位的程序,我现在基本上没有写了。
那么从低地址到高地址依次的段为:
1 第一部分是只读区,存放程序(.text)和文字常量(.rodata)。二进制代码和文字常量在内存中具体怎么个分布法,我不清楚。也有可能本身就是混着放的,需要一个证明的方法。代码区用来存放程序的二进制代码。常量字符串就是放在文字常量区,程序结束后由系统释放。
2 第二部分是可读写区,存放全局变量和静态变量。可读写区从低地址到高地址分成两个部分,第一部分是已经初始化的(.data),第二部分是未初始化的(.bss)。已经初始化的区域,从低地址到高地址,先是全局初始化的,后面是局部静态初始化的。未初始化区域,从低地址到高地址,先是局部静态未初始化的,后是全局未初始化的。
3 第三部分是堆区域,从低地址向高地址增加。
4 第四部分是栈区域,从高地址向低地址增加。
5 第五部分是命令行参数和环境变量。
6 第六部分是操作系统使用的区域。
以上的部分内容,是我从网上看到的,加上自己代码验证的,有不对的地方,请指正。详细的验证过程代码太多,就不在这里贴了。所以内存从低地址到高地址,各段分别是.text,.rodata,.data,.bss,heap,stack。以上的内存的分布情况,而C语言中那些东西放到什么地方,我们需要代码来看一下。
int g_a; // 全局未初始化区 int g_b = 0; // 全局初始化区 char* g_p1; // 全局未初始化区 char* g_p2 = 0; // 全局初始化区 int main() { static int d ; // 全局未初始化区 static int c =0; // 全局初始化区 int a;// 栈区 int b = 0;// 栈区 char s[] = "abc"; // 栈区 char* p2; // 栈区 char* p3 = "123456"; // "123456/0" 在常量区,p3在栈区 g_p1 = (char *)malloc(20); // 分配得来的20字节的区域就在堆区 strcpy(g_p1, "123456"); // "123456/0" 放在常量区,编译器可能会将它与p3所指向的"123456"优化成一个地方。 return 0; }
注意的是:全局未初始化区的变量都被初始化为0
相关文章推荐
- 【资源】C++学习资料 - 逆天整理 - 精华无密版【最新】
- C/C++中作用域详解
- C语言 输出系统时间
- 使用G++编译运行c++(by命令行)
- C语言scanf函数详细解释
- C++11学习1
- C++ Primer Plus 学习笔记(第六章)
- @清晰掉 C++ 中的 enum 结构在内存中是怎么存储的?
- OC语言__实现中等难度通讯录
- 利用栈实现精制转换c++
- 象棋比赛问题(排序/C++)
- 缺少libstdc++.so.6库的原因及解决办法
- 在C语言中关于scanf()函数需要注意的一些事项
- C++生成全局唯一Guid
- C++--String类型各种重载函数的实现
- C++如何实现DNS域名解析
- C++ 字符串
- C++中的RAII机制
- 【总结】关于C++虚函数、多态和对象切割
- C++内部数据类型和非内部数据类型