// Copyright (c) 2012-2022 Wojciech Figat. All rights reserved. #pragma once #include "Engine/Core/Types/String.h" #include "ManagedCLR/MTypes.h" #include "Engine/Core/Log.h" /// /// Represents errors that occur during script execution. /// class FLAXENGINE_API MException { public: /// /// Gets a message that describes the current exception. /// String Message; /// /// Gets a string representation of the immediate frames on the call stack. /// String StackTrace; /// /// Gets an inner exception. Null if not used. /// MException* InnerException; public: #if USE_MONO /// /// Initializes a new instance of the class. /// /// The exception. explicit MException(MonoException* exception) : MException((MonoObject*)exception) { } #endif /// /// Initializes a new instance of the class. /// /// The exception object. explicit MException(MObject* exception); /// /// Disposes a instance of the class. /// ~MException(); public: /// /// Sends exception to the log. /// /// The log message type. /// Execution target name. void Log(const LogType type, const Char* target) { // Log inner exceptions chain auto inner = InnerException; while (inner) { auto stackTrace = inner->StackTrace.HasChars() ? *inner->StackTrace : TEXT(""); Log::Logger::Write(LogType::Warning, String::Format(TEXT("Inner exception. {0}\nStack strace:\n{1}\n"), inner->Message, stackTrace)); inner = inner->InnerException; } // Send stack trace only to log file auto stackTrace = StackTrace.HasChars() ? *StackTrace : TEXT(""); Log::Logger::Write(LogType::Warning, String::Format(TEXT("Exception has been thrown during {0}. {1}\nStack strace:\n{2}"), target, Message, stackTrace)); Log::Logger::Write(type, String::Format(TEXT("Exception has been thrown during {0}.\n{1}"), target, Message)); } };