:github_url: https://github.com/nyx-org/gaia .. _program_listing_file_lib_log.hpp: Program Listing for File log.hpp ================================ |exhale_lsh| :ref:`Return to documentation for file ` (``lib/log.hpp``) .. |exhale_lsh| unicode:: U+021B0 .. UPWARDS ARROW WITH TIP LEFTWARDS .. code-block:: cpp /* SPDX-License-Identifier: BSD-2-Clause */ #pragma once #include #include #include #include #include namespace Gaia { #define ENABLE_ASSERTS 1 #if ENABLE_ASSERTS #define ASSERT(CONDITION) \ ((CONDITION) ? (void)0 \ : panic("assertion '{}' failed at {}:{}", #CONDITION, __FILE__, \ __LINE__)) #else #define ASSERT(CONDITION) ((void)(0)) #endif class DebugSink { public: void operator()(const char *str) { while (*str) { Hal::debug_output(*str++); } } }; constexpr const char *file_name(const char *path) { const char *file = path; while (*path) { if (*path++ == '/') { file = path; } } return file; } struct FormatWithLocation { constexpr FormatWithLocation(char const *_format, char const *_file = __builtin_FILE(), int _line = __builtin_LINE()) : format{_format}, file{_file}, line{_line} {} char const *format; char const *file; int line; }; extern frg::stack_buffer_logger logger; extern frg::simple_spinlock log_lock; template void log(FormatWithLocation fmt, T... args) { #ifndef __KERNEL__ return; #endif if (locked) { log_lock.lock(); } char file_path[256]; // ok... this kinda sucks but hey it's pretty cool memcpy(file_path, fmt.file, strlen(fmt.file)); // remove .cpp file_path[strlen(fmt.file) - 4] = 0; logger() << frg::fmt("\x1b[32m[{:5}.{:06d}]\x1b[0m ", Hal::get_time_since_boot().seconds, Hal::get_time_since_boot().milliseconds) << frg::fmt("\x1b[33m{}:\x1b[0m ", file_name(file_path)) << frg::fmt(fmt.format, args...) << "\n" << frg::endlog; if (locked) { log_lock.unlock(); } } template void error(FormatWithLocation fmt, T... args) { if (locked) { log_lock.lock(); } char file_path[256]; // ok... this kinda sucks but hey it's pretty cool memcpy(file_path, fmt.file, strlen(fmt.file)); // remove .cpp file_path[strlen(fmt.file) - 4] = 0; logger() << frg::fmt("\x1b[31m[{:5}.{:06d}]\x1b[0m ", Hal::get_time_since_boot().seconds, Hal::get_time_since_boot().milliseconds) << frg::fmt("\x1b[33m{}:\x1b[0m ", file_name(file_path)) << frg::fmt(fmt.format, args...) << "\n" << frg::endlog; if (locked) { log_lock.unlock(); } } template [[noreturn]] void panic(FormatWithLocation fmt, T... args) { char file_path[256]; memcpy(file_path, fmt.file, strlen(fmt.file)); file_path[strlen(fmt.file) - 4] = 0; logger() << frg::fmt("\x1b[31m[{:5}.{:06d}] PANIC \x1b[0m", Hal::get_time_since_boot().seconds, Hal::get_time_since_boot().milliseconds) << frg::fmt("\x1b[33m{}:{}\x1b[0m ", file_name(file_path), fmt.line) << frg::fmt(fmt.format, args...) << "\x1b[0m\n" << frg::endlog; #ifdef __KERNEL__ Hal::disable_interrupts(); #endif Hal::halt(); } } // namespace Gaia