updated to latest cppformat

This commit is contained in:
gabime 2015-11-26 14:50:44 +02:00
parent cbc8ba7203
commit 7b3fc4ba97
2 changed files with 2987 additions and 2620 deletions

View File

@ -34,6 +34,7 @@
#include <climits> #include <climits>
#include <cmath> #include <cmath>
#include <cstdarg> #include <cstdarg>
#include <cstddef> // for std::ptrdiff_t
#if defined(_WIN32) && defined(__MINGW32__) #if defined(_WIN32) && defined(__MINGW32__)
# include <cstring> # include <cstring>
@ -133,7 +134,9 @@ struct IntChecker {
unsigned max = INT_MAX; unsigned max = INT_MAX;
return value <= max; return value <= max;
} }
static bool fits_in_int(bool) { return true; } static bool fits_in_int(bool) {
return true;
}
}; };
template <> template <>
@ -142,7 +145,9 @@ struct IntChecker<true> {
static bool fits_in_int(T value) { static bool fits_in_int(T value) {
return value >= INT_MIN && value <= INT_MAX; return value >= INT_MIN && value <= INT_MAX;
} }
static bool fits_in_int(int) { return true; } static bool fits_in_int(int) {
return true;
}
}; };
const char RESET_COLOR[] = "\x1b[0m"; const char RESET_COLOR[] = "\x1b[0m";
@ -249,7 +254,9 @@ void report_error(FormatFunc func,
class IsZeroInt : public fmt::internal::ArgVisitor<IsZeroInt, bool> { class IsZeroInt : public fmt::internal::ArgVisitor<IsZeroInt, bool> {
public: public:
template <typename T> template <typename T>
bool visit_any_int(T value) { return value == 0; } bool visit_any_int(T value) {
return value == 0;
}
}; };
// Parses an unsigned integer advancing s to the end of the parsed input. // Parses an unsigned integer advancing s to the end of the parsed input.
@ -353,6 +360,11 @@ class ArgConverter : public fmt::internal::ArgVisitor<ArgConverter<T>, void> {
ArgConverter(fmt::internal::Arg &arg, wchar_t type) ArgConverter(fmt::internal::Arg &arg, wchar_t type)
: arg_(arg), type_(type) {} : arg_(arg), type_(type) {}
void visit_bool(bool value) {
if (type_ != 's')
visit_any_int(value);
}
template <typename U> template <typename U>
void visit_any_int(U value) { void visit_any_int(U value) {
bool is_signed = type_ == 'd' || type_ == 'i'; bool is_signed = type_ == 'd' || type_ == 'i';
@ -362,17 +374,20 @@ class ArgConverter : public fmt::internal::ArgVisitor<ArgConverter<T>, void> {
if (is_signed) { if (is_signed) {
arg_.type = Arg::INT; arg_.type = Arg::INT;
arg_.int_value = static_cast<int>(static_cast<T>(value)); arg_.int_value = static_cast<int>(static_cast<T>(value));
} else { }
else {
arg_.type = Arg::UINT; arg_.type = Arg::UINT;
arg_.uint_value = static_cast<unsigned>( arg_.uint_value = static_cast<unsigned>(
static_cast<typename fmt::internal::MakeUnsigned<T>::Type>(value)); static_cast<typename fmt::internal::MakeUnsigned<T>::Type>(value));
} }
} else { }
else {
if (is_signed) { if (is_signed) {
arg_.type = Arg::LONG_LONG; arg_.type = Arg::LONG_LONG;
arg_.long_long_value = arg_.long_long_value =
static_cast<typename fmt::internal::MakeUnsigned<U>::Type>(value); static_cast<typename fmt::internal::MakeUnsigned<U>::Type>(value);
} else { }
else {
arg_.type = Arg::ULONG_LONG; arg_.type = Arg::ULONG_LONG;
arg_.ulong_long_value = arg_.ulong_long_value =
static_cast<typename fmt::internal::MakeUnsigned<U>::Type>(value); static_cast<typename fmt::internal::MakeUnsigned<U>::Type>(value);
@ -409,28 +424,49 @@ class BasicArgFormatter : public ArgVisitor<Impl, void> {
FMT_DISALLOW_COPY_AND_ASSIGN(BasicArgFormatter); FMT_DISALLOW_COPY_AND_ASSIGN(BasicArgFormatter);
void write_pointer(const void *p) {
spec_.flags_ = HASH_FLAG;
spec_.type_ = 'x';
writer_.write_int(reinterpret_cast<uintptr_t>(p), spec_);
}
protected: protected:
BasicWriter<Char> &writer() { return writer_; } BasicWriter<Char> &writer() {
const FormatSpec &spec() const { return spec_; } return writer_;
}
FormatSpec &spec() {
return spec_;
}
void write(bool value) {
const char *str_value = value ? "true" : "false";
Arg::StringValue<char> str = { str_value, strlen(str_value) };
writer_.write_str(str, spec_);
}
void write(const char *value) {
Arg::StringValue<char> str = { value, value != 0 ? strlen(value) : 0 };
writer_.write_str(str, spec_);
}
public: public:
BasicArgFormatter(BasicWriter<Char> &w, FormatSpec &s) BasicArgFormatter(BasicWriter<Char> &w, FormatSpec &s)
: writer_(w), spec_(s) {} : writer_(w), spec_(s) {}
template <typename T> template <typename T>
void visit_any_int(T value) { writer_.write_int(value, spec_); } void visit_any_int(T value) {
writer_.write_int(value, spec_);
}
template <typename T> template <typename T>
void visit_any_double(T value) { writer_.write_double(value, spec_); } void visit_any_double(T value) {
writer_.write_double(value, spec_);
}
void visit_bool(bool value) { void visit_bool(bool value) {
if (spec_.type_) { if (spec_.type_)
writer_.write_int(value, spec_); return visit_any_int(value);
return; write(value);
}
const char *str_value = value ? "true" : "false";
Arg::StringValue<char> str = { str_value, strlen(str_value) };
writer_.write_str(str, spec_);
} }
void visit_char(int value) { void visit_char(int value) {
@ -450,18 +486,27 @@ class BasicArgFormatter : public ArgVisitor<Impl, void> {
if (spec_.align_ == ALIGN_RIGHT) { if (spec_.align_ == ALIGN_RIGHT) {
std::fill_n(out, spec_.width_ - CHAR_WIDTH, fill); std::fill_n(out, spec_.width_ - CHAR_WIDTH, fill);
out += spec_.width_ - CHAR_WIDTH; out += spec_.width_ - CHAR_WIDTH;
} else if (spec_.align_ == ALIGN_CENTER) { }
else if (spec_.align_ == ALIGN_CENTER) {
out = writer_.fill_padding(out, spec_.width_, out = writer_.fill_padding(out, spec_.width_,
internal::check(CHAR_WIDTH), fill); internal::check(CHAR_WIDTH), fill);
} else { }
else {
std::fill_n(out + CHAR_WIDTH, spec_.width_ - CHAR_WIDTH, fill); std::fill_n(out + CHAR_WIDTH, spec_.width_ - CHAR_WIDTH, fill);
} }
} else { }
else {
out = writer_.grow_buffer(CHAR_WIDTH); out = writer_.grow_buffer(CHAR_WIDTH);
} }
*out = internal::CharTraits<Char>::cast(value); *out = internal::CharTraits<Char>::cast(value);
} }
void visit_cstring(const char *value) {
if (spec_.type_ == 'p')
return write_pointer(value);
write(value);
}
void visit_string(Arg::StringValue<char> value) { void visit_string(Arg::StringValue<char> value) {
writer_.write_str(value, spec_); writer_.write_str(value, spec_);
} }
@ -475,9 +520,7 @@ class BasicArgFormatter : public ArgVisitor<Impl, void> {
void visit_pointer(const void *value) { void visit_pointer(const void *value) {
if (spec_.type_ && spec_.type_ != 'p') if (spec_.type_ && spec_.type_ != 'p')
report_unknown_type(spec_.type_, "pointer"); report_unknown_type(spec_.type_, "pointer");
spec_.flags_ = HASH_FLAG; write_pointer(value);
spec_.type_ = 'x';
writer_.write_int(reinterpret_cast<uintptr_t>(value), spec_);
} }
}; };
@ -501,10 +544,26 @@ class ArgFormatter : public BasicArgFormatter<ArgFormatter<Char>, Char> {
template <typename Char> template <typename Char>
class PrintfArgFormatter : class PrintfArgFormatter :
public BasicArgFormatter<PrintfArgFormatter<Char>, Char> { public BasicArgFormatter<PrintfArgFormatter<Char>, Char> {
void write_null_pointer() {
this->spec().type_ = 0;
this->write("(nil)");
}
typedef BasicArgFormatter<PrintfArgFormatter<Char>, Char> Base;
public: public:
PrintfArgFormatter(BasicWriter<Char> &w, FormatSpec &s) PrintfArgFormatter(BasicWriter<Char> &w, FormatSpec &s)
: BasicArgFormatter<PrintfArgFormatter<Char>, Char>(w, s) {} : BasicArgFormatter<PrintfArgFormatter<Char>, Char>(w, s) {}
void visit_bool(bool value) {
FormatSpec &fmt_spec = this->spec();
if (fmt_spec.type_ != 's')
return this->visit_any_int(value);
fmt_spec.type_ = 0;
this->write(value);
}
void visit_char(int value) { void visit_char(int value) {
const FormatSpec &fmt_spec = this->spec(); const FormatSpec &fmt_spec = this->spec();
BasicWriter<Char> &w = this->writer(); BasicWriter<Char> &w = this->writer();
@ -518,15 +577,33 @@ class PrintfArgFormatter :
if (fmt_spec.align_ != ALIGN_LEFT) { if (fmt_spec.align_ != ALIGN_LEFT) {
std::fill_n(out, fmt_spec.width_ - 1, fill); std::fill_n(out, fmt_spec.width_ - 1, fill);
out += fmt_spec.width_ - 1; out += fmt_spec.width_ - 1;
} else { }
else {
std::fill_n(out + 1, fmt_spec.width_ - 1, fill); std::fill_n(out + 1, fmt_spec.width_ - 1, fill);
} }
} else { }
else {
out = w.grow_buffer(1); out = w.grow_buffer(1);
} }
*out = static_cast<Char>(value); *out = static_cast<Char>(value);
} }
void visit_cstring(const char *value) {
if (value)
Base::visit_cstring(value);
else if (this->spec().type_ == 'p')
write_null_pointer();
else
this->write("(null)");
}
void visit_pointer(const void *value) {
if (value)
return Base::visit_pointer(value);
this->spec().type_ = 0;
write_null_pointer();
}
void visit_custom(Arg::CustomValue c) { void visit_custom(Arg::CustomValue c) {
BasicFormatter<Char> formatter(ArgList(), this->writer()); BasicFormatter<Char> formatter(ArgList(), this->writer());
const Char format_str[] = { '}', 0 }; const Char format_str[] = { '}', 0 };
@ -679,8 +756,12 @@ FMT_FUNC void fmt::internal::format_windows_error(
public: public:
String() : str_() {} String() : str_() {}
~String() { LocalFree(str_); } ~String() {
LPWSTR *ptr() { return &str_; } LocalFree(str_);
}
LPWSTR *ptr() {
return &str_;
}
LPCWSTR c_str() const { return str_; } LPCWSTR c_str() const { return str_; }
}; };
FMT_TRY{ FMT_TRY{
@ -696,7 +777,7 @@ FMT_FUNC void fmt::internal::format_windows_error(
} }
} }
} FMT_CATCH(...) {} } FMT_CATCH(...) {}
format_error_code(out, error_code, message); fmt::format_error_code(out, error_code, message); // 'fmt::' is for bcc32.
} }
#endif // FMT_USE_WINDOWS_H #endif // FMT_USE_WINDOWS_H
@ -719,7 +800,7 @@ FMT_FUNC void fmt::internal::format_system_error(
buffer.resize(buffer.size() * 2); buffer.resize(buffer.size() * 2);
} }
} FMT_CATCH(...) {} } FMT_CATCH(...) {}
format_error_code(out, error_code, message); fmt::format_error_code(out, error_code, message); // 'fmt::' is for bcc32.
} }
template <typename Char> template <typename Char>
@ -741,7 +822,8 @@ void fmt::internal::ArgMap<Char>::init(const ArgList &args) {
map_.insert(Pair(named_arg->name, *named_arg)); map_.insert(Pair(named_arg->name, *named_arg));
break; break;
default: default:
/*nothing*/; /*nothing*/
;
} }
} }
return; return;
@ -762,7 +844,8 @@ void fmt::internal::ArgMap<Char>::init(const ArgList &args) {
map_.insert(Pair(named_arg->name, *named_arg)); map_.insert(Pair(named_arg->name, *named_arg));
break; break;
default: default:
/*nothing*/; /*nothing*/
;
} }
} }
} }
@ -787,8 +870,6 @@ void fmt::BasicWriter<Char>::write_str(
FMT_THROW(FormatError("string pointer is null")); FMT_THROW(FormatError("string pointer is null"));
return; return;
} }
if (*str_value)
str_size = std::char_traits<StrChar>::length(str_value);
} }
std::size_t precision = spec.precision_; std::size_t precision = spec.precision_;
if (spec.precision_ >= 0 && precision < str_size) if (spec.precision_ >= 0 && precision < str_size)
@ -846,7 +927,8 @@ FMT_FUNC Arg fmt::internal::FormatterBase::do_get_arg(
case Arg::NAMED_ARG: case Arg::NAMED_ARG:
arg = *static_cast<const internal::Arg*>(arg.pointer); arg = *static_cast<const internal::Arg*>(arg.pointer);
default: default:
/*nothing*/; /*nothing*/
;
} }
return arg; return arg;
} }
@ -924,7 +1006,8 @@ unsigned fmt::internal::PrintfFormatter<Char>::parse_header(
if (*s == '$') { // value is an argument index if (*s == '$') { // value is an argument index
++s; ++s;
arg_index = value; arg_index = value;
} else { }
else {
if (c == '0') if (c == '0')
spec.fill_ = '0'; spec.fill_ = '0';
if (value != 0) { if (value != 0) {
@ -939,7 +1022,8 @@ unsigned fmt::internal::PrintfFormatter<Char>::parse_header(
// Parse width. // Parse width.
if (*s >= '0' && *s <= '9') { if (*s >= '0' && *s <= '9') {
spec.width_ = parse_nonnegative_int(s); spec.width_ = parse_nonnegative_int(s);
} else if (*s == '*') { }
else if (*s == '*') {
++s; ++s;
spec.width_ = WidthHandler(spec).visit(get_arg(s)); spec.width_ = WidthHandler(spec).visit(get_arg(s));
} }
@ -972,7 +1056,8 @@ void fmt::internal::PrintfFormatter<Char>::format(
++s; ++s;
if ('0' <= *s && *s <= '9') { if ('0' <= *s && *s <= '9') {
spec.precision_ = parse_nonnegative_int(s); spec.precision_ = parse_nonnegative_int(s);
} else if (*s == '*') { }
else if (*s == '*') {
++s; ++s;
spec.precision_ = PrecisionHandler().visit(get_arg(s)); spec.precision_ = PrecisionHandler().visit(get_arg(s));
} }
@ -1006,10 +1091,10 @@ void fmt::internal::PrintfFormatter<Char>::format(
ArgConverter<intmax_t>(arg, *s).visit(arg); ArgConverter<intmax_t>(arg, *s).visit(arg);
break; break;
case 'z': case 'z':
ArgConverter<size_t>(arg, *s).visit(arg); ArgConverter<std::size_t>(arg, *s).visit(arg);
break; break;
case 't': case 't':
ArgConverter<ptrdiff_t>(arg, *s).visit(arg); ArgConverter<std::ptrdiff_t>(arg, *s).visit(arg);
break; break;
case 'L': case 'L':
// printf produces garbage when 'L' is omitted for long double, no // printf produces garbage when 'L' is omitted for long double, no
@ -1027,7 +1112,8 @@ void fmt::internal::PrintfFormatter<Char>::format(
if (arg.type <= Arg::LAST_INTEGER_TYPE) { if (arg.type <= Arg::LAST_INTEGER_TYPE) {
// Normalize type. // Normalize type.
switch (spec.type_) { switch (spec.type_) {
case 'i': case 'u': case 'i':
case 'u':
spec.type_ = 'd'; spec.type_ = 'd';
break; break;
case 'c': case 'c':
@ -1082,7 +1168,8 @@ const Char *fmt::BasicFormatter<Char>::format(
FMT_THROW(FormatError("invalid fill character '{'")); FMT_THROW(FormatError("invalid fill character '{'"));
s += 2; s += 2;
spec.fill_ = c; spec.fill_ = c;
} else ++s; }
else ++s;
if (spec.align_ == ALIGN_NUMERIC) if (spec.align_ == ALIGN_NUMERIC)
require_numeric_argument(arg, '='); require_numeric_argument(arg, '=');
break; break;
@ -1123,7 +1210,8 @@ const Char *fmt::BasicFormatter<Char>::format(
// Parse width. // Parse width.
if ('0' <= *s && *s <= '9') { if ('0' <= *s && *s <= '9') {
spec.width_ = parse_nonnegative_int(s); spec.width_ = parse_nonnegative_int(s);
} else if (*s == '{') { }
else if (*s == '{') {
++s; ++s;
Arg width_arg = is_name_start(*s) ? Arg width_arg = is_name_start(*s) ?
parse_arg_name(s) : parse_arg_index(s); parse_arg_name(s) : parse_arg_index(s);
@ -1161,7 +1249,8 @@ const Char *fmt::BasicFormatter<Char>::format(
spec.precision_ = 0; spec.precision_ = 0;
if ('0' <= *s && *s <= '9') { if ('0' <= *s && *s <= '9') {
spec.precision_ = parse_nonnegative_int(s); spec.precision_ = parse_nonnegative_int(s);
} else if (*s == '{') { }
else if (*s == '{') {
++s; ++s;
Arg precision_arg = Arg precision_arg =
is_name_start(*s) ? parse_arg_name(s) : parse_arg_index(s); is_name_start(*s) ? parse_arg_name(s) : parse_arg_index(s);
@ -1191,7 +1280,8 @@ const Char *fmt::BasicFormatter<Char>::format(
if (value > INT_MAX) if (value > INT_MAX)
FMT_THROW(FormatError("number is too big")); FMT_THROW(FormatError("number is too big"));
spec.precision_ = static_cast<int>(value); spec.precision_ = static_cast<int>(value);
} else { }
else {
FMT_THROW(FormatError("missing precision specifier")); FMT_THROW(FormatError("missing precision specifier"));
} }
if (arg.type <= Arg::LAST_INTEGER_TYPE || arg.type == Arg::POINTER) { if (arg.type <= Arg::LAST_INTEGER_TYPE || arg.type == Arg::POINTER) {
@ -1237,13 +1327,15 @@ void fmt::BasicFormatter<Char>::format(BasicCStringRef<Char> format_str) {
FMT_FUNC void fmt::report_system_error( FMT_FUNC void fmt::report_system_error(
int error_code, fmt::StringRef message) FMT_NOEXCEPT{ int error_code, fmt::StringRef message) FMT_NOEXCEPT{
report_error(internal::format_system_error, error_code, message); // 'fmt::' is for bcc32.
fmt::report_error(internal::format_system_error, error_code, message);
} }
#if FMT_USE_WINDOWS_H #if FMT_USE_WINDOWS_H
FMT_FUNC void fmt::report_windows_error( FMT_FUNC void fmt::report_windows_error(
int error_code, fmt::StringRef message) FMT_NOEXCEPT{ int error_code, fmt::StringRef message) FMT_NOEXCEPT{
report_error(internal::format_windows_error, error_code, message); // 'fmt::' is for bcc32.
fmt::report_error(internal::format_windows_error, error_code, message);
} }
#endif #endif

File diff suppressed because it is too large Load Diff