#include < stdlib..."/>
您好,登錄后才能下訂單哦!
利用mmap實現的一個文件拷貝例子,供大家參考,具體內容如下
/* * gcc -Wall -O3 -o copy_mmap copy_mmap.c */ #include < stdio.h > #include < stdlib.h > #include < string .h > /* for memcpy */ #include < strings.h > #include < sys / mman.h > #include < sys / types.h > #include < sys / stat.h > #include < fcntl.h > #include < unistd.h > #define PERMS 0600 int main ( int argc, char * argv[] ) { int src, dst; void * sm, * dm; struct stat statbuf; if ( argc != 3 ) { fprintf( stderr, " Usage: %s \n " , argv[ 0 ] ); exit( EXIT_FAILURE ); } if ( ( src = open( argv[ 1 ], O_RDONLY ) ) < 0 ) { perror( " open source " ); exit( EXIT_FAILURE ); } /* 為了完成復制,必須包含讀打開,否則mmap()失敗 */ if ( ( dst = open( argv[ 2 ], O_RDWR | O_CREAT | O_TRUNC, PERMS ) ) < 0 ) { perror( " open target " ); exit( EXIT_FAILURE ); } if ( fstat( src, & statbuf ) < 0 ) { perror( " fstat source " ); exit( EXIT_FAILURE ); } /* * 參看前面man手冊中的說明,mmap()不能用于擴展文件長度。所以這里必須事 * 先擴大目標文件長度,準備一個空架子等待復制。 */ if ( lseek( dst, statbuf.st_size - 1 , SEEK_SET ) < 0 ) { perror( " lseek target " ); exit( EXIT_FAILURE ); } if ( write( dst, & statbuf, 1 ) != 1 ) { perror( " write target " ); exit( EXIT_FAILURE ); } /* 讀的時候指定 MAP_PRIVATE 即可 */ sm = mmap( 0 , ( size_t )statbuf.st_size, PROT_READ, MAP_PRIVATE | MAP_NORESERVE, src, 0 ); if ( MAP_FAILED == sm ) { perror( " mmap source " ); exit( EXIT_FAILURE ); } /* 這里必須指定 MAP_SHARED 才可能真正改變靜態(tài)文件 */ dm = mmap( 0 , ( size_t )statbuf.st_size, PROT_WRITE, MAP_SHARED, dst, 0 ); if ( MAP_FAILED == dm ) { perror( " mmap target " ); exit( EXIT_FAILURE ); } memcpy( dm, sm, ( size_t )statbuf.st_size ); /* * 可以不要這行代碼 * * msync( dm, ( size_t )statbuf.st_size, MS_SYNC ); */ return ( EXIT_SUCCESS ); }
mmap()好處是處理大文件時速度明顯快于標準文件I/O,無論讀寫,都少了一次用戶空間與內核空間之間的復制過程。操作內存還便于設計、優(yōu)化算法。
文件I/O操作/proc/self/mem不存在頁邊界對齊的問題,但至少Linux的mmap()的最后一個形參offset并未強制要求頁邊界對齊,如果提供的值未對齊,系統(tǒng)自動向上舍入到頁邊界上。malloc()分配得到的地址不見得對齊在頁邊界上。
/proc/self/mem和/dev/kmem不同。root用戶打開/dev/kmem就可以在用戶空間訪問到內核空間的數據,包括偏移0處的數據,系統(tǒng)提供了這樣的支持。顯然代碼段經過/proc/self/mem可寫映射后已經可寫,無須mprotect()介入。
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持億速云。
免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng)、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。