From 95ac6071b9fdaa543bd0c8ab7665d262db708683 Mon Sep 17 00:00:00 2001 From: Marcello Desantis Date: Wed, 9 Apr 2014 23:58:56 +0200 Subject: [PATCH] decoder/sndfile: work around libsndfile bug on partial read --- NEWS | 1 + src/decoder/SndfileDecoderPlugin.cxx | 26 ++++++++++++++++++++------ 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/NEWS b/NEWS index 3ab9a5b67..0c30b5eda 100644 --- a/NEWS +++ b/NEWS @@ -3,6 +3,7 @@ ver 0.18.10 (not yet released) - ffmpeg: fix seeking bug - ffmpeg: handle unknown stream start time - gme: fix memory leak + - sndfile: work around libsndfile bug on partial read * don't interrupt playback when current song gets deleted ver 0.18.9 (2014/03/02) diff --git a/src/decoder/SndfileDecoderPlugin.cxx b/src/decoder/SndfileDecoderPlugin.cxx index 3360cd1bf..77b132962 100644 --- a/src/decoder/SndfileDecoderPlugin.cxx +++ b/src/decoder/SndfileDecoderPlugin.cxx @@ -55,14 +55,28 @@ sndfile_vio_read(void *ptr, sf_count_t count, void *user_data) { InputStream &is = *(InputStream *)user_data; + sf_count_t total_bytes = 0; Error error; - size_t nbytes = is.LockRead(ptr, count, error); - if (nbytes == 0 && error.IsDefined()) { - LogError(error); - return -1; - } - return nbytes; + /* this loop is necessary because libsndfile chokes on partial + reads */ + + do { + size_t nbytes = is.LockRead((char *)ptr + total_bytes, + count - total_bytes, error); + if (nbytes == 0) { + if (error.IsDefined()) { + LogError(error); + return -1; + } + + break; + } + + total_bytes += nbytes; + } while (total_bytes < count); + + return total_bytes; } static sf_count_t