linux 文件IO与内存映射:内存映射
生活随笔
收集整理的這篇文章主要介紹了
linux 文件IO与内存映射:内存映射
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
前言
前面幾篇我們學習了用戶空間的IO緩沖區,以及IO緩沖區的分散聚合IO技術.
為了減少系統調用的次數,提升系統性能,操作系統開發者門提出了這么多的緩存技術。
但是到這里這些技術同樣有不足的地方:不論是讀或者寫文件,都需要將內容拷貝到IO緩沖區以及頁高速緩沖區,這就增加了數據拷貝的次數,無形之中增加了CPU和內存的開銷。
有沒有一種辦法既可以減少系統調用的次數同時又可以降低數據的拷貝次數呢?這里系統開發者推出了內存映射技術。
描述
將文件映射到內存:
- 內存數據與文件數據一一對應
- 通過內存代替read/write系統調用接口來訪問文件
- 減少數據拷貝,減少系統調用次數,提高了系統性能
映射完成之后,用戶對內存的讀寫即會轉換為讀文件的讀寫。
編程接口
- 頭文件
<sys/mman.h> - 函數使用
void *mmap(void *addr, size_t length, int prot, int flags, int fd, off_t offset); - 函數功能:在用戶虛地址空間創建一個和實際物理內存相映射的關系。
- 函數參數:
addr:進程要映射的虛擬內存的起始地址,一般為NULL。操作系統會自動分配一個合適的內存地址。
length:要映射實際的內存區域大小
prot:內存保護標志,PROT_EXEC,PROT_READ,PROT_WRITE
flags: 映射的對象類型,MAP_FIXED,MAP_SHARED,MAP_PRIVATE
fd:要映射的文件描述符
offset:文件偏移地址
mmap:以頁單位操作,參數addr和offset必須按頁對齊(4K對齊) - 返回值:
成功:指向映射后的實際內存的地址
失敗:MAP_FAILED
編程案例
map_write.c
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/mman.h>int main(int argc,char *argv[]){int fd,i = 0;char *p_map;fd = open(argv[1],O_CREAT|O_RDWR,0666);if (-1 == fd) {printf("open failed \n");_exit(-1);}//初始化文件描述符,設置文件大小;此處也可以用ftruncate直接設置write(fd,"",14);//將fd文件映射到物理內存區域,使用MAP_SHARED標記,即映射的內存可以和其他進程共享p_map =(char *)mmap(NULL, 20, PROT_READ|PROT_WRITE,MAP_SHARED,fd,0);if (MAP_FAILED == p_map) {printf("mmap failed \n");_exit(-1);}close(fd);//使用內存拷貝函數,將指定字符串拷貝到映射的內存區域memcpy(p_map, "hello world\n",14);sleep(5);//解除映射if (munmap(p_map,20) == -1) {printf("ummap failed \n");_exit(-1);}return 0;
}
mmap_read.c
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>
#include <sys/mman.h>int main(int argc,char *argv[]){int fd,i = 0;char *p_map;fd = open(argv[1],O_CREAT|O_RDWR,0666);if (-1 == fd) {printf("open failed \n");_exit(-1);}p_map =(char *)mmap(NULL, 20, PROT_READ|PROT_WRITE,MAP_SHARED,fd,0);if (MAP_FAILED == p_map) {printf("mmap failed \n");_exit(-1);}close(fd);//映射到內存之后可以直接從映射的地址中讀出寫入內存的數據printf("mmap read %s\n",p_map);if (munmap(p_map,20) == -1) {printf("ummap failed \n");_exit(-1);}return 0;
輸出如下:
zhang@ubuntu:~/Desktop/cpp_practice$ ./write map_write
zhang@ubuntu:~/Desktop/cpp_practice$ ./read map_write
mmap read hello world
總結
以上是生活随笔為你收集整理的linux 文件IO与内存映射:内存映射的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 耳钉多少钱啊?
- 下一篇: 编译内核指定模块,筛选当前模块依赖的组件