x86-64汇编中全局值位置及全局数组初始化形式咨询
x86-64汇编中全局数组的初始化位置与函数内初始化的区别
你的全局数组i在x86-64汇编里会被放在**.data数据段**中,编译时就完成初始化,和函数内的局部数组初始化逻辑完全不同。
1. 全局数组的汇编初始化形式
用GCC把你的代码编译成汇编(gcc -S -O0 test.c),会得到类似下面的片段:
.data .globl i # 声明i为全局可见符号 .type i, @object # 标记i是对象类型 .size i, 20 # 数组大小:5个int × 4字节 = 20字节 i: .long 1 # 数组第一个元素的值 .long 2 .long 3 .long 4 .long 5
这里的.data段是可执行文件中存储已初始化全局/静态数据的区域,程序加载时操作系统会直接把这段数据映射到内存,运行时不需要额外执行初始化代码——数组的初始值是硬编码在可执行文件里的。
2. 和函数内数组初始化的区别
如果是在main函数内声明初始化数组,比如:
int main(){ int local_i[] = {1,2,3,4,5}; // ... }
对应的汇编会是在函数栈上分配空间,然后通过mov指令逐个写入初始值:
main: pushq %rbp movq %rsp, %rbp subq $32, %rsp # 栈上分配局部变量空间 movl $1, -20(%rbp) # 把1写入栈上对应local_i[0]的位置 movl $2, -16(%rbp) # 写入local_i[1] movl $3, -12(%rbp) movl $4, -8(%rbp) movl $5, -4(%rbp) // ...
这种初始化是在函数执行时动态完成的,每次调用函数都会重新执行这些mov指令把值写入栈空间;而全局数组的初始化是一次性在编译链接阶段完成,程序启动后直接可用。
内容的提问来源于stack exchange,提问作者aurelius
相关产品推荐
相关产品推荐

