静态内存布局的 BSS 部分[应该]用于“未初始化的全局变量”或“全局变量设置为 0”。
\n我正在运行一些测试,突然注意到局部静态变量也在增加 BSS 段的大小。
\n例子 :-
\n在任何静态变量之前
\nint main (int argc, char argv[])\n{\n return 0;\n}\nRun Code Online (Sandbox Code Playgroud)\ndata/repos/e-c \n\xe2\x9d\xaf size a.out \n text data bss dec hex filename\n 1418 544 8 1970 7b2 a.out\nRun Code Online (Sandbox Code Playgroud)\n静态变量之后
\nint main (int argc, char *argv[])\n{\n static int a, b, c;\n return 0;\n}\nRun Code Online (Sandbox Code Playgroud)\ndata/repos/e-c \n\xe2\x9d\xaf !s\nsize a.out \n text data bss dec hex filename\n 1418 544 16 1978 7ba a.out\nRun Code Online (Sandbox Code Playgroud)\n这些变量肯定不是全局变量,那为什么BSS段会增加呢?或者“未初始化的全局变量的段”的想法不完全正确?
\n目前我使用的是 Linux,并使用 GCC 编译器(版本 9.3.0)。
\n静态内存布局的 BSS 部分[应该]用于“未初始化的全局变量”或“全局变量设置为 0”。
目前还不清楚你从哪里得到这种印象,但它充其量只是一种误导。大多数人在 C 上下文中使用术语“全局变量”意味着具有外部链接的对象标识符,这对于具有静态存储持续时间的对象来说是必然的。有一些附带条件,这样的标识符可以在程序中的任何地方使用来引用同一对象,因此是“全局的”。一些附带条件的存在和性质使用“全球”一词来表示这些有点令人担忧,但我将把它留给不同的答案。
BSS 的关键点不是链接,而是存储持续时间。静态存储持续时间意味着,至少在原则上,对象在程序开始时或之前就存在*并且(至少)生存到程序终止。与在不带 的块作用域中声明的变量对比static:这些变量具有自动存储持续时间,这意味着它们在声明时就存在,并且仅存活到最内层包含块的执行终止为止。
具有静态存储持续时间的对象需要在程序映像中表示,无论它们的链接如何,因为它们与程序本身具有相同的生命周期。C 指定,如果此类对象未显式初始化,则它们的初始值就像初始化为 0(对于数字类型)或NULL(指针类型)或按成员方式初始化为这些(对于复合类型)。BSS 是一种节省空间和时间的快捷方式,用于表示此类对象以及显式初始化为 0 的对象的存储。
满足初始化条件的所谓“全局”变量可以并且通常归因于 BSS,但也可以
static;这些变量自动具有静态存储持续时间,但只能从一个源文件访问,并且static在该作用域使用关键字来指定,即使它们没有链接。*在 C++ 中,其中一些对象稍后会进行动态初始化,但此类对象的内存仍然为程序的整个运行保留,并且它们在程序启动时会进行零初始化。它们具有保留的记忆和明确定义的价值,构成了本答案的存在。