From b5bd6323fcbe401e1fdda4ad550d87389d6a1efa Mon Sep 17 00:00:00 2001 From: Barry Revzin Date: Sun, 4 Jun 2023 12:28:00 -0500 Subject: [PATCH] Trying to improve errors in the unformattable case. --- include/fmt/core.h | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/include/fmt/core.h b/include/fmt/core.h index 4961310a..86dcd7a3 100644 --- a/include/fmt/core.h +++ b/include/fmt/core.h @@ -1539,12 +1539,18 @@ constexpr auto encode_types() -> unsigned long long { (encode_types() << packed_arg_bits); } +// This type is intentionally undefined, only used for errors +template struct type_is_unformattable_for; + template FMT_CONSTEXPR FMT_INLINE auto make_arg(T& val) -> value { using arg_type = remove_cvref_t().map(val))>; constexpr bool formattable_char = !std::is_same::value; + if constexpr (not formattable_char) { + type_is_unformattable_for _; + } static_assert(formattable_char, "Mixing character types is disallowed."); // Formatting of arbitrary pointers is disallowed. If you want to format a @@ -1552,10 +1558,16 @@ FMT_CONSTEXPR FMT_INLINE auto make_arg(T& val) -> value { // formatting of `[const] volatile char*` printed as bool by iostreams. constexpr bool formattable_pointer = !std::is_same::value; + if constexpr (not formattable_pointer) { + type_is_unformattable_for _; + } static_assert(formattable_pointer, "Formatting of non-void pointers is disallowed."); constexpr bool formattable = !std::is_same::value; + if constexpr (not formattable) { + type_is_unformattable_for _; + } static_assert( formattable, "Cannot format an argument. To make type T formattable provide a " @@ -2520,7 +2532,13 @@ FMT_CONSTEXPR auto parse_format_specs(ParseContext& ctx) mapped_type_constant::value != type::custom_type, decltype(arg_mapper().map(std::declval())), typename strip_named_arg::type>; - return formatter().parse(ctx); + if constexpr (std::is_default_constructible_v< + formatter>) { + return formatter().parse(ctx); + } else { + type_is_unformattable_for _; + return ctx.begin(); + } } // Checks char specs and returns true iff the presentation type is char-like.