我试图理解内存分配在编译和加载程序的不同阶段是如何工作的。
1)编译器和汇编器生成从地址0开始的代码和数据部分。
2)链接器通过关联内存位置来重定位这些部分 使用每个符号定义,然后修改所有引用 这些符号使它们指向这个内存位置。
3)加载程序将程序加载到主存储器,在进程的上下文中,以及
因此,在此步骤中,分页和所有与内存管理相关的操作都已完成。
我的问题是两件事:
1)链接器分配的地址与加载器分配的地址有何关系。我们可以调用链接器地址虚拟地址吗?
2)所有程序是否都具有相同的虚拟地址(最终映射到不同的物理地址?)
答案 0 :(得分:0)
通常编译器会生成无法在任何特定地址启动的可重定位代码。有些情况并非完全有可能。 E.g。
int x ;
int *y = &x ;
这些需要特殊处理。
链接器合并编译器引用的程序段。链接的输出是一个程序,它指示加载程序如何将程序放在内存中。这些说明将处理上述情况。
加载程序遵循链接器提供的指令。
1)链接器分配的地址与加载器分配的地址有何关系。我们可以调用链接器地址虚拟地址吗?
链接器通常会生成可重定位代码,除非编译器或程序集生成了无法重定位的内容。链接器不会生成虚拟地址。
2)所有程序是否都具有相同的虚拟地址(最终映射到不同的物理地址?)
在大多数系统中,程序的每次运行都会产生相同的逻辑地址布局。作为一种安全措施,这种情况越来越普遍。每次加载程序时,它的加载方式都不同。