diff --git a/include/date/date.h b/include/date/date.h index 1364f18..79a2e9d 100644 --- a/include/date/date.h +++ b/include/date/date.h @@ -6784,7 +6784,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, checked_set(m, static_cast(i % 12 + 1), not_a_month, is); ws(is); int td = not_a_day; - read(is, rs{td, 1, 2}); + read(is, ru{td, 1, 2}); checked_set(d, td, not_a_day, is); ws(is); using dfs = detail::decimal_format_seconds; @@ -6800,7 +6800,9 @@ from_stream(std::basic_istream& is, const CharT* fmt, not_a_second, is); ws(is); int tY = not_a_year; - read(is, rs{tY, 1, 4u}); + // No need for `rs` here, negative years can't parse + // with "%c" since `width` is hardcoded to 4 + read(is, ru{tY, 1, 4u}); checked_set(Y, tY, not_a_year, is); #endif } @@ -6834,7 +6836,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, int tm = not_a_month; int td = not_a_day; read(is, ru{tm, 1, 2}, CharT{'/'}, ru{td, 1, 2}, CharT{'/'}, - rs{ty, 1, 2}); + ru{ty, 1, 2}); checked_set(y, ty, not_a_2digit_year, is); checked_set(m, tm, not_a_month, is); checked_set(d, td, not_a_day, is); @@ -6930,7 +6932,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, int ty = not_a_2digit_year; read(is, ru{tn, 1, 2}, CharT{'\0'}, CharT{'/'}, CharT{'\0'}, ru{td, 1, 2}, CharT{'\0'}, CharT{'/'}, CharT{'\0'}, - rs{ty, 1, 2}); + ru{ty, 1, 2}); checked_set(y, ty, not_a_2digit_year, is); checked_set(m, tn, not_a_month, is); checked_set(d, td, not_a_day, is); @@ -6978,7 +6980,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, #endif { int td = not_a_day; - read(is, rs{td, 1, width == -1 ? 2u : static_cast(width)}); + read(is, ru{td, 1, width == -1 ? 2u : static_cast(width)}); checked_set(d, td, not_a_day, is); } #if !ONLY_C_LOCALE @@ -7042,7 +7044,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, { int tI = not_a_hour_12_value; // reads in an hour into I, but most be in [1, 12] - read(is, rs{tI, 1, width == -1 ? 2u : static_cast(width)}); + read(is, ru{tI, 1, width == -1 ? 2u : static_cast(width)}); if (!(1 <= tI && tI <= 12)) is.setstate(ios::failbit); checked_set(I, tI, not_a_hour_12_value, is); @@ -7116,7 +7118,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, #endif { int tn = not_a_month; - read(is, rs{tn, 1, width == -1 ? 2u : static_cast(width)}); + read(is, ru{tn, 1, width == -1 ? 2u : static_cast(width)}); checked_set(m, tn, not_a_month, is); } #if !ONLY_C_LOCALE @@ -7536,7 +7538,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, } if (modified == CharT{}) { - read(is, rs{tH, 2, 2}); + read(is, ru{tH, 2, 2}); if (!is.fail()) toff = hours{std::abs(tH)}; if (is.good()) @@ -7556,7 +7558,7 @@ from_stream(std::basic_istream& is, const CharT* fmt, } else { - read(is, rs{tH, 1, 2}); + read(is, ru{tH, 1, 2}); if (!is.fail()) toff = hours{std::abs(tH)}; if (is.good()) diff --git a/test/date_test/parse.pass.cpp b/test/date_test/parse.pass.cpp index 13ca909..aa15d95 100644 --- a/test/date_test/parse.pass.cpp +++ b/test/date_test/parse.pass.cpp @@ -204,6 +204,13 @@ test_c() assert(!in.bad()); assert(tp == sys_days{2016_y/12/11} + hours{14} + minutes{2} + seconds{43}); } + { + // can't parse negative years with "%c" directly + std::istringstream in{"Sun Dec 11 14:02:43 -2016"}; + sys_seconds tp; + in >> parse("%c", tp); + assert(in.fail()); + } } void @@ -362,6 +369,30 @@ test_d() assert(!in.bad()); assert(tp == 2016_y/12/9); } + { + std::istringstream in{"2016 +9 12"}; + sys_days tp; + in >> parse("%Y %d %m", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016 +9 12"}; + sys_days tp; + in >> parse("%Y %e %m", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016 -9 12"}; + sys_days tp; + in >> parse("%Y %d %m", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016 -9 12"}; + sys_days tp; + in >> parse("%Y %e %m", tp); + assert(in.fail()); + } { std::istringstream in{"2016 31 11"}; sys_days tp; @@ -459,6 +490,12 @@ test_Ip() in >> parse("%F %I %p", tp); assert(in.fail()); } + { + std::istringstream in{"2016-12-11 +1 pm"}; + sys_time tp; + in >> parse("%F %I %p", tp); + assert(in.fail()); + } } void @@ -503,6 +540,12 @@ test_m() in >> parse("%Y %d %m", tp); assert(in.fail()); } + { + std::istringstream in{"2016-12-+3"}; + sys_days tp; + in >> parse("%Y-%d-%m", tp); + assert(in.fail()); + } } void @@ -776,6 +819,30 @@ test_z() assert(!in.bad()); assert(tp == sys_days{2016_y/12/26} + hours{20} + minutes{53} + seconds{22}); } + { + std::istringstream in{"2016-12-26 15:53:22 -+500"}; + sys_seconds tp; + in >> parse("%F %T %z", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016-12-26 15:53:22 -+500"}; + sys_seconds tp; + in >> parse("%F %T %Ez", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016-12-26 15:53:22 --500"}; + sys_seconds tp; + in >> parse("%F %T %z", tp); + assert(in.fail()); + } + { + std::istringstream in{"2016-12-26 15:53:22 --500"}; + sys_seconds tp; + in >> parse("%F %T %Ez", tp); + assert(in.fail()); + } } void