aboutsummaryrefslogtreecommitdiffstats
path: root/src/decode.c (unfollow)
Commit message (Collapse)AuthorFilesLines
2008-04-12decode: fix unsigned comparision and add some paranoid assertionsEric Wong1-8/+9
git-svn-id: https://svn.musicpd.org/mpd/trunk@7301 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12Fix a few more warnings from -WshadowEric Wong1-4/+4
git-svn-id: https://svn.musicpd.org/mpd/trunk@7300 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12some assertions to check the unsigned changesMax Kellermann1-0/+3
git-svn-id: https://svn.musicpd.org/mpd/trunk@7297 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12yet more unsigned integersMax Kellermann1-4/+4
calculateCrossFadeChunks() still returns int, although the caller uses it as an unsigned value. Since the function body checks for negative values, it is safe to cast to unsigned. crossFade() takes signed parameters, although it callers pass unsigned integers. Change declaration to unsigned. git-svn-id: https://svn.musicpd.org/mpd/trunk@7291 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12use the notify API in the decoderMax Kellermann1-6/+8
git-svn-id: https://svn.musicpd.org/mpd/trunk@7281 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12use break instead of quitDecode()+returnMax Kellermann1-6/+3
The code paths which return from the functions all have to call quitDecode(). If we simply break instead of calling quitDecode() explicitly, this function gets called in the last line of this function anyway. git-svn-id: https://svn.musicpd.org/mpd/trunk@7278 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12moved expression to audioFormatSizeToTime()Max Kellermann1-3/+1
The multi-line expression which calculates sizeToTime is hard to read, partly because "cb->audioFormat." is too long. Create a separate inline function in audio.h for that. git-svn-id: https://svn.musicpd.org/mpd/trunk@7277 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12let calculateCrossFadeChunks() decideMax Kellermann1-14/+12
Moved the decision whether to cross-fade the current song to calculateCrossFadeChunks(). This simplifies the function decoderParent() and eliminates one layer of indentation. git-svn-id: https://svn.musicpd.org/mpd/trunk@7276 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12moved code to playChunk()Max Kellermann1-10/+20
Similar to the crossFade() patch: pass chunk objects to playChunk(), simplify decodeParent() by removing clutter. git-svn-id: https://svn.musicpd.org/mpd/trunk@7275 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12added outputBufferShift()Max Kellermann1-4/+1
Hiding OutputBuffer internals, yet again. Two more assertions. git-svn-id: https://svn.musicpd.org/mpd/trunk@7274 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12continue main loop instead of nesting loopsMax Kellermann1-13/+5
To unify the decoderParent() main loop some more, use it to wait for the decoder to change the song. Only one single processDecodeInput() caller left after this patch. git-svn-id: https://svn.musicpd.org/mpd/trunk@7273 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12sleep when waiting for cross-fade chunksMax Kellermann1-1/+3
When there are not enough decode cross-fade chunks in the buffer yet, the current code does busy-wait, which will delay the decoder even more. sleep instead, expecting the decoder to wake us up. git-svn-id: https://svn.musicpd.org/mpd/trunk@7272 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12moved code to crossFade()Max Kellermann1-15/+20
Calling crossFade() with the chunk objects is easier than unrolling all the chunk properties manually, and decodeParent() can really use more of these simplifications. git-svn-id: https://svn.musicpd.org/mpd/trunk@7271 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12added struct OutputBufferChunkMax Kellermann1-16/+19
To make access to OutputBuffer easier, move everything which belongs to a chunk into its own structure, namely OutputBufferChunk. git-svn-id: https://svn.musicpd.org/mpd/trunk@7269 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12added outputBufferChunkData()Max Kellermann1-4/+2
Hiding OutputBuffer internals, again. We get an extra assertion in return. git-svn-id: https://svn.musicpd.org/mpd/trunk@7267 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12removed "quit"Max Kellermann1-5/+3
The variable "quit" can be removed, since its only setter can use "break" instead, just like the other code paths. git-svn-id: https://svn.musicpd.org/mpd/trunk@7266 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12do not reset nextChunkMax Kellermann1-9/+5
The variables "nextChunk" and "crossFadeChunks" are only used when doCrossFade==1. This means that we do not have to reset these as long as doCrossFade!=1. git-svn-id: https://svn.musicpd.org/mpd/trunk@7265 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12added outputBufferRelative()Max Kellermann1-6/+2
The cross-fade check is still very complicated whenever it uses OutputBuffer internals. Greatly simplify another check by introducing outputBufferRelative(). git-svn-id: https://svn.musicpd.org/mpd/trunk@7264 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12added outputBufferEmpty()Max Kellermann1-2/+2
Another "don't use OutputBuffer internals" patch. This ignores the copied "end" value, but I do not think that has ever been a real issue. git-svn-id: https://svn.musicpd.org/mpd/trunk@7263 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12moved check to outputBufferAbsolute()Max Kellermann1-17/+4
decoderParent() uses a lot of OutputBuffer internals to see whether cross-fading should be started. Move these checks to outputBuffer.c, which also simplifies decoderParent(). git-svn-id: https://svn.musicpd.org/mpd/trunk@7262 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12make variables more localMax Kellermann1-4/+3
Declare the variables "test" and "fadePosition" in the scope where they are really used. This removes some of the clutter in the function decodeParent(). git-svn-id: https://svn.musicpd.org/mpd/trunk@7261 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12moved the initial buffering code into the big loopMax Kellermann1-13/+10
Eliminating some duplicated and. This also decreases the number of lines calling processDecodeInput(). git-svn-id: https://svn.musicpd.org/mpd/trunk@7260 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12some comments in decode.cMax Kellermann1-0/+39
I have spent some time to understand decodeParent(), which does a lot of obfuscated magic... I find it useful to help others to also understand it, so I wrote a few comments. git-svn-id: https://svn.musicpd.org/mpd/trunk@7259 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12integrated macro handleDecodeStart() into callerMax Kellermann1-43/+40
Another patch indended to improve the CPP macro hell. This enlarges the function decodeParent(), but it cannot be converted into a standalone function easily, because it references so many local variables. git-svn-id: https://svn.musicpd.org/mpd/trunk@7258 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12use clearOutputBuffer()Max Kellermann1-4/+2
clearOutputBuffer() also resets currentChunk; this might resolve a theoretical bug. git-svn-id: https://svn.musicpd.org/mpd/trunk@7257 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12do not check dc->start after loopMax Kellermann1-1/+1
dc->start cannot be true after the loop, because it was the loop condition. dc->start could have been set by another thread between the while loop and the if, but I suspect this is not the case the author intended, so we just remove the dc->start check. git-svn-id: https://svn.musicpd.org/mpd/trunk@7256 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12use DECODE_ERROR_NOERROR instead of 0Max Kellermann1-3/+3
In my opinion, the code becomes more readable when we explicitly check "==NOERROR" instead of an implicit 0 check. git-svn-id: https://svn.musicpd.org/mpd/trunk@7255 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12converted macro processDecodeInput() to functionMax Kellermann1-52/+80
Macros are ugly, and multi-line macros are even more ugly. This patch converts processDecodeInput() to a C function. The disadvantage may be that the function does not have access to the caller's local variables, which might be regarded as an advantage on the other hand. For this reason, we have to pass variable references. This costs a tiny bit of performance, but it's worth eliminating this monster macro, and further patches will optimize this cost down. git-svn-id: https://svn.musicpd.org/mpd/trunk@7254 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12don't set quit=1 before breakMax Kellermann1-5/+2
Instead of setting quit=1, we can simply break out of the loop. git-svn-id: https://svn.musicpd.org/mpd/trunk@7252 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12simplified some code in decode.cMax Kellermann1-11/+10
The block after "if" breaks out of the loop. To make the code a little bit more readable, don't write the rest in an "else" block, since this code path does not break. git-svn-id: https://svn.musicpd.org/mpd/trunk@7251 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12add method availableOutputBuffer()Max Kellermann1-2/+1
The method availableOutputBuffer() calculates how many chunks are in use. This simplifies code which needs this information, and it can run without knowing OutputBuffer internals. The function knows how to calculate this when begin>end; this might have been a bug in decodeParent(), which does not. git-svn-id: https://svn.musicpd.org/mpd/trunk@7250 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12replace advanceOutputBufferTo() with trivial assignmentMax Kellermann1-6/+1
After the previous patch, it is clear that the loop in advanceOutputBufferTo() can be replaced with a simple assignment. git-svn-id: https://svn.musicpd.org/mpd/trunk@7249 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12removed unused parameters from advanceOutputBufferTo()Max Kellermann1-6/+2
The parameter "currentChunkSent" is not used and can be dropped. git-svn-id: https://svn.musicpd.org/mpd/trunk@7248 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12Start using song pointers in core data structuresEric Wong1-34/+32
Instead of copying URLs everywhere... [merged r7186 from branches/ew] git-svn-id: https://svn.musicpd.org/mpd/trunk@7244 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12Drop metadata updates from HTTP for now (input HTTP, and shout)Eric Wong1-60/+4
It is way more complicated than it should be; and locking it for thread-safety is too difficult. [merged r7183 from branches/ew] git-svn-id: https://svn.musicpd.org/mpd/trunk@7241 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12Initial cut of fork() => pthreads() for decoder and playerEric Wong1-142/+101
I initially started to do a heavy rewrite that changed the way processes communicated, but that was too much to do at once. So this change only focuses on replacing the player and decode processes with threads and using condition variables instead of polling in loops; so the changeset itself is quiet small. * The shared output buffer variables will still need locking to guard against race conditions. So in this effect, we're probably just as buggy as before. The reduced context-switching overhead of using threads instead of processes may even make bugs show up more or less often... * Basic functionality appears to be working for playing local (and NFS) audio, including: play, pause, stop, seek, previous, next, and main playlist editing * I haven't tested HTTP streams yet, they should work. * I've only tested ALSA and Icecast. ALSA works fine, Icecast metadata seems to get screwy at times and breaks song advancement in the playlist at times. * state file loading works, too (after some last-minute hacks with non-blocking wakeup functions) * The non-blocking (*_nb) variants of the task management functions are probably overused. They're more lenient and easier to use because much of our code is still based on our previous polling-based system. * It currently segfaults on exit. I haven't paid much attention to the exit/signal-handling routines other than ensuring it compiles. At least the state file seems to work. We don't do any cleanups of the threads on exit, yet. * Update is still done in a child process and not in a thread. To do this in a thread, we'll need to ensure it does proper locking and communication with the main thread; but should require less memory in the end because we'll be updating the database "in-place" rather than updating a copy and then bulk-loading when done. * We're more sensitive to bugs in 3rd party libraries now. My plan is to eventually use a master process which forks() and restarts the child when it dies: locking and communication with the main thread; but should require less memory in the end because we'll be updating the database "in-place" rather than updating a copy and then bulk-loading when done. * We're more sensitive to bugs in 3rd party libraries now. My plan is to eventually use a master process which forks() and restarts the child when it dies: master - just does waitpid() + fork() in a loop \- main thread \- decoder thread \- player thread At the beginning of every song, the main thread will set a dirty flag and update the state file. This way, if we encounter a song that triggers a segfault killing the main thread, the master will start the replacement main on the next song. * The main thread still wakes up every second on select() to check for signals; which affects power management. [merged r7138 from branches/ew] git-svn-id: https://svn.musicpd.org/mpd/trunk@7240 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12whitespace cleanupMax Kellermann1-1/+1
Clean up some space indentations, replace with tabs. git-svn-id: https://svn.musicpd.org/mpd/trunk@7239 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12fix sign compare warningsMax Kellermann1-7/+7
Do explicit casts before comparing signed with unsigned. The one in log.c actually fixes another warning: in the expanded macro, there may be a check "logLevel>=0", which is always true. git-svn-id: https://svn.musicpd.org/mpd/trunk@7230 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-04-12use unsigned integers in decoder.cMax Kellermann1-5/+5
Use unsigned integers in decoderParent() for chunk numbers which cannot be negative. git-svn-id: https://svn.musicpd.org/mpd/trunk@7226 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-03-26send notify signal after SIGCONTMax Kellermann1-0/+2
When the decoder receives SIGCONT during waitNotify(), the kernel restarts the read() system call. This lets the decoder process block indefinitely, while the player process waits for it to react. This should probably be solved with a proper signal handler which aborts the read() system call, but for now, we just write to the pipe to make it wake up. git-svn-id: https://svn.musicpd.org/mpd/trunk@7216 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-03-26notify the decoder instead of polling 100hzMax Kellermann1-0/+1
When the decoder process is faster than the player process, all decodedd buffers are full at some point in time. The decoder has to wait for buffers to become free (finished playing). It used to do this by polling the buffer status 100 times a second. This generates a lot of unnecessary CPU wakeups. This patch adds a way for the player process to notify the decoder process that it may continue its work. We could use pthread_cond for that, unfortunately inter-process mutexes/conds are not supported by some kernels (Linux), so we cannot use this light-weight method until mpd moves to using threads instead of processes. The other method would be semaphores, which historically are global resources with a unique name; this historic API is cumbersome, and I wanted to avoid it. I came up with a quite naive solution for now: I create an anonymous pipe with pipe(), and the decoder process reads on that pipe. Until the player process sends data on it as a signal, the decoder process blocks. This can be optimized in a number of ways: - if the decoder process is still working (instead of waiting for buffers), we could save the write() system call, since there is nobody waiting for the notification. [ew: I tried this using a counter in shared memory, didn't help] - the pipe buffer will be full at some point, when the decoder thread is too slow. For this reason, the writer side of the pipe is non-blocking, and mpd can ignore the resulting EWOULDBLOCK. - since we have shared memory, we could check whether somebody is actually waiting without a context switch, and we could just not write the notification byte. [ew: tried same method/result as first point above] - if there is already a notification in the pipe, we could also not write another one. [ew: tried same method/result as first/third points above] - the decoder will only consume 64 bytes at a time. If the pipe buffer is full, this will result in a lot of read() invocations. This does not hurt badly, but on a heavily loaded system, this might add a little bit more load. The preceding optimizations however are able eliminate the this. - finally, we should use another method for inter process notifications - maybe kill() or just make mpd use threads, finally. In spite of all these possibilities to optimize this code further, this pipe notification trick is faster than the 100 Hz poll. On my machine, it reduced the number of wakeups to less than 30%. git-svn-id: https://svn.musicpd.org/mpd/trunk@7215 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-02-05fix -Wconst warningsMax Kellermann1-2/+2
[ew: cleaned up the dirty union hack a bit] Signed-off-by: Eric Wong <normalperson@yhbt.net> git-svn-id: https://svn.musicpd.org/mpd/trunk@7180 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-01-03Cleanup #includes of standard system headers and put them in one placeEric Wong1-8/+1
This will make refactoring features easier, especially now that pthreads support and larger refactorings are on the horizon. Hopefully, this will make porting to other platforms (even non-UNIX-like ones for masochists) easier, too. os_compat.h will house all the #includes for system headers considered to be the "core" of MPD. Headers for optional features will be left to individual source files. git-svn-id: https://svn.musicpd.org/mpd/trunk@7130 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-01-01silence is constant, as is the buffer we pass to playAudioEric Wong1-3/+1
git-svn-id: https://svn.musicpd.org/mpd/trunk@7123 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2008-01-01Simplify decode cleanup logic a bitEric Wong1-26/+15
DECODE_STATE_STOP is always set as dc->state, and dc->stop is always cleared. So handle it in decodeStart once rather than doing it in every plugin. While we're at it, fix a long-standing (but difficult to trigger) bug in mpc_decode where we failed to return if mpc_decoder_initialize() fails. git-svn-id: https://svn.musicpd.org/mpd/trunk@7122 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2007-12-28Merge branches/ew r7104Eric Wong1-18/+15
thread-safety work in preparation for rewrite to use pthreads Expect no regressions against trunk (r7078), possibly minor performance improvements in update (due to fewer heap allocations), but increased stack usage. Applied the following patches: * maxpath_str for reentrancy (temporary fix, reverted) * path: start working on thread-safe variants of these methods * Re-entrancy work on path/character-set conversions * directory.c: exploreDirectory() use reentrant functions here * directory/update: more use of reentrant functions + cleanups * string_toupper: a strdup-less version of strDupToUpper * get_song_url: a static-variable-free version of getSongUrl() * Use reentrant/thread-safe get_song_url everywhere * replace rmp2amp with the reentrant version, rmp2amp_r * Get rid of the non-reentrant/non-thread-safe rpp2app, too. * buffer2array: assert strdup() returns a usable value in unit tests * replace utf8ToFsCharset and fsCharsetToUtf8 with thread-safe variants * fix storing playlists w/o absolute paths * parent_path(), a reentrant version of parentPath() * parentPath => parent_path for reentrancy and thread-safety * allow "make test" to automatically run embedded unit tests * remove convStrDup() and maxpath_str() * use MPD_PATH_MAX everywhere instead of MAXPATHLEN * path: get rid of appendSlash, pfx_path and just use pfx_dir * get_song_url: fix the ability to play songs in the top-level music_directory git-svn-id: https://svn.musicpd.org/mpd/trunk@7106 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2007-09-07decode: fix seek when pausedEric Wong1-0/+1
We need to SIGCONT the decoder process to allow for seeking while paused. git-svn-id: https://svn.musicpd.org/mpd/trunk@6864 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2007-09-06Once again get rid of busy waiting and use SIGSTOP for pauseEric Wong1-4/+10
The problems I had were related to the OSS driver and USB device I was using. The problems existed even with the old busy-waiting scheme enabled. OSS - Bithead USB => bad ALSA - Bithead USB => OK OSS - Onboard i8x0 => OK ALSA - Onboard i8x0 => OK bad - slow shutdown, pauses, dropped audio after pause/resume git-svn-id: https://svn.musicpd.org/mpd/trunk@6861 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2007-09-06return to busy-waiting on pause for now..Eric Wong1-10/+4
Until we can fix it properly (or replace it with a cleaner event system), I don't want this in trunk. Currently there are strange pauses when queueing and during shutdown that I can't seem to figure out right away. git-svn-id: https://svn.musicpd.org/mpd/trunk@6860 09075e82-0dd4-0310-85a5-a0d7c8717e4f
2007-08-27removing debug messages from signal handlersJ. Alexander Treuman1-3/+5
As unfortunate as it is to remove such useful debugging messages, it's necessary to fix a potential deadlock with signal handling. A bunch of functions the debug functions call aren't safe to call from a signal handler. There are some alternate solutions, but they're neither pretty nor simple. So just remove them entirely for now. git-svn-id: https://svn.musicpd.org/mpd/trunk@6828 09075e82-0dd4-0310-85a5-a0d7c8717e4f