Subversion Repositories Kolibri OS

Rev

Rev 1905 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1905 serge 1
/*
2
	frame: Heap of routines dealing with the core mpg123 data structure.
3
 
3960 Serge 4
	copyright 2008-2010 by the mpg123 project - free software under the terms of the LGPL 2.1
1905 serge 5
	see COPYING and AUTHORS files in distribution or http://mpg123.org
6
	initially written by Thomas Orgis
7
*/
8
 
9
#include "mpg123lib_intern.h"
10
#include "getcpuflags.h"
11
#include "debug.h"
12
 
13
static void frame_fixed_reset(mpg123_handle *fr);
14
 
15
/* that's doubled in decode_ntom.c */
16
#define NTOM_MUL (32768)
3960 Serge 17
 
18
#define aligned_pointer(p, type, alignment) align_the_pointer(p, alignment)
19
static void *align_the_pointer(void *base, unsigned int alignment)
1905 serge 20
{
3960 Serge 21
	/*
22
		Work in unsigned integer realm, explicitly.
23
		Tricking the compiler into integer operations like % by invoking base-NULL is dangerous: It results into ptrdiff_t, which gets negative on big addresses. Big screw up, that.
24
		I try to do it "properly" here: Casting only to uintptr_t and no artihmethic with void*.
25
	*/
26
	uintptr_t baseval = (uintptr_t)(char*)base;
27
	uintptr_t aoff = baseval % alignment;
28
 
29
	debug3("align_the_pointer: pointer %p is off by %u from %u",
30
	       base, (unsigned int)aoff, alignment);
31
 
32
	if(aoff) return (char*)base+alignment-aoff;
33
	else     return base;
34
}
35
 
36
static void frame_default_pars(mpg123_pars *mp)
37
{
1905 serge 38
	mp->outscale = 1.0;
3960 Serge 39
	mp->flags = 0;
1905 serge 40
#ifdef GAPLESS
3960 Serge 41
	mp->flags |= MPG123_GAPLESS;
1905 serge 42
#endif
3960 Serge 43
	mp->flags |= MPG123_AUTO_RESAMPLE;
1905 serge 44
#ifndef NO_NTOM
45
	mp->force_rate = 0;
46
#endif
47
	mp->down_sample = 0;
48
	mp->rva = 0;
49
	mp->halfspeed = 0;
50
	mp->doublespeed = 0;
51
	mp->verbose = 0;
52
#ifndef NO_ICY
53
	mp->icy_interval = 0;
54
#endif
55
	mp->timeout = 0;
56
	mp->resync_limit = 1024;
57
#ifdef FRAME_INDEX
58
	mp->index_size = INDEX_SIZE;
59
#endif
60
	mp->preframes = 4; /* That's good  for layer 3 ISO compliance bitstream. */
61
	mpg123_fmt_all(mp);
3960 Serge 62
	/* Default of keeping some 4K buffers at hand, should cover the "usual" use case (using 16K pipe buffers as role model). */
63
#ifndef NO_FEEDER
64
	mp->feedpool = 5;
65
	mp->feedbuffer = 4096;
66
#endif
1905 serge 67
}
68
 
69
void frame_init(mpg123_handle *fr)
70
{
71
	frame_init_par(fr, NULL);
72
}
73
 
74
void frame_init_par(mpg123_handle *fr, mpg123_pars *mp)
75
{
3960 Serge 76
	fr->own_buffer = TRUE;
1905 serge 77
	fr->buffer.data = NULL;
3960 Serge 78
	fr->buffer.rdata = NULL;
79
	fr->buffer.fill = 0;
80
	fr->buffer.size = 0;
1905 serge 81
	fr->rawbuffs = NULL;
82
	fr->rawbuffss = 0;
83
	fr->rawdecwin = NULL;
84
	fr->rawdecwins = 0;
85
#ifndef NO_8BIT
86
	fr->conv16to8_buf = NULL;
87
#endif
88
#ifdef OPT_DITHER
89
	fr->dithernoise = NULL;
90
#endif
3960 Serge 91
	fr->layerscratch = NULL;
1905 serge 92
	fr->xing_toc = NULL;
93
	fr->cpu_opts.type = defdec();
94
	fr->cpu_opts.class = decclass(fr->cpu_opts.type);
95
#ifndef NO_NTOM
96
	/* these two look unnecessary, check guarantee for synth_ntom_set_step (in control_generic, even)! */
97
	fr->ntom_val[0] = NTOM_MUL>>1;
98
	fr->ntom_val[1] = NTOM_MUL>>1;
99
	fr->ntom_step = NTOM_MUL;
100
#endif
101
	/* unnecessary: fr->buffer.size = fr->buffer.fill = 0; */
102
	mpg123_reset_eq(fr);
103
	init_icy(&fr->icy);
104
	init_id3(fr);
105
	/* frame_outbuffer is missing... */
106
	/* frame_buffers is missing... that one needs cpu opt setting! */
107
	/* after these... frame_reset is needed before starting full decode */
108
	invalidate_format(&fr->af);
109
	fr->rdat.r_read = NULL;
110
	fr->rdat.r_lseek = NULL;
3960 Serge 111
	fr->rdat.iohandle = NULL;
112
	fr->rdat.r_read_handle = NULL;
113
	fr->rdat.r_lseek_handle = NULL;
114
	fr->rdat.cleanup_handle = NULL;
115
	fr->wrapperdata = NULL;
116
	fr->wrapperclean = NULL;
1905 serge 117
	fr->decoder_change = 1;
118
	fr->err = MPG123_OK;
119
	if(mp == NULL) frame_default_pars(&fr->p);
120
	else memcpy(&fr->p, mp, sizeof(struct mpg123_pars_struct));
121
 
3960 Serge 122
#ifndef NO_FEEDER
123
	bc_prepare(&fr->rdat.buffer, fr->p.feedpool, fr->p.feedbuffer);
124
#endif
125
 
1905 serge 126
	fr->down_sample = 0; /* Initialize to silence harmless errors when debugging. */
127
	frame_fixed_reset(fr); /* Reset only the fixed data, dynamic buffers are not there yet! */
128
	fr->synth = NULL;
129
	fr->synth_mono = NULL;
130
	fr->make_decode_tables = NULL;
131
#ifdef FRAME_INDEX
132
	fi_init(&fr->index);
133
	frame_index_setup(fr); /* Apply the size setting. */
134
#endif
135
}
136
 
