summaryrefslogtreecommitdiffhomepage
path: root/vendor/toml++/impl/toml_formatter.inl
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/toml++/impl/toml_formatter.inl')
-rw-r--r--vendor/toml++/impl/toml_formatter.inl731
1 files changed, 346 insertions, 385 deletions
diff --git a/vendor/toml++/impl/toml_formatter.inl b/vendor/toml++/impl/toml_formatter.inl
index e764448..02c6d0b 100644
--- a/vendor/toml++/impl/toml_formatter.inl
+++ b/vendor/toml++/impl/toml_formatter.inl
@@ -1,405 +1,366 @@
-//# This file is a part of toml++ and is subject to the the terms of the MIT license.
-//# Copyright (c) Mark Gillard <mark.gillard@outlook.com.au>
-//# See https://github.com/marzer/tomlplusplus/blob/master/LICENSE for the full license text.
-// SPDX-License-Identifier: MIT
+// # This file is a part of toml++ and is subject to the the terms of the MIT license.
+// # Copyright (c) Mark Gillard <mark.gillard@outlook.com.au>
+// # See https://github.com/marzer/tomlplusplus/blob/master/LICENSE for the full license text.
+// SPDX-License-Identifier: MIT
#pragma once
#include "preprocessor.hpp"
-//# {{
+// # {{
#if !TOML_IMPLEMENTATION
#error This is an implementation-only header.
#endif
-//# }}
+// # }}
#if TOML_ENABLE_FORMATTERS
-#include "toml_formatter.hpp"
+#include "array.hpp"
+#include "header_start.hpp"
#include "print_to_stream.hpp"
-#include "value.hpp"
#include "table.hpp"
-#include "array.hpp"
+#include "toml_formatter.hpp"
#include "unicode.hpp"
-#include "header_start.hpp"
+#include "value.hpp"
TOML_DISABLE_ARITHMETIC_WARNINGS;
-TOML_ANON_NAMESPACE_START
-{
- TOML_INTERNAL_LINKAGE
- size_t toml_formatter_count_inline_columns(const node& node, size_t line_wrap_cols) noexcept
- {
- switch (node.type())
- {
- case node_type::table:
- {
- auto& tbl = *reinterpret_cast<const table*>(&node);
- if (tbl.empty())
- return 2u; // "{}"
- size_t weight = 3u; // "{ }"
- for (auto&& [k, v] : tbl)
- {
- weight += k.length() + toml_formatter_count_inline_columns(v, line_wrap_cols) + 2u; // + ", "
- if (weight >= line_wrap_cols)
- break;
- }
- return weight;
- }
-
- case node_type::array:
- {
- auto& arr = *reinterpret_cast<const array*>(&node);
- if (arr.empty())
- return 2u; // "[]"
- size_t weight = 3u; // "[ ]"
- for (auto& elem : arr)
- {
- weight += toml_formatter_count_inline_columns(elem, line_wrap_cols) + 2u; // + ", "
- if (weight >= line_wrap_cols)
- break;
- }
- return weight;
- }
-
- case node_type::string:
- {
- // todo: proper utf8 decoding?
- // todo: tab awareness?
- auto& str = (*reinterpret_cast<const value<std::string>*>(&node)).get();
- return str.length() + 2u; // + ""
- }
-
- case node_type::integer:
- {
- auto val = (*reinterpret_cast<const value<int64_t>*>(&node)).get();
- if (!val)
- return 1u;
- size_t weight = {};
- if (val < 0)
- {
- weight += 1u;
- val *= -1;
- }
- return weight + static_cast<size_t>(log10(static_cast<double>(val))) + 1u;
- }
-
- case node_type::floating_point:
- {
- auto val = (*reinterpret_cast<const value<double>*>(&node)).get();
- if (val == 0.0)
- return 3u; // "0.0"
- size_t weight = 2u; // ".0"
- if (val < 0.0)
- {
- weight += 1u;
- val *= -1.0;
- }
- return weight + static_cast<size_t>(log10(val)) + 1u;
- break;
- }
-
- case node_type::boolean: return 5u;
- case node_type::date: [[fallthrough]];
- case node_type::time: return 10u;
- case node_type::date_time: return 30u;
- case node_type::none: TOML_UNREACHABLE;
- default: TOML_UNREACHABLE;
- }
-
- TOML_UNREACHABLE;
- }
-
- TOML_INTERNAL_LINKAGE
- bool toml_formatter_forces_multiline(const node& node, size_t line_wrap_cols, size_t starting_column_bias) noexcept
- {
- return (toml_formatter_count_inline_columns(node, line_wrap_cols) + starting_column_bias) >= line_wrap_cols;
- }
+TOML_ANON_NAMESPACE_START {
+ TOML_INTERNAL_LINKAGE
+ size_t toml_formatter_count_inline_columns(const node& node, size_t line_wrap_cols) noexcept {
+ switch (node.type()) {
+ case node_type::table: {
+ auto& tbl = *reinterpret_cast<const table*>(&node);
+ if (tbl.empty()) return 2u; // "{}"
+ size_t weight = 3u; // "{ }"
+ for (auto&& [k, v] : tbl) {
+ weight +=
+ k.length() + toml_formatter_count_inline_columns(v, line_wrap_cols) + 2u; // + ", "
+ if (weight >= line_wrap_cols) break;
+ }
+ return weight;
+ }
+
+ case node_type::array: {
+ auto& arr = *reinterpret_cast<const array*>(&node);
+ if (arr.empty()) return 2u; // "[]"
+ size_t weight = 3u; // "[ ]"
+ for (auto& elem : arr) {
+ weight += toml_formatter_count_inline_columns(elem, line_wrap_cols) + 2u; // + ", "
+ if (weight >= line_wrap_cols) break;
+ }
+ return weight;
+ }
+
+ case node_type::string: {
+ // todo: proper utf8 decoding?
+ // todo: tab awareness?
+ auto& str = (*reinterpret_cast<const value<std::string>*>(&node)).get();
+ return str.length() + 2u; // + ""
+ }
+
+ case node_type::integer: {
+ auto val = (*reinterpret_cast<const value<int64_t>*>(&node)).get();
+ if (!val) return 1u;
+ size_t weight = {};
+ if (val < 0) {
+ weight += 1u;
+ val *= -1;
+ }
+ return weight + static_cast<size_t>(log10(static_cast<double>(val))) + 1u;
+ }
+
+ case node_type::floating_point: {
+ auto val = (*reinterpret_cast<const value<double>*>(&node)).get();
+ if (val == 0.0) return 3u; // "0.0"
+ size_t weight = 2u; // ".0"
+ if (val < 0.0) {
+ weight += 1u;
+ val *= -1.0;
+ }
+ return weight + static_cast<size_t>(log10(val)) + 1u;
+ break;
+ }
+
+ case node_type::boolean:
+ return 5u;
+ case node_type::date:
+ [[fallthrough]];
+ case node_type::time:
+ return 10u;
+ case node_type::date_time:
+ return 30u;
+ case node_type::none:
+ TOML_UNREACHABLE;
+ default:
+ TOML_UNREACHABLE;
+ }
+
+ TOML_UNREACHABLE;
+ }
+
+ TOML_INTERNAL_LINKAGE
+ bool toml_formatter_forces_multiline(const node& node, size_t line_wrap_cols,
+ size_t starting_column_bias) noexcept {
+ return (toml_formatter_count_inline_columns(node, line_wrap_cols) + starting_column_bias) >=
+ line_wrap_cols;
+ }
}
TOML_ANON_NAMESPACE_END;
-TOML_NAMESPACE_START
-{
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print_pending_table_separator()
- {
- if (pending_table_separator_)
- {
- print_newline(true);
- print_newline(true);
- pending_table_separator_ = false;
- }
- }
-
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print(const key& k)
- {
- print_string(k.str(), false, true, false);
- }
-
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print_inline(const table& tbl)
- {
- if (tbl.empty())
- {
- print_unformatted("{}"sv);
- return;
- }
-
- print_unformatted("{ "sv);
-
- bool first = false;
- for (auto&& [k, v] : tbl)
- {
- if (first)
- print_unformatted(", "sv);
- first = true;
-
- print(k);
- if (terse_kvps())
- print_unformatted("="sv);
- else
- print_unformatted(" = "sv);
-
- const auto type = v.type();
- TOML_ASSUME(type != node_type::none);
- switch (type)
- {
- case node_type::table: print_inline(*reinterpret_cast<const table*>(&v)); break;
- case node_type::array: print(*reinterpret_cast<const array*>(&v)); break;
- default: print_value(v, type);
- }
- }
-
- print_unformatted(" }"sv);
- }
-
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print(const array& arr)
- {
- if (arr.empty())
- {
- print_unformatted("[]"sv);
- return;
- }
-
- const auto original_indent = indent();
- const auto multiline = TOML_ANON_NAMESPACE::toml_formatter_forces_multiline(
- arr,
- 120u,
- indent_columns() * static_cast<size_t>(original_indent < 0 ? 0 : original_indent));
-
- print_unformatted("["sv);
-
- if (multiline)
- {
- if (original_indent < 0)
- indent(0);
- if (indent_array_elements())
- increase_indent();
- }
- else
- print_unformatted(' ');
-
- for (size_t i = 0; i < arr.size(); i++)
- {
- if (i > 0u)
- {
- print_unformatted(',');
- if (!multiline)
- print_unformatted(' ');
- }
-
- if (multiline)
- {
- print_newline(true);
- print_indent();
- }
-
- auto& v = arr[i];
- const auto type = v.type();
- TOML_ASSUME(type != node_type::none);
- switch (type)
- {
- case node_type::table: print_inline(*reinterpret_cast<const table*>(&v)); break;
- case node_type::array: print(*reinterpret_cast<const array*>(&v)); break;
- default: print_value(v, type);
- }
- }
- if (multiline)
- {
- indent(original_indent);
- print_newline(true);
- print_indent();
- }
- else
- print_unformatted(' ');
-
- print_unformatted("]"sv);
- }
-
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print(const table& tbl)
- {
- static constexpr auto is_non_inline_array_of_tables = [](const node& n) noexcept
- {
- const auto arr = n.as_array();
- if (!arr || !arr->is_array_of_tables())
- return false;
-
- return !reinterpret_cast<const table*>(&(*arr)[0])->is_inline();
- };
-
- // values, arrays, and inline tables/table arrays
- for (auto&& [k, v] : tbl)
- {
- const auto type = v.type();
- if ((type == node_type::table && !reinterpret_cast<const table*>(&v)->is_inline())
- || (type == node_type::array && is_non_inline_array_of_tables(v)))
- continue;
-
- pending_table_separator_ = true;
- print_newline();
- print_indent();
- print(k);
- if (terse_kvps())
- print_unformatted("="sv);
- else
- print_unformatted(" = "sv);
- TOML_ASSUME(type != node_type::none);
- switch (type)
- {
- case node_type::table: print_inline(*reinterpret_cast<const table*>(&v)); break;
- case node_type::array: print(*reinterpret_cast<const array*>(&v)); break;
- default: print_value(v, type);
- }
- }
-
- const auto print_key_path = [&]()
- {
- size_t i{};
- for (const auto k : key_path_)
- {
- if (i++)
- print_unformatted('.');
- print(*k);
- }
- };
-
- // non-inline tables
- for (auto&& [k, v] : tbl)
- {
- const auto type = v.type();
- if (type != node_type::table || reinterpret_cast<const table*>(&v)->is_inline())
- continue;
- auto& child_tbl = *reinterpret_cast<const table*>(&v);
-
- // we can skip indenting and emitting the headers for tables that only contain other tables
- // (so we don't over-nest)
- size_t child_value_count{}; // includes inline tables and non-table arrays
- size_t child_table_count{};
- size_t child_table_array_count{};
- for (auto&& [child_k, child_v] : child_tbl)
- {
- TOML_UNUSED(child_k);
- const auto child_type = child_v.type();
- TOML_ASSUME(child_type != node_type::none);
- switch (child_type)
- {
- case node_type::table:
- if (reinterpret_cast<const table*>(&child_v)->is_inline())
- child_value_count++;
- else
- child_table_count++;
- break;
-
- case node_type::array:
- if (is_non_inline_array_of_tables(child_v))
- child_table_array_count++;
- else
- child_value_count++;
- break;
-
- default: child_value_count++;
- }
- }
- bool skip_self = false;
- if (child_value_count == 0u && (child_table_count > 0u || child_table_array_count > 0u))
- skip_self = true;
-
- key_path_.push_back(&k);
-
- if (!skip_self)
- {
- print_pending_table_separator();
- if (indent_sub_tables())
- increase_indent();
- print_indent();
- print_unformatted("["sv);
- print_key_path();
- print_unformatted("]"sv);
- pending_table_separator_ = true;
- }
-
- print(child_tbl);
-
- key_path_.pop_back();
- if (!skip_self && indent_sub_tables())
- decrease_indent();
- }
-
- // table arrays
- for (auto&& [k, v] : tbl)
- {
- if (!is_non_inline_array_of_tables(v))
- continue;
- auto& arr = *reinterpret_cast<const array*>(&v);
-
- if (indent_sub_tables())
- increase_indent();
- key_path_.push_back(&k);
-
- for (size_t i = 0; i < arr.size(); i++)
- {
- print_pending_table_separator();
- print_indent();
- print_unformatted("[["sv);
- print_key_path();
- print_unformatted("]]"sv);
- pending_table_separator_ = true;
- print(*reinterpret_cast<const table*>(&arr[i]));
- }
-
- key_path_.pop_back();
- if (indent_sub_tables())
- decrease_indent();
- }
- }
-
- TOML_EXTERNAL_LINKAGE
- void toml_formatter::print()
- {
- if (dump_failed_parse_result())
- return;
-
- switch (auto source_type = source().type())
- {
- case node_type::table:
- {
- auto& tbl = *reinterpret_cast<const table*>(&source());
- if (tbl.is_inline())
- print_inline(tbl);
- else
- {
- decrease_indent(); // so root kvps and tables have the same indent
- print(tbl);
- }
- break;
- }
-
- case node_type::array: print(*reinterpret_cast<const array*>(&source())); break;
-
- default: print_value(source(), source_type);
- }
- }
+TOML_NAMESPACE_START {
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print_pending_table_separator() {
+ if (pending_table_separator_) {
+ print_newline(true);
+ print_newline(true);
+ pending_table_separator_ = false;
+ }
+ }
+
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print(const key& k) {
+ print_string(k.str(), false, true, false);
+ }
+
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print_inline(const table& tbl) {
+ if (tbl.empty()) {
+ print_unformatted("{}"sv);
+ return;
+ }
+
+ print_unformatted("{ "sv);
+
+ bool first = false;
+ for (auto&& [k, v] : tbl) {
+ if (first) print_unformatted(", "sv);
+ first = true;
+
+ print(k);
+ if (terse_kvps())
+ print_unformatted("="sv);
+ else
+ print_unformatted(" = "sv);
+
+ const auto type = v.type();
+ TOML_ASSUME(type != node_type::none);
+ switch (type) {
+ case node_type::table:
+ print_inline(*reinterpret_cast<const table*>(&v));
+ break;
+ case node_type::array:
+ print(*reinterpret_cast<const array*>(&v));
+ break;
+ default:
+ print_value(v, type);
+ }
+ }
+
+ print_unformatted(" }"sv);
+ }
+
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print(const array& arr) {
+ if (arr.empty()) {
+ print_unformatted("[]"sv);
+ return;
+ }
+
+ const auto original_indent = indent();
+ const auto multiline = TOML_ANON_NAMESPACE::toml_formatter_forces_multiline(
+ arr, 120u,
+ indent_columns() * static_cast<size_t>(original_indent < 0 ? 0 : original_indent));
+
+ print_unformatted("["sv);
+
+ if (multiline) {
+ if (original_indent < 0) indent(0);
+ if (indent_array_elements()) increase_indent();
+ } else
+ print_unformatted(' ');
+
+ for (size_t i = 0; i < arr.size(); i++) {
+ if (i > 0u) {
+ print_unformatted(',');
+ if (!multiline) print_unformatted(' ');
+ }
+
+ if (multiline) {
+ print_newline(true);
+ print_indent();
+ }
+
+ auto& v = arr[i];
+ const auto type = v.type();
+ TOML_ASSUME(type != node_type::none);
+ switch (type) {
+ case node_type::table:
+ print_inline(*reinterpret_cast<const table*>(&v));
+ break;
+ case node_type::array:
+ print(*reinterpret_cast<const array*>(&v));
+ break;
+ default:
+ print_value(v, type);
+ }
+ }
+ if (multiline) {
+ indent(original_indent);
+ print_newline(true);
+ print_indent();
+ } else
+ print_unformatted(' ');
+
+ print_unformatted("]"sv);
+ }
+
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print(const table& tbl) {
+ static constexpr auto is_non_inline_array_of_tables = [](const node& n) noexcept {
+ const auto arr = n.as_array();
+ if (!arr || !arr->is_array_of_tables()) return false;
+
+ return !reinterpret_cast<const table*>(&(*arr)[0])->is_inline();
+ };
+
+ // values, arrays, and inline tables/table arrays
+ for (auto&& [k, v] : tbl) {
+ const auto type = v.type();
+ if ((type == node_type::table && !reinterpret_cast<const table*>(&v)->is_inline()) ||
+ (type == node_type::array && is_non_inline_array_of_tables(v)))
+ continue;
+
+ pending_table_separator_ = true;
+ print_newline();
+ print_indent();
+ print(k);
+ if (terse_kvps())
+ print_unformatted("="sv);
+ else
+ print_unformatted(" = "sv);
+ TOML_ASSUME(type != node_type::none);
+ switch (type) {
+ case node_type::table:
+ print_inline(*reinterpret_cast<const table*>(&v));
+ break;
+ case node_type::array:
+ print(*reinterpret_cast<const array*>(&v));
+ break;
+ default:
+ print_value(v, type);
+ }
+ }
+
+ const auto print_key_path = [&]() {
+ size_t i{};
+ for (const auto k : key_path_) {
+ if (i++) print_unformatted('.');
+ print(*k);
+ }
+ };
+
+ // non-inline tables
+ for (auto&& [k, v] : tbl) {
+ const auto type = v.type();
+ if (type != node_type::table || reinterpret_cast<const table*>(&v)->is_inline()) continue;
+ auto& child_tbl = *reinterpret_cast<const table*>(&v);
+
+ // we can skip indenting and emitting the headers for tables that only contain other tables
+ // (so we don't over-nest)
+ size_t child_value_count{}; // includes inline tables and non-table arrays
+ size_t child_table_count{};
+ size_t child_table_array_count{};
+ for (auto&& [child_k, child_v] : child_tbl) {
+ TOML_UNUSED(child_k);
+ const auto child_type = child_v.type();
+ TOML_ASSUME(child_type != node_type::none);
+ switch (child_type) {
+ case node_type::table:
+ if (reinterpret_cast<const table*>(&child_v)->is_inline())
+ child_value_count++;
+ else
+ child_table_count++;
+ break;
+
+ case node_type::array:
+ if (is_non_inline_array_of_tables(child_v))
+ child_table_array_count++;
+ else
+ child_value_count++;
+ break;
+
+ default:
+ child_value_count++;
+ }
+ }
+ bool skip_self = false;
+ if (child_value_count == 0u && (child_table_count > 0u || child_table_array_count > 0u))
+ skip_self = true;
+
+ key_path_.push_back(&k);
+
+ if (!skip_self) {
+ print_pending_table_separator();
+ if (indent_sub_tables()) increase_indent();
+ print_indent();
+ print_unformatted("["sv);
+ print_key_path();
+ print_unformatted("]"sv);
+ pending_table_separator_ = true;
+ }
+
+ print(child_tbl);
+
+ key_path_.pop_back();
+ if (!skip_self && indent_sub_tables()) decrease_indent();
+ }
+
+ // table arrays
+ for (auto&& [k, v] : tbl) {
+ if (!is_non_inline_array_of_tables(v)) continue;
+ auto& arr = *reinterpret_cast<const array*>(&v);
+
+ if (indent_sub_tables()) increase_indent();
+ key_path_.push_back(&k);
+
+ for (size_t i = 0; i < arr.size(); i++) {
+ print_pending_table_separator();
+ print_indent();
+ print_unformatted("[["sv);
+ print_key_path();
+ print_unformatted("]]"sv);
+ pending_table_separator_ = true;
+ print(*reinterpret_cast<const table*>(&arr[i]));
+ }
+
+ key_path_.pop_back();
+ if (indent_sub_tables()) decrease_indent();
+ }
+ }
+
+ TOML_EXTERNAL_LINKAGE
+ void toml_formatter::print() {
+ if (dump_failed_parse_result()) return;
+
+ switch (auto source_type = source().type()) {
+ case node_type::table: {
+ auto& tbl = *reinterpret_cast<const table*>(&source());
+ if (tbl.is_inline())
+ print_inline(tbl);
+ else {
+ decrease_indent(); // so root kvps and tables have the same indent
+ print(tbl);
+ }
+ break;
+ }
+
+ case node_type::array:
+ print(*reinterpret_cast<const array*>(&source()));
+ break;
+
+ default:
+ print_value(source(), source_type);
+ }
+ }
}
TOML_NAMESPACE_END;
#include "header_end.hpp"
-#endif // TOML_ENABLE_FORMATTERS
+#endif // TOML_ENABLE_FORMATTERS