我最近了解到,计算机程序实际上并未利用物理内存的地址。相反,我了解物理内存已由操作系统“隐藏”到应用程序。
这是我的问题: 指针返回物理内存还是虚拟内存的地址?
如果执行下面的代码,则会得到十六进制形式的地址。仅仅是操作系统随机分配的数字吗?而且,我发现数组中元素的地址是连续分配的。这是否意味着数组实际上是RAM中的“行”形式,还是有可能将它们分配在稀疏区域中,而OS只会伪造程序员?
int num = 3;
int arr[3];
printf("address of num: 0x%0x \n", &num);
printf("&arr[0]: 0x%0x \n", &arr[0]);
printf("&arr[1]: 0x%0x \n", &arr[1]);
printf("&arr[2]: 0x%0x \n", &arr[2]);
答案 0 :(得分:5)
在所有现代操作系统(Windows,Linux,BSD等)中,用户空间应用程序中的所有地址都是虚拟地址。某些RTOS或其他自定义的裸机应用程序除外。
虚拟地址不一定是随机,但是从硬件的角度来看,它们是任意的。内核通常会决定为给定映射请求分配的虚拟地址空间,有时会考虑用户空间请求。当使用诸如ASLR之类的东西时(这在当今很普遍),地址被有意地随机化。
这是否意味着数组实际上在RAM中是“行”形式的,还是有可能在稀疏区域中分配它们,而OS只是伪造了程序员?
两者。操作系统会创建内存的页面的物理到虚拟的映射,而不是单个地址。页面大小因架构而异,但通常为4 KiB。
因此,如果您有一个1 KiB数组(其起始地址至少与1 KiB对齐),则该数组在物理上是连续的。但是,一个16 KiB的阵列可能分散在彼此之间相距甚远的4页中。
答案 1 :(得分:1)
这取决于操作系统。但是大多数情况下(在大多数OS上)它们是逻辑地址。 有OS机制,例如虚拟内存,分页等,用于地址转换。通常这样做是为了确保不允许程序覆盖部分内存。 如果您在没有操作系统的裸机内核上运行此命令来处理虚拟地址。这将是物理地址。如果将其作为应用程序运行在OS之上,您将获得虚拟地址。