137
#ifdef OPT_DITHER
138
/* Also, only allocate the memory for the table on demand.
139
   In future, one could create special noise for different sampling frequencies(?). */
140
int frame_dither_init(mpg123_handle *fr)
141
{
142
	/* run-time dither noise table generation */
143
	if(fr->dithernoise == NULL)
144
	{
145
		fr->dithernoise = malloc(sizeof(float)*DITHERSIZE);
146
		if(fr->dithernoise == NULL) return 0;
147
 
148
		dither_table_init(fr->dithernoise);
149
	}
150
	return 1;
151
}
152
#endif
153
 
154
mpg123_pars attribute_align_arg *mpg123_new_pars(int *error)
155
{
156
	mpg123_pars *mp = malloc(sizeof(struct mpg123_pars_struct));
157
	if(mp != NULL){ frame_default_pars(mp); if(error != NULL) *error = MPG123_OK; }
158
	else if(error != NULL) *error = MPG123_OUT_OF_MEM;
159
	return mp;
160
}
161
 
162
void attribute_align_arg mpg123_delete_pars(mpg123_pars* mp)
163
{
164
	if(mp != NULL) free(mp);
165
}
166
 
167
int attribute_align_arg mpg123_reset_eq(mpg123_handle *mh)
168
{
169
	int i;
170
	mh->have_eq_settings = 0;
171
	for(i=0; i < 32; ++i) mh->equalizer[0][i] = mh->equalizer[1][i] = DOUBLE_TO_REAL(1.0);
172
 
173
	return MPG123_OK;
174
}
175
 
176
int frame_outbuffer(mpg123_handle *fr)
177
{
3960 Serge 178
	size_t size = fr->outblock;
179
	if(!fr->own_buffer)
1905 serge 180
	{
3960 Serge 181
		if(fr->buffer.size < size)
182
		{
183
			fr->err = MPG123_BAD_BUFFER;
184
			if(NOQUIET) error2("have external buffer of size %"SIZE_P", need %"SIZE_P, (size_p)fr->buffer.size, size);
185
 
186
			return MPG123_ERR;
187
		}
1905 serge 188
	}
3960 Serge 189
 
190
	debug1("need frame buffer of %"SIZE_P, (size_p)size);
191
	if(fr->buffer.rdata != NULL && fr->buffer.size != size)
192
	{
193
		free(fr->buffer.rdata);
194
		fr->buffer.rdata = NULL;
195
	}
1905 serge 196
	fr->buffer.size = size;
3960 Serge 197
	fr->buffer.data = NULL;
198
	/* be generous: use 16 byte alignment */
199
	if(fr->buffer.rdata == NULL) fr->buffer.rdata = (unsigned char*) malloc(fr->buffer.size+15);
200
	if(fr->buffer.rdata == NULL)
1905 serge 201
	{
202
		fr->err = MPG123_OUT_OF_MEM;
3960 Serge 203
		return MPG123_ERR;
1905 serge 204
	}
3960 Serge 205
	fr->buffer.data = aligned_pointer(fr->buffer.rdata, unsigned char*, 16);
1905 serge 206
	fr->own_buffer = TRUE;
207
	fr->buffer.fill = 0;
3960 Serge 208
	return MPG123_OK;
1905 serge 209
}
210
 
211
int attribute_align_arg mpg123_replace_buffer(mpg123_handle *mh, unsigned char *data, size_t size)
212
{
3960 Serge 213
	debug2("replace buffer with %p size %"SIZE_P, data, (size_p)size);
214
	/* Will accept any size, the error comes later... */
215
	if(data == NULL)
1905 serge 216
	{
217
		mh->err = MPG123_BAD_BUFFER;
218
		return MPG123_ERR;
219
	}
3960 Serge 220
	if(mh->buffer.rdata != NULL) free(mh->buffer.rdata);
1905 serge 221
	mh->own_buffer = FALSE;
3960 Serge 222
	mh->buffer.rdata = NULL;
1905 serge 223
	mh->buffer.data = data;
224
	mh->buffer.size = size;
225
	mh->buffer.fill = 0;
226
	return MPG123_OK;
227
}
228
 
229
#ifdef FRAME_INDEX
230
int frame_index_setup(mpg123_handle *fr)
231
{
232
	int ret = MPG123_ERR;
233
	if(fr->p.index_size >= 0)
234
	{ /* Simple fixed index. */
235
		fr->index.grow_size = 0;
236
		debug1("resizing index to %li", fr->p.index_size);
237
		ret = fi_resize(&fr->index, (size_t)fr->p.index_size);
238
		debug2("index resized... %lu at %p", (unsigned long)fr->index.size, (void*)fr->index.data);
239
	}
240
	else
241
	{ /* A growing index. We give it a start, though. */
242
		fr->index.grow_size = (size_t)(- fr->p.index_size);
243
		if(fr->index.size < fr->index.grow_size)
244
		ret = fi_resize(&fr->index, fr->index.grow_size);
245
		else
246
		ret = MPG123_OK; /* We have minimal size already... and since growing is OK... */
247
	}
248
	debug2("set up frame index of size %lu (ret=%i)", (unsigned long)fr->index.size, ret);
249
 
250
	return ret;
251
}
252
#endif
253
 
254
static void frame_decode_buffers_reset(mpg123_handle *fr)
255
{
256
	memset(fr->rawbuffs, 0, fr->rawbuffss);
257
}
258
 
