Commit cf9ee339 authored by Max Kellermann's avatar Max Kellermann

input/icy: support "charset" parameter in URI fragment

parent 4a47bbd8
...@@ -5,6 +5,7 @@ ver 0.22 (not yet released) ...@@ -5,6 +5,7 @@ ver 0.22 (not yet released)
* tags * tags
- new tags "Grouping" (for ID3 "TIT1") and "Work" - new tags "Grouping" (for ID3 "TIT1") and "Work"
* input * input
- curl: support "charset" parameter in URI fragment
- ffmpeg: allow partial reads - ffmpeg: allow partial reads
* archive * archive
- iso9660: support seeking - iso9660: support seeking
......
...@@ -985,6 +985,22 @@ is no way for :program:`MPD` to find out whether the DAC supports ...@@ -985,6 +985,22 @@ is no way for :program:`MPD` to find out whether the DAC supports
it. DSD to PCM conversion is the fallback if DSD cannot be used it. DSD to PCM conversion is the fallback if DSD cannot be used
directly. directly.
ICY-MetaData
------------
Some MP3 streams send information about the current song with a
protocol named `"ICY-MetaData"
<http://www.smackfu.com/stuff/programming/shoutcast.html>`_.
:program:`MPD` makes its ``StreamTitle`` value available as ``Title``
tag.
By default, :program:`MPD` assumes this tag is UTF-8-encoded. To tell
:program:`MPD` to assume a different character set, specify it in the
``charset`` URL fragment parameter, e.g.::
mpc add 'http://radio.example.com/stream#charset=cp1251'
Client Hacks Client Hacks
************ ************
......
...@@ -20,11 +20,27 @@ ...@@ -20,11 +20,27 @@
#include "IcyInputStream.hxx" #include "IcyInputStream.hxx"
#include "IcyMetaDataParser.hxx" #include "IcyMetaDataParser.hxx"
#include "tag/Tag.hxx" #include "tag/Tag.hxx"
#include "util/UriExtract.hxx"
#include "util/UriQueryParser.hxx"
#include "util/StringView.hxx"
#include <string>
IcyInputStream::IcyInputStream(InputStreamPtr _input, IcyInputStream::IcyInputStream(InputStreamPtr _input,
std::shared_ptr<IcyMetaDataParser> _parser) noexcept std::shared_ptr<IcyMetaDataParser> _parser)
:ProxyInputStream(std::move(_input)), parser(std::move(_parser)) :ProxyInputStream(std::move(_input)), parser(std::move(_parser))
{ {
#ifdef HAVE_ICU_CONVERTER
const char *fragment = uri_get_fragment(GetURI());
if (fragment != nullptr) {
const auto charset = UriFindRawQueryParameter(fragment,
"charset");
if (charset != nullptr) {
const std::string copy(charset.data, charset.size);
parser->SetCharset(copy.c_str());
}
}
#endif
} }
IcyInputStream::~IcyInputStream() noexcept = default; IcyInputStream::~IcyInputStream() noexcept = default;
......
...@@ -52,9 +52,12 @@ public: ...@@ -52,9 +52,12 @@ public:
* with our input; it needs to be shared because our input * with our input; it needs to be shared because our input
* needs to feed parameters (e.g. from the "icy-metaint" * needs to feed parameters (e.g. from the "icy-metaint"
* header) into it * header) into it
*
* Throws on error (e.g. if the charset converter specified by
* the URI fragment fails to initialize).
*/ */
IcyInputStream(InputStreamPtr _input, IcyInputStream(InputStreamPtr _input,
std::shared_ptr<IcyMetaDataParser> _parser) noexcept; std::shared_ptr<IcyMetaDataParser> _parser);
virtual ~IcyInputStream() noexcept; virtual ~IcyInputStream() noexcept;
IcyInputStream(const IcyInputStream &) = delete; IcyInputStream(const IcyInputStream &) = delete;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment