fread 的无限循环

Infinite loop with fread

我正在尝试分配一个 64 字节大小的数组,然后遍历数组索引以从输入文件中读取每个字节。但是当我不 malloc() 数组索引时,循环停留在 index0 中(因此每次循环时,它都会用下一个字节替换 index0 中的内容,而不是将每个字节放在下一个数组索引中并保持它们都是按时间顺序排列的)。

当我使用 malloc() 时,它正确地使用了数组索引,但它是一个无限循环并使用了 ram 的演出。

这是我的代码:

struct BitIO {
      FILE        *FilePointer;
      uint8_t      *Buffer[64];
      uint64_t   BitsAvailable;
      uint64_t BitsUnavailable;
} BitIO;


void Init_BitIO(const char *FileName, const char *Mode) {
     BitIO.FilePointer = fopen(FileName, Mode);
     malloc(sizeof(BitIO));
     while (!feof(BitIO.FilePointer)) {
         size_t BytesRead = 0;
         for (int i = 0; i < 64; i++) {
             BitIO.Buffer[i] = (uint8_t*)malloc(1);
             BytesRead = fread(BitIO.Buffer[i], 1, 1, BitIO.FilePointer);
        }
    }
}
  • 点 1

    您需要将 malloc() 的 return 值收集到某个变量中(并在使用 returned 指针之前检查 malloc() 是否成功)以使用分配的内存。然后,看到您的用法,我相信您对 struct 成员变量类型感到困惑。根据您的使用情况,您不需要 uint8_t *Buffer[64]; 作为结构成员。

    1.1. 如果要使用动态内存,那么,将结构体成员改成

    uint8_t *Buffer;
    

    并在 for 循环中执行

    BitIO.Buffer[i] = malloc(sizeof(uint8_t));   //allocate memory
    BytesRead = fread(BitIO.Buffer[i], 1, 1,BitIO.FilePointer);
    

    或者,更好的是,当您循环固定次数时,您可以获得在 for 循环之外一次性分配的内存

    BitIO.Buffer = malloc( 64 * sizeof(uint8_t));
    

    然后循环一次读取一个元素。

    1.2. 否则,将结构体成员改成

    uint8_t Buffer[64];
    

    并完全摆脱 malloc()

  • 第 2 点:

    阅读Why is “while ( !feof (file) )” always wrong?

  • 第 3 点:

    see why not to castmalloc()和家人C的return值。

如果您"trying to allocate an array 64 bytes in size",可以考虑

uint8_t      Buffer[64];

而不是

uint8_t      *Buffer[64];

(后者是64个指针到byte的数组)

执行此操作后,您将不需要 malloc,因为内部具有 64 字节数组的结构是静态分配的。 'main' 循环看起来像

for (int i = 0; i < 64; i++) {
     BytesRead += fread(&BitIO.Buffer[i], 1, 1,BitIO.FilePointer);
}

但是,当然,我会建议更有效的形式:

BytesRead = fread(BitIO.Buffer, 1, 64, BitIO.FilePointer);