From 96e75a023b2369135b7a12ca3b69ea1c367ab3b8 Mon Sep 17 00:00:00 2001 From: Timothy Flynn Date: Sat, 26 Jul 2025 08:01:09 -0400 Subject: [PATCH] AK: Implement a UTF-16 UnixDateTime stringifier --- AK/Time.cpp | 30 ++++++++++++++++++++++++------ AK/Time.h | 3 +++ 2 files changed, 27 insertions(+), 6 deletions(-) diff --git a/AK/Time.cpp b/AK/Time.cpp index 0525eb9c36f..b3d2e4cd7b1 100644 --- a/AK/Time.cpp +++ b/AK/Time.cpp @@ -10,6 +10,7 @@ #include #include #include +#include #ifdef AK_OS_WINDOWS # include @@ -310,7 +311,7 @@ UnixDateTime UnixDateTime::now_coarse() return UnixDateTime { now_time_from_clock(CLOCK_REALTIME_COARSE) }; } -ErrorOr UnixDateTime::to_string(StringView format, LocalTime local_time) const +ErrorOr UnixDateTime::to_string_impl(StringBuilder& builder, StringView format, LocalTime local_time) const { struct tm tm; @@ -320,15 +321,16 @@ ErrorOr UnixDateTime::to_string(StringView format, LocalTime local_time) else (void)gmtime_r(×tamp, &tm); - StringBuilder builder; size_t const format_len = format.length(); for (size_t i = 0; i < format_len; ++i) { if (format[i] != '%') { TRY(builder.try_append(format[i])); } else { - if (++i == format_len) - return String {}; + if (++i == format_len) { + builder.clear(); + return {}; + } switch (format[i]) { case 'a': @@ -452,7 +454,7 @@ ErrorOr UnixDateTime::to_string(StringView format, LocalTime local_time) break; case 'Z': { auto const* timezone_name = tzname[tm.tm_isdst == 0 ? 0 : 1]; - TRY(builder.try_append({ timezone_name, strlen(timezone_name) })); + TRY(builder.try_append(StringView { timezone_name, strlen(timezone_name) })); break; } case '%': @@ -466,12 +468,28 @@ ErrorOr UnixDateTime::to_string(StringView format, LocalTime local_time) } } + return {}; +} + +ErrorOr UnixDateTime::to_string(StringView format, LocalTime local_time) const +{ + StringBuilder builder; + TRY(to_string_impl(builder, format, local_time)); return builder.to_string(); } +Utf16String UnixDateTime::to_utf16_string(StringView format, LocalTime local_time) const +{ + StringBuilder builder(StringBuilder::Mode::UTF16); + MUST(to_string_impl(builder, format, local_time)); + return builder.to_utf16_string(); +} + ByteString UnixDateTime::to_byte_string(StringView format, LocalTime local_time) const { - return MUST(to_string(format, local_time)).to_byte_string(); + StringBuilder builder; + MUST(to_string_impl(builder, format, local_time)); + return builder.to_byte_string(); } } diff --git a/AK/Time.h b/AK/Time.h index 4d566fbe87d..d1a3e120b10 100644 --- a/AK/Time.h +++ b/AK/Time.h @@ -472,6 +472,7 @@ public: // %+: ignore until next '%' // %%: require character '%' ErrorOr to_string(StringView format = "%Y-%m-%d %H:%M:%S"sv, LocalTime = LocalTime::Yes) const; + Utf16String to_utf16_string(StringView format = "%Y-%m-%d %H:%M:%S"sv, LocalTime = LocalTime::Yes) const; ByteString to_byte_string(StringView format = "%Y-%m-%d %H:%M:%S"sv, LocalTime = LocalTime::Yes) const; // Offsetting a UNIX time by a duration yields another UNIX time. @@ -506,6 +507,8 @@ private: : Detail::UnawareTime(offset) { } + + ErrorOr to_string_impl(StringBuilder&, StringView format, LocalTime) const; }; // Monotonic time represents time returned from the CLOCK_MONOTONIC clock, which has an arbitrary fixed reference point.