aboutsummaryrefslogtreecommitdiff
path: root/test/scan.h
diff options
context:
space:
mode:
authorAndroid Build Coastguard Worker <android-build-coastguard-worker@google.com>2021-07-15 01:34:41 +0000
committerAndroid Build Coastguard Worker <android-build-coastguard-worker@google.com>2021-07-15 01:34:41 +0000
commit172add79bb7a1fba113612add5e4f298b676cbfe (patch)
tree97efd94993e7d4231147354ce6702478f1ceb2f9 /test/scan.h
parent6b096dba5818ddd3e0115181a4584ee44996e37b (diff)
parent1138f5110652e173ff33e03ccf84988b3ea2e168 (diff)
downloadfmtlib-172add79bb7a1fba113612add5e4f298b676cbfe.tar.gz
Change-Id: I544f03e4f8270492d424d66dd6138d774c0c6147
Diffstat (limited to 'test/scan.h')
-rw-r--r--test/scan.h48
1 files changed, 25 insertions, 23 deletions
diff --git a/test/scan.h b/test/scan.h
index 50ac0941..de82067a 100644
--- a/test/scan.h
+++ b/test/scan.h
@@ -6,6 +6,8 @@
// For the license information refer to format.h.
#include <array>
+#include <cassert>
+#include <climits>
#include "fmt/format.h"
@@ -29,7 +31,7 @@ class scan_parse_context {
FMT_CONSTEXPR iterator end() const { return format_.end(); }
void advance_to(iterator it) {
- format_.remove_prefix(internal::to_unsigned(it - begin()));
+ format_.remove_prefix(detail::to_unsigned(it - begin()));
}
};
@@ -46,11 +48,11 @@ struct scan_context {
iterator end() const { return begin() + input_.size(); }
void advance_to(iterator it) {
- input_.remove_prefix(internal::to_unsigned(it - begin()));
+ input_.remove_prefix(detail::to_unsigned(it - begin()));
}
};
-namespace internal {
+namespace detail {
enum class scan_type {
none_type,
int_type,
@@ -105,20 +107,20 @@ class scan_arg {
ctx.advance_to(s.scan(*static_cast<T*>(arg), ctx));
}
};
-} // namespace internal
+} // namespace detail
struct scan_args {
int size;
- const internal::scan_arg* data;
+ const detail::scan_arg* data;
template <size_t N>
- scan_args(const std::array<internal::scan_arg, N>& store)
+ scan_args(const std::array<detail::scan_arg, N>& store)
: size(N), data(store.data()) {
static_assert(N < INT_MAX, "too many arguments");
}
};
-namespace internal {
+namespace detail {
struct scan_handler : error_handler {
private:
@@ -135,21 +137,20 @@ struct scan_handler : error_handler {
char c = *it++;
if (c < '0' || c > '9') on_error("invalid input");
// TODO: check overflow
- value = value * 10 + (c - '0');
+ value = value * 10 + static_cast<unsigned>(c - '0');
}
scan_ctx_.advance_to(it);
return value;
}
template <typename T = int> T read_int() {
- T value = 0;
auto it = scan_ctx_.begin(), end = scan_ctx_.end();
bool negative = it != end && *it == '-';
if (negative) ++it;
scan_ctx_.advance_to(it);
- value = read_uint<typename std::make_unsigned<T>::type>();
- if (negative) value = -value;
- return value;
+ const auto value = read_uint<typename std::make_unsigned<T>::type>();
+ if (negative) return -static_cast<T>(value);
+ return static_cast<T>(value);
}
public:
@@ -159,7 +160,7 @@ struct scan_handler : error_handler {
const char* pos() const { return scan_ctx_.begin(); }
void on_text(const char* begin, const char* end) {
- auto size = end - begin;
+ auto size = to_unsigned(end - begin);
auto it = scan_ctx_.begin();
if (it + size > scan_ctx_.end() ||
!std::equal(begin, end, make_checked(it, size))) {
@@ -168,14 +169,15 @@ struct scan_handler : error_handler {
scan_ctx_.advance_to(it + size);
}
- void on_arg_id() { on_arg_id(next_arg_id_++); }
- void on_arg_id(int id) {
+ int on_arg_id() { return on_arg_id(next_arg_id_++); }
+ int on_arg_id(int id) {
if (id >= args_.size) on_error("argument index out of range");
arg_ = args_.data[id];
+ return id;
}
- void on_arg_id(string_view) { on_error("invalid format"); }
+ int on_arg_id(string_view) { return on_error("invalid format"), 0; }
- void on_replacement_field(const char*) {
+ void on_replacement_field(int, const char*) {
auto it = scan_ctx_.begin(), end = scan_ctx_.end();
switch (arg_.type) {
case scan_type::int_type:
@@ -197,7 +199,7 @@ struct scan_handler : error_handler {
case scan_type::string_view_type: {
auto s = it;
while (it != end && *it != ' ') ++it;
- *arg_.string_view = fmt::string_view(s, it - s);
+ *arg_.string_view = fmt::string_view(s, to_unsigned(it - s));
scan_ctx_.advance_to(it);
break;
}
@@ -207,24 +209,24 @@ struct scan_handler : error_handler {
}
}
- const char* on_format_specs(const char* begin, const char*) {
+ const char* on_format_specs(int, const char* begin, const char*) {
if (arg_.type != scan_type::custom_type) return begin;
parse_ctx_.advance_to(begin);
arg_.custom.scan(arg_.custom.value, parse_ctx_, scan_ctx_);
return parse_ctx_.begin();
}
};
-} // namespace internal
+} // namespace detail
template <typename... Args>
-std::array<internal::scan_arg, sizeof...(Args)> make_scan_args(Args&... args) {
+std::array<detail::scan_arg, sizeof...(Args)> make_scan_args(Args&... args) {
return {{args...}};
}
string_view::iterator vscan(string_view input, string_view format_str,
scan_args args) {
- internal::scan_handler h(format_str, input, args);
- internal::parse_format_string<false>(format_str, h);
+ detail::scan_handler h(format_str, input, args);
+ detail::parse_format_string<false>(format_str, h);
return input.begin() + (h.pos() - &*input.begin());
}