C将二进制文件读取到缓冲区

时间:2015-09-12 21:45:46

标签: c binary buffer

我试图创建一个可以读取二进制文件的简单VM,按照二进制文件中的指令(每个指令4个字 - 32位),然后在遵循所有指令后输出结果。

我目前处于项目的第一阶段,我正在尝试使用fread / fopen将我文件的内容读入缓冲区。在大多数情况下,代码类似于cplusplus.com上为fread提供的示例,但是我想找到一种方法将我的文件一次分成4个单词。我以前从未在如此低的水平上工作,并且在查明我是否正确地做这件事时遇到了问题,并且希望有人在这里可以帮助我确保我将文件分成4个正确的话。

FILE * pFile;
long lSize;
unsigned char * buffer;
size_t result;

  pFile = fopen ( "test.bin" , "rb" );

  if (pFile==NULL) {fprint("error, file null")}

  fseek (pFile , 0 , SEEK_END);
  lSize = ftell (pFile);
  rewind (pFile);

  // allocate memory to contain the whole file:
  buffer = (unsigned char*) malloc (sizeof(unsigned char)*lSize);
  if (buffer == NULL) {fputs ("Memory error",stderr); exit (2);}

  // copy the file into the buffer:
  result = fread (buffer, 4,lSize,pFile); //The error is here, if I use 1 instead of 4 there is no error output but I am not sure this would properly break the file into 4 words read at a time.
  if (result != lSize) {fputs ("Reading error",stderr); exit (3);}
   printf("%ld\n",lSize);

现在,当我运行此操作时,我收到一个错误,除非我更改了我评论回的行中的数字。

1 个答案:

答案 0 :(得分:2)

将二进制文件表示为缓冲区是您的操作系统可以为您做的事情; mmap的手册页在C89中有一个工作示例(所以它是古董):

       fd = open(argv[1], O_RDONLY);

...

       if (fstat(fd, &sb) == -1)           /* To obtain file size */
           handle_error("fstat");

       offset = atoi(argv[2]);
       pa_offset = offset & ~(sysconf(_SC_PAGE_SIZE) - 1);
           /* offset for mmap() must be page aligned */

...

       if (argc == 4) {
           length = atoi(argv[3]);
           if (offset + length > sb.st_size)
               length = sb.st_size - offset;
                   /* Can't display bytes past end of file */

       } else {    /* No length arg ==> display to end of file */
           length = sb.st_size - offset;
       }

       addr = mmap(NULL, length + offset - pa_offset, PROT_READ,
                   MAP_PRIVATE, fd, pa_offset);
       if (addr == MAP_FAILED)
           handle_error("mmap");

现在,addr指向包含进程'地址空间中的输入文件的内存区域。

这将节省您在开始处理之前读取整个文件,因为您的操作系统可以自动只读取您实际访问的文件部分,而无需进一步操作。

另外,既然你正在写一个虚拟机(对你来说意味着什么!)你应该知道典型的进程内存结构,所以学习mmap做的是一个很好的练习。