259
int frame_buffers(mpg123_handle *fr)
260
{
261
	int buffssize = 0;
262
	debug1("frame %p buffer", (void*)fr);
263
/*
264
	the used-to-be-static buffer of the synth functions, has some subtly different types/sizes
265
 
266
	2to1, 4to1, ntom, generic, i386: real[2][2][0x110]
267
	mmx, sse: short[2][2][0x110]
268
	i586(_dither): 4352 bytes; int/long[2][2][0x110]
269
	i486: int[2][2][17*FIR_BUFFER_SIZE]
270
	altivec: static real __attribute__ ((aligned (16))) buffs[4][4][0x110]
271
 
272
	Huh, altivec looks like fun. Well, let it be large... then, the 16 byte alignment seems to be implicit on MacOSX malloc anyway.
273
	Let's make a reasonable attempt to allocate enough memory...
274
	Keep in mind: biggest ones are i486 and altivec (mutually exclusive!), then follows i586 and normal real.
275
	mmx/sse use short but also real for resampling.
276
	Thus, minimum is 2*2*0x110*sizeof(real).
277
*/
278
	if(fr->cpu_opts.type == altivec) buffssize = 4*4*0x110*sizeof(real);
279
#ifdef OPT_I486
280
	else if(fr->cpu_opts.type == ivier) buffssize = 2*2*17*FIR_BUFFER_SIZE*sizeof(int);
281
#endif
282
	else if(fr->cpu_opts.type == ifuenf || fr->cpu_opts.type == ifuenf_dither || fr->cpu_opts.type == dreidnow)
283
	buffssize = 2*2*0x110*4; /* don't rely on type real, we need 4352 bytes */
284
 
285
	if(2*2*0x110*sizeof(real) > buffssize)
286
	buffssize = 2*2*0x110*sizeof(real);
287
	buffssize += 15; /* For 16-byte alignment (SSE likes that). */
288
 
289
	if(fr->rawbuffs != NULL && fr->rawbuffss != buffssize)
290
	{
291
		free(fr->rawbuffs);
292
		fr->rawbuffs = NULL;
293
	}
294
 
295
	if(fr->rawbuffs == NULL) fr->rawbuffs = (unsigned char*) malloc(buffssize);
296
	if(fr->rawbuffs == NULL) return -1;
297
	fr->rawbuffss = buffssize;
298
	fr->short_buffs[0][0] = aligned_pointer(fr->rawbuffs,short,16);
299
	fr->short_buffs[0][1] = fr->short_buffs[0][0] + 0x110;
300
	fr->short_buffs[1][0] = fr->short_buffs[0][1] + 0x110;
301
	fr->short_buffs[1][1] = fr->short_buffs[1][0] + 0x110;
302
	fr->real_buffs[0][0] = aligned_pointer(fr->rawbuffs,real,16);
303
	fr->real_buffs[0][1] = fr->real_buffs[0][0] + 0x110;
304
	fr->real_buffs[1][0] = fr->real_buffs[0][1] + 0x110;
305
	fr->real_buffs[1][1] = fr->real_buffs[1][0] + 0x110;
306
#ifdef OPT_I486
307
	if(fr->cpu_opts.type == ivier)
308
	{
309
		fr->int_buffs[0][0] = (int*) fr->rawbuffs;
310
		fr->int_buffs[0][1] = fr->int_buffs[0][0] + 17*FIR_BUFFER_SIZE;
311
		fr->int_buffs[1][0] = fr->int_buffs[0][1] + 17*FIR_BUFFER_SIZE;
312
		fr->int_buffs[1][1] = fr->int_buffs[1][0] + 17*FIR_BUFFER_SIZE;
313
	}
314
#endif
315
#ifdef OPT_ALTIVEC
316
	if(fr->cpu_opts.type == altivec)
317
	{
318
		int i,j;
319
		fr->areal_buffs[0][0] = (real*) fr->rawbuffs;
320
		for(i=0; i<4; ++i) for(j=0; j<4; ++j)
321
		fr->areal_buffs[i][j] = fr->areal_buffs[0][0] + (i*4+j)*0x110;
322
	}
323
#endif
324
	/* now the different decwins... all of the same size, actually */
325
	/* The MMX ones want 32byte alignment, which I'll try to ensure manually */
326
	{
327
		int decwin_size = (512+32)*sizeof(real);
328
#ifdef OPT_MMXORSSE
329
#ifdef OPT_MULTI
330
		if(fr->cpu_opts.class == mmxsse)
331
		{
332
#endif
333
			/* decwin_mmx will share, decwins will be appended ... sizeof(float)==4 */
334
			if(decwin_size < (512+32)*4) decwin_size = (512+32)*4;
335
 
336
			/* the second window + alignment zone -- we align for 32 bytes for SSE as
337
			   requirement, 64 byte for matching cache line size (that matters!) */
338
			decwin_size += (512+32)*4 + 63;
339
			/* (512+32)*4/32 == 2176/32 == 68, so one decwin block retains alignment for 32 or 64 bytes */
340
#ifdef OPT_MULTI
341
		}
342
#endif
343
#endif
344
#if defined(OPT_ALTIVEC) || defined(OPT_ARM)
3960 Serge 345
		/* sizeof(real) >= 4 ... yes, it could be 8, for example.
346
		   We got it intialized to at least (512+32)*sizeof(real).*/
347
		decwin_size += 512*sizeof(real);
1905 serge 348
#endif
349
		/* Hm, that's basically realloc() ... */
350
		if(fr->rawdecwin != NULL && fr->rawdecwins != decwin_size)
351
		{
352
			free(fr->rawdecwin);
353
			fr->rawdecwin = NULL;
354
		}
355
 
356
		if(fr->rawdecwin == NULL)
357
		fr->rawdecwin = (unsigned char*) malloc(decwin_size);
358
 
359
		if(fr->rawdecwin == NULL) return -1;
360
 
361
		fr->rawdecwins = decwin_size;
362
		fr->decwin = (real*) fr->rawdecwin;
363
#ifdef OPT_MMXORSSE
364
#ifdef OPT_MULTI
365
		if(fr->cpu_opts.class == mmxsse)
366
		{
367
#endif
368
			/* align decwin, assign that to decwin_mmx, append decwins */
369
			/* I need to add to decwin what is missing to the next full 64 byte -- also I want to make gcc -pedantic happy... */
370
			fr->decwin = aligned_pointer(fr->rawdecwin,real,64);
371
			debug1("aligned decwin: %p", (void*)fr->decwin);
372
			fr->decwin_mmx = (float*)fr->decwin;
373
			fr->decwins = fr->decwin_mmx+512+32;
374
#ifdef OPT_MULTI
375
		}
376
		else debug("no decwins/decwin_mmx for that class");
377
#endif
378
#endif
379
	}
3960 Serge 380
 
381
	/* Layer scratch buffers are of compile-time fixed size, so allocate only once. */
382
	if(fr->layerscratch == NULL)
383
	{
384
		/* Allocate specific layer1/2/3 buffers, so that we know they'll work for SSE. */
385
		size_t scratchsize = 0;
386
		real *scratcher;
387
#ifndef NO_LAYER1
388
		scratchsize += sizeof(real) * 2 * SBLIMIT;
389
#endif
390
#ifndef NO_LAYER2
391
		scratchsize += sizeof(real) * 2 * 4 * SBLIMIT;
392
#endif
393
#ifndef NO_LAYER3
394
		scratchsize += sizeof(real) * 2 * SBLIMIT * SSLIMIT; /* hybrid_in */
395
		scratchsize += sizeof(real) * 2 * SSLIMIT * SBLIMIT; /* hybrid_out */
396
#endif
397
		/*
398
			Now figure out correct alignment:
399
			We need 16 byte minimum, smallest unit of the blocks is 2*SBLIMIT*sizeof(real), which is 64*4=256. Let's do 64bytes as heuristic for cache line (as proven useful in buffs above).
400
		*/
401
		fr->layerscratch = malloc(scratchsize+63);
402
		if(fr->layerscratch == NULL) return -1;
403
 
404
		/* Get aligned part of the memory, then divide it up. */
405
		scratcher = aligned_pointer(fr->layerscratch,real,64);
406
		/* Those funky pointer casts silence compilers...
407
		   One might change the code at hand to really just use 1D arrays, but in practice, that would not make a (positive) difference. */
408
#ifndef NO_LAYER1
409
		fr->layer1.fraction = (real(*)[SBLIMIT])scratcher;
410
		scratcher += 2 * SBLIMIT;
411
#endif
412
#ifndef NO_LAYER2
413
		fr->layer2.fraction = (real(*)[4][SBLIMIT])scratcher;
414
		scratcher += 2 * 4 * SBLIMIT;
415
#endif
416
#ifndef NO_LAYER3
417
		fr->layer3.hybrid_in = (real(*)[SBLIMIT][SSLIMIT])scratcher;
418
		scratcher += 2 * SBLIMIT * SSLIMIT;
419
		fr->layer3.hybrid_out = (real(*)[SSLIMIT][SBLIMIT])scratcher;
420
		scratcher += 2 * SSLIMIT * SBLIMIT;
421
#endif
422
		/* Note: These buffers don't need resetting here. */
423
	}
424
 
1905 serge 425
	/* Only reset the buffers we created just now. */
426
	frame_decode_buffers_reset(fr);
427
 
428
	debug1("frame %p buffer done", (void*)fr);
429
	return 0;
430
}
431
 
