首页 > 解决方案 > 读取二进制文件并将其存储到 c 中的 struct

问题描述

我正在尝试创建一个存储 wav 文件元数据的软件。

这是一个MWE:


#include <stdio.h>
#include <string.h>
#include <stdint.h>
#include <stdlib.h>

FILE   *  READ_WAV_FILE;

struct WAV_FILE_HEADER{
   char      ChunkID[4];     // RIFF
   uint32_t  ChunkSize;
   char      Format[4];      // WAVE
   char      Subchunk1ID[4]; // fmt
   uint32_t  Subchunk1Size;
   uint16_t  AudioFormat;
   uint16_t  NumChannels;
   uint32_t  SampleRate;
   uint32_t  ByteRate;
   uint16_t  BlockAlign;
   uint16_t  BitsPerSample;
};

struct WAV_FILE_HEADER WAV_FILE_0;

void print_wav_struct(){
   printf("ChunkID:      %s\n", WAV_FILE_0.ChunkID);
   printf("ChunkSize     %u\n", WAV_FILE_0.ChunkSize);
   printf("Format        %s\n", WAV_FILE_0.Format);
   printf("Subchunk1ID   %s\n", WAV_FILE_0.Subchunk1ID);
   printf("Subchunk1Size %u\n", WAV_FILE_0.Subchunk1Size);
   printf("AudioFormat   %hu\n", WAV_FILE_0.AudioFormat);
   printf("NumChannels   %hu\n", WAV_FILE_0.NumChannels);
   printf("SampleRate    %u\n", WAV_FILE_0.SampleRate);
   printf("ByteRate      %u\n", WAV_FILE_0.ByteRate);
   printf("BlockAlign    %hu\n", WAV_FILE_0.BlockAlign);
   printf("BitsPerSample %hu\n", WAV_FILE_0.BitsPerSample);

}

int read_wavfile(){

   READ_WAV_FILE = fopen("read.wav", "rb");
   fseek(READ_WAV_FILE,0,SEEK_SET);
   fread(&WAV_FILE_0,sizeof(WAV_FILE_0),1,READ_WAV_FILE);
   fclose(READ_WAV_FILE);
   return 0;
}
int main(){

   if (read_wavfile()){
      printf("Something went wrong\n");
      return -1;
   }
   print_wav_struct();
   return 0;

}

这里的问题是“ChunkID”、“Format”和“Subchunk1ID”的输出:

ChunkID:      RIFFF
ChunkSize     48824390
Format        WAVEfmt
Subchunk1ID   fmt
Subchunk1Size 16
AudioFormat   1
NumChannels   2
SampleRate    48000
ByteRate      192000
BlockAlign    4
BitsPerSample 16

在这个问题中,只有那些字符串会受到影响。整数不是。

“ChunkID”应该只有“RIFF”,“格式”应该只有“WAVE”,“Subchunk1ID”应该是“fmt”。

我在阅读文件时出了什么问题?

PS 对不起,荒谬的长代码,但这是我发现这是最小的唯一方法。

标签: cstructwav

解决方案


经过三个小时的研究,我终于得出结论,问题在于它缺少一个NUL终结器。使用带有非空终止字符串的 printf

这解决了我的问题:

...
printf("ChunkID:    %.*s\n",4,WAV_HEADER.ChunkID);
printf("ChunkSize:  %u\n",WAV_HEADER.ChunkSize);
printf("Format:     %.*s\n",4,WAV_HEADER.Format);
...

推荐阅读