Skip to content

SuperLAME 1.1.0

Latest

Choose a tag to compare

@MSIVST MSIVST released this 12 Jul 19:08

SuperLAME 1.1.0

Multithreaded encoding is 1.8–1.9x faster at every thread count, a new
--bench mode gives honest, LAME-comparable timing numbers, and a
fuzzer-found FLAC robustness hole is closed. Frontend-only changes — the four
engine libraries (znver5/znver4/znver3/SSE2) are identical to the v1.0.1
build, and encoded output is byte-identical to v1.0.3 in every
configuration.

Faster multithreading (condition-variable handoffs)

Every dispatcher↔worker handoff used to wait in a 1 ms sleep-poll loop; on
Windows that sleep rounds up to the ~15.6 ms scheduler tick, taxing each of
the thousands of chunk handoffs. All six polling loops are now
condition-variable event waits (microsecond wakeups). Measured on a Ryzen 7
5800X3D encoding a 44-minute album at CBR 320:

Threads v1.0.3 v1.1.0 Speedup
2 24.3 s 13.8 s 1.76x
4 12.8 s 7.1 s 1.80x
8 9.8 s 5.1 s 1.93x
16 7.2 s 3.9 s 1.87x

New: --bench[=N]

Encode fully in RAM, write nothing (give an output file anyway to keep the
result), and get numbers you can actually compare:

bench: stages  read=0.30s  resample=0.00s  encode=4.20s  total=4.50s
bench: frames=100920 wall=4.20 cpu=38.30 play/wall=628x play/cpu=68.8x kbps=320 threads=16 engine=znver3 par-eff=9.1x/16t (57%)
  • play/wall — honest multithreaded throughput
  • play/cpu — per-core figure, directly comparable to stock LAME's "x"
  • par-eff — parallel efficiency (cpu/wall vs thread count)
  • --bench=N repeats the encode on the in-RAM audio and reports wall
    min/median/mean (run 1 is warmup, discarded)
  • Works from a pipe; read time is labeled n/a (pipe) because that stage
    would measure the upstream producer (e.g. FFmpeg), not the encoder

FLAC input hardening

A corrupt STREAMINFO header claiming billions of samples could demand a
multi-gigabyte allocation from a kilobyte-sized file (found by fuzzing; the
process thrashed instead of erroring — present in all prior releases).
Sample counts implausible for the file size (>512x — real FLAC maxes out
near ~420 samples/byte on pure silence) are now treated as unknown length
and decoded by the streaming path, which sizes buffers by what actually
decodes. Input fuzzer: 920/920 clean.

Docs

docs/FFMPEG-NOTES.md collects verified FFmpeg interop quirks. The one that
will bite you: ffmpeg ... -f wav - silently downconverts 24-bit/float
sources to 16-bit unless you pin -c:a pcm_s24le / -c:a pcm_f32le.

Validation

  • Regression suite 42/42 (35 existing + 7 new --bench checks)
  • SQAM: 350 encodes (70 tracks x 5 modes), 0 desyncs
  • ODAQ: 132 encodes, worst ST-vs-MT diff −59.2 dB, FLAC==WAV input
  • Input fuzzer: 920 malformed/truncated/random files, 0 crashes/hangs
  • FFmpeg interop: pipe==file byte-identity across 16/24-bit, float, mono,
    hi-res resample, stdout chains and 3-stage round trips

SHA-256 (SuperLAME-1.1.0.exe):
20bcbbaa9b96b7d135ba04460c62755d140484310c85db23993638035891b8b3