432
int frame_buffers_reset(mpg123_handle *fr)
433
{
434
	fr->buffer.fill = 0; /* hm, reset buffer fill... did we do a flush? */
435
	fr->bsnum = 0;
436
	/* Wondering: could it be actually _wanted_ to retain buffer contents over different files? (special gapless / cut stuff) */
437
	fr->bsbuf = fr->bsspace[1];
438
	fr->bsbufold = fr->bsbuf;
3960 Serge 439
	fr->bitreservoir = 0;
1905 serge 440
	frame_decode_buffers_reset(fr);
441
	memset(fr->bsspace, 0, 2*(MAXFRAMESIZE+512));
442
	memset(fr->ssave, 0, 34);
443
	fr->hybrid_blc[0] = fr->hybrid_blc[1] = 0;
444
	memset(fr->hybrid_block, 0, sizeof(real)*2*2*SBLIMIT*SSLIMIT);
445
	return 0;
446
}
447
 
3960 Serge 448
static void frame_icy_reset(mpg123_handle* fr)
1905 serge 449
{
450
#ifndef NO_ICY
451
	if(fr->icy.data != NULL) free(fr->icy.data);
452
	fr->icy.data = NULL;
453
	fr->icy.interval = 0;
454
	fr->icy.next = 0;
455
#endif
456
}
457
 
3960 Serge 458
static void frame_free_toc(mpg123_handle *fr)
1905 serge 459
{
460
	if(fr->xing_toc != NULL){ free(fr->xing_toc); fr->xing_toc = NULL; }
461
}
462
 
463
/* Just copy the Xing TOC over... */
464
int frame_fill_toc(mpg123_handle *fr, unsigned char* in)
465
{
466
	if(fr->xing_toc == NULL) fr->xing_toc = malloc(100);
467
	if(fr->xing_toc != NULL)
468
	{
469
		memcpy(fr->xing_toc, in, 100);
470
#ifdef DEBUG
471
		debug("Got a TOC! Showing the values...");
472
		{
473
			int i;
474
			for(i=0; i<100; ++i)
475
			debug2("entry %i = %i", i, fr->xing_toc[i]);
476
		}
477
#endif
478
		return TRUE;
479
	}
480
	return FALSE;
481
}
482
 
483
/* Prepare the handle for a new track.
484
   Reset variables, buffers... */
485
int frame_reset(mpg123_handle* fr)
486
{
487
	frame_buffers_reset(fr);
488
	frame_fixed_reset(fr);
489
	frame_free_toc(fr);
490
#ifdef FRAME_INDEX
491
	fi_reset(&fr->index);
492
#endif
493
 
494
	return 0;
495
}
496
 
