From fac70421d77519bbdcac1417c62bcb463ef57354 Mon Sep 17 00:00:00 2001 From: Alex Kotov Date: Sun, 6 Dec 2020 07:42:56 +0500 Subject: [PATCH] Add function "kernaux_console_printf" --- README.md | 2 +- include/kernaux/console.h | 1 + src/console.c | 59 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 61 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index edde0de..e4cef39 100644 --- a/README.md +++ b/README.md @@ -23,7 +23,7 @@ API * [Simple command line parser](/include/kernaux/cmdline.h) *(work in progress)* * [Multiboot 2 (GRUB 2) information parser](/include/kernaux/multiboot2.h) -* [Serial console](/include/kernaux/console.h) +* [Serial console](/include/kernaux/console.h) *(work in progress)* * [Page Frame Allocator](/include/kernaux/pfa.h) *(work in progress)* * ELF utils *(planned)* * [Architecture-specific helpers](/include/kernaux/arch/) diff --git a/include/kernaux/console.h b/include/kernaux/console.h index 07de3f0..9a27f94 100644 --- a/include/kernaux/console.h +++ b/include/kernaux/console.h @@ -6,6 +6,7 @@ extern "C" { #endif void kernaux_console_print(const char *s); +void kernaux_console_printf(const char *format, ...); void kernaux_console_putc(char c); void kernaux_console_puts(const char *s); void kernaux_console_write(const char *data, unsigned int size); diff --git a/src/console.c b/src/console.c index 6264b10..e58da7f 100644 --- a/src/console.c +++ b/src/console.c @@ -31,3 +31,62 @@ void kernaux_console_write(const char *const data, const unsigned int size) kernaux_console_putc(data[i]); } } + +void kernaux_console_printf(const char *format, ...) +{ + char **arg = (char **) &format; + int c; + char buf[20]; + arg++; + + while ((c = *format++) != 0) + { + if (c == '\n') { + if (*format != 0) { + kernaux_console_putc('\n'); + } + } + else if (c != '%') { + kernaux_console_putc(c); + } + else { + char *p, *p2; + int pad0 = 0, pad = 0; + c = *format++; + if (c == '0') + { + pad0 = 1; + c = *format++; + } + if (c >= '0' && c <= '9') + { + pad = c - '0'; + c = *format++; + } + switch (c) + { + case 'd': + case 'u': + case 'x': + kernaux_itoa(*((int*)arg++), buf, c); + p = buf; + goto string; + break; + case 's': + p = *arg++; + if (! p) + p = "(null)"; +string: + for (p2 = p; *p2; p2++); + for (; p2 < p + pad; p2++) + kernaux_console_putc(pad0 ? '0' : ' '); + while (*p) + kernaux_console_putc(*p++); + break; + default: + kernaux_console_putc(*((int *) arg++)); + break; + } + } + } +}