【问题标题】:Reaching EOF before end of file on windows在 Windows 上的文件结束之前到达 EOF
【发布时间】:2021-05-11 20:10:36
【问题描述】:
#include <stdio.h>
#include <stdlib.h>

const int size = 512;
int main(int argc, char *argv[])
{
    if (argc != 2)
    {
        fprintf(stderr, "Usage: ./recover image\n");
        return 1;
    }

    FILE *file = fopen(argv[1], "r");
    if (file == NULL)
    {
        fprintf(stderr, "Could not open file\n");
        return 1;
    }
    unsigned char buffer[size];
    int count = 0;
    FILE *jpeg = NULL;

    while(fread(buffer, size, 1, file))
    {
        if (buffer[0] == 0xff && buffer[1] == 0xd8 && buffer[2] == 0xff && (buffer[3] & 0xf0) == 0xe0)
        {
            char image[7];
            if (count != 0)
            {
                fclose(jpeg);
            }
            sprintf(image, "%03i.jpg", count);
            jpeg = fopen(image, "w");
            if (jpeg == NULL)
            {
                fprintf(stderr, "couldn't open file\n");
                return 1;
            }
            count++;
        }
        if (count != 0)
        {
            fwrite(&buffer, size, 1, jpeg);
        }
    }
    fclose(file);

}

此代码在 card.raw 中查找 jpeg 当我在 linux 上运行上述代码时,它运行正常。但在 windows 代码上只读取前三个 512 字节的 card.raw 文件块。 我做错了什么? 我也在linux上使用clang。在 Windows 上我使用 gcc。

【问题讨论】:

  • fopen(argv[1], "r") -> fopen(argv[1], "rb")
  • 我已经试过了,但还是同样的问题。
  • 不确定是否重要,但fread(buffer, size, 1, file) 不应该是fread(buffer, 1, size, file)
  • 还是同样的问题
  • char image[7]; sprintf(image, "%03i.jpg", count); 糟糕,访问范围外!

标签: c file-io jpeg eof fat32


【解决方案1】:

首先,二进制文件应该以二进制模式打开。这意味着对于fopen() 模式,您应该使用"rb""wb" 而不是"r""w"。否则,换行符可能会被意外转换,并且可能会在字节 0x1a 处停止。

其次,对数组 char image[7]; 执行 sprintf(image, "%03i.jpg", count); 是不好的。 sprintf() 的结果将是(至少)7 个字符,因此需要具有 8 个或更多元素的数组来存储包含终止空字符的字符串。为了安全起见,您应该使用snprintf(),它接受缓冲区大小。

【讨论】:

  • 我是新手,所以我从 2 天开始就一直在努力解决这个问题。
猜你喜欢
  • 1970-01-01
  • 2017-10-21
  • 2015-07-17
  • 1970-01-01
  • 2013-02-08
  • 1970-01-01
  • 1970-01-01
  • 2021-03-12
  • 1970-01-01
相关资源
最近更新 更多