497
/* Reset everythign except dynamic memory. */
498
static void frame_fixed_reset(mpg123_handle *fr)
499
{
500
	frame_icy_reset(fr);
501
	open_bad(fr);
502
	fr->to_decode = FALSE;
503
	fr->to_ignore = FALSE;
504
	fr->metaflags = 0;
3960 Serge 505
	fr->outblock = 0; /* This will be set before decoding! */
1905 serge 506
	fr->num = -1;
3960 Serge 507
	fr->input_offset = -1;
1905 serge 508
	fr->playnum = -1;
3960 Serge 509
	fr->state_flags = FRAME_ACCURATE;
1905 serge 510
	fr->silent_resync = 0;
511
	fr->audio_start = 0;
512
	fr->clip = 0;
513
	fr->oldhead = 0;
514
	fr->firsthead = 0;
515
	fr->vbr = MPG123_CBR;
516
	fr->abr_rate = 0;
517
	fr->track_frames = 0;
518
	fr->track_samples = -1;
519
	fr->framesize=0;
520
	fr->mean_frames = 0;
521
	fr->mean_framesize = 0;
522
	fr->freesize = 0;
523
	fr->lastscale = -1;
524
	fr->rva.level[0] = -1;
525
	fr->rva.level[1] = -1;
526
	fr->rva.gain[0] = 0;
527
	fr->rva.gain[1] = 0;
528
	fr->rva.peak[0] = 0;
529
	fr->rva.peak[1] = 0;
530
	fr->fsizeold = 0;
531
	fr->firstframe = 0;
532
	fr->ignoreframe = fr->firstframe-fr->p.preframes;
533
	fr->lastframe = -1;
534
	fr->fresh = 1;
535
	fr->new_format = 0;
536
#ifdef GAPLESS
3960 Serge 537
	frame_gapless_init(fr,-1,0,0);
1905 serge 538
	fr->lastoff = 0;
539
	fr->firstoff = 0;
540
#endif
541
#ifdef OPT_I486
542
	fr->i486bo[0] = fr->i486bo[1] = FIR_SIZE-1;
543
#endif
544
	fr->bo = 1; /* the usual bo */
545
#ifdef OPT_DITHER
546
	fr->ditherindex = 0;
547
#endif
548
	reset_id3(fr);
549
	reset_icy(&fr->icy);
550
	/* ICY stuff should go into icy.c, eh? */
551
#ifndef NO_ICY
552
	fr->icy.interval = 0;
553
	fr->icy.next = 0;
554
#endif
555
	fr->halfphase = 0; /* here or indeed only on first-time init? */
556
	fr->error_protection = 0;
557
	fr->freeformat_framesize = -1;
558
}
559
 
3960 Serge 560
static void frame_free_buffers(mpg123_handle *fr)
1905 serge 561
{
562
	if(fr->rawbuffs != NULL) free(fr->rawbuffs);
563
	fr->rawbuffs = NULL;
564
	fr->rawbuffss = 0;
565
	if(fr->rawdecwin != NULL) free(fr->rawdecwin);
566
	fr->rawdecwin = NULL;
567
	fr->rawdecwins = 0;
568
#ifndef NO_8BIT
569
	if(fr->conv16to8_buf != NULL) free(fr->conv16to8_buf);
570
	fr->conv16to8_buf = NULL;
571
#endif
3960 Serge 572
	if(fr->layerscratch != NULL) free(fr->layerscratch);
1905 serge 573
}
574
 
575
void frame_exit(mpg123_handle *fr)
576
{
3960 Serge 577
	if(fr->buffer.rdata != NULL)
1905 serge 578
	{
3960 Serge 579
		debug1("freeing buffer at %p", (void*)fr->buffer.rdata);
580
		free(fr->buffer.rdata);
1905 serge 581
	}
3960 Serge 582
	fr->buffer.rdata = NULL;
1905 serge 583
	frame_free_buffers(fr);
584
	frame_free_toc(fr);
585
#ifdef FRAME_INDEX
586
	fi_exit(&fr->index);
587
#endif
588
#ifdef OPT_DITHER
589
	if(fr->dithernoise != NULL)
590
	{
591
		free(fr->dithernoise);
592
		fr->dithernoise = NULL;
593
	}
594
#endif
595
	exit_id3(fr);
596
	clear_icy(&fr->icy);
3960 Serge 597
	/* Clean up possible mess from LFS wrapper. */
598
	if(fr->wrapperclean != NULL)
599
	{
600
		fr->wrapperclean(fr->wrapperdata);
601
		fr->wrapperdata = NULL;
602
	}
603
#ifndef NO_FEEDER
604
	bc_cleanup(&fr->rdat.buffer);
605
#endif
1905 serge 606
}
607
 
608
int attribute_align_arg mpg123_info(mpg123_handle *mh, struct mpg123_frameinfo *mi)
609
{
610
	if(mh == NULL) return MPG123_ERR;
611
	if(mi == NULL)
612
	{
613
		mh->err = MPG123_ERR_NULL;
614
		return MPG123_ERR;
615
	}
616
	mi->version = mh->mpeg25 ? MPG123_2_5 : (mh->lsf ? MPG123_2_0 : MPG123_1_0);
617
	mi->layer = mh->lay;
618
	mi->rate = frame_freq(mh);
619
	switch(mh->mode)
620
	{
621
		case 0: mi->mode = MPG123_M_STEREO; break;
622
		case 1: mi->mode = MPG123_M_JOINT;  break;
623
		case 2: mi->mode = MPG123_M_DUAL;   break;
624
		case 3: mi->mode = MPG123_M_MONO;   break;
625
		default: error("That mode cannot be!");
626
	}
627
	mi->mode_ext = mh->mode_ext;
628
	mi->framesize = mh->framesize+4; /* Include header. */
629
	mi->flags = 0;
630
	if(mh->error_protection) mi->flags |= MPG123_CRC;
631
	if(mh->copyright)        mi->flags |= MPG123_COPYRIGHT;
632
	if(mh->extension)        mi->flags |= MPG123_PRIVATE;
633
	if(mh->original)         mi->flags |= MPG123_ORIGINAL;
634
	mi->emphasis = mh->emphasis;
635
	mi->bitrate  = frame_bitrate(mh);
636
	mi->abr_rate = mh->abr_rate;
637
	mi->vbr = mh->vbr;
638
	return MPG123_OK;
639
}
640
 
3960 Serge 641
int attribute_align_arg mpg123_framedata(mpg123_handle *mh, unsigned long *header, unsigned char **bodydata, size_t *bodybytes)
642
{
643
	if(mh == NULL)     return MPG123_ERR;
644
	if(!mh->to_decode) return MPG123_ERR;
1905 serge 645
 
3960 Serge 646
	if(header    != NULL) *header    = mh->oldhead;
647
	if(bodydata  != NULL) *bodydata  = mh->bsbuf;
648
	if(bodybytes != NULL) *bodybytes = mh->framesize;
649
 
650
	return MPG123_OK;
651
}
652
 
