FS#12485 - Seeking in .ape file doesn't work

Attached to Project: Rockbox
Opened by Ophir Lojkine (lovasoa) - Sunday, 25 December 2011, 21:25 GMT
Last edited by Boris Gjenero (dreamlayers) - Wednesday, 28 December 2011, 16:57 GMT
Task Type Bugs
Category Codecs
Status Unconfirmed
Assigned To No-one
Operating System SW-codec
Severity Low
Priority Normal
Reported Version Release 3.10
Due in Version Undecided
Due Date Undecided
Percent Complete 0%
Votes 0
Private No


The .ape file I join make rockbox produce a horrible noise (like random audio) when seeking inside it. The original file was very large, so I created this one with:
dd if=original.ape of=test.ape bs=512 count=1000
So the produced file may not be correct, but it plays correctly in rockbox, and reproduces the bug, so I join it...
   test.ape (500 KiB)
This task depends upon

Comment by Boris Gjenero (dreamlayers) - Wednesday, 28 December 2011, 17:46 GMT
I see that ape.c does not check for end of file. It does not check the return value of ci->seek_buffer() or ci->request_buffer(), and it doesn't check bytesleft from ci->request_buffer(). This explains what happens when seeking past end of file in test.ape. It can even lead to crashes, eg.
at apps/codecs/demac/libdemac/entropy.c:176
176 rc.buffer = (rc.buffer << 8) | read_byte();

I also see that even seeks to valid positions within test.ape lead to noise. These lines in codec_run() change the return value of ape_calc_seekpos() and cause the problem:
/* APE's bytestream is weird... */
firstbyte = 3 - (newfilepos & 3);
newfilepos &= ~3;
For example, frame 0 can be decoded with firstbyte = 3 (as set before the start of playback) and newfilepos = 2570 (that equals ci->curpos at start of playback and ape_ctx->seektable[0]). However, seeking works on other APE files, so more investigation is needed.