From f9b39c5ff3fe504cf532b05c2e4ac8968219eb54 Mon Sep 17 00:00:00 2001 From: apio Date: Fri, 29 Mar 2024 14:41:45 +0100 Subject: [PATCH] libos: Add ways to format output to a File --- libos/include/os/File.h | 35 +++++++++++++----- libos/src/File.cpp | 79 ++++++++++++++++++++++++++--------------- 2 files changed, 77 insertions(+), 37 deletions(-) diff --git a/libos/include/os/File.h b/libos/include/os/File.h index 112941c9..ac0b0e00 100644 --- a/libos/include/os/File.h +++ b/libos/include/os/File.h @@ -9,6 +9,7 @@ #pragma once #include +#include #include #include #include @@ -126,6 +127,24 @@ namespace os */ Result write(const Buffer& buf); + /** + * @brief Write a formatted string to this File. + * + * @param format The format string. + * @param ... The format arguments. + * @return Result Whether the operation succeeded. + */ + Result write_formatted(const char* format, ...) _format(2, 3); + + /** + * @brief Write a formatted string to this File. + * + * @param format The format string. + * @param args The format arguments. + * @return Result Whether the operation succeeded. + */ + Result write_vformatted(const char* format, va_list args); + /** * @brief Read a line from this File. * @@ -247,36 +266,36 @@ namespace os /** * @brief Print a formatted string to standard output. * - * @param fmt The format string (in the same format as printf(3)). + * @param format The format string (in the same format as printf(3)). * @param ... The format arguments. * @return Result Whether the operation succeeded. */ - Result print(StringView fmt, ...); + Result print(const char* format, ...) _format(1, 2); /** * @brief Print a newline-terminated formatted string to standard output. * - * @param fmt The format string (in the same format as printf(3)). + * @param format The format string (in the same format as printf(3)). * @param ... The format arguments. * @return Result Whether the operation succeeded. */ - Result println(StringView fmt, ...); + Result println(const char* format, ...) _format(1, 2); /** * @brief Print a formatted string to standard error. * - * @param fmt The format string (in the same format as printf(3)). + * @param format The format string (in the same format as printf(3)). * @param ... The format arguments. * @return Result Whether the operation succeeded. */ - Result eprint(StringView fmt, ...); + Result eprint(const char* format, ...) _format(1, 2); /** * @brief Print a newline-terminated formatted string to standard error. * - * @param fmt The format string (in the same format as printf(3)). + * @param format The format string (in the same format as printf(3)). * @param ... The format arguments. * @return Result Whether the operation succeeded. */ - Result eprintln(StringView fmt, ...); + Result eprintln(const char* format, ...) _format(1, 2); } diff --git a/libos/src/File.cpp b/libos/src/File.cpp index 28421c50..3733874d 100644 --- a/libos/src/File.cpp +++ b/libos/src/File.cpp @@ -8,6 +8,7 @@ */ #include +#include #include #include #include @@ -141,6 +142,33 @@ namespace os return {}; } + Result File::write_formatted(const char* format, ...) + { + va_list ap; + va_start(ap, format); + + auto result = write_vformatted(format, ap); + + va_end(ap); + + return result; + } + + Result File::write_vformatted(const char* format, va_list args) + { + auto rc = TRY(cstyle_format( + format, + [](char c, void* f) -> Result { + TRY(((File*)f)->raw_write((const u8*)&c, 1)); + return {}; + }, + this, args)); + + flush(); + + return rc; + } + Result File::read_line() { Vector data; @@ -246,64 +274,57 @@ namespace os setvbuf(m_file, NULL, mode, 0); } - // FIXME: Do not allocate memory for printing. - Result print_impl(SharedPtr f, StringView fmt, va_list ap) - { - auto str = TRY(String::vformat(fmt, ap)); - auto rc = f->write(str.view()); - f->flush(); - return rc; - } - - Result print(StringView fmt, ...) + Result print(const char* format, ...) { va_list ap; - va_start(ap, fmt); + va_start(ap, format); - auto rc = print_impl(File::standard_output(), fmt, ap); + TRY(File::standard_output()->write_vformatted(format, ap)); va_end(ap); - return rc; + return {}; } - Result println(StringView fmt, ...) + Result println(const char* format, ...) { va_list ap; - va_start(ap, fmt); + va_start(ap, format); - auto rc = print_impl(File::standard_output(), fmt, ap); + auto file = File::standard_output(); + + TRY(file->write_vformatted(format, ap)); + TRY(file->write("\n"_sv)); va_end(ap); - TRY(rc); - - return File::standard_output()->write("\n"_sv); + return {}; } - Result eprint(StringView fmt, ...) + Result eprint(const char* format, ...) { va_list ap; - va_start(ap, fmt); + va_start(ap, format); - auto rc = print_impl(File::standard_error(), fmt, ap); + TRY(File::standard_error()->write_vformatted(format, ap)); va_end(ap); - return rc; + return {}; } - Result eprintln(StringView fmt, ...) + Result eprintln(const char* format, ...) { va_list ap; - va_start(ap, fmt); + va_start(ap, format); - auto rc = print_impl(File::standard_error(), fmt, ap); + auto file = File::standard_error(); + + TRY(file->write_vformatted(format, ap)); + TRY(file->write("\n"_sv)); va_end(ap); - TRY(rc); - - return File::standard_error()->write("\n"_sv); + return {}; } }