1905 serge 653
/*
654
	Fuzzy frame offset searching (guessing).
655
	When we don't have an accurate position, we may use an inaccurate one.
656
	Possibilities:
657
		- use approximate positions from Xing TOC (not yet parsed)
658
		- guess wildly from mean framesize and offset of first frame / beginning of file.
659
*/
660
 
3960 Serge 661
static off_t frame_fuzzy_find(mpg123_handle *fr, off_t want_frame, off_t* get_frame)
1905 serge 662
{
663
	/* Default is to go to the beginning. */
664
	off_t ret = fr->audio_start;
665
	*get_frame = 0;
666
 
667
	/* But we try to find something better. */
668
	/* Xing VBR TOC works with relative positions, both in terms of audio frames and stream bytes.
669
	   Thus, it only works when whe know the length of things.
670
	   Oh... I assume the offsets are relative to the _total_ file length. */
671
	if(fr->xing_toc != NULL && fr->track_frames > 0 && fr->rdat.filelen > 0)
672
	{
673
		/* One could round... */
674
		int toc_entry = (int) ((double)want_frame*100./fr->track_frames);
675
		/* It is an index in the 100-entry table. */
676
		if(toc_entry < 0)  toc_entry = 0;
677
		if(toc_entry > 99) toc_entry = 99;
678
 
679
		/* Now estimate back what frame we get. */
680
		*get_frame = (off_t) ((double)toc_entry/100. * fr->track_frames);
3960 Serge 681
		fr->state_flags &= ~FRAME_ACCURATE;
1905 serge 682
		fr->silent_resync = 1;
683
		/* Question: Is the TOC for whole file size (with/without ID3) or the "real" audio data only?
684
		   ID3v1 info could also matter. */
685
		ret = (off_t) ((double)fr->xing_toc[toc_entry]/256.* fr->rdat.filelen);
686
	}
687
	else if(fr->mean_framesize > 0)
688
	{	/* Just guess with mean framesize (may be exact with CBR files). */
689
		/* Query filelen here or not? */
3960 Serge 690
		fr->state_flags &= ~FRAME_ACCURATE; /* Fuzzy! */
1905 serge 691
		fr->silent_resync = 1;
692
		*get_frame = want_frame;
693
		ret = (off_t) (fr->audio_start+fr->mean_framesize*want_frame);
694
	}
695
	debug5("fuzzy: want %li of %li, get %li at %li B of %li B",
696
		(long)want_frame, (long)fr->track_frames, (long)*get_frame, (long)ret, (long)(fr->rdat.filelen-fr->audio_start));
697
	return ret;
698
}
699
 
700
/*
701
	find the best frame in index just before the wanted one, seek to there
702
	then step to just before wanted one with read_frame
703
	do not care tabout the stuff that was in buffer but not played back
704
	everything that left the decoder is counted as played
705
 
706
	Decide if you want low latency reaction and accurate timing info or stable long-time playback with buffer!
707
*/
708
 
709
off_t frame_index_find(mpg123_handle *fr, off_t want_frame, off_t* get_frame)
710
{
711
	/* default is file start if no index position */
712
	off_t gopos = 0;
713
	*get_frame = 0;
714
#ifdef FRAME_INDEX
715
	/* Possibly use VBRI index, too? I'd need an example for this... */
716
	if(fr->index.fill)
717
	{
718
		/* find in index */
719
		size_t fi;
720
		/* at index fi there is frame step*fi... */
721
		fi = want_frame/fr->index.step;
722
		if(fi >= fr->index.fill) /* If we are beyond the end of frame index...*/
723
		{
724
			/* When fuzzy seek is allowed, we have some limited tolerance for the frames we want to read rather then jump over. */
725
			if(fr->p.flags & MPG123_FUZZY && want_frame - (fr->index.fill-1)*fr->index.step > 10)
726
			{
727
				gopos = frame_fuzzy_find(fr, want_frame, get_frame);
728
				if(gopos > fr->audio_start) return gopos; /* Only in that case, we have a useful guess. */
729
				/* Else... just continue, fuzzyness didn't help. */
730
			}
731
			/* Use the last available position, slowly advancing from that one. */
732
			fi = fr->index.fill - 1;
733
		}
734
		/* We have index position, that yields frame and byte offsets. */
735
		*get_frame = fi*fr->index.step;
736
		gopos = fr->index.data[fi];
3960 Serge 737
		fr->state_flags |= FRAME_ACCURATE; /* When using the frame index, we are accurate. */
1905 serge 738
	}
739
	else
740
	{
741
#endif
742
		if(fr->p.flags & MPG123_FUZZY)
743
		return frame_fuzzy_find(fr, want_frame, get_frame);
744
		/* A bit hackish here... but we need to be fresh when looking for the first header again. */
745
		fr->firsthead = 0;
746
		fr->oldhead = 0;
747
#ifdef FRAME_INDEX
748
	}
749
#endif
750
	debug2("index: 0x%lx for frame %li", (unsigned long)gopos, (long) *get_frame);
751
	return gopos;
752
}
753
 
754
off_t frame_ins2outs(mpg123_handle *fr, off_t ins)
755
{
756
	off_t outs = 0;
757
	switch(fr->down_sample)
758
	{
759
		case 0:
760
#		ifndef NO_DOWNSAMPLE
761
		case 1:
762
		case 2:
763
#		endif
764
			outs = ins>>fr->down_sample;
765
		break;
766
#		ifndef NO_NTOM
767
		case 3: outs = ntom_ins2outs(fr, ins); break;
768
#		endif
769
		default: error1("Bad down_sample (%i) ... should not be possible!!", fr->down_sample);
770
	}
771
	return outs;
772
}
773
 
774
off_t frame_outs(mpg123_handle *fr, off_t num)
775
{
776
	off_t outs = 0;
777
	switch(fr->down_sample)
778
	{
779
		case 0:
780
#		ifndef NO_DOWNSAMPLE
781
		case 1:
782
		case 2:
783
#		endif
784
			outs = (spf(fr)>>fr->down_sample)*num;
785
		break;
786
#ifndef NO_NTOM
787
		case 3: outs = ntom_frmouts(fr, num); break;
788
#endif
789
		default: error1("Bad down_sample (%i) ... should not be possible!!", fr->down_sample);
790
	}
791
	return outs;
792
}
793
 
