From c275891a77cc424bf70d13324135d7cdf27c4e52 Mon Sep 17 00:00:00 2001 From: manuaudio Date: Fri, 14 Aug 2026 23:23:59 -0700 Subject: [PATCH] DSDIFF: do not convert an out of range length to int Same shape as the DSF change: sampleCount comes from a chunk size in the file and sampleRate is read from it, so static_cast(static_cast(d->sampleCount) * 1000.0 / d->sampleRate + 0.5) can be handed a value int cannot represent, which is undefined. In the PR I said I had not demonstrated this one, because chunkFits bounds the sample count by the file length so a few mutated bytes will not do it. Constructing the file it does need - a 700 kB DSD chunk with a sample rate of 1 - reaches it: taglib/dsdiff/dsdiffproperties.cpp:61:24: runtime error: 2.8e+09 is outside the range of representable values of type 'int' Two reports before the change, none after. tests/data/empty10ms.dff is unchanged at lengthMs=10 bitrate=5644 rate=2822400 ch=2. Assisted-By: Claude Code (Claude Opus 5) --- taglib/dsdiff/dsdiffproperties.cpp | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/taglib/dsdiff/dsdiffproperties.cpp b/taglib/dsdiff/dsdiffproperties.cpp index e0785c60..37e4d2b5 100644 --- a/taglib/dsdiff/dsdiffproperties.cpp +++ b/taglib/dsdiff/dsdiffproperties.cpp @@ -25,6 +25,8 @@ #include "dsdiffproperties.h" +#include + #include "tstring.h" using namespace TagLib; @@ -57,9 +59,17 @@ DSDIFF::Properties::Properties(unsigned int sampleRate, d->sampleWidth = 1; d->sampleRate = sampleRate; d->bitrate = bitrate; - d->length = d->sampleRate > 0 - ? static_cast(static_cast(d->sampleCount) * 1000.0 / d->sampleRate + 0.5) - : 0; + // sampleCount is derived from a chunk size in the file and sampleRate is read from + // it, so the millisecond count can land outside int, and converting a double the + // destination type cannot represent is undefined. Report an unknown length instead, + // which is what a zero sample rate already does. + d->length = 0; + if(d->sampleRate > 0 && d->sampleCount > 0) { + const double milliseconds = + static_cast(d->sampleCount) * 1000.0 / d->sampleRate + 0.5; + if(milliseconds < static_cast(std::numeric_limits::max())) + d->length = static_cast(milliseconds); + } } DSDIFF::Properties::~Properties() = default;