music_mad.c
author Ozkan Sezer <sezeroz@gmail.com>
Sun, 07 Oct 2018 11:47:50 +0300
branchSDL-1.2
changeset 890 ae9b46ccd5ab
parent 868 989790afc9d9
child 930 1f6c6389391a
permissions -rw-r--r--
music_mad.c: handle and skip tags (bug #4295).
     1 /*
     2   SDL_mixer:  An audio mixer library based on the SDL library
     3   Copyright (C) 1997-2012 Sam Lantinga <slouken@libsdl.org>
     4 
     5   This software is provided 'as-is', without any express or implied
     6   warranty.  In no event will the authors be held liable for any damages
     7   arising from the use of this software.
     8 
     9   Permission is granted to anyone to use this software for any purpose,
    10   including commercial applications, and to alter it and redistribute it
    11   freely, subject to the following restrictions:
    12 
    13   1. The origin of this software must not be misrepresented; you must not
    14      claim that you wrote the original software. If you use this software
    15      in a product, an acknowledgment in the product documentation would be
    16      appreciated but is not required.
    17   2. Altered source versions must be plainly marked as such, and must not be
    18      misrepresented as being the original software.
    19   3. This notice may not be removed or altered from any source distribution.
    20 */
    21 
    22 #ifdef MP3_MAD_MUSIC
    23 
    24 #include <string.h>
    25 
    26 #include "music_mad.h"
    27 
    28 mad_data *
    29 mad_openFileRW(SDL_RWops *rw, SDL_AudioSpec *mixer, int freerw)
    30 {
    31   mad_data *mp3_mad;
    32 
    33   mp3_mad = (mad_data *)SDL_malloc(sizeof(mad_data));
    34   if (mp3_mad) {
    35 	mp3_mad->rw = rw;
    36 	mp3_mad->freerw = freerw;
    37 	mad_stream_init(&mp3_mad->stream);
    38 	mad_frame_init(&mp3_mad->frame);
    39 	mad_synth_init(&mp3_mad->synth);
    40 	mp3_mad->frames_read = 0;
    41 	mad_timer_reset(&mp3_mad->next_frame_start);
    42 	mp3_mad->volume = MIX_MAX_VOLUME;
    43 	mp3_mad->status = 0;
    44 	mp3_mad->output_begin = 0;
    45 	mp3_mad->output_end = 0;
    46 	mp3_mad->mixer = *mixer;
    47   }
    48   return mp3_mad;
    49 }
    50 
    51 void
    52 mad_closeFile(mad_data *mp3_mad)
    53 {
    54   mad_stream_finish(&mp3_mad->stream);
    55   mad_frame_finish(&mp3_mad->frame);
    56   mad_synth_finish(&mp3_mad->synth);
    57 
    58   if (mp3_mad->freerw) {
    59 	SDL_RWclose(mp3_mad->rw);
    60   }
    61   SDL_free(mp3_mad);
    62 }
    63 
    64 /* Starts the playback. */
    65 void
    66 mad_start(mad_data *mp3_mad) {
    67   mp3_mad->status |= MS_playing;
    68 }
    69 
    70 /* Stops the playback. */
    71 void 
    72 mad_stop(mad_data *mp3_mad) {
    73   mp3_mad->status &= ~MS_playing;
    74 }
    75 
    76 /* Returns true if the playing is engaged, false otherwise. */
    77 int
    78 mad_isPlaying(mad_data *mp3_mad) {
    79   return ((mp3_mad->status & MS_playing) != 0);
    80 }
    81 
    82 
    83 /*************************** TAG HANDLING: ******************************/
    84 
    85 static __inline__ SDL_bool is_id3v1(const Uint8 *data, size_t length)
    86 {
    87     /* http://id3.org/ID3v1 :  3 bytes "TAG" identifier and 125 bytes tag data */
    88     if (length < 3 || SDL_memcmp(data,"TAG",3) != 0) {
    89         return SDL_FALSE;
    90     }
    91     return SDL_TRUE;
    92 }
    93 static __inline__ SDL_bool is_id3v2(const Uint8 *data, size_t length)
    94 {
    95     /* ID3v2 header is 10 bytes:  http://id3.org/id3v2.4.0-structure */
    96     /* bytes 0-2: "ID3" identifier */
    97     if (length < 10 || SDL_memcmp(data,"ID3",3) != 0) {
    98         return SDL_FALSE;
    99     }
   100     /* bytes 3-4: version num (major,revision), each byte always less than 0xff. */
   101     if (data[3] == 0xff || data[4] == 0xff) {
   102         return SDL_FALSE;
   103     }
   104     /* bytes 6-9 are the ID3v2 tag size: a 32 bit 'synchsafe' integer, i.e. the
   105      * highest bit 7 in each byte zeroed.  i.e.: 7 bit information in each byte ->
   106      * effectively a 28 bit value.  */
   107     if (data[6] >= 0x80 || data[7] >= 0x80 || data[8] >= 0x80 || data[9] >= 0x80) {
   108         return SDL_FALSE;
   109     }
   110     return SDL_TRUE;
   111 }
   112 static __inline__ SDL_bool is_apetag(const Uint8 *data, size_t length)
   113 {
   114    /* http://wiki.hydrogenaud.io/index.php?title=APEv2_specification
   115     * APEv2 header is 32 bytes: bytes 0-7 ident, bytes 8-11 version,
   116     * bytes 12-17 size.  bytes 24-31 are reserved: must be all zeroes.
   117     * APEv1 has no header, so no luck.  */
   118     Uint32 v;
   119 
   120     if (length < 32 || SDL_memcmp(data,"APETAGEX",8) != 0) {
   121         return SDL_FALSE;
   122     }
   123     v = (data[11]<<24) | (data[10]<<16) | (data[9]<<8) | data[8]; /* version */
   124     if (v != 2000U) {
   125         return SDL_FALSE;
   126     }
   127     v = 0; /* reserved bits : */
   128     if (SDL_memcmp(&data[24],&v,4) != 0 || SDL_memcmp(&data[28],&v,4) != 0) {
   129         return SDL_FALSE;
   130     }
   131     return SDL_TRUE;
   132 }
   133 
   134 static size_t get_tagsize(const Uint8 *data, size_t length)
   135 {
   136     size_t size;
   137 
   138     if (is_id3v1(data, length)) {
   139         return 128; /* fixed length */
   140     }
   141     if (is_id3v2(data, length)) {
   142         /* size is a 'synchsafe' integer (see above) */
   143         size = (data[6]<<21) + (data[7]<<14) + (data[8]<<7) + data[9];
   144         size += 10; /* header size */
   145         /* ID3v2 header[5] is flags (bits 4-7 only, 0-3 are zero).
   146          * bit 4 set: footer is present (a copy of the header but
   147          * with "3DI" as ident.)  */
   148         if (data[5] & 0x10) {
   149             size += 10; /* footer size */
   150         }
   151         /* optional padding (always zeroes) */
   152         while (size < length && data[size] == 0) {
   153             ++size;
   154         }
   155         return size;
   156     }
   157     if (is_apetag(data, length)) {
   158         size = (data[15]<<24) | (data[14]<<16) | (data[13]<<8) | data[12];
   159         size += 32; /* header size */
   160         return size;
   161     }
   162     return 0;
   163 }
   164 
   165 static int consume_tag(struct mad_stream *stream)
   166 {
   167     /* FIXME: what if the buffer doesn't have the full tag ??? */
   168     size_t remaining = stream->bufend - stream->next_frame;
   169     size_t tagsize = get_tagsize(stream->this_frame, remaining);
   170     if (tagsize != 0) {
   171         mad_stream_skip(stream, tagsize);
   172         return 0;
   173     }
   174     return -1;
   175 }
   176 
   177 /* Reads the next frame from the file.  Returns true on success or
   178    false on failure. */
   179 static int
   180 read_next_frame(mad_data *mp3_mad) {
   181   if (mp3_mad->stream.buffer == NULL || 
   182 	  mp3_mad->stream.error == MAD_ERROR_BUFLEN) {
   183 	size_t read_size;
   184 	size_t remaining;
   185 	unsigned char *read_start;
   186 	
   187 	/* There might be some bytes in the buffer left over from last
   188 	   time.  If so, move them down and read more bytes following
   189 	   them. */
   190 	if (mp3_mad->stream.next_frame != NULL) {
   191 	  remaining = mp3_mad->stream.bufend - mp3_mad->stream.next_frame;
   192 	  memmove(mp3_mad->input_buffer, mp3_mad->stream.next_frame, remaining);
   193 	  read_start = mp3_mad->input_buffer + remaining;
   194 	  read_size = MAD_INPUT_BUFFER_SIZE - remaining;
   195 	  
   196 	} else {
   197 	  read_size = MAD_INPUT_BUFFER_SIZE;
   198 	  read_start = mp3_mad->input_buffer;
   199 	  remaining = 0;
   200 	}
   201 
   202 	/* Now read additional bytes from the input file. */
   203 	read_size = SDL_RWread(mp3_mad->rw, read_start, 1, read_size);
   204 	
   205 	if (read_size <= 0) {
   206 	  if ((mp3_mad->status & (MS_input_eof | MS_input_error)) == 0) {
   207 		if (read_size == 0) {
   208 		  mp3_mad->status |= MS_input_eof;
   209 		} else {
   210 		  mp3_mad->status |= MS_input_error;
   211 		}
   212 		
   213 		/* At the end of the file, we must stuff MAD_BUFFER_GUARD
   214 		   number of 0 bytes. */
   215 		memset(read_start + read_size, 0, MAD_BUFFER_GUARD);
   216 		read_size += MAD_BUFFER_GUARD;
   217 	  }
   218 	}
   219 	
   220 	/* Now feed those bytes into the libmad stream. */
   221 	mad_stream_buffer(&mp3_mad->stream, mp3_mad->input_buffer,
   222 					  read_size + remaining);
   223 	mp3_mad->stream.error = MAD_ERROR_NONE;
   224   }
   225   
   226   /* Now ask libmad to extract a frame from the data we just put in
   227 	 its buffer. */
   228   if (mad_frame_decode(&mp3_mad->frame, &mp3_mad->stream)) {
   229 	if (MAD_RECOVERABLE(mp3_mad->stream.error)) {
   230 	  consume_tag(&mp3_mad->stream); /* consume any ID3 tags */
   231 	  mad_stream_sync(&mp3_mad->stream); /* to frame seek mode */
   232 	  return 0;
   233 	  
   234 	} else if (mp3_mad->stream.error == MAD_ERROR_BUFLEN) {
   235 	  return 0;
   236 	  
   237 	} else {
   238 	  mp3_mad->status |= MS_decode_error;
   239 	  return 0;
   240 	}
   241   }
   242   
   243   mp3_mad->frames_read++;
   244   mad_timer_add(&mp3_mad->next_frame_start, mp3_mad->frame.header.duration);
   245 
   246   return 1;
   247 }
   248 
   249 /* Scale a MAD sample to 16 bits for output. */
   250 static signed int
   251 scale(mad_fixed_t sample) {
   252   /* round */
   253   sample += (1L << (MAD_F_FRACBITS - 16));
   254 
   255   /* clip */
   256   if (sample >= MAD_F_ONE)
   257     sample = MAD_F_ONE - 1;
   258   else if (sample < -MAD_F_ONE)
   259     sample = -MAD_F_ONE;
   260 
   261   /* quantize */
   262   return sample >> (MAD_F_FRACBITS + 1 - 16);
   263 }
   264 
   265 /* Once the frame has been read, copies its samples into the output
   266    buffer. */
   267 static void
   268 decode_frame(mad_data *mp3_mad) {
   269   struct mad_pcm *pcm;
   270   unsigned int nchannels, nsamples;
   271   mad_fixed_t const *left_ch, *right_ch;
   272   unsigned char *out;
   273   int ret;
   274 
   275   mad_synth_frame(&mp3_mad->synth, &mp3_mad->frame);
   276   pcm = &mp3_mad->synth.pcm;
   277   out = mp3_mad->output_buffer + mp3_mad->output_end;
   278 
   279   if ((mp3_mad->status & MS_cvt_decoded) == 0) {
   280 	mp3_mad->status |= MS_cvt_decoded;
   281 
   282 	/* The first frame determines some key properties of the stream.
   283 	   In particular, it tells us enough to set up the convert
   284 	   structure now. */
   285 	SDL_BuildAudioCVT(&mp3_mad->cvt, AUDIO_S16, pcm->channels, mp3_mad->frame.header.samplerate, mp3_mad->mixer.format, mp3_mad->mixer.channels, mp3_mad->mixer.freq);
   286   }
   287 
   288   /* pcm->samplerate contains the sampling frequency */
   289 
   290   nchannels = pcm->channels;
   291   nsamples  = pcm->length;
   292   left_ch   = pcm->samples[0];
   293   right_ch  = pcm->samples[1];
   294 
   295   while (nsamples--) {
   296     signed int sample;
   297 
   298     /* output sample(s) in 16-bit signed little-endian PCM */
   299 
   300     sample = scale(*left_ch++);
   301     *out++ = ((sample >> 0) & 0xff);
   302     *out++ = ((sample >> 8) & 0xff);
   303 
   304     if (nchannels == 2) {
   305       sample = scale(*right_ch++);
   306       *out++ = ((sample >> 0) & 0xff);
   307       *out++ = ((sample >> 8) & 0xff);
   308     }
   309   }
   310 
   311   mp3_mad->output_end = out - mp3_mad->output_buffer;
   312   /*assert(mp3_mad->output_end <= MAD_OUTPUT_BUFFER_SIZE);*/
   313 }
   314 
   315 int
   316 mad_getSamples(mad_data *mp3_mad, Uint8 *stream, int len) {
   317   int bytes_remaining;
   318   int num_bytes;
   319   Uint8 *out;
   320 
   321   if ((mp3_mad->status & MS_playing) == 0) {
   322 	/* We're not supposed to be playing, so send silence instead. */
   323 	memset(stream, 0, len);
   324 	return 0;
   325   }
   326 
   327   out = stream;
   328   bytes_remaining = len;
   329   while (bytes_remaining > 0) {
   330 	if (mp3_mad->output_end == mp3_mad->output_begin) {
   331 	  /* We need to get a new frame. */
   332 	  mp3_mad->output_begin = 0;
   333 	  mp3_mad->output_end = 0;
   334 	  if (!read_next_frame(mp3_mad)) {
   335 		if ((mp3_mad->status & MS_error_flags) != 0) {
   336 		  /* Couldn't read a frame; either an error condition or
   337 			 end-of-file.  Stop. */
   338 		  memset(out, 0, bytes_remaining);
   339 		  mp3_mad->status &= ~MS_playing;
   340 		  return bytes_remaining;
   341 		}
   342 	  } else {
   343 		decode_frame(mp3_mad);
   344 
   345 		/* Now convert the frame data to the appropriate format for
   346 		   output. */
   347 		mp3_mad->cvt.buf = mp3_mad->output_buffer;
   348 		mp3_mad->cvt.len = mp3_mad->output_end;
   349 		
   350 		mp3_mad->output_end = (int)(mp3_mad->output_end * mp3_mad->cvt.len_ratio);
   351 		/*assert(mp3_mad->output_end <= MAD_OUTPUT_BUFFER_SIZE);*/
   352 		SDL_ConvertAudio(&mp3_mad->cvt);
   353 	  }
   354 	}
   355 
   356 	num_bytes = mp3_mad->output_end - mp3_mad->output_begin;
   357 	if (bytes_remaining < num_bytes) {
   358 	  num_bytes = bytes_remaining;
   359 	}
   360 
   361 	if (mp3_mad->volume == MIX_MAX_VOLUME) {
   362 	  memcpy(out, mp3_mad->output_buffer + mp3_mad->output_begin, num_bytes);
   363 	} else {
   364 	  SDL_MixAudio(out, mp3_mad->output_buffer + mp3_mad->output_begin,
   365 				   num_bytes, mp3_mad->volume);
   366 	}
   367 	out += num_bytes;
   368 	mp3_mad->output_begin += num_bytes;
   369 	bytes_remaining -= num_bytes;
   370   }
   371   return 0;
   372 }
   373 
   374 void
   375 mad_seek(mad_data *mp3_mad, double position) {
   376   mad_timer_t target;
   377   int int_part;
   378 
   379   int_part = (int)position;
   380   mad_timer_set(&target, int_part, 
   381 				(int)((position - int_part) * 1000000), 1000000);
   382 
   383   if (mad_timer_compare(mp3_mad->next_frame_start, target) > 0) {
   384 	/* In order to seek backwards in a VBR file, we have to rewind and
   385 	   start again from the beginning.  This isn't necessary if the
   386 	   file happens to be CBR, of course; in that case we could seek
   387 	   directly to the frame we want.  But I leave that little
   388 	   optimization for the future developer who discovers she really
   389 	   needs it. */
   390 	mp3_mad->frames_read = 0;
   391 	mad_timer_reset(&mp3_mad->next_frame_start);
   392 	mp3_mad->status &= ~MS_error_flags;
   393 	mp3_mad->output_begin = 0;
   394 	mp3_mad->output_end = 0;
   395 
   396 	SDL_RWseek(mp3_mad->rw, 0, RW_SEEK_SET);
   397   }
   398 
   399   /* Now we have to skip frames until we come to the right one.
   400 	 Again, only truly necessary if the file is VBR. */
   401   while (mad_timer_compare(mp3_mad->next_frame_start, target) < 0) {
   402 	if (!read_next_frame(mp3_mad)) {
   403 	  if ((mp3_mad->status & MS_error_flags) != 0) {
   404 		/* Couldn't read a frame; either an error condition or
   405 		   end-of-file.  Stop. */
   406 		mp3_mad->status &= ~MS_playing;
   407 		return;
   408 	  }
   409 	}
   410   }
   411 
   412   /* Here we are, at the beginning of the frame that contains the
   413 	 target time.  Ehh, I say that's close enough.  If we wanted to,
   414 	 we could get more precise by decoding the frame now and counting
   415 	 the appropriate number of samples out of it. */
   416 }
   417 
   418 void
   419 mad_setVolume(mad_data *mp3_mad, int volume) {
   420   mp3_mad->volume = volume;
   421 }
   422 
   423 
   424 #endif  /* MP3_MAD_MUSIC */