개요
FFmpeg 명령어를 사용하여 특정 파일이 WAV 오디오 파일인지 확인할 수 있습니다:
./ffmpeg -i XXX.wav
내부적으로 FFmpeg는 wav_probe 함수를 통해 파일의 형식을 판별합니다. 컨테이너 형식 탐지를 담당하는 av_probe_input_format3 함수는 등록된 모든 AVInputFormat 구조체를 순회하면서 각각의 read_probe 함수를 호출하여 해당 형식과 얼마나 일치하는지 점수를 계산합니다. WAV 파일에 대응되는 이 함수가 바로 wav_probe입니다.
wav_probe 함수 정의
wav_probe 함수는 FFmpeg 소스코드(version 5.0.3)의 libavformat/wavdec.c 파일에 다음과 같이 정의되어 있습니다:
static int wav_probe(const AVProbeData *p)
{
if (p->buf_size <= 32)
return 0;
if (!memcmp(p->buf + 8, "WAVE", 4)) {
if (!memcmp(p->buf, "RIFF", 4) || !memcmp(p->buf, "RIFX", 4))
return AVPROBE_SCORE_MAX - 1;
else if ((!memcmp(p->buf, "RF64", 4) ||
!memcmp(p->buf, "BW64", 4)) &&
!memcmp(p->buf + 12, "ds64", 4))
return AVPROBE_SCORE_MAX;
}
return 0;
}
- 매개변수
p:AVProbeData구조체 포인터로, 파일 탐색에 필요한 정보를 담고 있습니다. - 반환값: 정수형 점수. 0은 완전히 불일치, 양수는 일정 수준 이상 일치함을 의미하며 최대값은
AVPROBE_SCORE_MAX(=100)입니다.
AVProbeData 구조체는 아래와 같습니다:
typedef struct AVProbeData {
const char *filename;
unsigned char *buf;
int buf_size;
const char *mime_type;
} AVProbeData;
filename: 탐색 대상 파일 경로buf: 파일 앞부분 일부 바이트를 읽어 저장한 버퍼buf_size: 버퍼 크기(보통 2048바이트)mime_type: MIME 타입(일반적으로 NULL)
구현 원리
먼저 최소한의 헤더 길이(32바이트)보다 짧으면 WAV 형식이 아님을 판단하고 0을 반환합니다:
if (p->buf_size <= 32)
return 0;
다음으로 WAV 파일 고유의 시그니처를 검사합니다:
- 오프셋 8~11바이트: "WAVE"
- 오프셋 0~3바이트: "RIFF" 또는 "RIFX"
위 조건을 만족하면 AVPROBE_SCORE_MAX - 1(즉, 99점)을 반환합니다:
if (!memcmp(p->buf + 8, "WAVE", 4)) {
if (!memcmp(p->buf, "RIFF", 4) || !memcmp(p->buf, "RIFX", 4))
return AVPROBE_SCORE_MAX - 1;
이때 완전한 100점을 주지 않는 이유는 ACT 형식도 동일한 WAV 헤더를 포함할 수 있어 충돌을 방지하기 위함입니다.
추가적으로 Wave64 확장 형식(RF64/BW64)도 지원됩니다:
else if ((!memcmp(p->buf, "RF64", 4) ||
!memcmp(p->buf, "BW64", 4)) &&
!memcmp(p->buf + 12, "ds64", 4))
return AVPROBE_SCORE_MAX;
이 경우는 완전히 유효한 WAV 형식으로 간주되어 최고 점수인 100점을 부여받습니다.