How can I extract audio data from an mp3 file?

I need to create a metadata-independent hash of the mp3 file (i.e. the same hash can be computed after retag). How can I extract audio data only into memory, without actually starting through the decompressor?

MAD seems like a good starting point - http://www.underbit.com/products/mad/ , but does not seem to explicitly demonstrate a function for this.

Any pointers appreciated!

+3
source share
6 answers

How can I extract audio data only into memory, without actually starting through the decompressor?

You cannot extract audio data without unpacking it - it is compressed! However, if you just need a raw compressed stream, read on!

mp3 :
[ ]
[ ]
[ XING/LAME [ ]]
[mp3 ]
[ ]

, : mp3 id3 . , mp3 , APE, .

: MP3 , , , . foobar2000 .

XING/LAME: mp3, . madplay , , . XING/LAME , . , , , .

MP3: , "". , 0xFFE.

. , . id3v1, APE, .

, , . , unsynchronization, 0xFFE.

, , , , . , / !

+6

ffmpeg . , , API ( ). , .

ffmpeg , . ffmpeg , libffmpeg (libavformat, libavcodec) ++/c, , , cmdline ffmpeg, stdout md5sum - ( unix, ).

"-acodec copy" , ffmpeg , . , .

+3

? PCM? MP3-? , MP3, .wav? .mp3, .wav-.

ID3v1 - 128 . ID3v2 - MP3, ( 4 , 7 , 28- ). .wav - , .wav .

+2

( mp3 , ID3). ffmpeg, mp3 ID3, md5.

. https://github.com/pepaslabs/mp3md5sum

+1

Only ffmpeg can calculate the MD5 hash of the audio segment of the audio file, i.e. without metadata.

Using:

ffmpeg -v -i $file -acodec copy -f md5 -

Note that FLAC already has an MD5 hash stored in metadata.

+1
source

I wrote this small fragment of a small fragment for a Linux box with an old mp3 player that could not handle tags. All that remains is the mp3 headers and data (on stdout encoded). You can use this for your md5.

#include <fcntl.h>
#define DUMPTAGS
int main(int argc, char **argv){
   unsigned char buf[4096];
   int len,fd = open(argv[1],O_RDONLY);
   while (len=read(fd,buf,10)){ // handle ID3v2 tags (maybe multiple)
      if (buf[0]=='I' && buf[1]=='D' && buf[2]=='3'){
         len=read(fd,buf,buf[9]|(buf[8] << 7)|(buf[7] << 14)|(buf[6] << 21));
#ifdef DUMPTAGS
         write(2,buf,len);
#endif
      } else break;
   }
   while (write(1,buf,len)){
      unsigned char tag[3] = {'T','A','G'}, *end;
      len=read(fd,buf,4096);
      end=(unsigned char *)memmem(buf,len,&tag,3);
      if (end){ //handle ID3v1 tag (should only be 1)
         write(1,buf,end-buf);
#ifdef DUMPTAGS
         write(2,end,len-(end-buf));
#endif
         break;
      }
   }
}
0
source

Source: https://habr.com/ru/post/1792248/


All Articles