2015년 10월 24일 토요일

오디오 드라이버 개발에 필요한 오디오 포맷 기본

다양한 오디오 포맷이 존재하지만 오디오 드라이버를 작성할 경우에는 wav와 pcm 포맷만 이해하면 별다른 문제가 없다. 다른 오디오 포맷은 오디오 코덱 담당자 혹은 멀티미디어 담당자들에게 맡기자.

먼저 wav포맷은 압축하지 않은 오디오를 저장하는 포맷으로 대부분의 OS에서 제공하는 기본  Player로 손쉽게 재생이 가능하기 때문에 많이 사용된다. 오디오 데이터는 sampling rate, bit size, endian, channels 등에 따라 데이터가 저장되는 순서가 바뀌므로 wav파일은 헤더에 이러한 정보를 저장하게 된다.  각각에 대한 상세 정보는 아래 사이트에서 확인 가능하다. (http://www.topherlee.com/software/pcm-tut-wavformat.html)

wav파일은 RIFF라는 오디오 포맷 스펙을 구현것으로 wav포맷은 RIFF포맷과 동일한 포맷이라고 생각하면 된다. RIFF와 유사한 포맷으로 RIFX 포맷이 있는데, RIFX 포맷과 RIFF포맷은 서로 data의 byte order 즉, endian이 다르다. RIFF 포맷은 little endian으로 저장되고, RIFX포맷은 big endian으로 저장된다.

pcm audio file은 header가 없이 raw audio data만 저장한 파일이다.   따라서 pcm포맷으로 저장된 오디오는 별도로 오디오에 대한 정보를 가지고 있지 않으면 제대로 play할 수 없다. 오디오 드라이버에서 오디오 데이터를 캡춰하였다면, 당연히 header가 없는 pcm 포맷이며 이때 오디오 드라이버가 어떤 상태(sampling rate, bit size, endian, channels)로 동작중이었는지에 따라 pcm 포맷을 해석해야 한다.  만일 데이터가 little endian이라면 RIFF포맷이므로 wav header만 붙여주면 wav player에서 play가 가능해 진다. 데이터가 big endian이라면 RIFX 포맷이므로, wav header를 붙여 주고 play하면 이상한 노이즈가 play 될 것이다. 따라서 데이터가 big endian이라면 header 추가 뿐만 아니라 오디오 데이터에 대한 endian 변환까지 해주어야 한다.

sox라는 프로그램을 사용하면 간편하게 이러한 변환을 간단하게 수행할 수 있다. (http://sox.sourceforge.net)

아래는 header가 없는 RIFX 포맷의 48kHz/16bit/2 channel pcm데이터를 wav 파일로 변환하는 명령이다.

sox -traw -esigned -r48k -b16 -c2 --endian big foo.pcm foo.wav

-t : type - file type (raw | wav | ... ) 
-e : encoding (signed | unsigned)
-r : rate - sampling rate of audio (8k | 44.1k | 48k | ... )
-b: bits - encoded sample size in bits ( 8 | 16 | ... )


-c: channel (1 | 2 |... )
--endian : Encoded byte-order (little | big)