MoiN
I found some _really_ weird error encoding files at specific
samplingrates (16, 24, 32 and 48kHz). I found the padding bit set
for every frame but that frame did contain as many bits as it
would without the padding bit set. Everything else was fine,
though.
I compiled lame 3.66beta with gcc 2.95.2 with the options enabled
that are suggested in the Makefile:
# these options for gcc-2.95.2 to produce fast code
# CC_OPTS = $(FEATURES)\
# -Wall -O9 -fomit-frame-pointer -march=pentium \
# -finline-functions -fexpensive-optimizations \
# -ffast-math -malign-double -mfancy-math-387 \
# -funroll-loops -funroll-all-loops -pipe -fschedule-insns2 \
# -fno-strength-reduce
Then I encoded some ripped data with
lame -h --resample 16 cdda.wav output.mp3
I was not able to listen to the output, mpg123 produces a nice
bubbling sound and a whole bunch of missing frame headers and
skips.
Then I tried compiling lame without the switch "-ffast-math" and
encoding the file again. I compared the output with "cmp -l" and
got:
3 212 210
291 212 210
579 212 210
867 212 210
...
569229 212 210
As you can see the only difference is in the header!?
With the invocation of lame as given above, avg_slots_per_frame
is calculated in "lame.c", line 637, with the following
parameters set:
bit_rate = 64; gfp->framesize = 576; sampfreq = 16; bitsPerSlot = 8;
=> (64 * 576) / (16 * 8) = ? 288 ?
But with "-ffast-math" the result is not 288 but ca. 288 - 5e-15.
So the next instruction sets frac_SpF = 1 which causes the
padding flag set for all frames. But why is the block doesn't the
block size differ?
The block size is calculated in "util.c", line 63, with the same
formula. So it is calculated one byte to small, too.
Here is the patch against lame 3.66beta. Some parts (the floor()
calls) are already in CVS but they don't suffice to solve the
problem. Thanks to Mark who point me to the changes he already
did in CVS.
--- lame-3.66beta.orig/lame.c
+++ lame-3.66beta/lame.c
@@ -636,10 +636,11 @@
bitsPerSlot = 8;
avg_slots_per_frame = (bit_rate*gfp->framesize) /
(sampfreq* bitsPerSlot);
- frac_SpF = avg_slots_per_frame - (int) avg_slots_per_frame;
+ frac_SpF = avg_slots_per_frame - floor(avg_slots_per_frame + 1e-9);
+ if (fabs(frac_SpF) < 1e-9) frac_SpF = 0;
slot_lag = -frac_SpF;
gfp->padding = 1;
- if (fabs(frac_SpF) < 1e-9) gfp->padding = 0;
+ if (frac_SpF == 0) gfp->padding = 0;
/* check FFT will not use a negative starting offset */
assert(576>=FFTOFFSET);
--- lame-3.66beta.orig/util.c
+++ lame-3.66beta/util.c
@@ -60,7 +60,7 @@
if (gfp->error_protection) sideinfo_len += 16;
- whole_SpF = (gfp->framesize /samp)*(bit_rate / (FLOAT8)bitsPerSlot);
+ whole_SpF = floor( (gfp->framesize /samp)*(bit_rate / (FLOAT8)bitsPerSlot) + 1e-9);
*bitsPerFrame = 8 * whole_SpF + (gfp->padding * 8);
*mean_bits = (*bitsPerFrame - sideinfo_len) / gfp->mode_gr;
}
Ingo
--
Windows, me?
--
MP3 ENCODER mailing list ( http://geek.rcc.se/mp3encoder/ )