-
Notifications
You must be signed in to change notification settings - Fork 2.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix partial specialization problem for filesystem for Visual Studio #2957
Changes from 4 commits
5eeeb31
09f52a0
8101036
5e45aaa
6eab289
4cc8b6f
34e3b6f
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -57,6 +57,7 @@ inline void write_escaped_path<std::filesystem::path::value_type>( | |
|
||
} // namespace detail | ||
|
||
#if !FMT_MSC_VERSION || FMT_MSC_VERSION >= 1920 | ||
template <typename Char> | ||
struct formatter<std::filesystem::path, Char> | ||
: formatter<basic_string_view<Char>> { | ||
|
@@ -69,6 +70,33 @@ struct formatter<std::filesystem::path, Char> | |
basic_string_view<Char>(quoted.data(), quoted.size()), ctx); | ||
} | ||
}; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't think the above conditional branch is needed because character types other than char and wchar_t won't work anyway. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Are you writing about a generic implementation? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ah, you are right. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. At least according to There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Yes, I think it's better to disable There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'm not suggesting to disable path support unconditionally. I'm suggesting to enable it conditionally for all cases that we know to work, so effectively not providing any specialization if There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
It will keep the implementation simple if I understood your question correctly. We generally try to avoid conditional compilation unless absolutely necessary and limiting it to test significantly reduces the scope. Also:
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
My revised solution wasn't suggesting to enable it partially for some character types. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The revised solution seems OK to me. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Done |
||
#else | ||
// Workaround for MSVC 2017 and earlier. | ||
template <> | ||
struct formatter<std::filesystem::path, char> | ||
: formatter<basic_string_view<char>> { | ||
template <typename FormatContext> | ||
auto format(const std::filesystem::path& p, FormatContext& ctx) const -> | ||
typename FormatContext::iterator { | ||
basic_memory_buffer<char> quoted; | ||
detail::write_escaped_path(quoted, p); | ||
return formatter<basic_string_view<char>>::format( | ||
basic_string_view<char>(quoted.data(), quoted.size()), ctx); | ||
} | ||
}; | ||
template <> | ||
struct formatter<std::filesystem::path, wchar_t> | ||
: formatter<basic_string_view<wchar_t>> { | ||
template <typename FormatContext> | ||
auto format(const std::filesystem::path& p, FormatContext& ctx) const -> | ||
typename FormatContext::iterator { | ||
basic_memory_buffer<wchar_t> quoted; | ||
detail::write_escaped_path(quoted, p); | ||
return formatter<basic_string_view<wchar_t>>::format( | ||
basic_string_view<wchar_t>(quoted.data(), quoted.size()), ctx); | ||
} | ||
}; | ||
#endif | ||
FMT_END_NAMESPACE | ||
#endif | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -78,13 +78,15 @@ add_fmt_test(printf-test) | |
add_fmt_test(ranges-test ranges-odr-test.cc) | ||
add_fmt_test(scan-test) | ||
add_fmt_test(std-test) | ||
add_fmt_test(ranges-std-test) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Please merge this into There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Are you really sure that you want that? This means that your preexisting test does not actually test anymore that the inclusion of stl.h suffices to get the wanted effects, it only tests that the combined inclusion has these effects. I really recommend to keep the separate test translation unit, because this introduces exactly the errornous situation. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Yes. Just make sure to keep There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Done. |
||
try_compile(compile_result_unused | ||
${CMAKE_CURRENT_BINARY_DIR} | ||
SOURCES ${CMAKE_CURRENT_LIST_DIR}/detect-stdfs.cc | ||
OUTPUT_VARIABLE RAWOUTPUT) | ||
string(REGEX REPLACE ".*libfound \"([^\"]*)\".*" "\\1" STDLIBFS "${RAWOUTPUT}") | ||
if (STDLIBFS) | ||
target_link_libraries(std-test ${STDLIBFS}) | ||
target_link_libraries(ranges-std-test ${STDLIBFS}) | ||
endif () | ||
add_fmt_test(unicode-test HEADER_ONLY) | ||
if (MSVC) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
// Formatting library for C++ - tests for ranges and std combination | ||
// | ||
// Copyright (c) 2012 - present, Victor Zverovich | ||
// All rights reserved. | ||
// | ||
// For the license information refer to format.h. | ||
// | ||
// Copyright (c) 2022 - present, Dani-Hub (Daniel Kruegler) | ||
// All rights reserved | ||
|
||
#include "fmt/ranges.h" | ||
#include "fmt/std.h" | ||
|
||
#include <string> | ||
#include <vector> | ||
|
||
#include "gtest/gtest.h" | ||
|
||
TEST(ranges_std_test, format_vector_path) { | ||
#ifdef __cpp_lib_filesystem | ||
auto p = std::filesystem::path("foo/bar.txt"); | ||
auto c = std::vector<std::string>{"abc", "def"}; | ||
EXPECT_EQ(fmt::format("path={}, range={}", p, c), | ||
"path=\"foo/bar.txt\", range=[\"abc\", \"def\"]"); | ||
#endif | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not use a simpler implementation like the one from cppreference?
And the same for conjunction.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I suggested the current implementation, because it is the same one that I committed for libstdc++ years ago and that worked for all known compilers regardless of completeness of variadic templates and minor rule changes in variadic templates. That being said, I guess the suggested alternative will work for all supported compilers. While adjusting this, we also can add a minor compile-conditional regarding
__cpp_lib_logical_traits
and take advantage of the STL variant in this case.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I suggest keeping it simple and not introducing conditional compilation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK.