x86汇编.data section声明全局变量的内存分配机制疑问
.data段全局变量内存分配逻辑解答
疑问1:编译阶段汇编器/链接器如何知晓可用内存?
编译、链接阶段根本不需要感知实际物理内存的空闲情况,分配的是进程专属的虚拟地址空间偏移
- 现代操作系统都会给每个运行的进程分配独立的虚拟地址空间,这个空间是进程独占的,不会和其他进程的地址冲突,因此汇编器、链接器只需要遵循可执行文件格式(比如Windows下的PE、Linux下的ELF)的规范,给不同段(.text代码段、.data已初始化数据段、.bss未初始化数据段等)分配互不重叠的虚拟地址区间即可,不需要关心物理内存的实际使用情况。
- 虚拟地址到物理地址的映射由操作系统的内存管理单元(MMU)自动完成,对上层应用完全透明。
疑问2:运行时没有写分配代码,程序如何完成.data段内存分配?
.data段的内存分配完全由操作系统在程序加载阶段自动完成,不需要用户态代码手动操作:
- 你在汇编代码的.data段写的变量声明,比如
my_var dd 100,本质是给汇编器、链接器传递两个信息:① 需要在.data段预留N字节的空间,初始值为XXX;② 给这个预留空间的起始地址绑定一个符号名(这里就是my_var)。这些信息最终会被写到可执行文件的段表结构中。 - 操作系统加载可执行文件时,会读取段表的信息,按照标注的大小给.data段对应的虚拟地址范围映射物理内存、写入初始值,加载完成后你直接通过符号名就能访问对应的变量,不需要额外执行分配操作。
补充说明
- 只有堆、栈上的动态内存分配才需要你手动调用
malloc、brk这类内存分配接口,全局变量所在的.data、.bss段的分配都是操作系统加载程序时自动处理的。
内容的提问来源于stack exchange,提问作者Minhas Ali
相关产品推荐
相关产品推荐

