请让我知道指针(在 C/C++ 编程语言中)如何引用硬盘中的段,例如高达 1 GB 的存储空间。
更详细地说,我将编写一个函数的签名,该函数将指针作为参数,并且应该指向硬盘中的一个段,该段最多可以容纳 1 GB 空间,而不是传递指向地址的指针,这拥有相同数量的存储空间,在堆上我希望它指向硬盘段。系统是Linux,编程语言C和C++。
请让我知道指针(在 C/C++ 编程语言中)如何引用硬盘中的段,例如高达 1 GB 的存储空间。
更详细地说,我将编写一个函数的签名,该函数将指针作为参数,并且应该指向硬盘中的一个段,该段最多可以容纳 1 GB 空间,而不是传递指向地址的指针,这拥有相同数量的存储空间,在堆上我希望它指向硬盘段。系统是Linux,编程语言C和C++。
你可以调查一下mmap
。这允许将文件映射到您的主内存中。
您必须将数据映射到您的虚拟地址空间。
打开您的文件或块设备(例如/dev/sda
)open(2)
并在此处传递文件描述符:
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <sys/mman.h>
void * map_file_descriptr(int fd) {
struct stat file_stat;
if (fstat(fd, &file_stat)) {
perror("fstat");
// do something on error
return NULL;
}
void * data = mmap(
NULL // place the the VM segment anywhere in the process virtual address space
, file_stat.st_size // file size
// For read-only:
, PROT_READ
, MAP_PRIVATE
// for read-write
/*
, PROT_READ | PROT_WRITE
, MAP_SHARED
*/
, fd // file which belongs to this file descriptor
, 0 // from the beginning
);
if (data == MAP_FAILED) {
perror("mmap");
// you most likely are out of memory to allocate the VM table
// this very rarely happens
return NULL;
}
return data;
}
如果您将文件映射MAP_SHARED
为进行读写访问,那么您需要msync(2)
将更新刷新到磁盘。
小心:MAP_PRIVATE
如果文件在映射后被另一个进程修改,则映射文件具有未定义的行为。此外,如果在映射后更改文件大小,则任何映射都将导致未定义的行为。
注意:可以写入MAP_PRIVATE
映射,但删除映射时不会将更改写回文件,这些映射也无法同步。PROT_WRITE