diff --git a/ChangeLog b/ChangeLog index c5308f422..5d121e4ab 100644 --- a/ChangeLog +++ b/ChangeLog @@ -81,6 +81,7 @@ release 0.14.6 the torrent was paused * fixed download piece performance bug in piece picker * fixed bug in connect candidate counter + * replaces invalid filename characters with . release 0.14.5 diff --git a/src/torrent_info.cpp b/src/torrent_info.cpp index 700b27b2b..e93b00b35 100644 --- a/src/torrent_info.cpp +++ b/src/torrent_info.cpp @@ -80,6 +80,20 @@ namespace libtorrent str += 0x80 | (chr & 0x3f); } + bool valid_path_character(char c) + { +#ifdef TORRENT_WINDOWS + static const char invalid_chars[] = "&?<>\"|\b*:+"; +#else + static const char invalid_chars[] = ""; +#endif + if (c >= 0 && c < 32) return false; + return std::strchr(invalid_chars, c) == 0; + } + + // fixes invalid UTF-8 sequences and + // replaces characters that are invalid + // in paths bool verify_encoding(std::string& target) { std::string tmp_path; @@ -90,7 +104,16 @@ namespace libtorrent // valid ascii-character if ((*i & 0x80) == 0) { - tmp_path += *i; + // replace invalid characters with '.' + if (valid_path_character(*i)) + { + tmp_path += *i; + } + else + { + tmp_path += '.'; + valid_encoding = false; + } continue; } diff --git a/test/test_primitives.cpp b/test/test_primitives.cpp index 2a7739221..7ed55da03 100644 --- a/test/test_primitives.cpp +++ b/test/test_primitives.cpp @@ -353,6 +353,12 @@ struct parse_state std::string url_base; }; +namespace libtorrent +{ + // defined in torrent_info.cpp + bool verify_encoding(std::string& target); +} + void find_control_url(int type, char const* string, parse_state& state); int test_main() @@ -544,6 +550,19 @@ int test_main() == test_string); std::cerr << unescape_string(escape_string(test_string, strlen(test_string)), ec) << std::endl; + // verify_encoding + + test = "\b?filename=4"; + TEST_CHECK(!verify_encoding(test)); +#ifdef TORRENT_WINDOWS + TEST_CHECK(test == "..filename=4"); +#else + TEST_CHECK(test == ".?filename=4"); +#endif + + test = "filename=4"; + TEST_CHECK(verify_encoding(test)); + TEST_CHECK(test == "filename=4"); // HTTP request parser http_parser parser;