3960 Serge 794
/* Compute the number of output samples we expect from this frame.
795
   This is either simple spf() or a tad more elaborate for ntom. */
796
off_t frame_expect_outsamples(mpg123_handle *fr)
797
{
798
	off_t outs = 0;
799
	switch(fr->down_sample)
800
	{
801
		case 0:
802
#		ifndef NO_DOWNSAMPLE
803
		case 1:
804
		case 2:
805
#		endif
806
			outs = spf(fr)>>fr->down_sample;
807
		break;
808
#ifndef NO_NTOM
809
		case 3: outs = ntom_frame_outsamples(fr); break;
810
#endif
811
		default: error1("Bad down_sample (%i) ... should not be possible!!", fr->down_sample);
812
	}
813
	return outs;
814
}
815
 
1905 serge 816
off_t frame_offset(mpg123_handle *fr, off_t outs)
817
{
818
	off_t num = 0;
819
	switch(fr->down_sample)
820
	{
821
		case 0:
822
#		ifndef NO_DOWNSAMPLE
823
		case 1:
824
		case 2:
825
#		endif
826
			num = outs/(spf(fr)>>fr->down_sample);
827
		break;
828
#ifndef NO_NTOM
829
		case 3: num = ntom_frameoff(fr, outs); break;
830
#endif
831
		default: error("Bad down_sample ... should not be possible!!");
832
	}
833
	return num;
834
}
835
 
836
#ifdef GAPLESS
837
/* input in _input_ samples */
3960 Serge 838
void frame_gapless_init(mpg123_handle *fr, off_t framecount, off_t bskip, off_t eskip)
1905 serge 839
{
3960 Serge 840
	debug3("frame_gaples_init: given %"OFF_P" frames, skip %"OFF_P" and %"OFF_P, (off_p)framecount, (off_p)bskip, (off_p)eskip);
841
	fr->gapless_frames = framecount;
842
	if(fr->gapless_frames > 0)
843
	{
844
		fr->begin_s = bskip+GAPLESS_DELAY;
845
		fr->end_s = framecount*spf(fr)-eskip+GAPLESS_DELAY;
846
	}
847
	else fr->begin_s = fr->end_s = 0;
1905 serge 848
	/* These will get proper values later, from above plus resampling info. */
849
	fr->begin_os = 0;
850
	fr->end_os = 0;
3960 Serge 851
	fr->fullend_os = 0;
852
	debug2("frame_gapless_init: from %"OFF_P" to %"OFF_P" samples", (off_p)fr->begin_s, (off_p)fr->end_s);
1905 serge 853
}
854
 
855
void frame_gapless_realinit(mpg123_handle *fr)
856
{
857
	fr->begin_os = frame_ins2outs(fr, fr->begin_s);
858
	fr->end_os   = frame_ins2outs(fr, fr->end_s);
3960 Serge 859
	fr->fullend_os = frame_ins2outs(fr, fr->gapless_frames*spf(fr));
860
	debug2("frame_gapless_realinit: from %"OFF_P" to %"OFF_P" samples", (off_p)fr->begin_os, (off_p)fr->end_os);
1905 serge 861
}
862
 
3960 Serge 863
/* At least note when there is trouble... */
1905 serge 864
void frame_gapless_update(mpg123_handle *fr, off_t total_samples)
865
{
3960 Serge 866
	off_t gapless_samples = fr->gapless_frames*spf(fr);
867
	debug2("gapless update with new sample count %"OFF_P" as opposed to known %"OFF_P, total_samples, gapless_samples);
868
	if(NOQUIET && total_samples != gapless_samples)
869
	fprintf(stderr, "\nWarning: Real sample count differs from given gapless sample count. Frankenstein stream?\n");
870
 
871
	if(gapless_samples > total_samples)
1905 serge 872
	{
3960 Serge 873
		if(NOQUIET) error2("End sample count smaller than gapless end! (%"OFF_P" < %"OFF_P"). Disabling gapless mode from now on.", (off_p)total_samples, (off_p)fr->end_s);
874
		/* This invalidates the current position... but what should I do? */
875
		frame_gapless_init(fr, -1, 0, 0);
1905 serge 876
		frame_gapless_realinit(fr);
3960 Serge 877
		fr->lastframe = -1;
878
		fr->lastoff = 0;
1905 serge 879
	}
880
}
881
 
882
#endif
883
 
884
/* Compute the needed frame to ignore from, for getting accurate/consistent output for intended firstframe. */
885
static off_t ignoreframe(mpg123_handle *fr)
886
{
887
	off_t preshift = fr->p.preframes;
888
	/* Layer 3 _really_ needs at least one frame before. */
889
	if(fr->lay==3 && preshift < 1) preshift = 1;
890
	/* Layer 1 & 2 reall do not need more than 2. */
891
	if(fr->lay!=3 && preshift > 2) preshift = 2;
892
 
893
	return fr->firstframe - preshift;
894
}
895
 
896
/* The frame seek... This is not simply the seek to fe*spf(fr) samples in output because we think of _input_ frames here.
897
   Seek to frame offset 1 may be just seek to 200 samples offset in output since the beginning of first frame is delay/padding.
898
   Hm, is that right? OK for the padding stuff, but actually, should the decoder delay be better totally hidden or not?
899
   With gapless, even the whole frame position could be advanced further than requested (since Homey don't play dat). */
