diff options
Diffstat (limited to 'Kernel/Library/Panic.cpp')
-rw-r--r-- | Kernel/Library/Panic.cpp | 54 |
1 files changed, 54 insertions, 0 deletions
diff --git a/Kernel/Library/Panic.cpp b/Kernel/Library/Panic.cpp new file mode 100644 index 0000000000..227cc1b22a --- /dev/null +++ b/Kernel/Library/Panic.cpp @@ -0,0 +1,54 @@ +/* + * Copyright (c) 2021, Andreas Kling <kling@serenityos.org> + * + * SPDX-License-Identifier: BSD-2-Clause + */ + +#include <AK/Format.h> +#include <Kernel/Arch/Processor.h> +#if ARCH(X86_64) +# include <Kernel/Arch/x86_64/Shutdown.h> +#elif ARCH(AARCH64) +# include <Kernel/Arch/aarch64/RPi/Watchdog.h> +#endif +#include <Kernel/CommandLine.h> +#include <Kernel/KSyms.h> +#include <Kernel/Library/Panic.h> +#include <Kernel/Tasks/Thread.h> + +namespace Kernel { + +[[noreturn]] static void __shutdown() +{ +#if ARCH(X86_64) + qemu_shutdown(); + virtualbox_shutdown(); +#elif ARCH(AARCH64) + RPi::Watchdog::the().system_shutdown(); +#endif + // Note: If we failed to invoke platform shutdown, we need to halt afterwards + // to ensure no further execution on any CPU still happens. + Processor::halt(); +} + +void __panic(char const* file, unsigned int line, char const* function) +{ + // Avoid lock ranking checks on crashing paths, just try to get some debugging messages out. + auto* thread = Thread::current(); + if (thread) + thread->set_crashing(); + + critical_dmesgln("at {}:{} in {}", file, line, function); + dump_backtrace(PrintToScreen::Yes); + if (!CommandLine::was_initialized()) + Processor::halt(); + switch (kernel_command_line().panic_mode()) { + case PanicMode::Shutdown: + __shutdown(); + case PanicMode::Halt: + [[fallthrough]]; + default: + Processor::halt(); + } +} +} |