diff --git a/src/DecoderThread.cxx b/src/DecoderThread.cxx index 3ccbd1082..ef6655484 100644 --- a/src/DecoderThread.cxx +++ b/src/DecoderThread.cxx @@ -280,54 +280,66 @@ decoder_load_replay_gain(Decoder &decoder, const char *path_fs) decoder_replay_gain(decoder, &info); } +static bool +TryDecoderFile(Decoder &decoder, const char *path_fs, const char *suffix, + const DecoderPlugin &plugin) +{ + if (!plugin.SupportsSuffix(suffix)) + return false; + + DecoderControl &dc = decoder.dc; + + if (plugin.file_decode != nullptr) { + dc.Lock(); + + if (decoder_file_decode(plugin, decoder, path_fs)) + return true; + + dc.Unlock(); + } else if (plugin.stream_decode != nullptr) { + InputStream *input_stream = + decoder_input_stream_open(dc, path_fs); + if (input_stream == nullptr) + return false; + + dc.Lock(); + + bool success = decoder_stream_decode(plugin, decoder, + *input_stream); + + dc.Unlock(); + + input_stream->Close(); + + if (success) { + dc.Lock(); + return true; + } + } + + return false; +} + /** * Try decoding a file. */ static bool decoder_run_file(Decoder &decoder, const char *path_fs) { - DecoderControl &dc = decoder.dc; const char *suffix = uri_get_suffix(path_fs); - const struct DecoderPlugin *plugin = nullptr; - if (suffix == nullptr) return false; + DecoderControl &dc = decoder.dc; dc.Unlock(); decoder_load_replay_gain(decoder, path_fs); - while ((plugin = decoder_plugin_from_suffix(suffix, plugin)) != nullptr) { - if (plugin->file_decode != nullptr) { - dc.Lock(); - - if (decoder_file_decode(*plugin, decoder, path_fs)) - return true; - - dc.Unlock(); - } else if (plugin->stream_decode != nullptr) { - InputStream *input_stream; - bool success; - - input_stream = decoder_input_stream_open(dc, path_fs); - if (input_stream == nullptr) - continue; - - dc.Lock(); - - success = decoder_stream_decode(*plugin, decoder, - *input_stream); - - dc.Unlock(); - - input_stream->Close(); - - if (success) { - dc.Lock(); - return true; - } - } - } + if (decoder_plugins_try([&decoder, path_fs, suffix](const DecoderPlugin &plugin){ + return TryDecoderFile(decoder, path_fs, suffix, + plugin); + })) + return true; dc.Lock(); return false;