VIDEO: Wrap out-of-range VMD audio samples instead of clipping

The 16-bit DPCM decompressors in SSCI and Urban Runner use a 16-bit
register to store sample data, without any special handling of
overflow. As such, out-of-range samples simply wrap around, rather
than getting clipped.

It is not totally clear if the wrapping behaviour was intentionally
exploited to handle extreme transients, but in any case, videos
like GK2 5280.VMD that generate samples outside the signed 16-bit
range cause a loud pop when using clipping, but play back correctly
when wrapping.
This commit is contained in:
Colin Snover 2017-06-16 20:04:46 -05:00
parent 12afcaec49
commit 0d63d2a7ad

View File

@ -2617,7 +2617,14 @@ int DPCMStream::readBuffer(int16 *buffer, const int numSamples) {
else
_buffer[i] += tableDPCM[data];
*buffer++ = _buffer[i] = CLIP<int32>(_buffer[i], -32768, 32767);
// Emulating x86 16-bit signed register overflow
if (_buffer[i] > 32767) {
_buffer[i] -= 65536;
} else if (_buffer[i] < -32768) {
_buffer[i] += 65536;
}
*buffer++ = _buffer[i];
}
samples += _channels;