1 /**********************************************************
2  * libmp3splt -- library based on mp3splt,
3  *               for mp3/ogg splitting without decoding
4  *
5  * Copyright (c) 2002-2005 M. Trotta - <mtrotta@users.sourceforge.net>
6  * Copyright (c) 2005-2014 Alexandru Munteanu - m@ioalex.net
7  *
8  * Bit reservoir fix heavily inspired from pcutmp3.
9  * It worth reminding that:
10  *    pcutmp3 was created by Sebastian Gesemann
11  *    pcutmp3 source code is here
12  *       http://wiki.themixingbowl.org/Pcutmp3
13  *    pcutmp3 is licensed as BSD
14  *       quoting the author from source: http://www.hydrogenaudio.org/forums/index.php?showtopic=35654&pid=569128&mode=threaded&start=100#entry569128
15  *          "Let's say BSD. :)"
16  *    See below for the pcutmp3 license
17  *
18  *********************************************************/
19 
20 /**********************************************************
21  * This program is free software; you can redistribute it and/or
22  * modify it under the terms of the GNU General Public License
23  * as published by the Free Software Foundation; either version 2
24  * of the License, or (at your option) any later version.
25  *
26  * This program is distributed in the hope that it will be useful,
27  * but WITHOUT ANY WARRANTY; without even the implied warranty of
28  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
29  * GNU General Public License for more details.
30  *
31  * You should have received a copy of the GNU General Public License
32  * along with this program; if not, write to the Free Software
33  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
34  * USA.
35  *********************************************************/
36 
37 /**********************************************************
38  * Reminder of the pcutmp3 license:
39  *
40  * Pcutmp3 Copyright (c) 2005, Sebastian Gesemann
41  * All rights reserved.
42  *
43  * Redistribution and use in source and binary forms, with or without modification, are permitted
44  * provided that the following conditions are met:
45  *
46  * 1. Redistributions of source code must retain the above copyright notice, this list of conditions
47  * and the following disclaimer.
48  *
49  * 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions
50  * and the following disclaimer in the documentation and/or other materials provided with the
51  * distribution.
52  *
53  * 3. Neither the name of the Sebastian Gesemann nor the names of its contributors may be used to endorse
54  * or promote products derived from this software without specific prior written permission.
55  *
56  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR
57  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
58  * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
59  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
60  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
61  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
62  * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
63  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
64  *********************************************************/
65 
66 #include "mp3_utils.h"
67 
68 //! Initializes a stream frame
splt_mp3_init_stream_frame(splt_mp3_state * mp3state)69 void splt_mp3_init_stream_frame(splt_mp3_state *mp3state)
70 {
71   mad_stream_init(&mp3state->stream);
72   mad_frame_init(&mp3state->frame);
73 }
74 
75 //! Finishes a stream frame
splt_mp3_finish_stream_frame(splt_mp3_state * mp3state)76 void splt_mp3_finish_stream_frame(splt_mp3_state *mp3state)
77 {
78   mad_stream_finish(&mp3state->stream);
79   mad_frame_finish(&mp3state->frame);
80 }
81 
82 /*! does nothing important for libmp3splt
83 
84 \todo review this..
85 */
splt_mp3_checksync(splt_mp3_state * mp3state)86 void splt_mp3_checksync(splt_mp3_state *mp3state)
87 {
88   //char junk[32];
89   //fprintf(stderr, "\nWarning: Too many sync errors! This may not be a mp3 file. Continue? (y/n) ");
90   //fgets(junk, 31, stdin);
91   //if (junk[0]=='y')
92 
93   //we don't use user interactivity in a library
94   //always continue
95   mp3state->syncdetect = 0;
96 
97   //else error("Aborted.",125);
98 }
99 
100 //!calculates bitrate
splt_mp3_c_bitrate(unsigned long head)101 int splt_mp3_c_bitrate(unsigned long head)
102 {
103   if ((head & 0xffe00000) != 0xffe00000) return 0;
104   if (!((head>>17)&3)) return 0;
105   if (((head>>12)&0xf) == 0xf) return 0;
106   if (!((head >> 12) & 0xf)) return 0;
107   if (((head>>10)&0x3) == 0x3 ) return 0;
108   if (((head >> 19) & 1)==1 && ((head>>17)&3)==3 &&
109       ((head>>16)&1)==1) return 0;
110   if ((head & 0xffff0000) == 0xfffe0000) return 0;
111 
112   return ((head>>12)&0xf);
113 }
114 
splt_mp3_makehead(unsigned long headword,struct splt_mp3 mp3f,struct splt_header head,off_t ptr)115 struct splt_header splt_mp3_makehead(unsigned long headword,
116     struct splt_mp3 mp3f, struct splt_header head, off_t ptr)
117 {
118   head.ptr = ptr;
119 
120   int mpeg_index = splt_mp3_get_mpeg_as_int(mp3f.mpgid) != 1;
121   head.bitrate = splt_mp3_tabsel_123[mpeg_index][mp3f.layer-1][splt_mp3_c_bitrate(headword)];
122   head.padding = ((headword >> 9) & 0x1);
123 
124   int is_mpeg1 = mp3f.mpgid == SPLT_MP3_MPEG1_ID;
125 
126   if (mp3f.layer == MAD_LAYER_I)
127     head.framesize = (head.bitrate * 12000 / mp3f.freq + head.padding) * 4;
128   else if (is_mpeg1 || (mp3f.layer != MAD_LAYER_III))
129     head.framesize = head.bitrate * 144000 / mp3f.freq + head.padding;
130   else
131     head.framesize = head.bitrate * 72000 / mp3f.freq + head.padding;
132 
133   head.has_crc = ! ((headword >> 16) & 0x1);
134 
135   if (mp3f.layer == 3)
136   {
137     int is_mono = ((headword >> 6 & 3) == 3); // 3 = mono
138     if (is_mpeg1)
139       head.sideinfo_size = is_mono ? 17 : 32;
140     else
141       head.sideinfo_size = is_mono ? 9 : 17;
142   }
143   else
144   {
145     head.sideinfo_size = 0;
146   }
147 
148   //4 is the header size
149   head.frame_data_space = head.framesize - head.sideinfo_size - 4;
150 
151   return head;
152 }
153 
splt_mp3_store_header(splt_mp3_state * mp3state)154 static void splt_mp3_store_header(splt_mp3_state *mp3state)
155 {
156   struct splt_header *h = &mp3state->br_headers[mp3state->next_br_header_index];
157   h->ptr = mp3state->h.ptr;
158   h->bitrate = mp3state->h.bitrate;
159   h->padding = mp3state->h.padding;
160   h->framesize = mp3state->h.framesize;
161   h->has_crc = mp3state->h.has_crc;
162   h->sideinfo_size = mp3state->h.sideinfo_size;
163   h->main_data_begin = mp3state->h.main_data_begin;
164   h->frame_data_space = mp3state->h.frame_data_space;
165 
166   mp3state->next_br_header_index++;
167 
168   if (mp3state->number_of_br_headers_stored < SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS)
169   {
170     mp3state->number_of_br_headers_stored++;
171   }
172 
173   if (mp3state->next_br_header_index >= SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS)
174   {
175     mp3state->next_br_header_index = 0;
176   }
177 }
178 
splt_mp3_read_process_side_info_main_data_begin(splt_mp3_state * mp3state,off_t offset)179 void splt_mp3_read_process_side_info_main_data_begin(splt_mp3_state *mp3state, off_t offset)
180 {
181   //side info is only for layer 3
182   if (mp3state->mp3file.layer != 3) { return; }
183 
184   //skip crc
185   if (mp3state->h.has_crc)
186   {
187     fgetc(mp3state->file_input);
188     fgetc(mp3state->file_input);
189   }
190 
191   unsigned int main_data_begin = 0;
192   main_data_begin = (unsigned int) fgetc(mp3state->file_input);
193   //main_data_begin has 9 bits in MPEG1 and 8 in MPEG2
194   if (mp3state->mp3file.mpgid == SPLT_MP3_MPEG1_ID)
195   {
196     main_data_begin <<= 8;
197     main_data_begin |= fgetc(mp3state->file_input);
198     main_data_begin >>= 7;
199   }
200 
201   mp3state->h.main_data_begin = (int) main_data_begin;
202 
203   /*fprintf(stdout, "frame size = %d\t sideinfo_size = %d\t main_data_begin = %d\t frame data space = %d\n",
204       mp3state->h.framesize, mp3state->h.sideinfo_size, mp3state->h.main_data_begin,
205       mp3state->h.frame_data_space);
206   fflush(stdout);*/
207 
208   splt_mp3_store_header(mp3state);
209 }
210 
splt_mp3_update_existing_xing(splt_mp3_state * mp3state,unsigned long frames,unsigned long bytes)211 static void splt_mp3_update_existing_xing(splt_mp3_state *mp3state, unsigned long frames,
212     unsigned long bytes)
213 {
214   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+4] = (frames >> 24) & 0xFF;
215   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+5] = (frames >> 16) & 0xFF;
216   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+6] = (frames >> 8) & 0xFF;
217   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+7] = frames & 0xFF;
218 
219   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+8] = (bytes >> 24) & 0xFF;
220   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+9] = (bytes >> 16) & 0xFF;
221   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+10] = (bytes >> 8) & 0xFF;
222   mp3state->mp3file.xingbuffer[mp3state->mp3file.xing_offset+11] = bytes & 0xFF;
223 }
224 
splt_mp3_xing_content_size(splt_mp3_state * mp3state)225 static int splt_mp3_xing_content_size(splt_mp3_state *mp3state)
226 {
227   struct splt_mp3 *mp3file = &mp3state->mp3file;
228 
229   unsigned long xing_flags =
230     (unsigned long) ((mp3file->xingbuffer[mp3file->xing_offset] << 24) |
231         (mp3file->xingbuffer[mp3file->xing_offset + 1] << 16) |
232         (mp3file->xingbuffer[mp3file->xing_offset + 2] << 8) |
233         (mp3file->xingbuffer[mp3file->xing_offset + 3]));
234 
235   int xing_content_size = 0;
236   if (xing_flags & SPLT_MP3_XING_FRAMES)
237   {
238     xing_content_size += 4;
239     mp3file->xing_has_frames = SPLT_TRUE;
240   }
241   if (xing_flags & SPLT_MP3_XING_BYTES)
242   {
243     xing_content_size += 4;
244     mp3file->xing_has_bytes = SPLT_TRUE;
245   }
246   if (xing_flags & SPLT_MP3_XING_TOC)
247   {
248     xing_content_size += 100;
249     mp3file->xing_has_toc = SPLT_TRUE;
250   }
251   if (xing_flags & SPLT_MP3_XING_QUALITY)
252   {
253     xing_content_size += 4;
254     mp3file->xing_has_quality = SPLT_TRUE;
255   }
256 
257   return xing_content_size;
258 }
259 
splt_mp3_xing_frame_has_lame(splt_mp3_state * mp3state)260 static int splt_mp3_xing_frame_has_lame(splt_mp3_state *mp3state)
261 {
262   struct splt_mp3 mp3file = mp3state->mp3file;
263 
264   off_t end_xing_offset =
265     mp3file.xing_offset + mp3file.xing_content_size + SPLT_MP3_XING_FLAGS_SIZE;
266 
267   //4 for the LAME characters
268   if (mp3state->mp3file.xing <= end_xing_offset + 4)
269   {
270     return SPLT_FALSE;
271   }
272 
273   if (mp3file.xingbuffer[end_xing_offset] == 'L' &&
274       mp3file.xingbuffer[end_xing_offset + 1] == 'A' &&
275       mp3file.xingbuffer[end_xing_offset + 2] == 'M' &&
276       mp3file.xingbuffer[end_xing_offset + 3] == 'E')
277   {
278     return SPLT_TRUE;
279   }
280 
281   return SPLT_FALSE;
282 }
283 
splt_mp3_get_delay_offset(splt_mp3_state * mp3state)284 static off_t splt_mp3_get_delay_offset(splt_mp3_state *mp3state)
285 {
286   off_t end_xing_offset =
287     mp3state->mp3file.xing_offset + mp3state->mp3file.xing_content_size + SPLT_MP3_XING_FLAGS_SIZE;
288   return end_xing_offset + SPLT_MP3_LAME_DELAY_OFFSET;
289 }
290 
splt_mp3_xing_info_off(splt_mp3_state * mp3state)291 static int splt_mp3_xing_info_off(splt_mp3_state *mp3state)
292 {
293   unsigned long headw = 0;
294   int i;
295 
296   for (i=0; i<mp3state->mp3file.xing; i++)
297   {
298     if ((headw == SPLT_MP3_XING_MAGIC) ||
299         (headw == SPLT_MP3_INFO_MAGIC)) // "Xing" or "Info"
300     {
301       return i;
302     }
303     headw <<= 8;
304     headw |= mp3state->mp3file.xingbuffer[i];
305   }
306 
307   return 0;
308 }
309 
splt_mp3_get_samples_per_frame(struct splt_mp3 * mp3file)310 int splt_mp3_get_samples_per_frame(struct splt_mp3 *mp3file)
311 {
312   if (mp3file->layer == MAD_LAYER_I)
313   {
314     return SPLT_MP3_LAYER1_SAMPLES_PER_FRAME;
315   }
316 
317   if (mp3file->layer == MAD_LAYER_II)
318   {
319     return SPLT_MP3_LAYER3_MPEG1_AND_LAYER2_SAMPLES_PER_FRAME;
320   }
321 
322   if (mp3file->mpgid == SPLT_MP3_MPEG1_ID)
323   {
324     return SPLT_MP3_LAYER3_MPEG1_AND_LAYER2_SAMPLES_PER_FRAME;
325   }
326 
327   return SPLT_MP3_LAYER3_MPEG2_SAMPLES_PER_FRAME;
328 }
329 
splt_mp3_handle_bit_reservoir(splt_state * state)330 int splt_mp3_handle_bit_reservoir(splt_state *state)
331 {
332   int with_bit_reservoir = splt_o_get_int_option(state, SPLT_OPT_HANDLE_BIT_RESERVOIR);
333   long overlap_time = splt_o_get_long_option(state, SPLT_OPT_OVERLAP_TIME);
334   int with_auto_adjust = splt_o_get_int_option(state, SPLT_OPT_AUTO_ADJUST);
335   int input_not_seekable = splt_o_get_int_option(state, SPLT_OPT_INPUT_NOT_SEEKABLE);
336 
337   int supported_split_mode = SPLT_TRUE;
338   int split_mode = splt_o_get_int_option(state, SPLT_OPT_SPLIT_MODE);
339   if ((split_mode == SPLT_OPTION_SILENCE_MODE) || (split_mode == SPLT_OPTION_TRIM_SILENCE_MODE))
340   {
341     supported_split_mode = SPLT_FALSE;
342   }
343 
344   int with_xing = splt_o_get_int_option(state, SPLT_OPT_XING);
345   int with_frame_mode = splt_o_get_int_option(state, SPLT_OPT_FRAME_MODE);
346 
347   int handle_bit_reservoir = with_bit_reservoir &&
348     overlap_time == 0 && !with_auto_adjust && !input_not_seekable &&
349     supported_split_mode && with_xing && with_frame_mode;
350 
351   return handle_bit_reservoir;
352 }
353 
splt_mp3_get_mpeg_as_int(int mpgid)354 int splt_mp3_get_mpeg_as_int(int mpgid)
355 {
356   if (mpgid == SPLT_MP3_MPEG1_ID) { return 1; }
357   if (mpgid == SPLT_MP3_MPEG2_ID) { return 2; }
358   return 25;
359 }
360 
splt_mp3_parse_xing_lame(splt_mp3_state * mp3state)361 void splt_mp3_parse_xing_lame(splt_mp3_state *mp3state)
362 {
363   mp3state->mp3file.xing_offset = splt_mp3_xing_info_off(mp3state);
364   mp3state->mp3file.xing_content_size = splt_mp3_xing_content_size(mp3state);
365 
366   if (!splt_mp3_xing_frame_has_lame(mp3state))
367   {
368     mp3state->mp3file.lame_delay = -1;
369     mp3state->mp3file.lame_padding = -1;
370     return;
371   }
372 
373   off_t delay_offset = splt_mp3_get_delay_offset(mp3state);
374   char *delay_padding_ptr = &mp3state->mp3file.xingbuffer[delay_offset];
375 
376   int first = (int) *delay_padding_ptr;
377   int middle = (int) *(delay_padding_ptr + 1);
378   int last = (int) *(delay_padding_ptr + 2);
379 
380   mp3state->mp3file.lame_delay = ((first & 0xFF) << 4) | (middle >> 4);
381   mp3state->mp3file.lame_padding = ((middle & 0xF) << 8) | (last & 0xFF);
382 }
383 
splt_mp3_create_new_xing_lame_frame(splt_mp3_state * mp3state,splt_state * state,int * frame_size,int * xing_offset,int * end_xing_offset,splt_code * error)384 static unsigned char *splt_mp3_create_new_xing_lame_frame(splt_mp3_state *mp3state, splt_state *state,
385     int *frame_size, int *xing_offset, int *end_xing_offset, splt_code *error)
386 {
387   unsigned long frame_header = mp3state->first_frame_header_for_reservoir | 0x00010000; //disable crc
388   int frame_header_created = SPLT_FALSE;
389 
390   struct splt_header first_frame_header;
391   first_frame_header =
392     splt_mp3_makehead(frame_header, mp3state->mp3file, first_frame_header, 0);
393 
394   struct splt_header h;
395 
396   int i = 1;
397   for (; i < 15; i++) {
398     unsigned long new_frame_header = ((unsigned long) frame_header & 0xFFFF0FFF) | (i << 12);
399 
400     h = splt_mp3_makehead(new_frame_header, mp3state->mp3file, h, 0);
401     if (h.framesize < 0xC0) { continue; }
402 
403     if (first_frame_header.bitrate == h.bitrate)
404     {
405       frame_header_created = SPLT_TRUE;
406       frame_header = new_frame_header;
407       break;
408     }
409   }
410 
411   if (!frame_header_created)
412   {
413     splt_d_print_debug(state,"Failed to create xing lame frame for bitrate %d \n",
414         first_frame_header.bitrate);
415 
416     *error = SPLT_ERROR_FAILED_BITRESERVOIR;
417     splt_e_set_error_data(state, "failed to create xing lame frame");
418     return NULL;
419   }
420 
421   *frame_size = h.framesize;
422 
423   unsigned char *frame = malloc(sizeof(unsigned char) * h.framesize);
424   if (frame == NULL)
425   {
426     *error = SPLT_ERROR_CANNOT_ALLOCATE_MEMORY;
427     return NULL;
428   }
429 
430   frame[0] = (unsigned char) (frame_header >> 24);
431   frame[1] = (unsigned char) (frame_header >> 16);
432   frame[2] = (unsigned char) (frame_header >> 8);
433   frame[3] = (unsigned char) frame_header;
434 
435   int j = 4;
436   for (; j < h.framesize;j++) { frame[j] = 0x0; }
437 
438   int xing_tag_offset = 4 + h.sideinfo_size;
439 
440   if (mp3state->is_guessed_vbr)
441   {
442     frame[xing_tag_offset++] = 'X';
443     frame[xing_tag_offset++] = 'i';
444     frame[xing_tag_offset++] = 'n';
445     frame[xing_tag_offset++] = 'g';
446   }
447   else
448   {
449     frame[xing_tag_offset++] = 'I';
450     frame[xing_tag_offset++] = 'n';
451     frame[xing_tag_offset++] = 'f';
452     frame[xing_tag_offset++] = 'o';
453   }
454 
455   *xing_offset = xing_tag_offset;
456 
457   frame[xing_tag_offset++] = 0;
458   frame[xing_tag_offset++] = 0;
459   frame[xing_tag_offset++] = 0;
460   frame[xing_tag_offset++] = 0x0F;
461   //0x0F = SPLT_MP3_XING_FRAMES | SPLT_MP3_XING_BYTES | SPLT_MP3_XING_TOC | SPLT_MP3_XING_QUALITY
462 
463   xing_tag_offset += (100 + 4 + 4 + 4);
464 
465   *end_xing_offset = xing_tag_offset;
466 
467   frame[xing_tag_offset++] = 'L';
468   frame[xing_tag_offset++] = 'A';
469   frame[xing_tag_offset++] = 'M';
470   frame[xing_tag_offset++] = 'E';
471 
472   frame[xing_tag_offset++] = '3';
473   frame[xing_tag_offset++] = '.';
474   frame[xing_tag_offset++] = '9';
475   frame[xing_tag_offset++] = '4';
476 
477   return frame;
478 }
479 
splt_mp3_update_delay_and_padding_on_lame_frame(splt_mp3_state * mp3state,char * delay_padding_ptr,short reservoir_frame,unsigned long * frames)480 static void splt_mp3_update_delay_and_padding_on_lame_frame(splt_mp3_state *mp3state,
481     char *delay_padding_ptr, short reservoir_frame, unsigned long *frames)
482 {
483   int delay = mp3state->mp3file.lame_delay;
484   int padding = mp3state->mp3file.lame_padding;
485 
486   delay += (mp3state->begin_sample -
487       mp3state->first_frame_inclusive * mp3state->mp3file.samples_per_frame);
488 
489   long number_of_frames = 0;
490   long last_frame = mp3state->last_frame_inclusive;
491 
492   if (last_frame == -1 || last_frame > mp3state->frames)
493   {
494     last_frame = mp3state->frames - 1;
495   }
496 
497   if (last_frame != mp3state->first_frame_inclusive)
498   {
499     number_of_frames = last_frame - mp3state->first_frame_inclusive + 1;
500   }
501   *frames = number_of_frames;
502 
503   /*fprintf(stdout, "last frame = %ld\n", last_frame);
504   fprintf(stdout, "first frame = %ld\n", mp3state->first_frame_inclusive);
505   fflush(stdout);*/
506 
507   long number_of_samples = number_of_frames * mp3state->mp3file.samples_per_frame;
508   long number_of_samples_to_play = mp3state->end_sample - mp3state->begin_sample;
509 
510   padding = number_of_samples - number_of_samples_to_play - delay;
511 
512   if (reservoir_frame)
513   {
514     delay += mp3state->mp3file.samples_per_frame;
515     *frames = *frames + 1;
516   }
517 
518   if (delay > SPLT_MP3_LAME_MAX_DELAY) { delay = SPLT_MP3_LAME_MAX_DELAY; }
519   if (padding > SPLT_MP3_LAME_MAX_PADDING) { padding = SPLT_MP3_LAME_MAX_PADDING; }
520   if (delay < 0) { delay = 0; }
521   if (padding < 0) { padding = 0; }
522 
523   *delay_padding_ptr = (char) (delay >> 4);
524   *(delay_padding_ptr + 1) = (char) (delay & 0xF) << 4 | (padding >> 8);
525   *(delay_padding_ptr + 2) = (char) padding;
526 }
527 
splt_mp3_build_xing_lame_frame(splt_mp3_state * mp3state,off_t begin,off_t end,unsigned long fbegin,splt_code * error,splt_state * state)528 void splt_mp3_build_xing_lame_frame(splt_mp3_state *mp3state, off_t begin, off_t end,
529     unsigned long fbegin, splt_code *error, splt_state *state)
530 {
531   short reservoir_frame = 0;
532   short reservoir_bytes = 0;
533   if (mp3state->reservoir.reservoir_frame != NULL)
534   {
535     reservoir_frame = 1;
536     reservoir_bytes = mp3state->reservoir.reservoir_frame_size;
537   }
538 
539   if (end == -1) { end = mp3state->mp3file.len; }
540 
541   unsigned long frames = (unsigned long) mp3state->frames - fbegin;
542   unsigned long bytes = (unsigned long) (end - begin + reservoir_bytes + mp3state->overlapped_frames_bytes);
543 
544   if (!splt_mp3_handle_bit_reservoir(state))
545   {
546     bytes += mp3state->mp3file.xing;
547 
548     if (mp3state->mp3file.xing > 0)
549     {
550       splt_mp3_update_existing_xing(mp3state, frames, bytes);
551     }
552 
553     return;
554   }
555 
556   if (mp3state->mp3file.xing <= 0)
557   {
558     int xing_offset = 0;
559     int end_xing_offset = 0;
560     int frame_size = 0;
561     unsigned char *frame = splt_mp3_create_new_xing_lame_frame(mp3state, state, &frame_size,
562         &xing_offset, &end_xing_offset, error);
563     if (*error < 0) { return; }
564 
565     char *delay_padding_ptr = (char *) &frame[end_xing_offset + SPLT_MP3_LAME_DELAY_OFFSET];
566     splt_mp3_update_delay_and_padding_on_lame_frame(mp3state, delay_padding_ptr, reservoir_frame, &frames);
567 
568     frame[xing_offset + 4] = (frames >> 24) & 0xFF;
569     frame[xing_offset + 5] = (frames >> 16) & 0xFF;
570     frame[xing_offset + 6] = (frames >> 8) & 0xFF;
571     frame[xing_offset + 7] = frames & 0xFF;
572 
573     bytes += frame_size;
574 
575     frame[xing_offset + 8] = (bytes >> 24) & 0xFF;
576     frame[xing_offset + 9] = (bytes >> 16) & 0xFF;
577     frame[xing_offset + 10] = (bytes >> 8) & 0xFF;
578     frame[xing_offset + 11] = bytes & 0xFF;
579 
580     if (mp3state->new_xing_lame_frame)
581     {
582       free(mp3state->new_xing_lame_frame);
583     }
584 
585     mp3state->new_xing_lame_frame_size = frame_size;
586     mp3state->new_xing_lame_frame = frame;
587 
588     return;
589   }
590 
591   if (splt_mp3_xing_frame_has_lame(mp3state))
592   {
593     bytes += mp3state->mp3file.xing;
594 
595     char *delay_padding_ptr = &mp3state->mp3file.xingbuffer[splt_mp3_get_delay_offset(mp3state)];
596     splt_mp3_update_delay_and_padding_on_lame_frame(mp3state, delay_padding_ptr, reservoir_frame, &frames);
597     splt_mp3_update_existing_xing(mp3state, frames, bytes);
598     return;
599   }
600 
601   if (mp3state->mp3file.xing > 0)
602   {
603     *error = SPLT_ERROR_FAILED_BITRESERVOIR;
604     splt_e_set_error_data(state, "input files with Xing frame without LAME not yet supported");
605   }
606 
607   //TODO2: update lame crc16
608 }
609 
splt_mp3_current_br_header_index(splt_mp3_state * mp3state)610 static int splt_mp3_current_br_header_index(splt_mp3_state *mp3state)
611 {
612   int current_header_index = mp3state->next_br_header_index - 1;
613   if (current_header_index < 0)
614   {
615     current_header_index = SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS - 1;
616   }
617 
618   return current_header_index;
619 }
620 
splt_mp3_previous_br_header_index(splt_mp3_state * mp3state,int current_header_index)621 static int splt_mp3_previous_br_header_index(splt_mp3_state *mp3state, int current_header_index)
622 {
623   int header_index = current_header_index - 1;
624   if (header_index < 0)
625   {
626     header_index = SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS - 1;
627   }
628 
629   return header_index;
630 }
631 
splt_mp3_back_br_header_index(splt_mp3_state * mp3state)632 static void splt_mp3_back_br_header_index(splt_mp3_state *mp3state)
633 {
634   mp3state->next_br_header_index--;
635   if (mp3state->next_br_header_index < 0)
636   {
637     mp3state->next_br_header_index = SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS - 1;
638   }
639 }
640 
splt_mp3_get_overlapped_frames(long last_frame,splt_mp3_state * mp3state,splt_state * state,splt_code * error)641 void splt_mp3_get_overlapped_frames(long last_frame, splt_mp3_state *mp3state,
642     splt_state *state, splt_code *error)
643 {
644   if (last_frame <= 0) { return; }
645 
646   long number_of_frames_to_be_overlapped = last_frame - mp3state->first_frame_inclusive + 1;
647 
648   /*fprintf(stdout, "frames to be overlapped = %ld\n", number_of_frames_to_be_overlapped);
649   fflush(stdout);*/
650 
651   int current_header_index = splt_mp3_current_br_header_index(mp3state);
652   mp3state->overlapped_frames_bytes = 0;
653 
654   int index = 0;
655   off_t frame_offsets[SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS] = { 0 };
656   int frame_sizes[SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS] = { 0 };
657 
658   int i = 0;
659   for (;i < number_of_frames_to_be_overlapped; i++)
660   {
661     current_header_index = splt_mp3_previous_br_header_index(mp3state, current_header_index);
662 
663     mp3state->overlapped_frames_bytes += mp3state->br_headers[current_header_index].framesize;
664     frame_offsets[index] = mp3state->br_headers[current_header_index].ptr;
665     frame_sizes[index] = mp3state->br_headers[current_header_index].framesize;
666     index++;
667     mp3state->overlapped_number_of_frames++;
668   }
669 
670   off_t previous_position = ftello(mp3state->file_input);
671 
672   if (mp3state->overlapped_frames) {
673     free(mp3state->overlapped_frames);
674   }
675   mp3state->overlapped_frames = malloc(sizeof(unsigned char) * mp3state->overlapped_frames_bytes);
676   if (mp3state->overlapped_frames == NULL)
677   {
678     *error = SPLT_ERROR_CANNOT_ALLOCATE_MEMORY;
679     return;
680   }
681 
682   long current_index_in_frames = 0;
683   for (i = index - 1;i >= 0; i--)
684   {
685     off_t frame_offset = frame_offsets[i];
686 
687     if (fseeko(mp3state->file_input, frame_offset, SEEK_SET) == -1)
688     {
689       splt_e_set_strerror_msg_with_data(state, splt_t_get_filename_to_split(state));
690       *error = SPLT_ERROR_SEEKING_FILE;
691       return;
692     }
693 
694     int frame_size = frame_sizes[i];
695     unsigned char *frame = splt_io_fread(mp3state->file_input, frame_size);
696     if (!frame)
697     {
698       splt_e_clean_strerror_msg(state);
699       splt_e_set_error_data(state, splt_t_get_filename_to_split(state));
700       *error = SPLT_ERROR_WHILE_READING_FILE;
701       return;
702     }
703 
704     memcpy(mp3state->overlapped_frames + current_index_in_frames, frame, frame_size);
705     current_index_in_frames += frame_size;
706     free(frame);
707 
708     splt_mp3_back_br_header_index(mp3state);
709   }
710 
711   if (fseeko(mp3state->file_input, previous_position, SEEK_SET) == -1)
712   {
713     splt_e_set_strerror_msg_with_data(state, splt_t_get_filename_to_split(state));
714     *error = SPLT_ERROR_SEEKING_FILE;
715     return;
716   }
717 
718   /*fprintf(stdout, "overlapped frames bytes follows:\n");
719   int j = 0;
720   for (j = 0;j < mp3state->overlapped_frames_bytes;j++)
721   {
722     fprintf(stdout, "%02x ", mp3state->overlapped_frames[j]);
723     fflush(stdout);
724   }
725   fprintf(stdout, "\n");
726   fflush(stdout);*/
727 }
728 
splt_mp3_find_begin_frame(double fbegin_sec,splt_mp3_state * mp3state,splt_state * state,splt_code * error)729 unsigned long splt_mp3_find_begin_frame(double fbegin_sec, splt_mp3_state *mp3state,
730     splt_state *state, splt_code *error)
731 {
732   unsigned long without_bit_reservoir_begin_frame =
733     (unsigned long) (fbegin_sec * mp3state->mp3file.fps);
734 
735   if (!splt_mp3_handle_bit_reservoir(state))
736   {
737     return without_bit_reservoir_begin_frame;
738   }
739 
740   /*fprintf(stdout, "fbegin sec = %ld\n", fbegin_sec);
741   fflush(stdout);*/
742 
743   long begin_sample = (long) rint((double) fbegin_sec * (double) mp3state->mp3file.freq);
744   mp3state->begin_sample = begin_sample;
745 
746   long first_frame_inclusive = (long)
747     ((begin_sample + mp3state->mp3file.lame_delay - SPLT_MP3_MIN_OVERLAP_SAMPLES_START)
748      / mp3state->mp3file.samples_per_frame);
749   if (first_frame_inclusive < 0) { first_frame_inclusive = 0; }
750 
751   /*fprintf(stdout, "begin_sample = %ld\n", begin_sample);
752   fprintf(stdout, "first frame inclusive = %ld\n", first_frame_inclusive);
753   fflush(stdout);*/
754 
755   mp3state->first_frame_inclusive = first_frame_inclusive;
756 
757   long last_frame = mp3state->last_frame_inclusive;
758   splt_mp3_get_overlapped_frames(last_frame, mp3state, state, error);
759   if (*error < 0) { return 0; }
760 
761   return (unsigned long) first_frame_inclusive;
762 }
763 
splt_mp3_find_end_frame(double fend_sec,splt_mp3_state * mp3state,splt_state * state)764 unsigned long splt_mp3_find_end_frame(double fend_sec, splt_mp3_state *mp3state,
765     splt_state *state)
766 {
767   if (!splt_mp3_handle_bit_reservoir(state))
768   {
769     //prefer to split a bit after the end than loosing some frame
770     //before the end
771     return (unsigned long) ceilf(fend_sec * mp3state->mp3file.fps);
772   }
773 
774   long end_sample = (long) rint((double) fend_sec * (double) mp3state->mp3file.freq);
775   if (end_sample < 0) { end_sample = 0; }
776   mp3state->end_sample = end_sample;
777 
778   long last_frame_inclusive = (long)
779     ((end_sample + mp3state->mp3file.lame_delay + SPLT_MP3_MIN_OVERLAP_SAMPLES_END)
780      / mp3state->mp3file.samples_per_frame);
781 
782   mp3state->last_frame_inclusive = last_frame_inclusive;
783 
784   /*fprintf(stdout, "samples_per_frame = %d\n", mp3state->mp3file.samples_per_frame);
785   fprintf(stdout, "lame_delay = %d\n", mp3state->mp3file.lame_delay);
786   fprintf(stdout, "end_sample = %ld\n", end_sample);
787   fprintf(stdout, "computed end frame = %ld\n", last_frame_inclusive + 1);
788   fflush(stdout);*/
789 
790   return (unsigned long) (last_frame_inclusive + 1);
791 }
792 
splt_mp3_extract_reservoir_main_data_bytes(splt_mp3_state * mp3state,splt_state * state,splt_code * error)793 static void splt_mp3_extract_reservoir_main_data_bytes(splt_mp3_state *mp3state, splt_state *state, splt_code *error)
794 {
795   //reservoir is only for layer 3
796   if (mp3state->mp3file.layer != 3) { return; }
797 
798   int number_of_headers_stored = mp3state->number_of_br_headers_stored;
799 
800   int current_header_index = splt_mp3_current_br_header_index(mp3state);
801   struct splt_header *h = &mp3state->br_headers[current_header_index];
802   int back_pointer = h->main_data_begin;
803 
804   /*fprintf(stdout, "back pointer = %d\n", back_pointer);
805   fflush(stdout);*/
806 
807   if (back_pointer > 511)
808   {
809     splt_e_set_error_data(state, splt_t_get_filename_to_split(state));
810     *error = SPLT_ERROR_INVALID;
811     return;
812   }
813 
814   off_t previous_position = ftello(mp3state->file_input);
815 
816   unsigned char **data_from_frames = malloc(sizeof(unsigned char *) * SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS);
817   int *bytes_to_copy = malloc(sizeof(int *) * SPLT_MP3_MAX_BYTE_RESERVOIR_HEADERS);
818   if (data_from_frames == NULL || bytes_to_copy == NULL)
819   {
820     *error = SPLT_ERROR_CANNOT_ALLOCATE_MEMORY;
821     return;
822   }
823 
824   int is_first_file = splt_t_get_current_split_file_number(state) == 1;
825 
826   int number_of_frames = 0;
827   while (back_pointer > 0)
828   {
829     current_header_index = splt_mp3_previous_br_header_index(mp3state, current_header_index);
830     number_of_headers_stored--;
831 
832     //this might happend for the first file, but we don't care for the first file
833     //(for example when splitting starting at ~7 hundreths of seconds - at frame number ~2)
834     if ((number_of_headers_stored < 0) && !is_first_file)
835     {
836       splt_e_set_error_data(state, "Bit reservoir number of headers stored is negative !");
837       *error = SPLT_ERROR_INVALID_CODE;
838       goto end;
839     }
840 
841     h = &mp3state->br_headers[current_header_index];
842 
843     if (h->frame_data_space == 0) { continue; }
844 
845     unsigned int number_of_bytes_to_copy = h->frame_data_space;
846     if (back_pointer < h->frame_data_space)
847     {
848       number_of_bytes_to_copy = back_pointer;
849     }
850 
851     off_t frame_main_data_offset = h->ptr + h->sideinfo_size + 4;
852     if (number_of_bytes_to_copy < h->frame_data_space)
853     {
854       frame_main_data_offset += h->frame_data_space - number_of_bytes_to_copy;
855     }
856 
857     /*fprintf(stdout, "Copying %d bytes into reservoir\n", number_of_bytes_to_copy);
858     fflush(stdout);*/
859 
860     if (fseeko(mp3state->file_input, frame_main_data_offset, SEEK_SET) == -1)
861     {
862       splt_e_set_strerror_msg_with_data(state, splt_t_get_filename_to_split(state));
863       *error = SPLT_ERROR_SEEKING_FILE;
864       goto end;
865     }
866 
867     unsigned char *data_from_frame = splt_io_fread(mp3state->file_input, number_of_bytes_to_copy);
868     if (data_from_frame)
869     {
870       /*unsigned int it = 0;
871       for (;it < number_of_bytes_to_copy;it++)
872       {
873         fprintf(stdout, "%02x ", data_from_frame[it]);
874       }
875       fprintf(stdout, "\n");
876       fflush(stdout);*/
877 
878       data_from_frames[number_of_frames] = data_from_frame;
879       bytes_to_copy[number_of_frames] = number_of_bytes_to_copy;
880       number_of_frames++;
881     }
882     else
883     {
884       splt_e_clean_strerror_msg(state);
885       splt_e_set_error_data(state, splt_t_get_filename_to_split(state));
886       *error = SPLT_ERROR_WHILE_READING_FILE;
887       goto end;
888     }
889 
890     back_pointer -= number_of_bytes_to_copy;
891   }
892 
893   struct splt_reservoir *res = &mp3state->reservoir;
894   res->reservoir_end = 0;
895 
896   number_of_frames--;
897   for (;number_of_frames >= 0; number_of_frames--)
898   {
899     unsigned char *data_from_frame = data_from_frames[number_of_frames];
900     int number_of_bytes_to_copy = bytes_to_copy[number_of_frames];
901 
902     memcpy(res->reservoir + res->reservoir_end, data_from_frame, number_of_bytes_to_copy);
903     res->reservoir_end += number_of_bytes_to_copy;
904     free(data_from_frame);
905   }
906 
907   /*unsigned int index = 0;
908   fprintf(stdout, "reservoir= _");
909   for (;index < res->reservoir_end;index++)
910   {
911     fprintf(stdout, "%02x ", res->reservoir[index]);
912   }
913   fprintf(stdout, "_\n");
914   fflush(stdout);*/
915 
916   if (res->reservoir_end > 0)
917   {
918     if (fseeko(mp3state->file_input, previous_position, SEEK_SET) == -1)
919     {
920       splt_e_set_strerror_msg_with_data(state, splt_t_get_filename_to_split(state));
921       *error = SPLT_ERROR_SEEKING_FILE;
922     }
923   }
924 
925 end:
926   free(bytes_to_copy);
927   free(data_from_frames);
928 }
929 
splt_mp3_build_reservoir_frame(splt_mp3_state * mp3state,splt_state * state,splt_code * error)930 static void splt_mp3_build_reservoir_frame(splt_mp3_state *mp3state, splt_state *state, splt_code *error)
931 {
932   struct splt_reservoir *res = &mp3state->reservoir;
933 
934   if (res->reservoir_end == 0)
935   {
936     if (res->reservoir_frame) { free(res->reservoir_frame); }
937     res->reservoir_frame = NULL;
938     res->reservoir_frame_size = 0;
939     return;
940   }
941 
942   unsigned long first_frame_header = mp3state->headw;
943   first_frame_header |= 0x00010000; //set protection bit to 1 in order to turn off CRC
944 
945   int bytes_in_main_data = res->reservoir_end + 4; //keep 4 extra bytes
946 
947   int bitrate_mask = 1;
948   for (;bitrate_mask <= 14; bitrate_mask++)
949   {
950     unsigned long header = (first_frame_header & 0xFFFF0FFF) + (bitrate_mask << 12);
951     struct splt_header h;
952     h = splt_mp3_makehead(header, mp3state->mp3file, h, 0);
953 
954     if (h.frame_data_space < bytes_in_main_data)
955     {
956       continue;
957     }
958 
959     unsigned char *frame = malloc(sizeof(unsigned char) * h.framesize);
960     if (frame == NULL)
961     {
962       *error = SPLT_ERROR_CANNOT_ALLOCATE_MEMORY;
963       return;
964     }
965 
966     frame[0] = (unsigned char) (header >> 24);
967     frame[1] = (unsigned char) (header >> 16);
968     frame[2] = (unsigned char) (header >> 8);
969     frame[3] = (unsigned char) header;
970 
971     int i = 4;
972     for (; i < 4 + h.sideinfo_size;i++) { frame[i] = 0x0; }
973     for (; i < h.framesize;i++) { frame[i] = 0x78; }
974 
975     memcpy(frame + h.framesize - res->reservoir_end, res->reservoir, res->reservoir_end);
976 
977     if (res->reservoir_frame) { free(res->reservoir_frame); }
978     res->reservoir_frame = frame;
979     res->reservoir_frame_size = h.framesize;
980 
981     return;
982   }
983 }
984 
splt_mp3_extract_reservoir_and_build_reservoir_frame(splt_mp3_state * mp3state,splt_state * state,splt_code * error)985 void splt_mp3_extract_reservoir_and_build_reservoir_frame(splt_mp3_state *mp3state,
986     splt_state *state, splt_code *error)
987 {
988   if (!splt_mp3_handle_bit_reservoir(state))
989   {
990     return;
991   }
992 
993   splt_mp3_extract_reservoir_main_data_bytes(mp3state, state, error);
994   if (*error < 0) { return; }
995 
996   splt_mp3_build_reservoir_frame(mp3state, state, error);
997 
998   struct splt_reservoir *reservoir = &mp3state->reservoir;
999   if (reservoir->reservoir_frame == NULL)
1000   {
1001     /*fprintf(stdout, "reservoir frame follows : NO reservoir frame\n");
1002     fflush(stdout);*/
1003     return;
1004   }
1005 
1006   /*fprintf(stdout, "reservoir frame follows : _ ");
1007   int i = 0;
1008   for (i = 0;i < reservoir->reservoir_frame_size; i++)
1009   {
1010     fprintf(stdout, "%02x ", reservoir->reservoir_frame[i]);
1011   }
1012   fprintf(stdout, "_\n");
1013   fflush(stdout);*/
1014 }
1015 
1016 //!finds first header from start_pos. Returns -1 if no header is found
splt_mp3_findhead(splt_mp3_state * mp3state,off_t start)1017 off_t splt_mp3_findhead(splt_mp3_state *mp3state, off_t start)
1018 {
1019   if (splt_io_get_word(mp3state->file_input,
1020         start, SEEK_SET, &mp3state->headw) == -1)
1021   {
1022     return -1;
1023   }
1024   if (feof(mp3state->file_input))
1025   {
1026     return -1;
1027   }
1028   while (!(splt_mp3_c_bitrate(mp3state->headw)))
1029   {
1030     if (feof(mp3state->file_input))
1031     {
1032       return -1;
1033     }
1034     mp3state->headw <<= 8;
1035     mp3state->headw |= fgetc(mp3state->file_input);
1036     start++;
1037   }
1038 
1039   return start;
1040 }
1041 
1042 //! Finds first valid header from start. Will work with high probabilty, i hope :)
splt_mp3_findvalidhead(splt_mp3_state * mp3state,off_t start)1043 off_t splt_mp3_findvalidhead(splt_mp3_state *mp3state, off_t start)
1044 {
1045   off_t begin;
1046   struct splt_header h;
1047 
1048   begin = splt_mp3_findhead(mp3state, start);
1049 
1050   do {
1051     start = begin;
1052     if (start == -1)
1053     {
1054       break;
1055     }
1056     h = splt_mp3_makehead (mp3state->headw, mp3state->mp3file, h, start);
1057     begin = splt_mp3_findhead(mp3state, (start + 1));
1058   } while (begin!=(start + h.framesize));
1059 
1060   return start;
1061 }
1062 
1063 /*! Get a frame
1064 
1065 \return  negative value means: error
1066 */
splt_mp3_get_frame(splt_mp3_state * mp3state)1067 int splt_mp3_get_frame(splt_mp3_state *mp3state)
1068 {
1069   if(mp3state->stream.buffer==NULL ||
1070       mp3state->stream.error==MAD_ERROR_BUFLEN)
1071   {
1072     size_t readSize, remaining;
1073     unsigned char *readStart;
1074 
1075     if (feof(mp3state->file_input))
1076     {
1077       return -2;
1078     }
1079 
1080     if(mp3state->stream.next_frame!=NULL)
1081     {
1082       remaining = mp3state->stream.bufend - mp3state->stream.next_frame;
1083       memmove(mp3state->inputBuffer, mp3state->stream.next_frame, remaining);
1084       readStart = mp3state->inputBuffer + remaining;
1085       readSize = SPLT_MAD_BSIZE - remaining;
1086     }
1087     else
1088     {
1089       readSize = SPLT_MAD_BSIZE;
1090       readStart=mp3state->inputBuffer;
1091       remaining=0;
1092     }
1093 
1094     readSize=fread(readStart, 1, readSize, mp3state->file_input);
1095     if (readSize <= 0)
1096     {
1097       return -2;
1098     }
1099 
1100     mp3state->buf_len = readSize + remaining;
1101     mp3state->bytes += readSize;
1102     //does not set any error
1103     mad_stream_buffer(&mp3state->stream, mp3state->inputBuffer,
1104         readSize+remaining);
1105     mp3state->stream.error = MAD_ERROR_NONE;
1106   }
1107 
1108   //mad_frame_decode() returns -1 if error, 0 if no error
1109   return mad_frame_decode(&mp3state->frame, &mp3state->stream);
1110 }
1111 
1112 /*! used by mp3split and mp3_scan_silence
1113 
1114 gets a frame and checks for its validity; sets the mp3state->data_ptr
1115 the pointer to the frame  and the mp3state->data_len the length of the
1116 frame
1117 
1118 \param state The central structure libmp3splt keeps all its data in
1119 \param error Contains the error number for libmp3splt
1120 
1121 \return
1122  - 1 if ok,
1123  - -1 if end of file,
1124  - 0 if nothing (???)
1125  - and -3 if other error;
1126  .
1127 On error the error number will be set in the '*error' parameter
1128 */
splt_mp3_get_valid_frame(splt_state * state,int * error)1129 int splt_mp3_get_valid_frame(splt_state *state, int *error)
1130 {
1131   splt_mp3_state *mp3state = state->codec;
1132   int ok = 0;
1133   do
1134   {
1135     int ret = splt_mp3_get_frame(mp3state);
1136     if(ret != 0)
1137     {
1138       if (ret == -2)
1139       {
1140         return -1;
1141       }
1142       if (mp3state->stream.error == MAD_ERROR_LOSTSYNC)
1143       {
1144         //syncerrors
1145         state->syncerrors++;
1146         if ((mp3state->syncdetect) && (state->syncerrors>SPLT_MAXSYNC))
1147         {
1148           splt_mp3_checksync(mp3state);
1149         }
1150       }
1151       if(MAD_RECOVERABLE(mp3state->stream.error))
1152       {
1153         continue;
1154       }
1155       else
1156       {
1157         if(mp3state->stream.error==MAD_ERROR_BUFLEN)
1158         {
1159           continue;
1160         }
1161         else
1162         {
1163           splt_e_set_error_data(state, mad_stream_errorstr(&mp3state->stream));
1164           *error = SPLT_ERROR_PLUGIN_ERROR;
1165           return -3;
1166         }
1167       }
1168     }
1169     else
1170     {
1171       //the important stuff
1172       mp3state->data_ptr = (unsigned char *) mp3state->stream.this_frame;
1173       if (mp3state->stream.next_frame!=NULL)
1174       {
1175         mp3state->data_len = (long) (mp3state->stream.next_frame - mp3state->stream.this_frame);
1176       }
1177       ok = 1;
1178     }
1179 
1180   } while (!ok);
1181 
1182   return ok;
1183 }
1184 
1185