| Summary: | Audio buffer may contain more frames than decoded. | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|
| Product: | WebKit | Reporter: | Jean-Yves Avenard [:jya] <jean-yves.avenard> | ||||||||
| Component: | Web Audio | Assignee: | Jean-Yves Avenard [:jya] <jean-yves.avenard> | ||||||||
| Status: | RESOLVED FIXED | ||||||||||
| Severity: | Normal | CC: | cdumez, eric.carlson, ews-watchlist, glenn, jer.noble, philipj, rniwa, sergio, webkit-bug-importer | ||||||||
| Priority: | P2 | Keywords: | InRadar | ||||||||
| Version: | WebKit Nightly Build | ||||||||||
| Hardware: | Unspecified | ||||||||||
| OS: | Unspecified | ||||||||||
| Attachments: |
|
||||||||||
|
Description
Jean-Yves Avenard [:jya]
2021-08-02 23:35:00 PDT
Created attachment 435241 [details]
Patch
Turned out that our use of EXTAudioFileRead was incorrect. The callers should call `ExtAudioFileRead` again when the initial call reads fewer bytes than requested. From the docs: ``` @param ioNumberFrames On entry, ioNumberFrames is the number of frames to be read from the file. On exit, it is the number of frames actually read. A number of factors may cause a fewer number of frames to be read, including the supplied buffers not being large enough, and internal optimizations. If 0 frames are returned, however, this indicates that end-of-file was reached. ``` Created attachment 435252 [details]
Patch
Add extra test
Comment on attachment 435252 [details] Patch View in context: https://bugs.webkit.org/attachment.cgi?id=435252&action=review > Source/WebCore/platform/audio/cocoa/AudioFileReaderCocoa.cpp:590 > + framesToRead = std::min<size_t>(std::numeric_limits<UInt32>::max(), framesLeftToRead); Shouldn't this be `std::min<UInt32>`? > Source/WebCore/platform/audio/cocoa/AudioFileReaderCocoa.cpp:599 > + for (size_t i = 0; i < numberOfChannels; ++i) { > + bufferList->mBuffers[i].mDataByteSize = (numberOfFrames - framesRead) * sizeof(float); > + bufferList->mBuffers[i].mData = static_cast<float*>(bufferList->mBuffers[i].mData) + framesToRead; > + } If we go through the `while` loop more than once, won't we end up with just the last chunk returned by ExtAudioFileRead? Comment on attachment 435252 [details] Patch View in context: https://bugs.webkit.org/attachment.cgi?id=435252&action=review >> Source/WebCore/platform/audio/cocoa/AudioFileReaderCocoa.cpp:590 >> + framesToRead = std::min<size_t>(std::numeric_limits<UInt32>::max(), framesLeftToRead); > > Shouldn't this be `std::min<UInt32>`? framesLeftToRead is a size_t, doing std::min<UInt32< would cast framesLeftToRead to UInt32 before the comparison which could cause loss. So we make sure to never have more than UINT32_MAX >> Source/WebCore/platform/audio/cocoa/AudioFileReaderCocoa.cpp:599 >> + } > > If we go through the `while` loop more than once, won't we end up with just the last chunk returned by ExtAudioFileRead? bufferList is only an accessor to the underlying AudioBus memory buffer ; it's content is irrelevant once we exit the loop. /Volumes/Data/worker/Commit-Queue/build/LayoutTests/ChangeLog neither lists a valid reviewer nor contains the string "Unreviewed" or "Rubber stamp" (case insensitive). Comment on attachment 435252 [details] Patch View in context: https://bugs.webkit.org/attachment.cgi?id=435252&action=review > Source/WebCore/ChangeLog:11 > + New test: webaudio/decode-audio-data-wav.html. It should look like this instead: Test: webaudio/decode-audio-data-wav.html > LayoutTests/ChangeLog:6 > + You're missing: Reviewed by NOBODY (OOPS!) Created attachment 435388 [details]
Patch
Committed r280948 (240456@main): <https://commits.webkit.org/240456@main> All reviewed patches have been landed. Closing bug and clearing flags on attachment 435388 [details]. |