|
||||||||||||||
Goals of playback reworking
Current statusChanges and resolved bugs since the commit of Metadata on Buffer:
Reported bugsFlyspray bugs in Music Playback: open - all statuses (Note that reported data abort/crashing bugs may be related to Portal Player CPU frequency scaling, not playback problems.) The following bugs have been reported and need putting on Flyspray (if they are not already on there, and have not been resolved recently):
Rockbox software codec proposed audio output structureThree independent processes -
Rockbox software codec current audio playback functional descriptionThe primary control thread of the system is the audio thread. This thread reads audio files and codecs into the large compressed audio buffer. When playback is requested, the audio thread reads the metadata of the first audio file in the playlist, and reads the required codec into memory, then executes it on the codec thread. The codec thread is where all audio decoding and writes to the PCM decompressed audio buffer take place. Once the codec is initialized, it calls back (on thread) for compressed audio data using what look to it like standard file-like operations. It then decodes this compressed audio, and again calls back with a decompressed buffer to be written to the PCM buffer. After inserting the decompressed data into the PCM buffer, the codec thread updates the position indicators with two more callbacks. The codec thread doesnÂt have any knowledge of the state of the compressed audio buffer, and simply requests and decompresses data as fast as it is able. Buffer levels are managed by the audio thread when there is contention for buffer fill resources. This is done by yielding and/or/nor sleeping on the audio thread to allow the codec thread to fill the PCM buffer, or to fill the compressed audio buffer as needed. On each write to the PCM buffer, the buffer level is checked, and if the buffer is below the watermark level, the CPU is boosted to try and recover the buffer level. This works, because the PCM buffer is the more heavily CPU limited of the two buffers. User triggered events are handled primarily on the audio thread. Most events are handled entirely on this thread, however track skips are handled partially on the requesting thread for better interactive performance. Events are primarily converted to linear execution by the use of the audio event queue. Most events will eventually require a change in behavior on the codec thread. For a seek, the codec thread is notified by simply setting the seek time on the codec API to the desired seek location. The codec thread picks this up on the next loop and moves to the desired location, calling the seek complete callback when this is done. For track changes that do not require a change of codec, the reload codec variable on the codec api is set, this tells the codec to immediately terminate decoding of the current track and request a new track through the request next track callback. The request next track callback is responsible for moving the buffer pointers, and ensuring that the new track is at least partially buffered before allowing the codec thread to continue. For track changes which do require a change of codec, the stop codec variable on the codec api is set, telling the current codec to exit immediately. The codec thread then sleeps until it receives a codec load event on its event queue, at which point it executes the new codec and audio resumes. The voice ui operates on a separate thread from the codec thread, however only one of the two decode threads will be awake at any given time (mutex enforced). When the voice codec has decoded a section of audio, it calls the same callback to insert that data into the PCM buffer as the codec thread. If audio is not playing the callback functions exactly as it does for audio playback. If audio is playing then the callback inserts the audio into a special mix buffer, and instructs the pcmbuffer to mix the data into the audio stream as soon as possible. The PCM buffer inserts any mix data (beeps or voice) as close as possible to the currently playing buffer (1/8 second past the end of the chunk that the hardware is currently reading). In the insertion callback, priority is balanced between the two codecs, swapping as necessary in an attempt to ensure uninterrupted playback and smooth voice insertion. See also:
r147 - 02 Apr 2021 - 20:46:07 - UnknownUser
Copyright © by the contributing authors.
|