2017-04-12 56 views
0

我想写数据到内存映射文件,它显示垃圾。不知道我做错了什么。我正在创建一个内存映射文件并将int写入它。我看到垃圾输出。C:写数据到内存映射文件显示垃圾

我打开为读/写,我非常希望其他进程读取下面

#include <stdio.h> 
#include <stdlib.h> 
#include <sys/types.h> 
#include <sys/stat.h> 
#include <unistd.h> 
#include <fcntl.h> 
#include <sys/mman.h> 

#define FILEPATH "test" 
#define NUMINTS (1000) 
#define FILESIZE (NUMINTS * sizeof(int)) 

int main(int argc, char *argv[]) 
{ 
    int i; 
    int fd; 
    int result; 
    int *map; /* mmapped array of int's */ 

    /* Open a file for writing. 
    * - Creating the file if it doesn't exist. 
    * - Truncating it to 0 size if it already exists. (not really needed) 
    * 
    * Note: "O_WRONLY" mode is not sufficient when mmaping. 
    */ 
    fd = open(FILEPATH, O_RDWR | O_CREAT | O_TRUNC, (mode_t)0600); 
    if (fd == -1) { 
    perror("Error opening file for writing"); 
    exit(EXIT_FAILURE); 
    } 

    /* Stretch the file size to the size of the (mmapped) array of ints 
    */ 
    result = lseek(fd, FILESIZE-1, SEEK_SET); 
    if (result == -1) { 
    close(fd); 
    perror("Error calling lseek() to 'stretch' the file"); 
    exit(EXIT_FAILURE); 
    } 

    /* Something needs to be written at the end of the file to 
    * have the file actually have the new size. 
    * Just writing an empty string at the current file position will do. 
    * 
    * Note: 
    * - The current position in the file is at the end of the stretched 
    * file due to the call to lseek(). 
    * - An empty string is actually a single '\0' character, so a zero-byte 
    * will be written at the last byte of the file. 
    */ 
    result = write(fd, "", 1); 
    if (result != 1) { 
    close(fd); 
    perror("Error writing last byte of the file"); 
    exit(EXIT_FAILURE); 
    } 

    /* Now the file is ready to be mmapped. 
    */ 
    map = mmap(0, FILESIZE, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); 
    if (map == MAP_FAILED) { 
    close(fd); 
    perror("Error mmapping the file"); 
    exit(EXIT_FAILURE); 
    } 

    /* Now write int's to the file as if it were memory (an array of ints). 
    */ 
    for (i = 1; i <=10; ++i) { 
     map[i] = i; 
    } 

    /* Don't forget to free the mmapped memory 
    */ 
    if (munmap(map, FILESIZE) == -1) { 
    perror("Error un-mmapping the file"); 
    /* Decide here whether to close(fd) and exit() or not. Depends... */ 
    } 

    /* Un-mmaping doesn't close the file, so we still need to do that. 
    */ 
    close(fd); 
    return 0; 
} 
+0

你可以检查输出文件的hexdump都可以? – Rajeshkumar

+1

你如何验证你的结果?通过在*文本*编辑器中打开文件? 'map [i] = i;'创建* binary *数据。如果使用文本工具查看,它会看起来像垃圾。 – kaylum

+0

糟糕我的坏.. hexdump显示正确的输出。我如何写文本数据而不是二进制文件? – Nikhil

回答

3

test内容写入到它

代码数据的文件看起来就像我会预计:

$ hexdump -C test 
00000000 00 00 00 00 01 00 00 00 02 00 00 00 03 00 00 00 |................| 
00000010 04 00 00 00 05 00 00 00 06 00 00 00 07 00 00 00 |................| 
00000020 08 00 00 00 09 00 00 00 0a 00 00 00 00 00 00 00 |................| 
00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| 
* 
00000fa0 

有你的10个整数。

当然,在文本编辑器看起来像垃圾,因为它是整数的二进制值,而不是ASCII "1""2" ...

+0

令人惊讶的是[** www.asciitable.com **](http://www.asciitable.com/)可以帮助清除':)' –

+0

@ DavidC.Rankin:当我处理各种编码时,并且必须定期检查0x80-0xff范围以确定哪个编码正好*,我写了自己的版本,[encoding.rootdirectory.de](http://encoding.rootdirectory.de)。 – DevSolar

+0

这更合理,对于混淆感到抱歉。 –