From 959f94b06c3527185d03044df96192cd3f70fb62 Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Sat, 2 Jan 2010 19:24:31 +0100 Subject: dbUtils: return empty tag value only if no value was found This fixes a regression in the patch "return multiple tag values per song": even when the song has values for the specified tag type, the empty string gets added to the set, because the "return" was removed. This patch adds a flag which remembers whether at least one value was found. --- src/dbUtils.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'src') diff --git a/src/dbUtils.c b/src/dbUtils.c index fa2cfa27a..2e2552698 100644 --- a/src/dbUtils.c +++ b/src/dbUtils.c @@ -234,6 +234,7 @@ visitTag(struct client *client, struct strset *set, struct song *song, enum tag_type tagType) { struct tag *tag = song->tag; + bool found = false; if (tagType == LOCATE_TAG_FILE_TYPE) { song_print_url(client, song); @@ -246,10 +247,12 @@ visitTag(struct client *client, struct strset *set, for (unsigned i = 0; i < tag->num_items; i++) { if (tag->items[i]->type == tagType) { strset_add(set, tag->items[i]->value); + found = true; } } - strset_add(set, ""); + if (!found) + strset_add(set, ""); } struct list_tags_data { -- cgit v1.2.3 From 90d16af66adfe1ef9d3fc07fe7b238f3c02adaaf Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Sat, 16 Jan 2010 19:20:11 +0100 Subject: decoder_thread: fix CUE track playback The patch "input/file: don't fall back to parent directory" introduced a regression: when trying to play a CUE track, decoder_run_song() tries to open the file as a stream first, but this fails, because the path is virtual. This patch fixes decoder_run_song() (instead of reverting the previous patch) to accept input_stream_open() failures if the song is a local file. It passes the responsibility to handle non-existing files to the decoder's file_decode() method. --- src/decoder_thread.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/decoder_thread.c b/src/decoder_thread.c index d6ff058ec..cbb670616 100644 --- a/src/decoder_thread.c +++ b/src/decoder_thread.c @@ -89,7 +89,8 @@ static void decoder_run_song(const struct song *song, const char *uri) struct input_stream input_stream; const struct decoder_plugin *plugin; - if (!input_stream_open(&input_stream, uri)) { + close_instream = input_stream_open(&input_stream, uri); + if (!close_instream && !song_is_file(song)) { dc.state = DECODE_STATE_ERROR; return; } @@ -108,7 +109,7 @@ static void decoder_run_song(const struct song *song, const char *uri) /* wait for the input stream to become ready; its metadata will be available then */ - while (!input_stream.ready) { + while (close_instream && !input_stream.ready) { if (dc.command == DECODE_COMMAND_STOP) { input_stream_close(&input_stream); dc.state = DECODE_STATE_STOP; @@ -124,7 +125,8 @@ static void decoder_run_song(const struct song *song, const char *uri) } if (dc.command == DECODE_COMMAND_STOP) { - input_stream_close(&input_stream); + if (close_instream) + input_stream_close(&input_stream); dc.state = DECODE_STATE_STOP; return; } @@ -179,8 +181,11 @@ static void decoder_run_song(const struct song *song, const char *uri) const char *s = uri_get_suffix(uri); while ((plugin = decoder_plugin_from_suffix(s, next++))) { if (plugin->file_decode != NULL) { - input_stream_close(&input_stream); - close_instream = false; + if (close_instream) { + input_stream_close(&input_stream); + close_instream = false; + } + ret = decoder_file_decode(plugin, &decoder, uri); if (ret) -- cgit v1.2.3 From 8ba08edd0ef5babfee4e603b62e748f15646019b Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Sat, 16 Jan 2010 20:58:24 +0100 Subject: queue: don't repeat current song in consume mode Check consume mode in queue_next_order(), because the current song would be deleted as soon as it's finished; it cannot be played again. --- src/queue.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src') diff --git a/src/queue.c b/src/queue.c index 141222a80..16891d0aa 100644 --- a/src/queue.c +++ b/src/queue.c @@ -45,14 +45,14 @@ queue_next_order(const struct queue *queue, unsigned order) if (queue->single) { - if (queue->repeat) + if (queue->repeat && !queue->consume) return order; else return -1; } if (order + 1 < queue->length) return order + 1; - else if (queue->repeat) + else if (queue->repeat && (order > 0 || !queue->consume)) /* restart at first song */ return 0; else -- cgit v1.2.3 From 1b441837f1b51d2504256b730129e0fe92d64375 Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Sun, 17 Jan 2010 02:35:15 +0100 Subject: decoder/ffmpeg: append file name suffix to virtual stream URL To allow libavformat to detect the format of the input file, append the suffix of the input file to the URL of the virtual stream. This specifically enables the "shorten" codec, which is supported by libavformat/raw.c, detected only by the suffix. --- src/decoder/ffmpeg_plugin.c | 32 ++++++++++++++++++++++++++++---- 1 file changed, 28 insertions(+), 4 deletions(-) (limited to 'src') diff --git a/src/decoder/ffmpeg_plugin.c b/src/decoder/ffmpeg_plugin.c index d2bd642fd..0e15d99c1 100644 --- a/src/decoder/ffmpeg_plugin.c +++ b/src/decoder/ffmpeg_plugin.c @@ -55,7 +55,7 @@ struct ffmpeg_context { struct ffmpeg_stream { /** hack - see url_to_struct() */ - char url[8]; + char url[64]; struct decoder *decoder; struct input_stream *input; @@ -140,8 +140,28 @@ ffmpeg_find_audio_stream(const AVFormatContext *format_context) return -1; } +/** + * Append the suffix of the original URI to the virtual stream URI. + * Without this, libavformat cannot detect some of the codecs + * (e.g. "shorten"). + */ +static void +append_uri_suffix(struct ffmpeg_stream *stream, const char *uri) +{ + assert(stream != NULL); + assert(uri != NULL); + + char *base = g_path_get_basename(uri); + + const char *suffix = strrchr(base, '.'); + if (suffix != NULL && suffix[1] != 0) + g_strlcat(stream->url, suffix, sizeof(stream->url)); + + g_free(base); +} + static bool -ffmpeg_helper(struct input_stream *input, +ffmpeg_helper(const char *uri, struct input_stream *input, bool (*callback)(struct ffmpeg_context *ctx), struct ffmpeg_context *ctx) { @@ -154,6 +174,9 @@ ffmpeg_helper(struct input_stream *input, }; bool ret; + if (uri != NULL) + append_uri_suffix(&stream, uri); + stream.input = input; if (ctx && ctx->decoder) { stream.decoder = ctx->decoder; //are we in decoding loop ? @@ -349,7 +372,8 @@ ffmpeg_decode(struct decoder *decoder, struct input_stream *input) ctx.input = input; ctx.decoder = decoder; - ffmpeg_helper(input, ffmpeg_decode_internal, &ctx); + ffmpeg_helper(decoder_get_uri(decoder), input, + ffmpeg_decode_internal, &ctx); } #if LIBAVFORMAT_VERSION_INT >= ((52<<16)+(31<<8)+0) @@ -426,7 +450,7 @@ static struct tag *ffmpeg_tag(const char *file) ctx.decoder = NULL; ctx.tag = tag_new(); - ret = ffmpeg_helper(&input, ffmpeg_tag_internal, &ctx); + ret = ffmpeg_helper(file, &input, ffmpeg_tag_internal, &ctx); if (!ret) { tag_free(ctx.tag); ctx.tag = NULL; -- cgit v1.2.3 From 2579a2f924091b3e48a9cb5eac82a85078dfa05b Mon Sep 17 00:00:00 2001 From: Max Kellermann Date: Sun, 17 Jan 2010 16:00:14 +0100 Subject: decoder/ffmpeg: added more MIME types Taken from the ffmpeg sources. --- src/decoder/ffmpeg_plugin.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'src') diff --git a/src/decoder/ffmpeg_plugin.c b/src/decoder/ffmpeg_plugin.c index 0e15d99c1..2a46601f4 100644 --- a/src/decoder/ffmpeg_plugin.c +++ b/src/decoder/ffmpeg_plugin.c @@ -486,6 +486,7 @@ static const char *const ffmpeg_suffixes[] = { }; static const char *const ffmpeg_mime_types[] = { + "application/m4a", "application/mp4", "application/octet-stream", "application/ogg", @@ -498,9 +499,12 @@ static const char *const ffmpeg_mime_types[] = { "audio/16sv", "audio/aac", "audio/ac3", + "audio/aiff" "audio/amr", "audio/basic", "audio/flac", + "audio/m4a", + "audio/mp4", "audio/mpeg", "audio/musepack", "audio/ogg", @@ -519,6 +523,7 @@ static const char *const ffmpeg_mime_types[] = { "audio/x-flac", "audio/x-gsm", "audio/x-mace", + "audio/x-matroska", "audio/x-monkeys-audio", "audio/x-mpeg", "audio/x-ms-wma", @@ -531,6 +536,7 @@ static const char *const ffmpeg_mime_types[] = { "audio/x-pn-multirate-realaudio", "audio/x-speex", "audio/x-tta" + "audio/x-voc", "audio/x-wav", "audio/x-wma", "audio/x-wv", -- cgit v1.2.3