900
void frame_set_frameseek(mpg123_handle *fr, off_t fe)
901
{
902
	fr->firstframe = fe;
903
#ifdef GAPLESS
3960 Serge 904
	if(fr->p.flags & MPG123_GAPLESS && fr->gapless_frames > 0)
1905 serge 905
	{
906
		/* Take care of the beginning... */
907
		off_t beg_f = frame_offset(fr, fr->begin_os);
908
		if(fe <= beg_f)
909
		{
910
			fr->firstframe = beg_f;
911
			fr->firstoff   = fr->begin_os - frame_outs(fr, beg_f);
912
		}
913
		else fr->firstoff = 0;
914
		/* The end is set once for a track at least, on the frame_set_frameseek called in get_next_frame() */
915
		if(fr->end_os > 0)
916
		{
917
			fr->lastframe  = frame_offset(fr,fr->end_os);
918
			fr->lastoff    = fr->end_os - frame_outs(fr, fr->lastframe);
3960 Serge 919
		} else {fr->lastframe = -1; fr->lastoff = 0; }
1905 serge 920
	} else { fr->firstoff = fr->lastoff = 0; fr->lastframe = -1; }
921
#endif
922
	fr->ignoreframe = ignoreframe(fr);
923
#ifdef GAPLESS
924
	debug5("frame_set_frameseek: begin at %li frames and %li samples, end at %li and %li; ignore from %li",
925
	       (long) fr->firstframe, (long) fr->firstoff,
926
	       (long) fr->lastframe,  (long) fr->lastoff, (long) fr->ignoreframe);
927
#else
928
	debug3("frame_set_frameseek: begin at %li frames, end at %li; ignore from %li",
929
	       (long) fr->firstframe, (long) fr->lastframe, (long) fr->ignoreframe);
930
#endif
931
}
932
 
933
void frame_skip(mpg123_handle *fr)
934
{
935
#ifndef NO_LAYER3
936
	if(fr->lay == 3) set_pointer(fr, 512);
937
#endif
938
}
939
 
940
/* Sample accurate seek prepare for decoder. */
941
/* This gets unadjusted output samples and takes resampling into account */
942
void frame_set_seek(mpg123_handle *fr, off_t sp)
943
{
944
	fr->firstframe = frame_offset(fr, sp);
3960 Serge 945
	debug1("frame_set_seek: from %"OFF_P, fr->num);
1905 serge 946
#ifndef NO_NTOM
947
	if(fr->down_sample == 3) ntom_set_ntom(fr, fr->firstframe);
948
#endif
949
	fr->ignoreframe = ignoreframe(fr);
950
#ifdef GAPLESS /* The sample offset is used for non-gapless mode, too! */
951
	fr->firstoff = sp - frame_outs(fr, fr->firstframe);
952
	debug5("frame_set_seek: begin at %li frames and %li samples, end at %li and %li; ignore from %li",
953
	       (long) fr->firstframe, (long) fr->firstoff,
954
	       (long) fr->lastframe,  (long) fr->lastoff, (long) fr->ignoreframe);
955
#else
956
	debug3("frame_set_seek: begin at %li frames, end at %li; ignore from %li",
957
	       (long) fr->firstframe, (long) fr->lastframe, (long) fr->ignoreframe);
958
#endif
959
}
960
 
961
int attribute_align_arg mpg123_volume_change(mpg123_handle *mh, double change)
962
{
963
	if(mh == NULL) return MPG123_ERR;
964
	return mpg123_volume(mh, change + (double) mh->p.outscale);
965
}
966
 
967
int attribute_align_arg mpg123_volume(mpg123_handle *mh, double vol)
968
{
969
	if(mh == NULL) return MPG123_ERR;
970
 
971
	if(vol >= 0) mh->p.outscale = vol;
972
	else mh->p.outscale = 0.;
973
 
974
	do_rva(mh);
975
	return MPG123_OK;
976
}
977
 
978
static int get_rva(mpg123_handle *fr, double *peak, double *gain)
979
{
980
	double p = -1;
981
	double g = 0;
982
	int ret = 0;
983
	if(fr->p.rva)
984
	{
985
		int rt = 0;
986
		/* Should one assume a zero RVA as no RVA? */
987
		if(fr->p.rva == 2 && fr->rva.level[1] != -1) rt = 1;
988
		if(fr->rva.level[rt] != -1)
989
		{
990
			p = fr->rva.peak[rt];
991
			g = fr->rva.gain[rt];
992
			ret = 1; /* Success. */
993
		}
994
	}
995
	if(peak != NULL) *peak = p;
996
	if(gain != NULL) *gain = g;
997
	return ret;
998
}
999
 
1000
/* adjust the volume, taking both fr->outscale and rva values into account */
1001
void do_rva(mpg123_handle *fr)
1002
{
1003
	double peak = 0;
1004
	double gain = 0;
1005
	double newscale;
1006
	double rvafact = 1;
1007
	if(get_rva(fr, &peak, &gain))
1008
	{
1009
		if(NOQUIET && fr->p.verbose > 1) fprintf(stderr, "Note: doing RVA with gain %f\n", gain);
1010
		rvafact = pow(10,gain/20);
1011
	}
1012
 
1013
	newscale = fr->p.outscale*rvafact;
1014
 
1015
	/* if peak is unknown (== 0) this check won't hurt */
1016
	if((peak*newscale) > 1.0)
1017
	{
1018
		newscale = 1.0/peak;
1019
		warning2("limiting scale value to %f to prevent clipping with indicated peak factor of %f", newscale, peak);
1020
	}
1021
	/* first rva setting is forced with fr->lastscale < 0 */
1022
	if(newscale != fr->lastscale || fr->decoder_change)
1023
	{
1024
		debug3("changing scale value from %f to %f (peak estimated to %f)", fr->lastscale != -1 ? fr->lastscale : fr->p.outscale, newscale, (double) (newscale*peak));
1025
		fr->lastscale = newscale;
1026
		/* It may be too early, actually. */
1027
		if(fr->make_decode_tables != NULL) fr->make_decode_tables(fr); /* the actual work */
1028
	}
1029
}
1030
 
1031
 
1032
int attribute_align_arg mpg123_getvolume(mpg123_handle *mh, double *base, double *really, double *rva_db)
1033
{
1034
	if(mh == NULL) return MPG123_ERR;
1035
	if(base)   *base   = mh->p.outscale;
1036
	if(really) *really = mh->lastscale;
1037
	get_rva(mh, NULL, rva_db);
1038
	return MPG123_OK;
1039
}
1040
 
3960 Serge 1041
off_t attribute_align_arg mpg123_framepos(mpg123_handle *mh)
1042
{
1043
	if(mh == NULL) return MPG123_ERR;
1044
 
1045
	return mh->input_offset;
1046
}