Linux内核是否可以随意产生重大页面错误?是否可以编写一个程序来保证在执行时导致主要页面错误。
答案1
要产生主要页面错误,您需要强制从磁盘读取。以下代码映射命令行上给出的文件,告诉内核它不需要它;如果文件足够大(在 中选择一个大文件/usr/bin
),您总是会遇到主要页面错误:
#include <fcntl.h>
#include <stdio.h>
#include <sys/mman.h>
#include <sys/stat.h>
int main(int argc, char ** argv) {
int fd = open(argv[1], O_RDONLY);
struct stat stats;
fstat(fd, &stats);
posix_fadvise(fd, 0, stats.st_size, POSIX_FADV_DONTNEED);
char * map = (char *) mmap(NULL, stats.st_size, PROT_READ, MAP_SHARED, fd, 0);
if (map == MAP_FAILED) {
perror("Failed to mmap");
return 1;
}
int result = 0;
int i;
for (i = 0; i < stats.st_size; i++) {
result += map[i];
}
munmap(map, stats.st_size);
return result;
}
错误处理的方式不多,这只是为了演示这个想法。在我的系统上,
gcc majorfault.c -o majorfault && /usr/bin/time -v ./majorfault /usr/bin/git-annex
总是产生 154 个主要页面错误。
答案2
此 C 程序导致我的 Mac 上的内存压力图出现 PDQ 峰值:
#include <stdlib.h>
int main(void)
{
while (1) {
char* p = malloc(1 * 1024 * 1024 * 1024);
for (int i = 0; i < 1024; ++i) {
p[i * 1024 * 1024] = 0; /* touch the pages */
}
}
return 0;
}
内循环很重要。如果您至少不触及分配的某些内存页,内存管理子系统就会足够聪明,意识到您只是在请求从未使用过的内存。然而,这很可能是 OS X 特定的实现细节。